REST API
The neuro-symbolic feature exposes a rule CRUD surface, an LLM-free reasoning
endpoint, and the verifiable query endpoint. All paths are relative to the
HyperMesh API server (default http://localhost:8000).
| Method & path | Auth | Purpose |
|---|---|---|
GET /v1/rules | read | List rules |
POST /v1/rules | write | Create/update a rule (re-validates the whole set) |
POST /v1/rules/validate | read | Dry-run validate a rule (no write) |
GET /v1/rules/{id} | read | Fetch one rule |
DELETE /v1/rules/{id} | write | Delete a rule |
POST /v1/reason | read | Retrieve + reason (LLM-free) → derived facts + proofs |
POST /v1/rag/query | read | Full pipeline; mode, require_proof, mock, rules |
GET /v1/rules
Section titled “GET /v1/rules”curl -s localhost:8000/v1/rules{ "rules": [ {"id": "...", "name": "...", "enabled": true, "priority": 10, "version": 1, "head": "coordinated_threat", "body_size": 4} ] }POST /v1/rules
Section titled “POST /v1/rules”Body is a rule object (see Rules). Re-validates and
re-stratifies the entire set; returns the stored rule plus its stratum.
422 with a precise message if the rule is malformed, unsafe, or makes the
set non-stratifiable.
curl -sX POST localhost:8000/v1/rules \ -H 'content-type: application/json' -d @rule.json{ "id": "rule:coordinated_threat", "name": "...", "enabled": true, "if": [...], "then": {"pred": "coordinated_threat", "args": ["?E"], "confidence": 0.9}, "stratum": 1 }POST /v1/rules/validate
Section titled “POST /v1/rules/validate”Dry-run; never writes. Safe to call from an editor on every change.
curl -sX POST localhost:8000/v1/rules/validate \ -H 'content-type: application/json' -d @rule.json{ "ok": true, "errors": [], "stratum": 1 }GET /v1/rules/{id} · DELETE /v1/rules/{id}
Section titled “GET /v1/rules/{id} · DELETE /v1/rules/{id}”curl -s localhost:8000/v1/rules/rule:coordinated_threatcurl -sX DELETE localhost:8000/v1/rules/rule:coordinated_threat404 if the id doesn’t exist. Delete returns {"id": "...", "deleted": true}.
POST /v1/reason — reason only (no LLM)
Section titled “POST /v1/reason — reason only (no LLM)”Retrieves hyperedges for the query and runs the symbolic reasoner. No model is called. Use it for audits, CI, and air-gapped checks.
Request
| Field | Type | Default | Meaning |
|---|---|---|---|
query | str | — | Natural-language query (drives retrieval). |
table | str | — | Hyperedge table. |
top_k | int | 40 | Max edges retrieved. |
require_proof | bool | false | Abstain unless something is proved. |
rules | list | null | null | Ad-hoc rules; else the durable rule store. |
curl -sX POST localhost:8000/v1/reason -H 'content-type: application/json' -d '{ "query": "which edges are coordinated threats?", "table": "DRONES", "require_proof": true}'Response
{ "query": "...", "table": "DRONES", "answer": "coordinated_threat(42) is established by rule ... [RULE-0][STEP-1][HEDGE-42] (confidence 0.90). Sources: [STEP-1]", "abstained": false, "derived_facts": [ {"step_tag": "STEP-1", "fact": "coordinated_threat(42)", "predicate": "coordinated_threat", "args": [42], "confidence": 0.9, "rule_id": "rule:coordinated_threat", "rule_tag": "RULE-0", "hedge_tags": ["HEDGE-42"]} ], "proofs": [ { "proof_id": "proof-1", "status": "proved", "nodes": [...], "edges": [...] } ], "rules_fired": ["rule:coordinated_threat"], "reasoning_ms": 1.2}422 for a bad table, bad mode, or invalid ad-hoc rule.
POST /v1/rag/query — full verifiable query
Section titled “POST /v1/rag/query — full verifiable query”The complete pipeline: retrieve → reason → prove → generate → firewall.
Request
| Field | Type | Default | Meaning |
|---|---|---|---|
query | str | — | NL query. |
table | str | — | Hyperedge table. |
mode | str | "hybrid" | neuro | symbolic | hybrid. |
require_proof | bool | false | Abstain unless proved. |
mock | bool | false | Use the deterministic mock LLM (no network). |
rules | list | null | null | Ad-hoc rules; else the rule store. |
model | str | gpt-4o-mini | LLM model (ignored if mock). |
base_url | str | OpenAI | API base URL. |
openai_api_key | str | env | Key (or OPENAI_API_KEY). |
top_k | int | 40 | Max edges retrieved (1–200). |
token_budget | int | 3000 | Context token budget (500–12000). |
time_start / time_end | int | null | null | Override the parsed time window. |
curl -sX POST localhost:8000/v1/rag/query -H 'content-type: application/json' -d '{ "query": "summarize the coordinated threats", "table": "DRONES", "mode": "hybrid", "require_proof": true, "mock": true}'Response — the full RAGResult.as_dict():
{ "query": "...", "answer": "...", "table": "DRONES", "mode": "hybrid", "abstained": false, "cited_edges": [...], "all_edges": [...], "derived_facts": [...], "proofs": [...], "firewall": {"outcome": "supported", "abstained": false, "coverage": 1.0, "supported_count": 1, "stripped_count": 0, "stripped": []}, "rules_fired": ["rule:coordinated_threat"], "confidence": 0.9, "low_confidence": false, "model": "mock", "prompt_tokens": 0, "completion_tokens": 64, "retrieval_ms": 3.1, "reasoning_ms": 1.2, "generation_ms": 0.4, "total_ms": 5.0, "context_tokens": 240, "interaction_id": "..."}422 for an invalid mode or bad ad-hoc rule; 404 if the table isn’t found.
Rule writes (POST /v1/rules, DELETE /v1/rules/{id}) require a write-scoped
key; the rest require a read key. See Authentication & Keys.