Quickstart¶
This page gets you from pip install to reading manga pages with the Nyora
library in a few minutes. Everything here uses the importable nyora package
(import nyora).
Note
The library (pip install nyora, import nyora) and the nyora-cli terminal
tool are separate. This page documents the library. For the command-line
tool and its terminal UI, see the CLI docs.
Install¶
Nyora requires Python 3.10 or newer.
pip install nyora
That is all you need. The default client is a thin HTTP client over the Nyora
cloud (https://api.hasanraza.tech), so there
is nothing else to run — no local server and no Node process. HTTP is
handled by httpx, which is pulled in automatically.
The default client: nyora.Nyora¶
nyora.Nyora is the default client. By default it targets the Nyora cloud, so a
bare Nyora() just works. Use it as a context manager so the HTTP connection is
released cleanly:
from nyora import Nyora
with Nyora() as client:
...
client exposes several service objects; the two you need to browse and read
are:
client.sources— list and find sources.client.manga— browse popular/latest, search, fetch details and pages.
Tip
Nyora() resolves its base URL in order: an explicit base_url argument, the
NYORA_BASE_URL environment variable, a running local helper’s port file, and
finally the public cloud (nyora.CLOUD_BASE_URL). Pass Nyora(base_url=...) to
point at a different deployment.
List sources¶
from nyora import Nyora
with Nyora() as client:
for source in client.sources.list():
print(source.id, "|", source.name, "|", source.lang)
Each item is a nyora.models.Source dataclass. Find a
single source by a case-insensitive id or name substring:
with Nyora() as client:
source = client.sources.find("mangadex")
print(source.id, source.name, source.base_url)
find raises LookupError if nothing matches.
Browse and search¶
popular, latest, and search all return a
nyora.models.SearchPage whose .entries is a list of
nyora.models.Manga.
with Nyora() as client:
source = client.sources.find("mangadex")
popular = client.manga.popular(source.id, page=1)
for manga in popular.entries:
print(manga.title, "->", manga.url)
results = client.manga.search(source.id, "berserk")
print("matches:", len(results.entries))
print("more pages?", results.has_next_page)
Fetch details and chapters¶
details returns a nyora.models.MangaDetails with the
.manga metadata and its .chapters:
with Nyora() as client:
source = client.sources.find("mangadex")
entry = client.manga.popular(source.id).entries[0]
details = client.manga.details(source.id, entry.url)
print(details.manga.title)
print("chapters:", len(details.chapters))
first_chapter = details.chapters[0]
print(first_chapter.number, first_chapter.title, first_chapter.url)
details also accepts an optional manga_id= keyword to disambiguate an entry
when the source needs it.
Resolve the pages of a chapter¶
pages returns a list of nyora.models.MangaPage. Each
page has a .url and the .headers you must send when fetching the image
(some sources require a Referer):
import httpx
from nyora import Nyora
with Nyora() as client:
source = client.sources.find("mangadex")
entry = client.manga.popular(source.id).entries[0]
details = client.manga.details(source.id, entry.url)
chapter = details.chapters[0]
pages = client.manga.pages(source.id, chapter.url)
for page in pages:
print(page.url, page.headers)
# Download the first page using its required headers.
first = pages[0]
image = httpx.get(first.url, headers=first.headers).content
print("first page bytes:", len(image))
Sync your library (optional)¶
Signed-in users can push and pull their library — favourites, history, and
bookmarks — across devices with nyora.sync.NyoraSync:
from nyora.sync import NyoraSync
sync = NyoraSync()
sync.sign_in("me@example.com", "hunter2") # tokens persist to ~/.config/nyora/sync.json
sync.upsert("nyora_favourite", [{"manga_id": "...", "sort_key": 0}])
favourites = sync.select("nyora_favourite")
See the sync guide for tables, token persistence, and the full API.
Error handling¶
Every SDK-specific failure derives from nyora.NyoraError:
from nyora import Nyora, NyoraError
try:
with Nyora() as client:
page = client.manga.popular("does-not-exist")
except NyoraError as exc:
print("Nyora failed:", exc)
client.sources.find(...) raises the standard library LookupError when no
source matches.
Next steps¶
Library guide — every method, return types, and the model dataclasses.
Sync guide — cloud account and library sync in depth.
CLI guide — the
nyora-clicommand-line tool.API reference — full autodoc of every public symbol.