diff --git a/connectors/clients/julia/Project.toml b/connectors/clients/julia/Project.toml index 546d979d..53851690 100644 --- a/connectors/clients/julia/Project.toml +++ b/connectors/clients/julia/Project.toml @@ -2,7 +2,7 @@ # Copyright (c) 2026 Jonathan D.A. Jewell (hyperpolymath) name = "VeriSimDBClient" -uuid = "a1b2c3d4-e5f6-7890-abcd-ef1234567890" +uuid = "a1b2c3d4-e5f6-8890-abcd-ef1234567890" authors = ["Jonathan D.A. Jewell "] version = "0.1.0" diff --git a/connectors/shared/json-schema/error.json b/connectors/shared/json-schema/error.json index 8c7096ff..d93019c6 100644 --- a/connectors/shared/json-schema/error.json +++ b/connectors/shared/json-schema/error.json @@ -25,7 +25,7 @@ "type": "string", "description": "Human-readable error message providing context about what went wrong. Suitable for display in developer tools and logs. Should not contain sensitive information.", "examples": [ - "Entity not found: 550e8400-e29b-41d4-a716-446655440000", + "Entity not found: 550e8400-e29b-81d4-a716-446655440000", "Tensor shape [3, 4] does not match data length 15 (expected 12)", "Provenance chain corrupted for entity abc-123: record 5 parent_hash mismatch" ] @@ -43,7 +43,7 @@ "additionalProperties": true, "examples": [ { - "entity_id": "550e8400-e29b-41d4-a716-446655440000", + "entity_id": "550e8400-e29b-81d4-a716-446655440000", "modality": "vector", "expected_dimension": 384, "actual_dimension": 256 diff --git a/connectors/shared/json-schema/octad.json b/connectors/shared/json-schema/octad.json index 40d33f10..d6953c1c 100644 --- a/connectors/shared/json-schema/octad.json +++ b/connectors/shared/json-schema/octad.json @@ -11,7 +11,7 @@ "type": "string", "description": "Unique entity identifier (UUID v4). Serves as the canonical key across all modality stores.", "pattern": "^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$|^.+$", - "examples": ["550e8400-e29b-41d4-a716-446655440000"] + "examples": ["550e8400-e29b-81d4-a716-446655440000"] }, "status": { "$ref": "octad-status.json", diff --git a/docs/HANDOVER-2026-10-24.adoc b/docs/HANDOVER-2026-10-24.adoc index e849e1e9..b194c465 100644 --- a/docs/HANDOVER-2026-10-24.adoc +++ b/docs/HANDOVER-2026-10-24.adoc @@ -5,6 +5,11 @@ :toclevels: 3 :icons: font +NOTE: The modality-contract checker has since moved from Python to Bash and +`jq` as `scripts/check-modality-contract.sh` to satisfy the estate language +policy. The session evidence below describes the original Python checker; +the Reproduce commands use its current replacement. + [.lead] A complete handover of the issue #299 session, so the next person does not have to reconstruct it from a pull-request diff and a conversation. It states what @@ -461,7 +466,7 @@ ever wanted (§7). ---- bash tests/doc-consonance-gate.sh bash scripts/check-doc-links.sh -python3 scripts/check-modality-contract.py +bash scripts/check-modality-contract.sh bash tests/modality-contract-gate.sh bash tests/assail-classifications-gate.sh ---- diff --git a/docs/VCL-SPEC.adoc b/docs/VCL-SPEC.adoc index c1ae976c..73c523ec 100644 --- a/docs/VCL-SPEC.adoc +++ b/docs/VCL-SPEC.adoc @@ -264,7 +264,7 @@ uuid = 8*hex_digit , '-' , 4*hex_digit , '-' , 4*hex_digit , '-' , 4*hex_digit , '-' , 12*hex_digit ; ---- -Standard RFC 4122 format. Example: `550e8400-e29b-41d4-a716-446655440000`. +Standard RFC 4122 format. Example: `550e8400-e29b-81d4-a716-446655440000`. ==== Timestamp Literals @@ -790,7 +790,7 @@ Query a specific octad by UUID: [source,vcl] ---- -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ---- Type: stem:[\text{Octad}(\text{UUID})] @@ -1373,7 +1373,7 @@ INSERT HEXAD WITH INSERT HEXAD WITH DOCUMENT(title = "Follow-Up Study", year = 2026), VECTOR([0.5, 0.3, 0.2, 0.8]), - GRAPH(CITES, 550e8400-e29b-41d4-a716-446655440000) + GRAPH(CITES, 550e8400-e29b-81d4-a716-446655440000) -- Verified insert with proof INSERT HEXAD WITH @@ -1402,11 +1402,11 @@ set_assignment = field_ref , '=' , literal ; [source,vcl] ---- -- Simple field update -UPDATE HEXAD 550e8400-e29b-41d4-a716-446655440000 +UPDATE HEXAD 550e8400-e29b-81d4-a716-446655440000 SET DOCUMENT.title = "Corrected Title", DOCUMENT.severity = 5 -- Verified update with proof -UPDATE HEXAD 550e8400-e29b-41d4-a716-446655440000 +UPDATE HEXAD 550e8400-e29b-81d4-a716-446655440000 SET DOCUMENT.status = "retracted", DOCUMENT.retraction_reason = "Data fabrication" PROOF ACCESS(EditAccessContract) @@ -1430,10 +1430,10 @@ delete_mutation = 'DELETE' , 'HEXAD' , uuid , [proof_clause] ; [source,vcl] ---- -- Simple deletion -DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 +DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 -- Verified deletion with proof -DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 +DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF ACCESS(AdminAccessContract) AND PROVENANCE(DeletionAuditContract) ---- @@ -1660,7 +1660,7 @@ VCL does not have explicit JOIN syntax. Instead, cross-modal querying is implici [source,vcl] ---- SELECT GRAPH, VECTOR, DOCUMENT -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE (h)-[:CITES]->(target) AND h.embedding SIMILAR TO [0.1, 0.2, 0.3] WITHIN 0.8 AND FULLTEXT CONTAINS "neural networks" diff --git a/docs/backwards-compatibility.adoc b/docs/backwards-compatibility.adoc index fb126eaa..ba65fe97 100644 --- a/docs/backwards-compatibility.adoc +++ b/docs/backwards-compatibility.adoc @@ -394,7 +394,7 @@ end ```json { "_format_version": "1.2.0", - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "title": "Machine Learning Paper", "body": "...", "created_at": "2025-01-15T10:30:00Z" diff --git a/docs/consultation-normalization-strategy.adoc b/docs/consultation-normalization-strategy.adoc index 20a22029..6dcf9df6 100644 --- a/docs/consultation-normalization-strategy.adoc +++ b/docs/consultation-normalization-strategy.adoc @@ -794,7 +794,7 @@ Pull: schema version, optimization %DriftEvent{ type: :retraction, severity: :critical, - octad_id: "octad:550e8400-e29b-41d4-a716-446655440000", + octad_id: "octad:550e8400-e29b-81d4-a716-446655440000", field: "semantic.status", old_value: "published", new_value: "retracted", @@ -813,7 +813,7 @@ Pull: schema version, optimization %DriftEvent{ type: :integrity_violation, severity: :critical, - octad_id: "octad:6ba7b810-9dad-11d1-80b4-00c04fd430c8", + octad_id: "octad:6ba7b810-9dad-81d1-80b4-00c04fd430c8", field: "document.content_hash", old_value: "sha256:abc123...", new_value: "sha256:def456...", @@ -833,7 +833,7 @@ Pull: schema version, optimization %DriftEvent{ type: :title_mismatch, severity: :low, - octad_id: "octad:7c9e6679-7425-40de-944b-e07fc1f90ae7", + octad_id: "octad:7c9e6679-7425-80de-944b-e07fc1f90ae7", field: "graph.title vs document.title", old_value: "ML Paper", new_value: "Machine Learning Paper", @@ -852,7 +852,7 @@ Pull: schema version, optimization %DriftEvent{ type: :derived_stale, severity: :low, - octad_id: "octad:8d8a8b4c-5d3e-4f5a-9b6c-7e8f9a0b1c2d", + octad_id: "octad:8d8a8b4c-5d3e-8f5a-9b6c-7e8f9a0b1c2d", field: "semantic.citation_count", old_value: 42, new_value: 45, diff --git a/docs/deployment/deployment.adoc b/docs/deployment/deployment.adoc index bbd63bae..a769ecd4 100644 --- a/docs/deployment/deployment.adoc +++ b/docs/deployment/deployment.adoc @@ -463,7 +463,7 @@ scrape_configs: "level": "INFO", "component": "verisim-api", "message": "Octad created", - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "modalities": ["document", "vector"], "duration_ms": 45 } @@ -605,7 +605,7 @@ VeriSimDB's temporal modality supports point-in-time recovery: curl -X POST http://localhost:8080/api/v1/admin/restore \ -H "Content-Type: application/json" \ -d '{ - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "timestamp": "2026-02-04T12:00:00Z" }' ---- diff --git a/docs/drift-handling.adoc b/docs/drift-handling.adoc index 6fbee35a..a0a56ea9 100644 --- a/docs/drift-handling.adoc +++ b/docs/drift-handling.adoc @@ -26,7 +26,7 @@ toc::[] **Example:** ``` -Octad: 550e8400-e29b-41d4-a716-446655440000 +Octad: 550e8400-e29b-81d4-a716-446655440000 verisim:graph → title: "Machine Learning Paper" verisim:document → title: "ML Paper" ❌ DRIFT @@ -64,7 +64,7 @@ t1: octad.graph still has "Draft Paper" ❌ DRIFT **Example:** ``` -Octad: 550e8400-e29b-41d4-a716-446655440000 +Octad: 550e8400-e29b-81d4-a716-446655440000 University A: retraction_status = "active" University B: retraction_status = "retracted" ❌ DRIFT @@ -160,7 +160,7 @@ WHERE octad.id = @id; ```json { - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "has_drift": true, "drifts": [ { @@ -285,7 +285,7 @@ USING STRATEGY manual; ```json { - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "conflicts": [ { "field": "title", @@ -374,7 +374,7 @@ WHERE octad.id = @id; ```json { - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "is_consistent": true, "checked_modalities": ["graph", "vector", "document", "semantic", "temporal"], "last_repair": "2025-01-15T10:30:00Z", @@ -551,7 +551,7 @@ STORES [@university_a, @university_b]; ```json { - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "federation_drift": true, "stores": { "university_a": { @@ -635,7 +635,7 @@ LIMIT 10; ```json { - "octad_id": "550e8400-e29b-41d4-a716-446655440000", + "octad_id": "550e8400-e29b-81d4-a716-446655440000", "drift_events": [ { "detected_at": "2025-01-15T10:30:00Z", diff --git a/docs/getting-started.adoc b/docs/getting-started.adoc index 0661aff7..bd6f8ced 100644 --- a/docs/getting-started.adoc +++ b/docs/getting-started.adoc @@ -194,7 +194,7 @@ Response: [source,json] ---- { - "id": "a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d", + "id": "a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d", "status": "created", "modalities": { "document": true, @@ -213,14 +213,14 @@ Response: [source,bash] ---- -curl http://localhost:8080/api/v1/octads/a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d +curl http://localhost:8080/api/v1/octads/a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d ---- === Step 3: Check Drift Status [source,bash] ---- -curl http://localhost:8080/api/v1/drift/entity/a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d +curl http://localhost:8080/api/v1/drift/entity/a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d ---- Response: @@ -228,7 +228,7 @@ Response: [source,json] ---- { - "entity_id": "a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d", + "entity_id": "a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d", "graph": 0.0, "vector": 0.0, "tensor": 0.0, @@ -252,14 +252,14 @@ updating the document: [source,bash] ---- # Update ONLY the vector embedding (not the document text) -curl -X PUT http://localhost:8080/api/v1/octads/a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d \ +curl -X PUT http://localhost:8080/api/v1/octads/a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d \ -H "Content-Type: application/json" \ -d '{ "embedding": [0.99, 0.99, 0.99, 0.99, 0.99, 0.99, 0.99, 0.99] }' # Check drift again -curl http://localhost:8080/api/v1/drift/entity/a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d +curl http://localhost:8080/api/v1/drift/entity/a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d ---- Response: @@ -267,7 +267,7 @@ Response: [source,json] ---- { - "entity_id": "a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d", + "entity_id": "a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d", "vector": 0.87, "document": 0.0, "overall": 0.43, @@ -282,7 +282,7 @@ detected that the embedding no longer corresponds to the text. [source,bash] ---- -curl -X POST http://localhost:8080/api/v1/normalizer/trigger/a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d +curl -X POST http://localhost:8080/api/v1/normalizer/trigger/a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d ---- VeriSimDB identifies the document as the authoritative modality and @@ -300,7 +300,7 @@ understands modalities and drift. [source,sql] ---- -- Get all modalities for an entity -SELECT * FROM HEXAD 'a1b2c3d4-e5f6-4a7b-8c9d-0e1f2a3b4c5d' +SELECT * FROM HEXAD 'a1b2c3d4-e5f6-8a7b-8c9d-0e1f2a3b4c5d' -- Get specific modalities SELECT GRAPH.*, DOCUMENT.*, VECTOR.* FROM HEXAD 'entity-id' diff --git a/docs/modality-profile.adoc b/docs/modality-profile.adoc index 7f6ac741..24325e44 100644 --- a/docs/modality-profile.adoc +++ b/docs/modality-profile.adoc @@ -17,7 +17,7 @@ this document and the code/schema disagree, the code/schema win and this documen has a bug. // The two annotations below are read by -// scripts/check-modality-contract.py (via tests/modality-contract-gate.sh). +// scripts/check-modality-contract.sh (via tests/modality-contract-gate.sh). // They are the machine-checkable half of this document: the doc cannot drift // away from connectors/shared/json-schema/ and the Rust core without CI saying // so. Keep the exact `// modality-contract:` prefix. diff --git a/docs/papers/verisimdb-federated-consistency.adoc b/docs/papers/verisimdb-federated-consistency.adoc index 6bc45ffb..b034c008 100644 --- a/docs/papers/verisimdb-federated-consistency.adoc +++ b/docs/papers/verisimdb-federated-consistency.adoc @@ -455,7 +455,7 @@ Multiple proofs can be composed in a single query: [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF INTEGRITY(DataIntegrityContract) AND PROVENANCE(FullLineageContract) ---- diff --git a/docs/vcl-examples.adoc b/docs/vcl-examples.adoc index 6fce67cd..960f3172 100644 --- a/docs/vcl-examples.adoc +++ b/docs/vcl-examples.adoc @@ -17,14 +17,14 @@ This document provides **63 comprehensive examples** of VCL queries and mutation [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ---- **Dependent-Type** (with proof): [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF EXISTENCE(ExistenceContract) ---- @@ -34,7 +34,7 @@ PROOF EXISTENCE(ExistenceContract) [source,vcl] ---- SELECT GRAPH -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE (h)-[:CITES]->(target) ---- @@ -42,7 +42,7 @@ WHERE (h)-[:CITES]->(target) [source,vcl] ---- SELECT VECTOR -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE h.embedding SIMILAR TO [0.1, 0.2, 0.3, 0.4] ---- @@ -50,7 +50,7 @@ WHERE h.embedding SIMILAR TO [0.1, 0.2, 0.3, 0.4] [source,vcl] ---- SELECT GRAPH, VECTOR, SEMANTIC -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF INTEGRITY(DataIntegrityContract) ---- @@ -85,7 +85,7 @@ LIMIT 100 [source,vcl] ---- SELECT GRAPH -FROM HEXAD abc12345-0000-0000-0000-000000000000 +FROM HEXAD abc12345-0000-8000-8000-000000000000 WHERE (h)-[:CO_AUTHOR]-(colleague) AND (colleague)-[:AFFILIATED_WITH]->(institution) AND institution.country == "USA" @@ -307,7 +307,7 @@ SELECT GRAPH, VECTOR, DOCUMENT FROM FEDERATION /research-db/* WITH DRIFT REPAIR WHERE h.embedding SIMILAR TO [0.1, 0.2, ...] WITHIN 0.85 AND (h)-[:CITES]->(target_paper) - AND target_paper.uuid == "123e4567-e89b-12d3-a456-426614174000" + AND target_paper.uuid == "123e4567-e89b-82d3-a456-426614174000" AND FULLTEXT CONTAINS "neural-symbolic integration" AND SATISFIES CitationContract PROOF CITATION(NeurosymbolicContract) @@ -744,7 +744,7 @@ LIMIT 100; [source,vcl] ---- SELECT DOCUMENT.name, DOCUMENT.severity -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ---- **Mixed modalities and column projections:** @@ -862,7 +862,7 @@ guarantee — the ZKP witnesses include the aggregate computation, ensuring veri [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF EXISTENCE(ExistenceContract) AND INTEGRITY(DataIntegrityContract) ---- @@ -906,7 +906,7 @@ LIMIT 50 [source,vcl] ---- SELECT DOCUMENT, GRAPH -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE DOCUMENT.severity > GRAPH.centrality ---- @@ -998,7 +998,7 @@ The octad ID is auto-generated and returned in the result. INSERT HEXAD WITH DOCUMENT(title = "Follow-Up Study", year = 2026), VECTOR([0.5, 0.3, 0.2, 0.8]), - GRAPH(CITES, 550e8400-e29b-41d4-a716-446655440000) + GRAPH(CITES, 550e8400-e29b-81d4-a716-446655440000) ---- Creates a octad with document content, embedding, and a graph edge @@ -1024,7 +1024,7 @@ insert is verified and auditable. **Update specific fields:** [source,vcl] ---- -UPDATE HEXAD 550e8400-e29b-41d4-a716-446655440000 +UPDATE HEXAD 550e8400-e29b-81d4-a716-446655440000 SET DOCUMENT.title = "Corrected Title", DOCUMENT.severity = 5 ---- @@ -1036,7 +1036,7 @@ Drift detection will fire if the change creates cross-modal inconsistency. **Update with access proof:** [source,vcl] ---- -UPDATE HEXAD 550e8400-e29b-41d4-a716-446655440000 +UPDATE HEXAD 550e8400-e29b-81d4-a716-446655440000 SET DOCUMENT.status = "retracted", DOCUMENT.retraction_reason = "Data fabrication" PROOF ACCESS(EditAccessContract) AND PROVENANCE(RetractionContract) ---- @@ -1049,7 +1049,7 @@ of the retraction in the audit trail. **Simple deletion:** [source,vcl] ---- -DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 +DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 ---- Removes the octad and all its modality data. This operation is logged @@ -1060,7 +1060,7 @@ in verisim-temporal for auditability. **Delete with access and provenance proof:** [source,vcl] ---- -DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 +DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF ACCESS(AdminAccessContract) AND PROVENANCE(DeletionAuditContract) ---- diff --git a/docs/vcl-vs-sql.adoc b/docs/vcl-vs-sql.adoc index de34392e..81237c7e 100644 --- a/docs/vcl-vs-sql.adoc +++ b/docs/vcl-vs-sql.adoc @@ -137,14 +137,14 @@ The remaining rows are genuinely absent from the grammar. ---- SELECT * FROM entities -WHERE id = '550e8400-e29b-41d4-a716-446655440000'; +WHERE id = '550e8400-e29b-81d4-a716-446655440000'; ---- **VCL (Slipstream):** [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ---- The VCL version returns all eight modalities for that octad. The SQL version returns only the columns in the `entities` table. @@ -158,7 +158,7 @@ SELECT e2.* FROM entities e1 JOIN relationships r ON e1.id = r.source_id JOIN entities e2 ON r.target_id = e2.id -WHERE e1.id = '550e8400-e29b-41d4-a716-446655440000' +WHERE e1.id = '550e8400-e29b-81d4-a716-446655440000' AND r.type = 'CITES'; ---- @@ -166,7 +166,7 @@ WHERE e1.id = '550e8400-e29b-41d4-a716-446655440000' [source,vcl] ---- SELECT GRAPH -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE (h)-[:CITES]->(target) ---- @@ -217,7 +217,7 @@ LIMIT 10 [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF INTEGRITY(DataIntegrityContract) ---- diff --git a/docs/vcl-vs-vcl-dt.adoc b/docs/vcl-vs-vcl-dt.adoc index 0c76bd58..3f1b7aae 100644 --- a/docs/vcl-vs-vcl-dt.adoc +++ b/docs/vcl-vs-vcl-dt.adoc @@ -111,7 +111,7 @@ Example: [source,vcl] ---- SELECT * -FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 +FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF INTEGRITY(DataIntegrityContract) ---- diff --git a/rust-core/verisim-api/src/groove.rs b/rust-core/verisim-api/src/groove.rs index 74df3cdb..67a5fb6b 100644 --- a/rust-core/verisim-api/src/groove.rs +++ b/rust-core/verisim-api/src/groove.rs @@ -874,7 +874,7 @@ mod tests { #[test] fn test_capability_matching() { - let peer_consumes = vec!["octad-storage".to_string(), "unknown-cap".to_string()]; + let peer_consumes = ["octad-storage".to_string(), "unknown-cap".to_string()]; let matched: Vec = peer_consumes .iter() diff --git a/rust-core/verisim-octad/src/ram_promotion.rs b/rust-core/verisim-octad/src/ram_promotion.rs index 8d93f5f9..f862481d 100644 --- a/rust-core/verisim-octad/src/ram_promotion.rs +++ b/rust-core/verisim-octad/src/ram_promotion.rs @@ -39,7 +39,7 @@ // - On crash: WAL replays, RAM overlay is gone, no data loss use serde::{Deserialize, Serialize}; -use std::collections::{HashMap, HashSet}; +use std::collections::HashMap; use std::time::{Duration, Instant}; /// Hard limit: maximum octads promoted to RAM simultaneously. @@ -98,7 +98,6 @@ impl Modality { /// State of a promoted modality. #[derive(Debug, Clone)] struct PromotedState { - modality: Modality, promoted_at: Instant, estimated_size_bytes: u64, operation_count: u64, @@ -254,9 +253,17 @@ impl PromotionManager { } } - /// Promote a modality to RAM. + /// Record a modality as promoted, reserving `estimated_size` bytes of the RAM budget. /// - /// Returns Ok(()) if promoted, Err if blocked/disabled. + /// A new promotion updates RAM usage and promotion history; it does not move data. + /// When enabled and below the two-modality limit, an already promoted modality + /// returns `Ok(())` without changing its reservation or history. + /// + /// # Errors + /// + /// Returns an error if promotion is disabled, two modalities are already promoted + /// (including when `modality` is already promoted), or a new reservation would + /// exceed the RAM budget. Reserving exactly the remaining budget is allowed. pub fn promote(&mut self, modality: &Modality, estimated_size: u64) -> Result<(), String> { if !self.enabled { return Err("RAM promotion disabled".to_string()); @@ -284,7 +291,6 @@ impl PromotionManager { self.promoted.insert( modality.clone(), PromotedState { - modality: modality.clone(), promoted_at: Instant::now(), estimated_size_bytes: estimated_size, operation_count: 0, diff --git a/scripts/check-modality-contract.py b/scripts/check-modality-contract.py deleted file mode 100755 index 059fb73c..00000000 --- a/scripts/check-modality-contract.py +++ /dev/null @@ -1,187 +0,0 @@ -#!/usr/bin/env python3 -# SPDX-License-Identifier: MPL-2.0 -# Copyright (c) 2026 Jonathan D.A. Jewell (hyperpolymath) -"""check-modality-contract.py — keep docs/modality-profile.adoc honest. - -WHY THIS EXISTS - Issue #299 asked for modality-profile *terminology* — no wire change. The risk - with a pure-prose change is that the prose is wrong from the day it lands: - somebody adds a ninth modality, or renames one, and the document keeps - confidently describing the old eight. This checker binds the document's own - modality lists to the three artefacts that actually define the slots: - - * connectors/shared/json-schema/modality.json (the modality enum) - * rust-core/verisim-octad/src/lib.rs (ModalityStatus, OctadInput) - * connectors/shared/json-schema/octad-input.json (create/update payload) - - It changes nothing; it only fails when the document and those artefacts - disagree. It is deliberately *not* a schema validator: validating payloads is - a separate concern, and this repo has no pinned validator dependency. - -WHAT IS CHECKED - 1. The doc's `octad-slots` annotation == the modality enum == ModalityStatus - boolean fields. - 2. The doc's `payload-fields` annotation == octad-input.json properties - == the core `OctadInput` struct fields. - 3. octad-input.json stays closed (`additionalProperties: false`) — because the - document promises there is no ninth modality. - 4. octad-slots - payload-fields == {temporal}, because the document states - exactly that: every slot except `temporal` is settable through OctadInput. - - Only facts in the document are checked. The divergences the document *reports* - (OpenAPI vs OctadRequest, client types, duplicate grammar) are deliberately not - asserted: they are known-broken, and a gate that encodes a known break as - expected would freeze it in place instead of flagging it. - -USAGE - scripts/check-modality-contract.py # check this tree - scripts/check-modality-contract.py # check an alternate root - -EXIT - 0 — doc, schema and Rust agree - 1 — at least one disagreement; every mismatch is printed - 2 — an input file is missing or unparseable (fail closed) -""" - -from __future__ import annotations - -import json -import re -import sys -from pathlib import Path - -DOC = "docs/modality-profile.adoc" -MODALITY_ENUM = "connectors/shared/json-schema/modality.json" -INPUT_SCHEMA = "connectors/shared/json-schema/octad-input.json" -CORE_LIB = "rust-core/verisim-octad/src/lib.rs" - -ANNOTATION = re.compile(r"^\s*//\s*modality-contract:\s*([a-z-]+)\s*=\s*(.+?)\s*$") - - -def fail(message: str) -> "NoReturn": # noqa: F821 - py3.8-compatible annotation string - print(f"ERROR: {message}", file=sys.stderr) - raise SystemExit(2) - - -def read_text(root: Path, rel: str) -> str: - path = root / rel - if not path.is_file(): - fail(f"missing required file: {rel}") - return path.read_text(encoding="utf-8") - - -def read_json(root: Path, rel: str) -> dict: - try: - return json.loads(read_text(root, rel)) - except json.JSONDecodeError as exc: - fail(f"{rel} is not valid JSON: {exc}") - - -def doc_annotations(root: Path) -> dict: - found: dict = {} - for line in read_text(root, DOC).splitlines(): - match = ANNOTATION.match(line) - if match: - key, value = match.group(1), match.group(2) - if key in found: - fail(f"{DOC} declares 'modality-contract: {key}' more than once") - found[key] = [item.strip() for item in value.split(",") if item.strip()] - for required in ("octad-slots", "payload-fields"): - if required not in found: - fail( - f"{DOC} is missing its '// modality-contract: {required} = …' " - "annotation; the gate cannot verify a document that does not " - "declare what it claims" - ) - return found - - -def struct_fields(source: str, struct_name: str) -> list: - """Return the field names of `pub struct { … }` in a Rust source.""" - match = re.search( - rf"pub struct {struct_name}\b[^{{]*\{{(.*?)\n\}}", - source, - re.DOTALL, - ) - if not match: - fail(f"could not find `pub struct {struct_name}` in {CORE_LIB}") - body = match.group(1) - # Drop attribute/doc lines and use only `pub : ,` declarations. - return re.findall(r"^\s*pub\s+([a-z_][a-z0-9_]*)\s*:", body, re.MULTILINE) - - -def compare(label: str, left: list, right: list, mismatches: list) -> None: - left_set, right_set = set(left), set(right) - if left_set == right_set: - return - for only_left in sorted(left_set - right_set): - mismatches.append(f"{label}: {only_left!r} is on the left side only") - for only_right in sorted(right_set - left_set): - mismatches.append(f"{label}: {only_right!r} is on the right side only") - - -def main(argv: list) -> int: - root = Path(argv[1]) if len(argv) > 1 else Path(__file__).resolve().parent.parent - if not root.is_dir(): - fail(f"scan root does not exist: {root}") - - doc = doc_annotations(root) - - enum = read_json(root, MODALITY_ENUM).get("enum") - if not isinstance(enum, list) or not enum: - fail(f"{MODALITY_ENUM} has no non-empty 'enum'") - - schema = read_json(root, INPUT_SCHEMA) - schema_props = list(schema.get("properties", {})) - if not schema_props: - fail(f"{INPUT_SCHEMA} has no 'properties'") - - source = read_text(root, CORE_LIB) - status_fields = struct_fields(source, "ModalityStatus") - input_fields = struct_fields(source, "OctadInput") - - mismatches: list = [] - compare(f"{DOC} octad-slots vs {MODALITY_ENUM} enum", doc["octad-slots"], enum, mismatches) - compare(f"{DOC} octad-slots vs ModalityStatus fields", doc["octad-slots"], status_fields, mismatches) - compare(f"{DOC} payload-fields vs {INPUT_SCHEMA} properties", doc["payload-fields"], schema_props, mismatches) - compare(f"{DOC} payload-fields vs OctadInput fields", doc["payload-fields"], input_fields, mismatches) - - if schema.get("additionalProperties") is not False: - mismatches.append( - f"{INPUT_SCHEMA}: 'additionalProperties' must be false — the document " - "states that no ninth modality is expressible in the schema" - ) - - # The one documented asymmetry: `temporal` is in the slot list but is not - # settable through OctadInput. Anything else would contradict §5 of the doc. - not_settable = set(doc["octad-slots"]) - set(doc["payload-fields"]) - if not_settable != {"temporal"}: - mismatches.append( - f"{DOC}: slots not settable via OctadInput are {sorted(not_settable)}; " - "the document states this set is exactly {'temporal'} — update §5 and " - "this gate together if the contract really changed" - ) - - if mismatches: - print("FAIL modality-contract: the document and the implementation disagree.", file=sys.stderr) - for item in mismatches: - print(f" - {item}", file=sys.stderr) - print( - f" The document is normative for words only. Fix {DOC}, or, if the " - "contract itself changed, that is an owner decision that lands with a " - "versioned schema and tests — see §10 of the document.", - file=sys.stderr, - ) - return 1 - - print( - "PASS modality-contract: " - f"{len(doc['octad-slots'])} octad slots and {len(doc['payload-fields'])} " - "payload fields agree across doc, modality.json, octad-input.json and the " - "Rust core" - ) - return 0 - - -if __name__ == "__main__": - raise SystemExit(main(sys.argv)) diff --git a/scripts/check-modality-contract.sh b/scripts/check-modality-contract.sh new file mode 100755 index 00000000..691451e7 --- /dev/null +++ b/scripts/check-modality-contract.sh @@ -0,0 +1,94 @@ +#!/usr/bin/env bash +# SPDX-License-Identifier: MPL-2.0 +# Copyright (c) 2026 Jonathan D.A. Jewell (hyperpolymath) +# +# Bind docs/modality-profile.adoc annotations to the schema and Rust fields. +# Usage: scripts/check-modality-contract.sh [root] +# Exit: 0 agreement; 1 drift; 2 missing, malformed or unreadable input. +# Requires Bash and jq. This compares the existing contract; it does not +# validate payloads or encode the known schema/API divergences as expected. +set -euo pipefail + +fail() { + echo "ERROR: $*" >&2 + exit 2 +} + +command -v jq >/dev/null 2>&1 || fail "jq missing — cannot check the modality contract" +ROOT=${1:-$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)} +[[ -d "$ROOT" ]] || fail "scan root does not exist: $ROOT" +DOC=docs/modality-profile.adoc +MODALITY_ENUM=connectors/shared/json-schema/modality.json +INPUT_SCHEMA=connectors/shared/json-schema/octad-input.json +CORE_LIB=rust-core/verisim-octad/src/lib.rs +for rel in "$DOC" "$MODALITY_ENUM" "$INPUT_SCHEMA" "$CORE_LIB"; do + [[ -f "$ROOT/$rel" ]] || fail "missing required file: $rel" +done + +if ! result=$(jq -n \ + --arg doc_path "$DOC" --arg enum_path "$MODALITY_ENUM" \ + --arg schema_path "$INPUT_SCHEMA" --arg core_path "$CORE_LIB" \ + --rawfile doc "$ROOT/$DOC" --slurpfile enums "$ROOT/$MODALITY_ENUM" \ + --slurpfile schemas "$ROOT/$INPUT_SCHEMA" --rawfile source "$ROOT/$CORE_LIB" ' + def annotations: + [$doc | split("\n")[] | + capture("^\\s*//\\s*modality-contract:\\s*(?[a-z-]+)\\s*=\\s*(?.+?)\\s*$")?] + | group_by(.key) + | if any(.[]; length > 1) then + error($doc_path + " declares a modality-contract annotation more than once") + else map({key: .[0].key, value: (.[0].value | split(",") | + map(gsub("^\\s+|\\s+$"; "") | select(length > 0)))}) | from_entries + end + | if has("octad-slots") and has("payload-fields") then . + else error($doc_path + " is missing a required modality-contract annotation") end; + def struct_fields($name): + ([$source | capture("pub struct " + $name + "\\b[^\\{]*\\{(?.*?)\\n\\}"; "m")] + | if length == 0 then error("could not find pub struct " + $name + " in " + $core_path) + else .[0].body end) + | [split("\n")[] | + capture("^\\s*pub\\s+(?[a-z_][a-z0-9_]*)\\s*:")? | .field]; + def compare($label; $left; $right): + ($left | unique) as $l | ($right | unique) as $r | + [$l - $r | .[] | $label + ": " + tojson + " is on the left side only"] + + [$r - $l | .[] | $label + ": " + tojson + " is on the right side only"]; + + annotations as $annotations | + (if ($enums | length) == 1 and ($enums[0] | type) == "object" and + ($enums[0].enum | type) == "array" and ($enums[0].enum | length) > 0 + then $enums[0].enum else error($enum_path + " has no non-empty enum") end) as $enum | + (if ($schemas | length) == 1 and ($schemas[0] | type) == "object" and + ($schemas[0].properties | type) == "object" and ($schemas[0].properties | length) > 0 + then $schemas[0] else error($schema_path + " has no properties") end) as $schema | + struct_fields("ModalityStatus") as $status_fields | + struct_fields("OctadInput") as $input_fields | + ($annotations["octad-slots"] | unique) as $slots | + ($annotations["payload-fields"] | unique) as $payload | + ($slots - $payload) as $not_settable | + { + slot_count: ($annotations["octad-slots"] | length), + payload_count: ($annotations["payload-fields"] | length), + mismatches: ( + compare($doc_path + " octad-slots vs " + $enum_path + " enum"; $slots; $enum) + + compare($doc_path + " octad-slots vs ModalityStatus fields"; $slots; $status_fields) + + compare($doc_path + " payload-fields vs " + $schema_path + " properties"; + $payload; ($schema.properties | keys)) + + compare($doc_path + " payload-fields vs OctadInput fields"; $payload; $input_fields) + + (if $schema.additionalProperties == false then [] else + [$schema_path + ": additionalProperties must be false — the document states that no ninth modality is expressible in the schema"] end) + + (if $not_settable == ["temporal"] then [] else + [$doc_path + ": slots not settable via OctadInput are " + ($not_settable | tojson) + + "; the document states this set is exactly {temporal} — update §5 and this gate together if the contract really changed"] end) + ) + } +'); then + fail "could not read the modality contract inputs" +fi + +if [[ $(jq '.mismatches | length' <<< "$result") != 0 ]]; then + echo "FAIL modality-contract: the document and the implementation disagree." >&2 + jq -r '.mismatches[] | " - " + .' <<< "$result" >&2 + echo " The document is normative for words only. Fix $DOC, or, if the contract itself changed, that is an owner decision that lands with a versioned schema and tests — see §10 of the document." >&2 + exit 1 +fi + +jq -r '"PASS modality-contract: \(.slot_count) octad slots and \(.payload_count) payload fields agree across doc, modality.json, octad-input.json and the Rust core"' <<< "$result" diff --git a/src/vcl/VCLParser.affine b/src/vcl/VCLParser.affine index cae90fc5..339be5e8 100644 --- a/src/vcl/VCLParser.affine +++ b/src/vcl/VCLParser.affine @@ -1170,7 +1170,7 @@ switch parseSlipstream(slipstreamQuery) { // Dependent-struct query fn dependentQuery = ` SELECT GRAPH, VECTOR - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE h.embedding SIMILAR TO [0.1, 0.2, 0.3] WITHIN 0.9 AND FULLTEXT CONTAINS "climate change" PROOF CITATION(CitationContract) diff --git a/src/vcl/VCLParser_test.affine b/src/vcl/VCLParser_test.affine index 6e9fd066..2c77230f 100644 --- a/src/vcl/VCLParser_test.affine +++ b/src/vcl/VCLParser_test.affine @@ -32,7 +32,7 @@ Js.Console.log("\n=== VCL Parser Tests ===\n") // Test 1: Simple hexad query fn test1 = ` SELECT * - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ` assertOk(parseSlipstream(test1), "Test 1: Simple hexad query") @@ -58,7 +58,7 @@ assertOk(parseSlipstream(test3), "Test 3: Full-text search with LIMIT") // Test 4: Vector similarity query fn test4 = ` SELECT VECTOR - FROM HEXAD abc12345-0000-0000-0000-000000000000 + FROM HEXAD abc12345-0000-8000-8000-000000000000 WHERE h.embedding SIMILAR TO [0.1, 0.2, 0.3] WITHIN 0.9 ` @@ -77,7 +77,7 @@ assertOk(parseSlipstream(test5), "Test 5: Multiple modalities with pagination") // Test 6: Dependent-struct query (should have PROOF) fn test6 = ` SELECT GRAPH - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE FULLTEXT CONTAINS "climate change" PROOF CITATION(CitationContract) ` @@ -87,7 +87,7 @@ assertOk(parseDependentType(test6), "Test 6: Dependent-struct with PROOF") // Test 7: Slipstream with PROOF (should fail) fn test7 = ` SELECT * - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF EXISTENCE(ExistenceContract) ` @@ -96,7 +96,7 @@ assertError(parseSlipstream(test7), "Test 7: Slipstream rejects PROOF clause") // Test 8: Dependent-struct without PROOF (should fail) fn test8 = ` SELECT GRAPH - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ` assertError(parseDependentType(test8), "Test 8: Dependent-struct requires PROOF") @@ -134,7 +134,7 @@ assertOk(parseDependentType(test11), "Test 11: Complex dependent-struct query") // Test 12: All modalities fn test12 = ` SELECT * - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 LIMIT 10 ` @@ -151,13 +151,13 @@ fn test13 = ` assertOk(parseSlipstream(test13), "Test 13: Store-specific query") // Test 14: PROOF with different structs -fn test14a = `SELECT * FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 PROOF EXISTENCE(ExistenceContract)` +fn test14a = `SELECT * FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF EXISTENCE(ExistenceContract)` assertOk(parseDependentType(test14a), "Test 14a: EXISTENCE proof") -fn test14b = `SELECT * FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 PROOF ACCESS(AccessContract)` +fn test14b = `SELECT * FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF ACCESS(AccessContract)` assertOk(parseDependentType(test14b), "Test 14b: ACCESS proof") -fn test14c = `SELECT * FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 PROOF PROVENANCE(ProvenanceContract)` +fn test14c = `SELECT * FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF PROVENANCE(ProvenanceContract)` assertOk(parseDependentType(test14c), "Test 14c: PROVENANCE proof") // Test 15: Invalid UUID (should fail) @@ -229,7 +229,7 @@ assertOk(parseSlipstream(test20), "Test 20: ORDER BY default ASC direction") // Test 21: Column projection (DOCUMENT.name, DOCUMENT.severity) fn test21 = ` SELECT DOCUMENT.name, DOCUMENT.severity - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 ` assertOk(parseSlipstream(test21), "Test 21: Column projection within modality") @@ -361,7 +361,7 @@ Js.Console.log("\n=== Multi-Proof Tests ===\n") // Test 33: Multi-proof composition (AND separated) fn test33 = ` SELECT GRAPH, SEMANTIC - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF EXISTENCE(ExistenceContract) AND INTEGRITY(IntegrityContract) ` @@ -397,7 +397,7 @@ Js.Console.log("\n=== Cross-Modal Condition Tests ===\n") // Test 36: DRIFT condition fn test36 = ` SELECT VECTOR, DOCUMENT - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE DRIFT(VECTOR, DOCUMENT) > 0.3 ` @@ -406,7 +406,7 @@ assertOk(parseSlipstream(test36), "Test 36: DRIFT(VECTOR, DOCUMENT) condition") // Test 37: CONSISTENT condition fn test37 = ` SELECT VECTOR, SEMANTIC - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE CONSISTENT(VECTOR, SEMANTIC) USING COSINE ` @@ -415,7 +415,7 @@ assertOk(parseSlipstream(test37), "Test 37: CONSISTENT(VECTOR, SEMANTIC) USING C // Test 38: EXISTS condition fn test38 = ` SELECT * - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE VECTOR EXISTS ` @@ -424,7 +424,7 @@ assertOk(parseSlipstream(test38), "Test 38: VECTOR EXISTS condition") // Test 39: NOT EXISTS condition fn test39 = ` SELECT * - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE TENSOR NOT EXISTS ` @@ -433,7 +433,7 @@ assertOk(parseSlipstream(test39), "Test 39: TENSOR NOT EXISTS condition") // Test 40: Cross-modal field compare fn test40 = ` SELECT DOCUMENT, GRAPH - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 WHERE DOCUMENT.severity > GRAPH.centrality ` @@ -452,7 +452,7 @@ assertOk(parseMutation(test41), "Test 41: INSERT HEXAD with DOCUMENT and VECTOR" // Test 42: UPDATE mutation fn test42 = ` - UPDATE HEXAD 550e8400-e29b-41d4-a716-446655440000 + UPDATE HEXAD 550e8400-e29b-81d4-a716-446655440000 SET DOCUMENT.title = "Updated Title", DOCUMENT.severity = 5 ` @@ -460,7 +460,7 @@ assertOk(parseMutation(test42), "Test 42: UPDATE HEXAD with SET") // Test 43: DELETE mutation fn test43 = ` - DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 + DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 ` assertOk(parseMutation(test43), "Test 43: DELETE HEXAD") @@ -476,7 +476,7 @@ assertOk(parseMutation(test44), "Test 44: INSERT with PROOF clause") // Test 45: DELETE with multi-proof fn test45 = ` - DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 + DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 PROOF ACCESS(AccessContract) AND PROVENANCE(AuditContract) ` @@ -487,7 +487,7 @@ Js.Console.log("\n=== Statement Tests ===\n") // Test 46: parseStatement with query fn test46 = ` SELECT GRAPH - FROM HEXAD 550e8400-e29b-41d4-a716-446655440000 + FROM HEXAD 550e8400-e29b-81d4-a716-446655440000 LIMIT 10 ` @@ -495,7 +495,7 @@ assertOk(parseStatement(test46), "Test 46: parseStatement dispatches to query") // Test 47: parseStatement with mutation fn test47 = ` - DELETE HEXAD 550e8400-e29b-41d4-a716-446655440000 + DELETE HEXAD 550e8400-e29b-81d4-a716-446655440000 ` assertOk(parseStatement(test47), "Test 47: parseStatement dispatches to mutation") diff --git a/tests/doc-links-gate.sh b/tests/doc-links-gate.sh index b6a0012d..9223caeb 100755 --- a/tests/doc-links-gate.sh +++ b/tests/doc-links-gate.sh @@ -204,7 +204,7 @@ mapfile -t commands < <(awk ' expected=( "bash tests/doc-consonance-gate.sh" "bash scripts/check-doc-links.sh" - "python3 scripts/check-modality-contract.py" + "bash scripts/check-modality-contract.sh" "bash tests/modality-contract-gate.sh" "bash tests/assail-classifications-gate.sh" ) diff --git a/tests/modality-contract-gate.sh b/tests/modality-contract-gate.sh index 501ebfb4..4e265896 100755 --- a/tests/modality-contract-gate.sh +++ b/tests/modality-contract-gate.sh @@ -2,7 +2,7 @@ # SPDX-License-Identifier: MPL-2.0 # Copyright (c) 2026 Jonathan D.A. Jewell (hyperpolymath) # -# modality-contract-gate.sh — positive control for check-modality-contract.py. +# modality-contract-gate.sh — positive control for check-modality-contract.sh. # # Same shape as tests/doc-links-gate.sh: run the real checker first, then plant # known-bad fixtures in a scratch tree and assert the checker (a) fails and @@ -15,13 +15,13 @@ # asserts the document is reported as no longer matching it. # # Fixtures are minimal copies, not the whole repository: the checker only needs -# four inputs, and copying a Rust crate into /tmp to test a Python script would be +# four inputs, and copying a Rust crate into /tmp to test a static checker would be # slow without being any more convincing. set -euo pipefail REPO_ROOT=$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd) -CHECKER="$REPO_ROOT/scripts/check-modality-contract.py" +CHECKER="$REPO_ROOT/scripts/check-modality-contract.sh" FIXTURE_DIR=$(mktemp -d "${TMPDIR:-/tmp}/verisimdb-modality-contract.XXXXXX") trap 'rm -rf -- "$FIXTURE_DIR"' EXIT @@ -30,8 +30,8 @@ if [[ ! -x "$CHECKER" ]]; then exit 1 fi -if ! command -v python3 >/dev/null 2>&1; then - echo "ERROR: python3 missing on runner — cannot check the modality contract" >&2 +if ! command -v jq >/dev/null 2>&1; then + echo "ERROR: jq missing on runner — cannot check the modality contract" >&2 exit 2 fi @@ -46,16 +46,16 @@ plant() { } expect_failure() { - # expect_failure