Stockholm
Meridan ReportStockholm: Nordic startup hub and fintech frontier

Advertisement · Why this ad?

Technology

Gnomon. Git for Postgres data, built for agents

Marcus Chen
Managing Editor · Friday, November 13, 2026 at 5:09 PM · 6 min read
Gnomon. Git for Postgres data, built for agents — Stockholm Technology news
Gnomon Git for Postgres data, built for agents. Give an agent its own branch of your real database, as nothing more than a connection string. See every field it changed, merge it into main when it's right, and undo it if it wasn't. Gnomon runs inside the Postgres you already have. One extension, no copies, no second database. create extension gnomon; select gnomon . track ( ' orders ' ); -- history starts now, no backfill select gnomon . create_branch ( ' agent/refunds ' ); select gnomon . use ( ' agent/refunds ' ); -- Every query from here on runs on the branch update orders set status = ' refunded ' where id = 4182 ; select * from gnomon . diff ( ' agent/refunds ' ); -- every row and field it changed select gnomon . merge ( ' agent/refunds ' ); -- three-way, type-aware, conflicts as rows select gnomon . undo_merge ( 1 ); -- and back Documentation: https://gnomon.bitsinfra.com/ Install: create extension gnomon on PostgreSQL 15-18, self-hosted or managed (RDS, Aurora, Supabase). See Installation . New here? The tutorial takes ten minutes. A branch of production, in an instant A branch reads everything from main and keeps only what it changes, so it opens instantly and copies nothing, however big your database is. Give one to every agent run, every pull request and every test. Your application doesn't change. A branch is a connection string: point a session at it, and the queries it already runs read and write the branch instead of main. Where How A session select gnomon.use('feature') One transaction (behind a pooler) select gnomon.begin('feature') A connection string gnomon branch url feature With the C module SET gnomon.branch = 'feature' A past moment select gnomon.use('main', '2026-10-31 23:59') Schema changes come along too. Run a migration on a branch to add a column, rename one or create a table, and main stays as it is until the merge, which brings the new shape and its data across together. Review data like code Every branch comes with a diff: each row and field it changed, before and after. Review it in your browser, comment on a single row and settle conflicts side by side. When an agent is done, Gnomon opens the review and sends you the link. Add checks written in SQL, and Gnomon runs them on the merged result before the merge is allowed to land. An approval covers what you saw: if the branch changes afterwards, it comes back to you. Merges that understand your data When main and a branch change the same value, Gnomon doesn't just pick a side. Counts add up, JSON merges key by key and text merges line by line. Anything that truly clashes becomes a conflict, for a person to settle or for a query to resolve. Branches merge into each other too, not only into main, and a single transaction can be picked from one branch onto another. Undo works the same way: take back one transaction, everything an agent did this afternoon, or a whole merge. Any moment, exactly as it was Gnomon keeps the history of every table you track. Read the whole database as it was at any moment, with the queries you already have, and get the same answer every time. When an agent makes a decision, you can see exactly what it saw. -- The open invoices at the end of October select gnomon . use ( ' main ' , ' 2026-10-31 23:59 ' ); select sum (amount) from invoices where status = ' open ' ; The same history streams out as it happens, to Kafka, NATS or a webhook, and into dbt as snapshots that keep deleted rows. Older history can move to object storage, and Gnomon brings it back when a query reaches that far. When a check that used to pass starts failing, gnomon bisect finds the transaction that broke it: who made it, when and why. Safe to hand to an agent One command gives an agent a database role, a branch of its own and a connection string. That's all it needs, whatever it's built with. It reads and writes its branch, and the database refuses the rest, main included, even when the agent asks for it by name. # A database role, a branch of its own and a connection string gnomon agent create support-bot It merges only what you allow. Merging is for the people you choose, or for an agent within rules you write: at most twenty rows, only these tables, every check passing. Postgres enforces them, whatever the agent is told. Nothing leaves before you approve. Emails, webhooks and payments an agent queues stay on its branch until the merge. Every change has a name on it. Each change records the agent, the run and the reason it gave. Replay what it saw. Gnomon records the moment of every read, so a replay returns exactly the rows the agent read. Try a few ways at once. Start several attempts from the same moment, compare their changes and checks, and keep the best one. Stop it, and take it back. One command locks an agent out, closes its branches and undoes what it merged, newest first. Ready for your agents. The Gnomon MCP server, on the agent's machine or over HTTP, lets it explore the schema, try a change without keeping it, and rewind its branch to a checkpoint. Build it into your product The TypeScript and Python SDKs give each task your agents take on a run: a branch of its own, with limits already set. Merge it, send it for review, or let it go. import { Gnomon } from "@bitsinfra/gnomon" ; import { nodePostgres } from "@bitsinfra/gnomon/pg" ; const gnomon = new Gnomon ( { app : nodePostgres ( appPool ) , // your application's own login runs : nodePostgres ( runsPool ) , // one login shared by every agent run } ) ; // A branch for this task, discarded unless it's merged or submitted await using run = await gnomon . startRun ( { task : "Refund order 4182" , actor : "support-bot" , } ) ; await run . sql ( "update orders set status = 'refunded' where id = 4182" ) ; const { checks , changes } = await run . summary ( ) ; if ( checks . passed && changes . rows <= 20 ) await run . merge ( ) ; else await run . submit ( { title : "Refund order 4182" } ) ; Runs can't read each other's branches, even when they share one database login. Bring the agent framework you already use: the Anthropic SDK, the Claude Agent SDK, the Vercel AI SDK, the OpenAI Agents SDK, LangChain or any MCP client gets the same few tools, bound to one run. They work through your drivers and ORMs, from node-postgres and Prisma to psycopg and Django. And in your tests, each test gets its own branch of one seeded database. npm install @bitsinfra/gnomon # TypeScript pip install gnomon-postgres # Python What is in the box Part Path What it does SQL core src/sql The extension: history, branches, merges, review, valid time, retention, archiving. Installs on managed Postgres. C module src/c Optional: SET gnomon.branch alone routes, real row locks, ON CONFLICT and TRUNCATE on branches, stale-read detection, faster writes and point reads. CLI, MCP server, review app cli One Go binary: gnomon branch/diff/merge/bisect/agent/migrate/serve/mcp/daemon/archive . SDKs sdk/ts , integrations/python @bitsinfra/gnomon and gnomon-postgres : a run per task, review, typed diffs, test helpers. One specification and conformance suite. GitHub Action action A database branch per pull request, migrations on it, the changes as a comment. Integrations integrations Python, Node, Ruby, Go, Java, Elixir, .NET, PHP; PostgREST and Supabase; a dbt package. Examples, container examples , docker The tutorial's shop database and a ready-made image. Documentation Everything is at https://gnomon.bitsinfra.com/ , and the same pages live in docs : Installation and the tutorial Concepts : branches, coordinates, merges Agents , runs and the SDKs , the MCP server Branches , schem
Up next6-11X speedup running Qwen3.6 on my RTX 4090, full repo.Technology · 5 min read
You're offline — showing the last loaded page