@odla-ai/kg
v0.2.4
Published
Ontology-driven knowledge-graph builder: pluggable source connectors, LLM extraction against a config-as-data ontology, and a provenance-preserving graph writer persisting into odla-db.
Maintainers
Readme
@odla-ai/kg
⚠️ Early access — pre-1.0. Agents work from bounded runbooks; humans approve credentials, production changes, releases, and merges. APIs and exact package availability can change. Review the documented guarantees and limitations; this software is MIT-licensed and provided without warranty.
An ontology-driven knowledge-graph builder. Pluggable source connectors pull from the web and data feeds, an LLM extracts entities + relationships against a config-as-data ontology, and a provenance-preserving graph writer persists the result into odla-db.
The library is host-agnostic: it runs in Cloudflare Workers, Node, or tests — the host supplies the database client, LLM keys, and a KV-like store. The public platform and package manuals describe how to compose it with Workflows, scheduled triggers, an HTTP API, and a viewer UI.
Architecture
Connector ──RawItem[]──▶ Extraction ──GraphFragment──▶ writeFragment ──Op[]──▶ odla-db
(how data (LLM forced-tool (ontology-typed (Lookup upserts +
was acquired) OR pure mapper) nodes + edges) links, idempotent)RawItem— a connector emits eithertext(→ LLM extraction) or a ready-madefragment(structured feeds bypass the LLM).GraphFragment— ontology-typednodes[]+edges[]; the single shape the writer consumes, whatever produced it.Ontology— data, not code. It compiles to the odla-db schema (toSerializedSchema), the writer's natural-key + merge-rule maps (naturalKeysOf,mergeRulesOf,humanAttrsOf), and by convention the extractor's tool schema.
Add a source → implement SourceConnector + one registry line. Add an
entity/edge type → edit the ontology data. Neither touches the pipeline.
Usage
import { init } from "@odla-ai/db";
import {
Store, getProvider, makeContext, ingestFresh, writeFragment,
toSerializedSchema, type Ontology, type PipelineDeps,
} from "@odla-ai/kg";
// 1. Your ontology is ordinary application-owned data.
const ontology: Ontology = { entities: { /* … */ }, edges: { /* … */ } };
// 2. Wire the host services once. Env-var keys work standalone…
const db = init({ appId, adminToken, endpoint });
const provider = getProvider({ LLM_PROVIDER: "claude", ANTHROPIC_API_KEY: key });
// …but platform apps should bring a configured Ai instead (no LLM keys in
// worker env): createProvider({ provider: "claude", ai }) with the ai from
// @odla-ai/ai's initFromPlatform. The
// platform's default model is ignored here; kg's MODEL_TIERS govern verbs.
const deps: PipelineDeps = { db, provider, ontology, extract: myExtractor, store: new Store(kv) };
// 3. Run items through the shared pipeline (or call writeFragment directly).
await ingestFresh(step, deps, freshItems, "ingest");Key seams the host supplies:
PipelineDeps— db (AdminDb), LLMProvider, the ontology, the extractor (your domain craft), and aStoreover anyKVLike.ContextConfig(→makeContext) — what connectors see: ontology, lazy provider, named secrets.StepLike— a structural view of Cloudflare'sWorkflowStep(asStepLike(step)); anydo(name, cfg?, fn)runner works, including a plain inline runner in tests.
Built-in connectors
rss, url, gdelt (text → LLM extraction) · fred, edgar (structured →
straight to the writer) · web-search (LLM web-search discovery) · gov-data
(template proving a new source needs no pipeline change).
Provenance & merging
writeFragment reads existing nodes by natural key (one batched query), merges
scalar attrs per the ontology's rules (replace / prefer / earliest /
latest), never writes human-owned attrs, and commits nodes-then-links in a
single idempotent transaction (deterministic mutationId).
