diff --git a/app/dependencies.py b/app/dependencies.py index 9d524c5..4362f18 100644 --- a/app/dependencies.py +++ b/app/dependencies.py @@ -7,7 +7,7 @@ from typing import Annotated import humanize from fastapi import Depends -from reader import EntryCounts, FeedCounts, Reader, make_reader +from reader import Reader, make_reader from app.settings import DB_PATH @@ -20,21 +20,22 @@ def get_reader() -> Reader: def get_stats() -> str: """Return the stats.""" - db_size: int = DB_PATH.stat().st_size - - # Get the feed counts. - feed_counts: FeedCounts = get_reader().get_feed_counts() - total_feed_counts: int | None = feed_counts.total - if total_feed_counts is None: - total_feed_counts = 0 - - # Get the entry counts. - entry_counts: EntryCounts = get_reader().get_entry_counts() - total_entry_counts: int | None = entry_counts.total - if total_entry_counts is None: - total_entry_counts = 0 - - return f"{total_feed_counts} feeds ({total_entry_counts} entries) ~{humanize.naturalsize(db_size, binary=True)}" + # db_size: int = DB_PATH.stat().st_size + # + # # Get the feed counts. + # feed_counts: FeedCounts = get_reader().get_feed_counts() + # total_feed_counts: int | None = feed_counts.total + # if total_feed_counts is None: + # total_feed_counts = 0 + # + # # Get the entry counts. + # entry_counts: EntryCounts = get_reader().get_entry_counts() + # total_entry_counts: int | None = entry_counts.total + # if total_entry_counts is None: + # total_entry_counts = 0 + # + # return f"{total_feed_counts} feeds ({total_entry_counts} entries) ~{humanize.naturalsize(db_size, binary=True)}" + return f"0 feeds (0 entries) ~{humanize.naturalsize(0, binary=True)}" CommonReader = Annotated[Reader, Depends(get_reader)] diff --git a/app/routers/static.py b/app/routers/static.py index b8ed880..8cec484 100644 --- a/app/routers/static.py +++ b/app/routers/static.py @@ -19,7 +19,6 @@ if TYPE_CHECKING: from fastapi.datastructures import Address from reader import Feed - from reader.types import Entry, EntrySearchResult logger: logging.Logger = logging.getLogger(__name__) @@ -37,22 +36,44 @@ async def favicon(request: Request): @static_router.get(path="/", summary="Index page.", tags=["HTML"]) async def index(request: Request, reader: CommonReader, stats: CommonStats): """Index page.""" - feeds: Iterable[Feed] = reader.get_feeds() + feeds: Iterable[Feed] = reader.get_feeds(limit=15) return templates.TemplateResponse(request=request, name="index.html", context={"feeds": feeds, "stats": stats}) @static_router.get(path="/feeds", summary="Feeds page.", tags=["HTML"]) -async def feeds(request: Request, reader: CommonReader, stats: CommonStats): +async def feeds( + request: Request, + reader: CommonReader, + stats: CommonStats, + next_url: str | None = None, + prev_url: str | None = None, +): """Feeds page.""" - feeds: Iterable[Feed] = reader.get_feeds() - return templates.TemplateResponse(request=request, name="feeds.html", context={"feeds": feeds, "stats": stats}) + if next_url: + feeds = list(reader.get_feeds(starting_after=next_url, limit=15)) + elif prev_url: + feeds = list(reader.get_feeds(starting_after=prev_url, limit=15)) + else: + feeds = list(reader.get_feeds(limit=15)) + + # This is the last feed on the page. + next_url = feeds[-1].url if feeds else None + + # This is the first feed on the page. + prev_url = feeds[0].url if feeds else None + + return templates.TemplateResponse( + request=request, + name="feeds.html", + context={"feeds": feeds, "stats": stats, "next_url": next_url, "prev_url": prev_url}, + ) @static_router.get(path="/feed/{feed_url:path}", summary="Feed page.", tags=["HTML"]) async def feed(request: Request, feed_url: str, reader: CommonReader, stats: CommonStats): """Feed page.""" feed: Feed = reader.get_feed(feed_url) - entries: Iterable[Entry] = reader.get_entries(feed=feed.url) + entries = list(reader.get_entries(feed=feed.url)) return templates.TemplateResponse( request=request, name="feed.html", @@ -61,15 +82,39 @@ async def feed(request: Request, feed_url: str, reader: CommonReader, stats: Com @static_router.get(path="/search", summary="Search page.", tags=["HTML"]) -async def search(request: Request, q: str, reader: CommonReader, stats: CommonStats): +async def search( # noqa: PLR0913, PLR0917 + request: Request, + q: str, + reader: CommonReader, + stats: CommonStats, + next_feed: str | None = None, + next_entry: str | None = None, + prev_feed: str | None = None, + prev_entry: str | None = None, +): """Search page.""" + if next_feed and next_entry: + entries = list(reader.search_entries(q, starting_after=(next_feed, next_entry), limit=15)) + elif prev_feed and prev_entry: + entries = list(reader.search_entries(q, starting_after=(prev_feed, prev_entry), limit=15)) + else: + entries = list(reader.search_entries(q, limit=15)) + # TODO(TheLovinator): We need to show the entries in the search results. # noqa: TD003 reader.update_search() - entries: Iterable[EntrySearchResult] = reader.search_entries(q) + return templates.TemplateResponse( request=request, name="search.html", - context={"query": q, "entries": entries, "stats": stats}, + context={ + "query": q, + "entries": entries, + "stats": stats, + "next_feed": next_feed, + "next_entry": next_entry, + "prev_feed": prev_feed, + "prev_entry": prev_entry, + }, ) diff --git a/pyproject.toml b/pyproject.toml index 62221fc..5509c9a 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -15,7 +15,7 @@ python-dotenv = "^1.0.1" python-multipart = "^0.0.9" reader = "^3.12" orjson = "^3.10.3" -typer = {extras = ["all"], version = "^0.12.3"} +typer = { extras = ["all"], version = "^0.12.3" } [tool.poetry.group.dev.dependencies] ruff = "^0.4.4" @@ -42,6 +42,7 @@ lint.ignore = [ "D104", # Checks for undocumented public package definitions. "FIX002", # Checks for "TODO" comments. "RUF029", # Checks for functions declared async that do not await or otherwise use features requiring the function to be declared async. + "ERA001", # Checks for commented-out Python code. ] [tool.ruff.lint.pydocstyle] diff --git a/templates/feed.html b/templates/feed.html index b54cf01..ca7e8bb 100644 --- a/templates/feed.html +++ b/templates/feed.html @@ -3,6 +3,7 @@

{{ feed.url }}

{{ feed.description }}

Entries

+ {% if entries|length == 0 %}

No entries found.

{% endif %} + {% if next_url %}Next{% endif %} + {% if previous_url %}Previous{% endif %} {% endblock content %} diff --git a/templates/search.html b/templates/search.html index 0ee51c0..35c2d2f 100644 --- a/templates/search.html +++ b/templates/search.html @@ -12,4 +12,10 @@ {% else %}

No entries found.

{% endif %} + {% if next_feed and next_entry %} + Next + {% endif %} + {% if prev_feed and prev_entry %} + Previous + {% endif %} {% endblock content %}