feat: Semaine 8

This commit is contained in:
gauvainboiche
2026-05-11 09:25:19 +02:00
parent 606e43e53f
commit 3315cb2336
123 changed files with 5748 additions and 0 deletions
@@ -0,0 +1,24 @@
from fastapi import FastAPI
from application.usecases.run_watch_cycle import RunWatchCycleUsecase
from adapters.outbound.rss_feed_adapter import RssFeedAdapter
from adapters.outbound.cli_notifier import CliNotifierAdapter
from domain.matcher import MatchingService
app = FastAPI()
rss_adapter = RssFeedAdapter("https://www.lemonde.fr/rss/une.xml")
notifier = CliNotifierAdapter()
matcher = MatchingService()
usecase = RunWatchCycleUsecase(rss_adapter, notifier, matcher)
@app.get("/rss/{keyword}")
def run_watch_by_http(keyword: str):
result = usecase.execute(keywords=[keyword])
return {
"status": "success",
"keyword_searched": keyword,
"articles_processed": result.processed,
"alerts_sent": result.alerts_sent
}
@@ -0,0 +1,10 @@
from domain.entities import Alert
from ports.outbound.notifier_protocol import Notifier
class CliNotifierAdapter(Notifier):
def send_alert(self, alert: Alert) -> None:
print("-" * 30)
print(f"Mots-clefs : {alert.matched_keywords}")
print(f"Titre : {alert.article.title}")
print(f"Lien : {alert.article.url}")
print("-" * 30)
@@ -0,0 +1,25 @@
import feedparser
from datetime import datetime
from time import mktime
from domain.entities import Article
class RssFeedAdapter():
def __init__(self, feed_url: str):
self.feed_url = feed_url
def fetch_articles(self) -> list[Article]:
# On consomme le flux externe
feed = feedparser.parse(self.feed_url)
articles = []
for entry in feed.entries:
# On convertit le format spécifique RSS vers notre Entité
published = datetime.fromtimestamp(mktime(entry.published_parsed)) #type: ignore
articles.append(Article(
title=entry.title,
url=entry.link,
published_at=published,
source=feed.feed.title
))
return articles