Beta 0.7.3 REST and adapter contract drift gate
Summary¶
Prove that native REST, qBittorrent-compatible, and Torznab-compatible surfaces
have not drifted from their intended contracts. Native /api/v1 behavior must
remain clean and typed; adapter-specific quirks must stay isolated in the qBit
and Torznab compatibility layers.
Acceptance Criteria¶
- [x] OpenAPI/native REST route manifest matches current implementation.
- [x] Safe native REST routes pass the contract smoke suite.
- [x] Destructive native REST routes have explicit confirmation or intent inventory coverage.
- [x] Native REST malformed input returns typed JSON errors where expected.
- [x] qBittorrent-compatible auth rejects missing, wrong, and stale sessions.
- [x] qBittorrent-compatible malformed booleans and hashes are rejected or handled according to the adapter contract.
- [x] Torznab API key, category, query, and feed behavior is replayed.
- [x] Adapter error shapes remain adapter-local and do not force native
/api/v1response aliases or envelopes.
Validation¶
python -m emule_workspace test python --path tests\python\test_rest_api_smoke.py --quietpython -m emule_workspace test live-e2e --config Release --platform x64 --suite rest-api
Completion Evidence¶
- 2026-05-10 refresh:
python -m emule_workspace validatepassed after updating the canonical branch-store checkout to apporigin/main.python -m emule_workspace build app --config Debug --platform x64passed after app commite05054ffixed an ambiguous debugEMFileSizezero check in the protected-volume demand path.python -m emule_workspace build app --config Release --platform x64passed.python -m emule_workspace test python --path tests\python\test_rest_api_smoke.py --path tests\python\test_release_golden.py --quietpassed:72tests.python -m emule_workspace test live-e2e --config Release --platform x64 --suite rest-api --rest-coverage-budget contract-stress --rest-stress-budget smoke --rest-stress-duration-seconds 10 --rest-stress-concurrency 4 --rest-download-trigger-count 3 --skip-live-seed-refreshpassed. Artifact:EMULE_WORKSPACE_ROOT\repos\emulebb-build-tests\reports\rest-api-smoke\20260510-235256-eMule-main-release\result.json.- Live contract parity recorded
openapi_route_count=85,registry_route_count=85,safe_route_count=82,unsafe_route_count=3,exercised_route_count=82, and no failed routes. Strict OpenAPI response-schema validation was active for successful native REST envelopes and typed JSON error envelopes. - Route execution reporting recorded
direct=1andui-thread=84; the only direct native route isGET /api/v1/app. - Live stress completed
4181requests withnative_rest_non_json_count=0,timeout_count=0, p95 latency68.172ms, and no failure sample. - Local dump configuration was enabled for
emule.exe,umdh.exe,procdump.exe, andprocdump64.exewith dump count64. - Dedicated Prowlarr/Torznab live proof passed:
EMULE_WORKSPACE_ROOT\repos\emulebb-build-tests\reports\prowlarr-emulebb-live\20260510-224143-eMule-main-release. - Dedicated Radarr/Sonarr plus qBit-compatible live proof passed:
EMULE_WORKSPACE_ROOT\repos\emulebb-build-tests\reports\radarr-sonarr-emulebb-live\20260510-224447-eMule-main-release. -
Dedicated aMuTorrent browser smoke did not reach browser execution:
EMULE_WORKSPACE_ROOT\repos\emulebb-build-tests\reports\amutorrent-browser-smoke\20260510-225224-eMule-main-release. eMule REST readiness passed, but aMuTorrent bound to127.0.0.1:57415from its persistent server config while the harness waited on the requested generated port127.0.0.1:55939. Treat this as an aMuTorrent/harness configuration drift follow-up (BUG-102), not a native/api/v1contract failure. -
python -m emule_workspace test python --path tests\python\test_rest_api_smoke.py --quietpassed:63tests. python -m emule_workspace test live-e2e --config Release --platform x64 --suite rest-apipassed. Artifact:EMULE_WORKSPACE_ROOT\repos\emulebb-build-tests\reports\rest-api-smoke\20260509-144340-eMule-main-release\result.json.- The live REST contract report recorded OpenAPI and registry parity:
openapi_route_count=82,registry_route_count=82,operation_count=82, and no missing or duplicate routes. - The contract smoke exercised
81safe routes with0failed routes;/api/v1/app/shutdownremained the single skipped unsafe route. - The destructive-route evidence includes the shutdown exclusion audit and expected confirmation/intent coverage for destructive native operations.
- Native REST malformed-input coverage stayed in the typed JSON error envelope
lane; expected negative contract routes reported
45expected errors and no undeclared failed routes. - qBittorrent-compatible adapter probes covered unauthenticated category reads, wrong cookies, bad login, malformed booleans, missing or bad hashes, category filtering, and add/delete/property/file flows.
- Torznab adapter probes covered unauthenticated and wrong API keys, duplicate query parameters, malformed search input, bad category input, caps, and feed behavior.
- Adapter error shapes remained adapter-local: qBit responses used qBit-style
text/plain outcomes and Torznab responses used XML feed/error behavior rather
than native
/api/v1JSON aliases or envelopes.