gj_catalog
Find schemas, relationships, syntax, workflows, capabilities, examples, and evidence before choosing a path.
Auto-learns your schema and gives AI agents one governed query graph across your databases, APIs, source code, filesystems, and workflows. Ask about the data, the services that enrich it, the code that touches it, and the files around it from one MCP-ready binary.
One config defines what agents can discover, query, execute, edit, and never touch. Humans can audit it. Models can inspect it. GraphJin enforces it across your entire AI surface.
npx graphjin servePoint GraphJin at as many systems as you need — Postgres for users, MySQL for orders, Snowflake for analytics, MongoDB for events, HTTP APIs for remote services, object storage for files, and CodeSQL for source trees — and query them through a single GraphQL endpoint. Joins, remote joins, subscriptions, search, and mutations compose across systems in one request, so an AI assistant can reason across the data, APIs, files, and code without learning every backend.
Point GraphJin at databases, object storage, source trees, and remote APIs. It learns the shape, compiles one GraphQL surface, enforces RBAC, and gives AI assistants, REST clients, and federated routers the same production-safe engine.
GraphQL in. Optimized queries, API calls, file ops, and code search out.
GraphJin is the operating graph agents use to understand a real organization. It auto-learns the live surface, compiles GraphQL into database and source-backed work, and keeps policy visible enough for both humans and models to inspect.
Find schemas, relationships, syntax, workflows, capabilities, examples, and evidence before choosing a path.
Read effective policy and high-risk findings before config, workflow, file, code, or mutation actions.
Validate filters, inspect generated work, run approved workflows, or preview CodeSQL changes before applying.
Execute through GraphQL, MCP, saved queries, workflows, and guarded source operations instead of raw credentials.
A compiler — not a query parser, not a resolver framework. It learns the live shape of your systems, plans the work, and emits optimized database operations. The result is calmer code, fewer round-trips, and a governed integration point where agents can explore without guessing.
Introspects tables, columns, relationships, source metadata, and configured surfaces so agents start from live shape instead of pasted context.
Nested GraphQL compiles into optimized database work. No N+1, no resolver sprawl, no ORM layer between the agent and the real system.
RBAC, row filters, allow-lists, saved queries, read-only sources, security rows, and audit trails give agents room to move inside visible boundaries.
GraphJin ships a Model Context Protocol server with the tools an assistant actually needs: catalog-first discovery, saved queries, where-clause validation, query repair, gj_security guidance, query execution, audit logs, and health checks. Same engine, same RBAC, same allow-lists — everything that protects your HTTP API protects the AI.
One install command wires GraphJin into Claude Desktop, Codex, or any
MCP host. Tools are discoverable, narrow, and audited:
agents search gj_catalog, inspect evidence and examples,
validate filters, check gj_security, then run approved
queries or workflows through the same governed surface.
For development, graphjin mcp runs over stdio. For team
access, run it as a long-lived HTTP+SSE endpoint, gated by the same JWT
or OIDC flow as the main API. No shell access, no raw SQL by default, no
surprise mutations.
# install for Claude Code (or codex / cursor / custom)
graphjin mcp install --client claude --scope global --yes
# or set up against a hosted GraphJin
graphjin mcp setup https://api.example.com // claude_desktop_config.json
{
"mcpServers": {
"graphjin": {
"command": "graphjin",
"args": ["mcp", "--config", "/etc/graphjin"],
"env": {
"GRAPHJIN_USER_ID": "system",
"GRAPHJIN_USER_ROLE": "user"
}
}
}
} GraphJin makes agents safer by giving them explicit boundaries, not by making them blind. Agents can explore more of the live organization because policy, evidence, and action paths are inspectable and enforced.
Humans can review and diff the policy. Models can inspect the same
posture through gj_catalog and gj_security
before acting. GraphJin enforces that policy across GraphQL, MCP,
workflows, code, files, APIs, and databases.
Databases, sources, roles, MCP settings, saved queries, mutations, read-only boundaries, and workflow access live in one policy artifact.
HTTP, WebSocket, SSE, CLI, workflows, and MCP land in the same request context before GraphJin compiles or executes work.
Roles, table permissions, column blocks, automatic filters, and mutation limits are enforced inside the compiler.
Production agents can run named, reviewed query contracts instead of inventing arbitrary operations at runtime.
Filesystems, CodeSQL, databases, and control-plane tables can expose discovery without granting writes.
CodeSQL change sets require file hashes, exact ranges, old text, optional locks, and a preview/apply loop.
Claude Desktop, Codex, or any MCP client talks to GraphJin — GraphJin compiles the query, hits your database, and the assistant answers with rows it can reason over.
who's the top customer?
{ customers { id full_name email purchases { quantity product { price } } } }Based on the purchase data, here are the top customers ranked by total spend:
| Rank | Customer | Orders | Items | Total Spent |
|---|---|---|---|---|
| 🥇 | Antwan Friesen | 20 | 124 | $928.45 |
| 🥈 | Lon Cruickshank | 20 | 94 | $586.50 |
| 🥉 | Susana Schaefer | 20 | 91 | $580.72 |
Antwan Friesen is the top customer with almost $1,000 in purchases — about 60% more than the runner-up.
GraphJin turns databases, HTTP APIs, discovered metadata, source code, and filesystems into one governed graph for AI agents. CodeSQL lets agents ask where a column exists, which code references it, which symbol owns that reference, and what guarded change set would update it — with preview/apply checks instead of raw file writes.
gj_columns { code_db_refs { file { path } symbol { name } } } export async function createInvoiceHandler(req) {
return workflows.run("sync-invoices")
} GraphJin streams multipart uploads straight to local disk, S3, Cloudflare R2, or Google Cloud Storage. Each backend exposes a virtual table — list, stat, get, put, delete, presign — and joins seamlessly with the rest of your schema.
Uploads follow the graphql-multipart-request-spec: send a single request, GraphJin parses, validates, signs, and persists. Returned rows include the storage URL and metadata, ready for the next mutation or a presigned download.
Bring your own bucket: GCS uses Application Default Credentials, S3 respects the standard AWS chain, local writes go to a configured volume. Backends are pluggable behind one interface.
# config/prod.yml
filesystems:
- name: "media"
type: s3 # local | s3 | gcs
bucket: "graphjin-media"
region: "us-east-1"
prefix: "uploads/"
uploads:
enabled: true
storage: "media"
storage_key_prefix: "avatars/{date}/"
allowed_mime: ["image/*", "application/pdf"]
max_size: 25_000_000
# graphql-multipart-request-spec
mutation ($file: Upload!) {
avatars(insert: { file: $file, user_id: $auth.user_id }) {
id
file_url
file_size
content_type
}
} Drop a Stripe, GitHub, or internal-service OpenAPI 3 spec into the config directory. GraphJin parses it, classifies the operations, and exposes them alongside your tables — joinable on any column → parameter mapping. One GraphQL query, one response, even when half the data lives behind REST.
Auth is configured once per spec — bearer, basic, API key, OAuth2 client-credentials, or token-exchange — and tokens are cached transparently. Concurrency caps per-spec keep upstream rate limits respected.
Joins are declarative: tell GraphJin which column feeds which parameter and the result is a nested field, RBAC-aware, with the same compiler that generates your SQL planning the calls.
# config/openapi/stripe.yml
base_url: "https://api.stripe.com"
auth:
scheme: bearer
token_url: "https://api.stripe.com/v1/oauth/token"
cache_ttl: "55m"
# Map a DB column onto a REST path/query param,
# so a join is just GraphQL.
joins:
- table: customers
operation: listInvoices
params:
- column: stripe_customer_id
param: customer query ($id: ID!) {
customers(id: $id) {
full_name
email
# joined live from Stripe via OpenAPI spec
invoices {
id
total
status
created
}
}
} One binary covers everything: a dev server with auto schema discovery, a database toolchain (setup, diff, migrate, seed), a remote client that authenticates over OIDC device-code, and an MCP server. No tokens to copy, no frameworks to learn.
graphjin serve --demo starts a working example in seconds.
graphjin cli setup opens the device-code login URL in your
browser and persists a refreshable JWT for every subsequent command.
Workflows can be invoked by name from CLI, MCP, REST,
or another workflow.
Every subcommand respects the same config, the same RBAC, and the same allow-list. What runs in CI matches what runs in production.
# spin up against a demo database
graphjin serve --demo
# scaffold and migrate a real schema
graphjin db setup
graphjin db migrate
graphjin db seed # authenticate via OIDC device-code flow
graphjin cli setup https://api.example.com
# run a saved query against prod
graphjin cli query top_customers --limit 5
# exec a workflow (chained queries + JS)
graphjin cli workflow customer_report
# tail audit logs
graphjin cli audit --since 1h JWT from Auth0, Firebase, Okta, or any JWKS endpoint. Header- or cookie-based sessions for legacy stacks. OIDC device-code login for the CLI and MCP. Whatever the source, every request lands in the same context, so one AI surface can be governed with RBAC, row-level filters, and audited policy.
Configure once. Every transport — HTTP, WebSocket, SSE, MCP — runs the same auth pipeline. Roles + row-level filters are authored in YAML and enforced inside the compiler, so even an agent-run workflow cannot read or write outside its lane.
The CLI and MCP authenticate via OIDC device-code: open a URL, approve, done. Tokens refresh automatically, and the resulting permissions are the same ones reflected back through catalog and security posture rows.
# config/prod.yml
auth:
type: jwt
jwt:
provider: "auth0" # or firebase, okta, custom
audience: "https://api.example.com"
jwks_url: "https://example.auth0.com/.well-known/jwks.json"
cookie: "gj_session"
auth_login:
enabled: true # OIDC device-code login for CLI / MCP
provider: "https://login.example.com"
client_id: "graphjin-cli"
scopes: ["openid", "email", "offline_access"]
# config/roles.yml
roles:
- name: anon
tables:
products: { query: { columns: [id, name, price] } }
- name: user
tables:
orders:
query: { filters: ["{ user_id: { eq: $user_id } }"] }
insert: { columns: [product_id, quantity] }
update: { filters: ["{ status: { eq: "draft" } }"] }
Subscribe with the same GraphQL you'd use for a query. GraphJin streams deltas over SSE or WebSockets, batches database polls into one statement, and emits cursors so clients can resume after a network hiccup without missing rows.
The subscription API is just queries with a cursor — no new schema, no resolver tree, no pub/sub bus to operate. Cursor-based pagination keeps feeds and chat-style UIs deterministic; the adaptive poll sizer keeps load predictable as subscriber count grows.
Multiple subscriptions can share a single WebSocket. Per-message timeouts and JWT expiry are enforced at the transport layer, not by hand-rolled middleware.
subscription LiveOrders($since: Cursor) {
orders(
where: { status: { eq: "open" } }
after: $since
first: 50
order_by: { id: asc }
) {
id
total
customer { id full_name }
cursor
}
} # config/prod.yml
subs_poll_duration: "2s" # adaptive batched polling
subs_max_clients: 10000
# both transports active at once
http:
sse: true
websocket: true
One binary, one config file — compiler, catalog, MCP, auth, workflows, CodeSQL, subscriptions, and a CLI. The agent sees a map; the organization keeps the controls.
Auditable config for agent access across the AI surface.
Databases supported through the same GraphQL surface.
Lines of resolver code. The compiler does the work.
Agents discover tables, columns, relationships, syntax, workflows, and safety notes through gj_catalog.
GraphQL compiles into optimized database work, with cross-database composition when sources allow it.
gj_security exposes policy rows and findings so agents can check risk before write-capable actions.
SSE and WebSocket transports with cursor-based resume.
Discover approved workflows, inspect variable contracts, and execute through GraphQL, REST, MCP, or CLI.
Lock a database to query-only with a single config flag.
Stitch in REST and GraphQL endpoints alongside your tables.
Source edits use hashes, exact ranges, old text, optional locks, and preview diffs before apply.
One YAML surface defines roles, sources, saved queries, MCP permissions, and read-only boundaries.
Pick your platform, copy the command, and you're querying. The demo flag ships a real schema and example queries so there's something to point an AI client at on the very first run.
npx graphjin serve --demographjin mcp install --client claude --scope global --yesgraphjin mcp install --client codex --scope global --yesPrefer interactive setup? graphjin mcp install
Configure the connection — PostgreSQL, MySQL, SQLite, MongoDB, Oracle, MSSQL.
GraphJin introspects tables, columns, and relationships on boot.
Joins, mutations, subscriptions, federation, MCP — all out of the box.
Already running Apollo Router, Cosmo, or Hive? Flip one config flag and every primary-keyed table becomes a federation v2 subgraph — SDL with @key, @shareable, and @inaccessible directives, plus a working _service entry point. No resolver code.
# config/prod.yml
federation:
enabled: true
version: v2.5
keys:
users: "id"
products: "sku" @shareable / @inaccessible