aboutsummaryrefslogtreecommitdiff
path: root/tests/conftest.py
diff options
context:
space:
mode:
authorDennis Fink2026-08-09 14:15:29 +0200
committerDennis Fink2026-08-09 14:22:00 +0200
commit67eff0a854da010cb6ecd119d84238ec3e119272 (patch)
treec4a85592b957bb01fa62f79329faa6ba0823d9b3 /tests/conftest.py
parentf53c1136184d2afabfb1e5974e527229aa71939a (diff)
downloadwebmentions-ssg-67eff0a854da010cb6ecd119d84238ec3e119272.tar.gz
webmentions-ssg-67eff0a854da010cb6ecd119d84238ec3e119272.zip
Implement received Webmention handling
Add the Flask application setup, database models and migrations, authentication, and configuration for development and testing. Implement asynchronous Webmention verification with Huey, including HTML and plain-text source validation, retries, status tracking, and size limits. Add status, login, and paginated received-Webmention views together with comprehensive tests for forms, views, and receiver tasks.
Diffstat (limited to 'tests/conftest.py')
-rw-r--r--tests/conftest.py125
1 files changed, 125 insertions, 0 deletions
diff --git a/tests/conftest.py b/tests/conftest.py
new file mode 100644
index 0000000..94ba650
--- /dev/null
+++ b/tests/conftest.py
@@ -0,0 +1,125 @@
+import uuid
+from collections.abc import Callable, Iterator
+from types import ModuleType
+
+import httpx
+import pytest
+from flask import Flask
+from flask.testing import FlaskClient
+
+from webmentions_ssg import DATABASE as db
+from webmentions_ssg import create_app
+from webmentions_ssg.config import TestingConfig
+from webmentions_ssg.models import ReceivedWebmention
+
+HTTPHandler = Callable[
+ [httpx.Request],
+ httpx.Response,
+]
+
+
+@pytest.fixture
+def app() -> Iterator[Flask]:
+ """
+ Create a new Flask application and in-memory database
+ for every test.
+ """
+
+ application = create_app(TestingConfig)
+
+ with application.app_context():
+ db.create_all()
+
+ yield application
+
+ with application.app_context():
+ db.session.remove()
+ db.drop_all()
+ db.engine.dispose()
+
+
+@pytest.fixture
+def client(app: Flask) -> FlaskClient:
+ return app.test_client()
+
+
+@pytest.fixture
+def receiver_module(app: Flask) -> ModuleType:
+ """
+ Ensure the application and Huey extension are initialized
+ before retrieving the tasks module.
+ """
+
+ from webmentions_ssg.tasks import receiver
+
+ return receiver
+
+
+@pytest.fixture
+def views_module(app: Flask) -> ModuleType:
+ from webmentions_ssg import views
+
+ return views
+
+
+@pytest.fixture
+def make_webmention(
+ app: Flask,
+) -> Callable[..., uuid.UUID]:
+ def create(
+ *,
+ source: str = "https://source.example/post",
+ target: str = ("https://dennisfink.me/blog/example/"),
+ status: str = "received",
+ failure_reason: str | None = None,
+ ) -> uuid.UUID:
+ identifier = uuid.uuid7()
+
+ with app.app_context():
+ webmention = ReceivedWebmention(
+ uuid=identifier,
+ source=source,
+ target=target,
+ status=status,
+ failure_reason=failure_reason,
+ )
+
+ db.session.add(webmention)
+ db.session.commit()
+
+ return identifier
+
+ return create
+
+
+@pytest.fixture
+def install_httpx_mock(
+ monkeypatch: pytest.MonkeyPatch,
+ receiver_module: ModuleType,
+) -> Callable[[HTTPHandler], None]:
+ """
+ Replace the HTTPX transport without replacing HTTPX itself.
+ """
+
+ real_client = httpx.Client
+
+ def install(handler: HTTPHandler) -> None:
+ transport = httpx.MockTransport(handler)
+
+ def create_client(
+ *args,
+ **kwargs,
+ ) -> httpx.Client:
+ return real_client(
+ *args,
+ transport=transport,
+ **kwargs,
+ )
+
+ monkeypatch.setattr(
+ receiver_module.httpx,
+ "Client",
+ create_client,
+ )
+
+ return install