Skip to content

Release v0.8.2 — Security & resilience hardening#10

Merged
senseibelbi merged 2 commits intomainfrom
codex/readme-0.8.1-release-notes
Apr 16, 2026
Merged

Release v0.8.2 — Security & resilience hardening#10
senseibelbi merged 2 commits intomainfrom
codex/readme-0.8.1-release-notes

Conversation

@senseibelbi
Copy link
Copy Markdown
Collaborator

Summary

This PR bumps the AOP MCP server to v0.8.2 and implements security / resilience hardening based on the ToxMCP Audit Reviewed v2 findings.

Key changes

  1. Hardened SPARQL query construction (AOP-01)

    • Introduces TemplateCatalog.render_safe() with categorized parameter binding: escaped string literals, scheme-validated URIs, cast integers, and explicitly separated trusted structural fragments.
    • Migrates all production adapters (aop_wiki.py, aop_db.py) away from unsafe template.format(**params) interpolation.
    • Fixes the CAS-URI injection path in map_chemical_to_aops by constructing the URI safely in Python with urllib.parse.quote.
  2. Resilience controls for SPARQL endpoints (AOP-02)

    • Adds per-endpoint CircuitBreaker with CLOSED / OPEN / HALF_OPEN states.
    • Adds exponential backoff + jitter between retries in SparqlClient._dispatch().
    • Non-retryable 4xx client errors (SparqlQueryError) are surfaced immediately and do not count as circuit-breaker failures.
  3. Strengthened draft audit chain (AOP-03 / AOP-04)

    • VersionMetadata now enforces checksum and previous_checksum as required fields.
    • Adds checksum_algorithm (default sha256-v1) so the verification algorithm is explicit.
    • Adds ElectronicSignature support with authored / reviewed / approved / rejected semantics.
    • Hardens verify_audit_chain() to reject unsupported algorithms, empty checksums, and broken chains.
  4. Ontology drift protection scaffold (AOP-05)

    • Replaces hardcoded _iri_to_curie() logic with configurable CurieResolver and a shared AOP_CURIE_RESOLVER.
    • Adds OntologyMigrator framework with BFS pathfinding and term-mapping support in src/semantic/migration.py.

Follow-up fixes (post-review)

Addressed all Copilot code-review comments:

  • Fixed circuit-breaker default inconsistency (success_threshold=1).
  • Reset success_count on OPEN → HALF_OPEN transitions.
  • Excluded SparqlQueryError from circuit-breaker failure counting.
  • Tightened URI validation to reject SPARQL-breaking characters (<>"{}|^ and whitespace).
  • Escaped \n, \r, \t in SPARQL literal rendering.
  • Removed the dangling inchikey parameter from map_chemical_to_aops (was accepted but never used in the query template).
  • Made the backoff retry test deterministic via monkeypatched asyncio.sleep and random.uniform.

Verification

  • 231 unit tests passing (1 skipped)
  • Live server smoke-tested on port 8050 (tools/list, search_aops, get_aop)

Version bump

  • pyproject.toml: 0.8.10.8.2
  • src/server/version.py: 0.8.10.8.2
  • README updated with v0.8.2 changelog.

…draft audit chain, and add ontology drift scaffold

Security & resilience hardening based on ToxMCP Audit Reviewed v2:

- Phase 1 (AOP-01): TemplateCatalog.render_safe() with escaped literals,
  validated URIs, and separated trusted structural fragments. All adapters
  migrated from unsafe .format() interpolation.
- Phase 2 (AOP-02): Per-endpoint circuit breaker + exponential backoff
  with jitter in SparqlClient._dispatch().
- Phase 3 (AOP-03/AOP-04): Mandatory checksums, checksum_algorithm field,
  ElectronicSignature support, and hardened verify_audit_chain().
- Phase 4 (AOP-05): Configurable CurieResolver, AOP_CURIE_RESOLVER, and
  OntologyMigrator scaffold for version-driven migrations.

README updated with v0.8.2 changelog. 231 unit tests passing.
- Fix circuit breaker defaults: success_threshold=1 to match half_open_max_calls=1.
- Reset success_count when transitioning OPEN -> HALF_OPEN.
- Exclude SparqlQueryError (4xx) from circuit breaker failure counting.
- Strengthen URI validation to reject SPARQL-breaking characters.
- Escape newline, carriage return, and tab in SPARQL literal rendering.
- Remove dangling inchikey parameter from map_chemical_to_aops.
- Make backoff test deterministic with monkeypatched sleep and random.uniform.
- All 231 unit tests passing.
@senseibelbi senseibelbi merged commit 255cdd5 into main Apr 16, 2026
8 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant