mindgraph
Python client for the MindGraph Cloud API — a structured semantic memory graph for AI agents.
Install
pip install mindgraph-sdk
Quick Start
from mindgraph import MindGraph
with MindGraph("https://api.mindgraph.cloud", api_key="mg_...") as graph:
# Add a node
node = graph.add_node(
label="User prefers dark mode",
node_type="Preference",
)
# Search
results = graph.search("what does the user prefer?")
# Connect knowledge
graph.add_link(
from_uid=node["uid"],
to_uid="user_abc",
edge_type="BelongsTo",
)
API Reference
Constructor
MindGraph(base_url, *, api_key=None, jwt=None, timeout=30.0)
Supports context manager protocol (with statement) for automatic cleanup.
Reality Layer
| Method | Description |
|---|---|
capture(**kwargs) |
Capture a source, snippet, or observation |
entity(**kwargs) |
Create, alias, resolve, or merge entities |
series(**kwargs) |
Call the time-series action surface directly |
create_series / append_series / series_window |
Create a Series, append sourced points, and page through a bounded time window |
aggregate_series / latest_series / list_series_for_entity |
Read bounded aggregates, cached latest values, and an entity's Series |
batch_latest_series / batch_aggregate_series / delete_series |
Compare Series across entities or tombstone a Series and its points |
find_or_create_entity(label, props?, agent_id?) |
Convenience: create or find an entity by label (generic fallback) |
find_or_create_person(label, props?, agent_id?) |
Find or create a Person entity |
find_or_create_organization(label, props?, agent_id?) |
Find or create an Organization entity |
find_or_create_nation(label, props?, agent_id?) |
Find or create a Nation entity |
find_or_create_event(label, props?, agent_id?) |
Find or create an Event entity |
find_or_create_place(label, props?, agent_id?) |
Find or create a Place entity |
find_or_create_concept(label, props?, agent_id?) |
Find or create a Concept entity |
add_claim(label, content, confidence?, agent_id?) |
Add a Claim node via the argument endpoint |
add_evidence(label, description, agent_id?) |
Add an Evidence node attached to a claim |
add_observation(label, description, agent_id?) |
Add an Observation node |
Typed entity example:
person = graph.find_or_create_person("Marie Curie", props={"nationality": "Polish"})
org = graph.find_or_create_organization("CERN", props={"org_type": "intergovernmental"})
concept = graph.find_or_create_concept("Nuclear Physics")
# find_or_create_entity() still works as a generic fallback for any entity type
entity = graph.find_or_create_entity("Some Entity")
Epistemic Layer
| Method | Description |
|---|---|
argue(**kwargs) |
Construct a full argument: claim + evidence + warrant + edges |
inquire(**kwargs) |
Add hypothesis, theory, paradigm, anomaly, assumption, or question |
structure(**kwargs) |
Add concept, pattern, mechanism, model, analogy, theorem, etc. |
Intent Layer
| Method | Description |
|---|---|
commit(**kwargs) |
Create a goal, project, or milestone |
deliberate(**kwargs) |
Open decisions, add options/constraints, resolve decisions |
resolve_decision(...) |
Resolve with optional informs_uid, as_of_date, session_id, and retrieval_trace_id linkage |
Action Layer
| Method | Description |
|---|---|
procedure(**kwargs) |
Build flows, add steps, affordances, and controls |
risk(**kwargs) |
Assess risk or retrieve existing assessments |
Memory Layer
| Method | Description |
|---|---|
session(**kwargs) |
Open a session, record traces, or close a session |
journal(label, props?, *, summary?, session_uid?, ...) |
Record a journal entry linked to an optional session |
remember(text, *, custom_id?, label?, space_uid?, on_near_duplicate?) |
Small-text fast path: synchronous write, BM25- and vector-searchable on return; custom_id makes re-sends an upsert |
forget(*, uid? | custom_id?, dry_run?, cascade?, reason?) |
Reversible removal; dry_run=True previews the affected edge uids |
set_remember_instructions(text, *, space_uid?) / get_remember_instructions() |
Per-Space guidance for what agents should remember; surfaced on remember() and retrieve_context() |
distill(**kwargs) |
Create a Summary, Lesson, or governed Skill candidate with source provenance |
memory_config(**kwargs) |
Set/get preferences and memory policies |
output_type="skill" requires caller-authored SKILL.md content and at
least one provenance field. It always creates a candidate for review:
graph.distill(
label="Recover a malformed import",
output_type="skill",
work_uid="work_import_42",
props={
"name": "recover-malformed-import",
"description": "Use after a spreadsheet import fails schema validation.",
"content": "# Recovery\n\nValidate headers, normalize dates, then retry.",
},
)
Agent Layer
| Method | Description |
|---|---|
plan(**kwargs) |
Create tasks, plans, plan steps, update status |
governance(**kwargs) |
Create policies, set safety budgets, request/resolve approvals |
execution(**kwargs) |
Track execution lifecycle and register agents |
Synthesis (Projects)
Scope a corpus to a Project (via commit(action="project", ...) then link documents with PartOfProject), then mine cross-document signals and generate synthesis articles.
| Method | Description |
|---|---|
signals(project_uid, *, signals?, target_types?) |
Mine cross-document structural signals for a project |
run_synthesis(project_uid) |
Spawn async synthesis job that turns top clusters into Article nodes; returns {"job_id": ...} |
project = graph.commit(action="project", label="Q2 China strategy")
# ...link documents to the project via PartOfProject edges...
signals = graph.signals(project["uid"], signals="clustered_claim_hubs,dialectical_pairs")
job = graph.run_synthesis(project["uid"])
status = graph.get_job(job["job_id"])
Operational Ontology (Layer 7)
Define typed domain objects (Customer, Order, Contract…) as a semantic contract and either bind them to a SQL database or extract them from documents — fused onto one object. Connecting a database (credentials/sync) is done in the dashboard; the SDK proposes/reviews schemas, queries, and lists the generated agent read tools.
| Method | Description |
|---|---|
propose_ontology_schema(...) |
Draft a schema from a description (+ optional sample docs); returns {"schema_id", "job_id"} |
activate_ontology_schema(id) / get_ontology_schema(id) / list_ontology_schemas() |
Schema lifecycle |
create_ontology_series_binding / sync_ontology_series_binding / archive_ontology_series_binding |
Manage SQL-backed dense-measurement bindings |
list_ontology_proposals(...) / approve_ontology_proposal(id) / reject_ontology_proposal(id) |
Review extracted-object proposals |
query_ontology(query=..., schema_id=...) |
Typed retrieval with the cognitive overlay fused in |
list_ontology_tools() |
The generated read-tool manifest (search_/get_/summarize_<obj>) the MCP server renders |
res = graph.propose_ontology_schema(description="Clients, orders, contracts.")
graph.activate_ontology_schema(res["schema_id"])
tools = graph.list_ontology_tools()
ctx = graph.query_ontology(query="Which customers are a churn risk?", schema_id=res["schema_id"])
See the Operational Ontology and Connect a database docs.
CRUD
| Method | Description |
|---|---|
get_node(uid) |
Get a node by UID |
add_node(label, node_type?, props?, agent_id?) |
Add a generic node |
update_node(uid, **kwargs) |
Update node fields |
delete_node(uid) |
Tombstone a node and all connected edges |
add_link(from_uid, to_uid, edge_type, agent_id?) |
Add a typed edge |
get_edges(from_uid?, to_uid?) |
Get edges by source or target |
Search
| Method | Description |
|---|---|
search(query, node_type?, layer?, limit?) |
Full-text search |
hybrid_search(query, k?, node_types?, layer?, explain?) |
BM25 + vector search with rank fusion; explain=True attaches per-leg contributions (legs: which legs surfaced each result, the within-leg rank the fusion used, and the leg's raw score) |
merge_candidates() |
Pending duplicate pairs recorded by the dedup pipeline, awaiting merge/dismiss |
Traversal
| Method | Description |
|---|---|
reasoning_chain(uid, max_depth=5) |
Follow epistemic edges from a node |
neighborhood(uid, max_depth=1) |
Get all nodes within N hops |
Ingestion & Retrieval
| Method | Description |
|---|---|
ingest_chunk(content, *, chunk_type?, ...) |
Ingest a single text chunk (sync): stores, embeds, and runs LLM extraction |
ingest_document(content, *, title?, ...) |
Ingest a full document (async): chunks text, returns job ID |
ingest_session(content, *, session_uid?, ...) |
Ingest a session transcript (async): links to session, returns job ID |
retrieve_context(query, *, graph_expansion_limit?, graph_max_depth?, ...) |
Direct retrieval plus optional cheapest-first graph expansion |
get_job(job_id) |
Get async job status and progress |
clear_graph() |
Clear all graph data |
Lifecycle Shortcuts
| Method | Description |
|---|---|
tombstone(uid, reason?, agent_id?) |
Soft-delete a node |
restore(uid, agent_id?) |
Restore a tombstoned node |
Cross-cutting
| Method | Description |
|---|---|
retrieve(**kwargs) |
Unified retrieval: text search, active goals, open questions, weak claims |
traverse(**kwargs) |
Budgeted min-cost traversal; response depth is witness-path hops |
evolve(**kwargs) |
Lifecycle mutations: update, tombstone, restore, decay, history |
Health & Stats
| Method | Description |
|---|---|
health() |
Health check |
stats() |
Graph-wide statistics |
Account sign-up, login, and API key management live in the MindGraph dashboard — not the SDK. Get your API key there, then pass it to the
MindGraphconstructor.
Examples
See examples/ for runnable demos, including a research continuity scenario showing cross-session memory retrieval.
Error Handling
All methods raise MindGraphError on HTTP errors:
from mindgraph import MindGraphError
try:
graph.get_node("nonexistent")
except MindGraphError as e:
print(e.status, e.body)
License
MIT
Retry and engine-error contract
HTTP 503 retries are bounded and apply only to reviewed reads (including selected
POST query actions) and keyed /agent/plan work operations: claim_task,
heartbeat, start_iteration, checkpoint_iteration, block_task,
complete_task, and abandon_iteration. These work operations atomically store
their mutation and idempotency receipt. A nonempty idempotency_key must stay
unchanged across attempts. Other writes are not retried automatically; supplying
a key or telemetry request ID on an unsupported route does not change that.
MindGraphError preserves the response status and body and exposes optional
code and retriable fields. Explicit retriable: false always stops retries,
including admission failures and index maintenance. Memory limits, timeouts,
and cancellation remain failures; they do not become empty search results.
Older responses without retry guidance retain retries only for the reviewed
operations above. Each delay, including fallback backoff, is capped at 10 seconds.
Network exceptions and other HTTP statuses are not automatically retried.
Metadata
Release files for mindgraph-sdk 0.16.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | Actions |
|---|---|---|---|---|
| mindgraph_sdk-0.16.0.tar.gz | 52.8 kB | With provenance | Details for mindgraph_sdk-0.16.0.tar.gz |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| mindgraph_sdk-0.16.0-py3-none-any.whl | Python 3 | none | any | Details for mindgraph_sdk-0.16.0-py3-none-any.whl |
Total release size: 78.8 kB
Release files / mindgraph_sdk-0.16.0.tar.gz
| Download URL | mindgraph_sdk-0.16.0.tar.gz |
|---|---|
| Size | 52.8 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
3e49a4c1696e8b1fecadab3d794e66f04637dd32a93976767e71c8f74152fdce
|
|
BLAKE2b-256 checksum How to use checksums |
ccf3540b6d157c072dd30798ec6c43492047f0e27c1f911e73579362d145af74
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 2, 2026.
Transparency logRelease files / mindgraph_sdk-0.16.0-py3-none-any.whl
| Download URL | mindgraph_sdk-0.16.0-py3-none-any.whl |
|---|---|
| Size | 26.0 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
3ea8b96e2b50167d819d214f7e3f58748fe33d09d666288aab3b173b6cf5a6fe
|
|
BLAKE2b-256 checksum How to use checksums |
4a6cbfeaa4ebb11d3bbd73b3efbcb38b42d9ca185fecf6f76820287d0ec63661
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 2, 2026.
Transparency logSecurity for mindgraph-sdk 0.16.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
Full provenance
All 2 files in this release have been uploaded with provenance metadata.
Attestation for mindgraph_sdk-0.16.0.tar.gz
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 2, 2026.
Transparency logA note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.