LatticeDB Python Bindings
Python bindings for LatticeDB, an embedded single-file property-graph database with native vector and BM25 full-text search.
Installation
pip install latticedb
Published wheels are expected to bundle the native shared library on supported platforms.
If you are installing from a source checkout, the package build can either:
- bundle a prebuilt
liblatticefromLATTICE_BUNDLE_LIB_DIR/LATTICE_BUNDLE_LIB_PATH, or - build
liblatticewith Zig during the wheel build
For example, to bundle a staged installed library into a locally built wheel:
export LATTICE_BUNDLE_LIB_DIR=/tmp/lattice-install/lib
pip wheel . -w dist
pip install dist/latticedb-*.whl
At runtime, explicit library discovery overrides still work via LATTICE_LIB_PATH, LATTICE_PREFIX, and pkg-config.
Migration note: embedding helpers now live in the dedicated latticedb.embedding module. See ../../docs/client_api_migration.md for the preferred API names and deprecated compatibility aliases.
Installed-prefix workflow:
zig build install --prefix /tmp/lattice-install
export LATTICE_PREFIX=/tmp/lattice-install
Alternatively, discovery can use pkg-config:
export PKG_CONFIG_PATH=/tmp/lattice-install/lib/pkgconfig
Quick Start
import numpy as np
from latticedb import Database
with Database("knowledge.db", create=True, enable_vectors=True, vector_dimensions=4) as db:
# Create nodes, edges, and index content
db.create_node_fts_index("Person", "bio")
with db.write() as txn:
alice = txn.create_node(
labels=["Person"],
properties={"name": "Alice", "age": 30},
)
bob = txn.create_node(
labels=["Person"],
properties={"name": "Bob", "age": 25},
)
txn.create_edge(alice.id, bob.id, "KNOWS")
# Writing the indexed property is what makes it searchable.
txn.set_property(alice.id, "bio", "Alice works on machine learning research")
txn.set_property(bob.id, "bio", "Bob studies deep learning and neural networks")
# Store vector embeddings
txn.set_vector(alice.id, "embedding", np.array([1.0, 0.0, 0.0, 0.0], dtype=np.float32))
txn.set_vector(bob.id, "embedding", np.array([0.0, 1.0, 0.0, 0.0], dtype=np.float32))
txn.commit()
# Query with Cypher
result = db.query("MATCH (n:Person) WHERE n.age > 20 RETURN n.name, n.age")
for row in result:
print(row)
# Vector similarity search
query_vec = np.array([0.9, 0.1, 0.0, 0.0], dtype=np.float32)
for r in db.vector_search(query_vec, k=2):
print(f"Node {r.node_id}: distance={r.distance:.4f}")
# Full-text search
for r in db.fts_search("Person", "bio", "machine learning"):
print(f"Node {r.node_id}: score={r.score:.4f}")
# Fuzzy search (typo-tolerant)
for r in db.fts_search_fuzzy("Person", "bio", "machin lerning"):
print(f"Node {r.node_id}: score={r.score:.4f}")
API Reference
Database
Database(
path: str | Path,
*,
create: bool = False, # Create if doesn't exist
read_only: bool = False, # Open in read-only mode
cache_size_mb: int = 100, # Page cache size
enable_vectors: bool | None = None, # Preferred vector config flag
enable_vector: bool | None = None, # Deprecated compatibility alias
vector_dimensions: int = 128 # Vector dimensions
)
Methods
open()/close()- Open/close the database (also works as context manager)read()- Start a read-only transaction (context manager)write()- Start a read-write transaction (context manager)query(cypher, parameters=None)- Execute a Cypher queryvector_search(vector, k=10, ef_search=64)- k-NN vector searchfts_search(query, limit=10)- Full-text searchfts_search_fuzzy(query, limit=10, max_distance=0, min_term_length=0)- Fuzzy full-text searchcreate_node_property_index(label, property_key)/drop_node_property_index(...)- Manage explicit node equality indexescreate_edge_property_index(edge_type, property_key)/drop_edge_property_index(...)- Manage explicit edge equality indexesread_stream(stream, after_sequence=0, limit=100, timeout_ms=0)- Read durable stream records by cursorget_stream_offset(stream, consumer)- Read a committed consumer offsetchanges(after_sequence=0, limit=100, timeout_ms=0)- Read the built-in graph changefeedcache_clear()- Clear the query cachecache_stats()- Get cache hit/miss statistics
Transaction
Read Operations
get_node(node_id)- Get a node by ID, returnsNodeorNonenode_exists(node_id)- Check if a node existsget_property(node_id, key)- Get a property valueget_outgoing_edges(node_id)- Get outgoing edges from a nodeget_incoming_edges(node_id)- Get incoming edges to a nodefind_nodes_by_label_property(label, property_key, value, limit=100)- Indexed node equality lookupfind_edges_by_type_property(edge_type, property_key, value, limit=100)- Indexed edge equality lookupis_read_only/is_active- Transaction state
Write Operations
create_node(labels=[], properties=None)- Create a nodedelete_node(node_id)- Delete a nodeset_property(node_id, key, value)- Set a property on a nodeset_vector(node_id, key, vector)- Set a vector embeddingbatch_insert_vectors(label, vectors)- Insert vector-bearing nodes in one callbatch_insert(label, vectors)- Deprecated compatibility alias forbatch_insert_vectorsdb.create_node_fts_index(label, property)- Declare a full-text index; writing that property keeps it currentcreate_edge(source_id, target_id, edge_type, properties=None)- Create an edgedelete_edge(source_id, target_id, edge_type)- Delete an edgeset_edge_property(edge_id, key, value)- Set an edge property by stable edge IDget_edge_property(edge_id, key)- Get an edge property by stable edge IDremove_edge_property(edge_id, key)- Remove an edge property by stable edge IDpublish_stream(stream, payload, kind="message")- Publish a durable stream recordset_stream_offset(stream, consumer, sequence)- Commit a durable consumer offsettrim_stream(stream, through_sequence)- Delete stream records through a sequencecommit()/rollback()- Commit or rollback the transaction
Bulk Vector Insertion
Insert many nodes with vectors in a single efficient call:
import numpy as np
with Database("vectors.db", create=True, enable_vectors=True, vector_dimensions=128) as db:
with db.write() as txn:
vectors = np.random.rand(1000, 128).astype(np.float32)
node_ids = txn.batch_insert_vectors("Document", vectors)
print(f"Created {len(node_ids)} nodes")
txn.commit()
Property Indexes
Property equality indexes are explicit and durable. Create them outside an active write transaction; lookup fails instead of silently scanning when the requested index does not exist.
db.create_node_property_index("Person", "email")
with db.read() as txn:
node_ids = txn.find_nodes_by_label_property(
"Person", "email", "alice@example.com", limit=10
)
# Inline Cypher equality can use the same index.
rows = db.query(
"MATCH (p:Person {email: $email}) RETURN p",
{"email": "alice@example.com"},
)
Full-Text Search
Exact Search
results = db.fts_search("Person", "bio", "machine learning", limit=10)
for r in results:
print(f"Node {r.node_id}: score={r.score:.4f}")
Fuzzy Search (Typo-Tolerant)
# Finds "machine learning" even with typos
results = db.fts_search_fuzzy("Person", "bio", "machne lerning", limit=10)
# Control fuzzy matching sensitivity
results = db.fts_search_fuzzy(
"machne",
limit=10,
max_distance=2, # Max edit distance (default: 2)
min_term_length=4, # Min term length for fuzzy matching (default: 4)
)
Embeddings
LatticeDB includes a built-in hash embedding function and an HTTP client for external embedding services. For new code, prefer the dedicated latticedb.embedding module. The package root still exposes deprecated compatibility aliases.
Hash Embeddings (Built-in)
Deterministic, no external service needed. Useful for testing or simple keyword-based similarity:
from latticedb.embedding import hash_embed
vec = hash_embed("hello world", dimensions=128)
print(vec.shape) # (128,)
HTTP Embedding Client
Connect to Ollama, OpenAI, or compatible APIs:
from latticedb.embedding import EmbeddingClient, EmbeddingApiFormat
# Ollama (default)
with EmbeddingClient("http://localhost:11434") as client:
vec = client.embed("hello world")
# OpenAI-compatible API
with EmbeddingClient(
"https://api.openai.com/v1",
model="text-embedding-3-small",
api_format=EmbeddingApiFormat.OPENAI,
api_key="sk-...",
) as client:
vec = client.embed("hello world")
Edge Traversal
with db.read() as txn:
outgoing = txn.get_outgoing_edges(node_id)
for edge in outgoing:
print(f"{edge.source_id} --[{edge.edge_type}]--> {edge.target_id}")
incoming = txn.get_incoming_edges(node_id)
for edge in incoming:
print(f"{edge.source_id} --[{edge.edge_type}]--> {edge.target_id}")
Cypher Queries
# Pattern matching
result = db.query("MATCH (n:Person) RETURN n.name")
# With parameters
result = db.query(
"MATCH (n:Person) WHERE n.name = $name RETURN n",
parameters={"name": "Alice"},
)
# Vector similarity in Cypher
result = db.query(
"MATCH (n:Document) WHERE n.embedding <=> $vec < 0.5 RETURN n.title",
parameters={"vec": query_vector},
)
# Full-text search in Cypher
result = db.query(
'MATCH (n:Document) WHERE n.content @@ "machine learning" RETURN n.title'
)
# Data mutation
db.query("CREATE (n:Person {name: 'Charlie', age: 35})")
db.query("MATCH (n:Person {name: 'Charlie'}) SET n.age = 36")
db.query("MATCH (n:Person {name: 'Charlie'}) DETACH DELETE n")
Query Cache
# Get cache statistics
stats = db.cache_stats()
print(f"Entries: {stats['entries']}, Hits: {stats['hits']}, Misses: {stats['misses']}")
# Clear the cache
db.cache_clear()
Durable Streams and Changefeeds
Streams are durable named event logs stored inside the database file. Records are published in write transactions, sequence numbers are per stream, and reads use an explicit cursor. Reads do not acknowledge records; commit offsets separately when your consumer has processed a batch.
with Database("events.db", create=True) as db:
with db.write() as txn:
txn.publish_stream("jobs", {"id": 1, "status": "queued"}, kind="job.queued")
txn.commit()
records = db.read_stream("jobs", after_sequence=0, limit=100, timeout_ms=0)
with db.write() as txn:
txn.set_stream_offset("jobs", "worker-a", records[-1].sequence)
txn.trim_stream("jobs", records[-1].sequence - 1)
txn.commit()
db.changes() reads the reserved __lattice_changes stream. It emits semantic
graph events such as node.insert, node.property_set, edge.delete, and
edge.property_remove, with payloads represented as normal Python values.
Supported Property Types
None- Null valuebool- Booleanint- 64-bit integerfloat- 64-bit floatstr- UTF-8 stringbytes- Binary data- NumPy
ndarray(float32) - Vector embeddings
Nested list and dict values are not currently exposed by the public bindings/C API.
Error Handling
from latticedb import LatticeError, LatticeNotFoundError, LatticeIOError
try:
with Database("nonexistent.db") as db:
pass
except LatticeNotFoundError:
print("Database not found")
except LatticeIOError:
print("I/O error")
except LatticeError as e:
print(f"Error: {e}")
Requirements
- Python 3.9+
- NumPy (for vector operations)
- The native LatticeDB library (
liblattice.dylib/liblattice.so)
License
MIT
Metadata
Release files for latticedb 0.15.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 | |
|---|---|---|---|
| latticedb-0.15.0.tar.gz | 48.1 kB | Details |
Built distributions (wheels)
| File | Reset | |||
|---|---|---|---|---|
| latticedb-0.15.0-py3-none-manylinux_2_17_x86_64.whl | Python 3 | none | Linux glibc 2.17+ x86-64 | Details |
| latticedb-0.15.0-py3-none-manylinux_2_17_aarch64.whl | Python 3 | none | Linux glibc 2.17+ ARM64 | Details |
| latticedb-0.15.0-py3-none-macosx_11_0_arm64.whl | Python 3 | none | macOS 11.0+ ARM64 | Details |
| latticedb-0.15.0-py3-none-macosx_10_9_x86_64.whl | Python 3 | none | macOS 10.9+ x86-64 | Details |
Total release size: 9.6 MB
Release files / latticedb-0.15.0.tar.gz
| Download URL | latticedb-0.15.0.tar.gz |
|---|---|
| Size | 48.1 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
9f7d931e47417fece2d8597db94eb53a8516345c61e6cb0b552b8ca0720fccb4
|
|
BLAKE2b-256 checksum How to use checksums |
e973705714e811095a67c6f053964ac55dbb76a7abd187c09a0ef9dfd0cc6432
|
| 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 Aug 29, 2026.
Transparency logRelease files / latticedb-0.15.0-py3-none-manylinux_2_17_x86_64.whl
| Download URL | latticedb-0.15.0-py3-none-manylinux_2_17_x86_64.whl |
|---|---|
| Size | 3.9 MB |
| Tags | Linux glibc 2.17+ x86-64 Python 3 |
|
SHA-256 checksum How to use checksums |
75ef8687d743a98ddc33e0fa1772eb3e636fd1f62759051ac879bb68075e7af5
|
|
BLAKE2b-256 checksum How to use checksums |
4c510484766d63bd8e363c20964811927cedc52b41ece2b6c31cbac5391c0faa
|
| 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 Aug 29, 2026.
Transparency logRelease files / latticedb-0.15.0-py3-none-manylinux_2_17_aarch64.whl
| Download URL | latticedb-0.15.0-py3-none-manylinux_2_17_aarch64.whl |
|---|---|
| Size | 3.8 MB |
| Tags | Linux glibc 2.17+ ARM64 Python 3 |
|
SHA-256 checksum How to use checksums |
fb8bda134ddf30881c453ea6a2089907be49aa0abef402b0dbb747ab4414500f
|
|
BLAKE2b-256 checksum How to use checksums |
9d34451a314c99740af73dd43ab8a22f04e54a7e62d2cfd9b100b077e1df6456
|
| 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 Aug 29, 2026.
Transparency logRelease files / latticedb-0.15.0-py3-none-macosx_11_0_arm64.whl
| Download URL | latticedb-0.15.0-py3-none-macosx_11_0_arm64.whl |
|---|---|
| Size | 909.4 kB |
| Tags | Python 3 macOS 11.0+ ARM64 |
|
SHA-256 checksum How to use checksums |
a9ba03a564fb1918b1e51b2c89f62ba76261d7f323f5bf45e590754fa025b7c7
|
|
BLAKE2b-256 checksum How to use checksums |
0bb35f99f4881bf0140f32a4a5b6edd00bd0ede1c312c15b24bb9492fc3d3546
|
| 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 Aug 29, 2026.
Transparency logRelease files / latticedb-0.15.0-py3-none-macosx_10_9_x86_64.whl
| Download URL | latticedb-0.15.0-py3-none-macosx_10_9_x86_64.whl |
|---|---|
| Size | 975.8 kB |
| Tags | Python 3 macOS 10.9+ x86-64 |
|
SHA-256 checksum How to use checksums |
21656e7cb43d5624676d23bf7f16cd1f2482b7e433bf697dfbb2114dd17b6fd1
|
|
BLAKE2b-256 checksum How to use checksums |
126314fe2bbe0804231381a1d0bcb67136134098efb7eaecba453640d0e6ca7e
|
| 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 Aug 29, 2026.
Transparency log