feedvault.se/app/cli.py
2024-05-22 01:51:07 +02:00

77 lines
2.4 KiB
Python

from __future__ import annotations
import sys
import traceback
from datetime import datetime, timedelta
from pathlib import Path
from typing import TYPE_CHECKING
import click
from reader import Feed, ParseError, Reader, StorageError, UpdateError, UpdateResult
from app.dependencies import get_reader
if TYPE_CHECKING:
from collections.abc import Iterable
def add_broken_feed_to_csv(feed: Feed | UpdateResult | None) -> None:
"""Add a broken feed to a CSV file."""
if feed is None:
click.echo("Feed is None.", err=True)
return
with Path("broken_feeds.csv").open("a", encoding="utf-8") as f:
f.write(f"{feed.url}\n")
@click.command()
def update_feeds() -> None:
"""Update all the feeds."""
reader: Reader = get_reader()
click.echo("Updating feeds...")
all_feeds: Iterable[Feed] = reader.get_feeds(updates_enabled=True)
feeds = []
# Only get feeds that hasn't been updated in the last 30 minutes.
for feed in all_feeds:
if feed.last_updated:
now: datetime = datetime.now(tz=feed.last_updated.tzinfo)
delta: timedelta = now - feed.last_updated
thirty_minutes: int = 60 * 30 # 30 minutes
if delta.total_seconds() < thirty_minutes:
feeds.append(feed)
else:
feeds.append(feed)
click.echo(f"Feeds to update: {len(feeds)}")
for feed in feeds:
try:
reader.update_feed(feed)
click.echo(f"Updated feed: {feed.url}")
except ParseError:
# An error occurred while retrieving/parsing the feed.
click.echo(f"Error parsing feed: {feed.url}", err=True)
except UpdateError:
# An error occurred while updating the feed.
# Parent of all update-related exceptions.
click.echo(f"Error updating feed: {feed.url}", err=True)
except StorageError as e:
# An exception was raised by the underlying storage.
click.echo(f"Error updating feed: {feed.url}", err=True)
click.echo(f"Storage error: {e}", err=True)
except AssertionError:
# An assertion failed.
click.echo(f"Assertion error: {feed.url}", err=True)
traceback.print_exc(file=sys.stderr)
reader.disable_feed_updates(feed)
add_broken_feed_to_csv(feed)
click.echo("Feeds updated.")
if __name__ == "__main__":
update_feeds()