[Verification] All acceptance criteria met. Verified complete. types.py line 7: patent_id: str. Already typed correctly. Closing as implemented.
[Verification] All acceptance criteria met. Verified complete. analyzer.py analyze_single_patent() checks if the PDF exists on disk, attempts to download via cached link from `db.get_cached_pat…
[Verification] All acceptance criteria met. Verified complete. docker-compose.yml includes named volume patent_data:/app/patents. storage.py provides a StorageBackend abstraction with both…
[Verification] All acceptance criteria met. Verified complete. config.py line 46: serp_cache_ttl_hours = int(os.getenv('SERP_CACHE_TTL_HOURS', '24')). Used in analyzer.py line 73. Documented…
[Verification] All acceptance criteria met. Verified complete. config.py line 43: model = os.getenv('MODEL', 'anthropic/claude-3.5-sonnet'). Used in llm.py. Documented in .env.example.…
[Verification] All acceptance criteria met. Verified complete. All three files (analyzer.py, serp_api.py, llm.py) use logger = logging.getLogger(__name__) with appropriate `logger.info/debu…
[Verification] All acceptance criteria met. Verified complete. tests/test_auth.py covers: registration (first user admin, subsequent user, duplicate email), login (valid returns tokens, invalid…
[Verification] All acceptance criteria met. Verified complete. slowapi rate limiter in api.py with 10/minute on /auth/login and 5/minute on /auth/register. Returns HTTP 429 with…
[Verification] All acceptance criteria met. Verified complete. api.py uses db.create_job(), db.get_job(), db.list_jobs(), db.update_job() for PostgreSQL-backed job state. `db.mark_stale_j…
[Verification] All acceptance criteria met. Verified complete. auth.py implements a module-level singleton _db_client with init_db_client()/close_db_client() called from the FastAPI…