rsshubtrans/translator/tests/test_app.py
2026-04-13 18:08:43 +02:00

97 lines
3.6 KiB
Python

from unittest.mock import MagicMock, patch
_SAMPLE_FEED = (
b'<?xml version="1.0" encoding="UTF-8"?>'
b"<rss version=\"2.0\"><channel>"
b"<item><title>Test</title></item>"
b"</channel></rss>"
)
def _mock_upstream(content=_SAMPLE_FEED, raise_error=False):
m = MagicMock()
m.content = content
if raise_error:
m.raise_for_status.side_effect = Exception("HTTP error")
else:
m.raise_for_status = MagicMock()
return m
# ── Frontend routes ───────────────────────────────────────────────────────────
def test_index_returns_200(app_client):
resp = app_client.get("/")
assert resp.status_code == 200
def test_reader_valid_lang_returns_200(app_client):
resp = app_client.get("/sk/")
assert resp.status_code == 200
def test_reader_invalid_lang_redirects(app_client):
resp = app_client.get("/xx/")
assert resp.status_code == 302
assert "/sk/" in resp.headers["Location"]
# ── Media proxy ───────────────────────────────────────────────────────────────
def test_media_proxy_allowed_host(app_client):
mock_resp = MagicMock()
mock_resp.content = b"imgdata"
mock_resp.headers = {"Content-Type": "image/jpeg"}
mock_resp.raise_for_status = MagicMock()
with patch("app.requests.get", return_value=mock_resp):
resp = app_client.get("/media?url=https://cdn.telesco.pe/photo.jpg")
assert resp.status_code == 200
def test_media_proxy_forbidden_host(app_client):
resp = app_client.get("/media?url=https://evil.com/img.jpg")
assert resp.status_code == 403
# ── Feed proxy ────────────────────────────────────────────────────────────────
def test_feed_proxy_cache_miss(app_client):
with patch("app.requests.get", return_value=_mock_upstream()), \
patch("app.translate_feed", return_value=_SAMPLE_FEED):
resp = app_client.get("/sk/telegram/channel/test")
assert resp.status_code == 200
assert resp.headers["X-Cache"] == "MISS"
def test_feed_proxy_cache_hit(app_client):
with patch("app.requests.get", return_value=_mock_upstream()) as mock_get, \
patch("app.translate_feed", return_value=_SAMPLE_FEED):
app_client.get("/sk/telegram/channel/test") # populate cache
mock_get.reset_mock()
resp = app_client.get("/sk/telegram/channel/test")
assert resp.status_code == 200
assert resp.headers["X-Cache"] == "HIT"
mock_get.assert_not_called()
def test_feed_proxy_304_on_matching_etag(app_client):
with patch("app.requests.get", return_value=_mock_upstream()), \
patch("app.translate_feed", return_value=_SAMPLE_FEED):
first = app_client.get("/sk/telegram/channel/test")
etag = first.headers["ETag"]
second = app_client.get(
"/sk/telegram/channel/test",
headers={"If-None-Match": etag},
)
assert second.status_code == 304
def test_feed_proxy_unknown_lang_returns_400(app_client):
resp = app_client.get("/xx/telegram/channel/test")
assert resp.status_code == 400
def test_feed_proxy_upstream_error_returns_502(app_client):
with patch("app.requests.get", side_effect=Exception("timeout")):
resp = app_client.get("/sk/telegram/channel/test")
assert resp.status_code == 502