The Python examples are the user-facing and notebook-facing complement to the Rust examples. They do not replace the Rust lakehouse loader. They make the warehouse, semantic sidecars, agent protocol, and audit trail easy to inspect, compose, and extend.
From the sister project:
cd ../qg-python
uv sync --extra test
uv run python -m pytestThe test suite checks both Python-only behavior and Rust equivalence for the semantic bundle. That matters because Python agents should speak the same semantic and security language as the Rust platform.
examples/osi_semantic_croissant.py starts with a
concrete Croissant dataset: files, record sets, fields, types, and
semantic meanings. It then projects the dataset into an OSI model:
uv run python examples/osi_semantic_croissant.pyThe result has:
row_count.This is the bridge from file metadata to business meaning. The agent
does not need to guess that monthly_energy_cost belongs to
an energy-burden concept. The OSI model says so.
After the Rust loader has materialized the warehouse, start Sail:
cd ../qg-rust
sail spark server --port 50051Register the data and audit tables from Python:
cd ../qg-python
uv sync --extra lakehouse
uv run querygraph lakehouse-register \
--manifest ../qg-rust/.querygraph/lakehouse/manifest/load-report.json \
--warehouse ../qg-rust/spark-warehouse
uv run querygraph audit-register \
--warehouse ../qg-rust/spark-warehouseOpen a shell:
uv run pyspark --remote sc://127.0.0.1:50051Example queries:
spark.sql("SELECT COUNT(*) AS rows FROM global_temp.government_finance__countydata").show()
spark.sql("SELECT COUNT(*) AS rows FROM global_temp.codata_constants_2022__codata_constants_2022").show()
spark.sql("SELECT quantity, value, unit FROM global_temp.codata_constants_2022__codata_constants_2022 LIMIT 5").show(truncate=False)
spark.sql("SELECT event_hash, event_type, job_name FROM global_temp.openlineage_events LIMIT 10").show(truncate=False)This gives Python users direct inspection of both governed data and audit evidence.
The Python QG Lakehouse story is:
uv run querygraph qglake-story --prettyIt creates the same cast as the Rust story: supervisor, finance, energy, mobility, climate-health, reference, restricted-data broker, and synthesis. Each request and response is a Pydantic TypeDID model. Each response carries a payload hash. The restricted broker returns a denial instead of leaking raw data. The final report includes OpenLineage and a DID-style attestation.
A minimal Python sketch looks like this:
from querygraph.typedid import TypeDidAgent
supervisor = TypeDidAgent.new("SupervisorAgent")
finance = TypeDidAgent.new("FinanceAgent")
request = supervisor.request(
finance,
action="summarize",
resource="compartment:finance",
payload={"question": "Where is fiscal stress highest?"},
)
response = finance.answer(
request,
status="allowed",
summary="Fiscal stress summary over governed finance tables.",
)
assert request.verify_payload()
assert response.envelope.payload["requestSha256"] == request.payload_sha256This is what Pydantic contributes: a natural Python object model that is still strict enough to validate, hash, serialize, and test.
LangChain is useful when a planner should choose tools. Querygraph’s
rule is that the tool must already be governed. The Python adapter turns
a TypeDID agent into a LangChain StructuredTool:
uv sync --extra agents
uv run python examples/typedid_langchain_agents.pyConceptually:
from querygraph.agents import TypeDidLangChainToolAdapter, deterministic_specialist
from querygraph.typedid import TypeDidAgent
finance = TypeDidAgent.new("FinanceAgent")
handler = deterministic_specialist(
finance,
summary="Fiscal capacity summary from governed Sail finance tables.",
evidence=["global_temp.government_finance__countydata"],
)
tool = TypeDidLangChainToolAdapter(finance, handler).as_tool()The LangChain planner can invoke the tool, but the tool returns a TypeDID response. The planner does not receive a secret back door into Sail.
Python is where new agent behavior can be prototyped quickly:
The ideal development loop is not Rust versus Python. It is Rust for the contract and Python for the exploration, both operating over the same Sail warehouse and the same semantic sidecars.