{"slug": "drafts-audit-logs-or-don-t-three-ways-platforms-handle-ai-agent-writes", "title": "Drafts, audit logs, or 'don't': three ways platforms handle AI agent writes", "summary": "A developer compared how Sanity, Notion, and Supabase handle AI agent write access, finding three distinct approaches: Sanity defaults to creating drafts before mutating published documents, Notion logs Custom Agent activity in enterprise audit logs, and Supabase advises against connecting its MCP server to production databases because RLS governs permissions rather than correctness. The analysis argues the three mechanisms operate at different layers and that audit logs, designed for slow human-paced writes, struggle when agents can update hundreds of rows per minute.", "body_md": "**Disclosure:** I work on [Busabase](https://busabase.com), which takes the approach described at the end. Everything before that is quoted from the three companies' own documentation, with links.\n\nThree platforms shipped AI agent write access in the last year. All three had to answer the same question — what happens when the agent writes something wrong — and they gave three genuinely different answers.\n\nI read the documentation for a comparison project and ended up with three quotes that are more interesting side by side than apart. None of these companies is wrong. They are solving the problem at different layers, and knowing which layer yours is on saves you from adopting the wrong mechanism.\n\nSanity's Agent Actions are event-driven APIs that generate, transform and translate content. The notable part is the default:\n\nBy default, Agent Actions never mutate a published document. Whenever you supply a published ID, the action creates a draft first before applying any changes.\n\nAnd if you run one against a published document, the new value \"was written to a new draft document and will need to be published.\"\n\nYou can turn this off with `forcePublishedWrite: true`, and schemas marked `liveEdit: true` already behave that way. But the safe path is the default — which is the opposite of how most products shipped agent write access, and it deserves more credit than it gets.\n\nWhat it buys: nothing reaches a reader until a human publishes it.\n\nWhat it does not answer: whether the *value* is correct. A draft with a confidently wrong number in it looks exactly like a draft with a right one.\n\nNotion 3.6 (July 2026) shipped External Agents, and the first two are Claude and Cursor. You \"assign them tasks from a board shared with your whole team, @-mention them like teammates, and watch them run.\" Custom Agents run on schedules and triggers; AI Autofill brings them directly into databases.\n\nFor oversight, Enterprise plans get this:\n\nThe audit log includes Custom Agent activity, so you can see when an agent runs, what it changed, and who triggered it.\n\nThat is a real mechanism. It answers *who changed this, and when*.\n\nWhat it does not answer: *should this have become true* — and it answers the first question only after the write has landed.\n\nThis is the part worth sitting with. Audit logs were designed for a world where writes were slow and the next reader was a person. An agent can update 800 rows in a minute, and the next reader is usually the next agent run, a scheduled report, or a page a customer sees. By the time a human notices, the wrong value has been read, summarized and acted on.\n\n\"You can see what the agent changed\" and \"you can control what the agent changes\" quietly stopped being the same promise.\n\nSupabase positions itself as \"the complete Postgres developer platform built for agentic workloads\" — MCP server, Agent Skills, RLS on every call. Their own engineering post about agents is unusually candid. Agents, they write:\n\n`security_invoker = true`, \"which silently bypasses RLS\"\nAnd plainly: \"agents are lazy about it.\"\n\nTheir conclusion follows from the evidence:\n\nWe strongly discourage connecting the Supabase MCP server to your production database.\n\nLocal or staging only.\n\nThat is sound advice, and it is worth noticing *why* it is sound. Look at their list again: every item is a failure of **correctness**, and the mechanism being asked to catch it — RLS — governs **permission**. RLS answers *may this caller write this row*. It cannot answer *is this the right value*. An agent with entirely correct permissions writing a confidently wrong number passes every check the database has.\n\nAt the engine layer there is no other answer available, which is exactly why \"keep agents off production\" is the honest recommendation rather than a cop-out.\n\nPut the three next to each other and they are not competing implementations of one idea. They are three different layers:\n\n| Platform | Gate | Unit | Catches | \n|---|---|---|---|\n| Sanity | Before publication | The document version | Content reaching an audience unreviewed | \n| Notion | After the write | The session | Attribution — who ran what, when | \n| Supabase | At the connection | The environment | Agents touching production at all | \n\nEach is well-matched to what that product is for. Sanity's destination is a reader, so the gate is publication. Notion's surface is a collaborative workspace where most edits are low-stakes, so the mechanism is attribution. Supabase is infrastructure, where the only lever available is who may connect.\n\nThe gap all three leave open is the same one: **a write that is permitted, well-formed, and false.**\n\nThree questions, in order:\n\nThe third case is where teams get surprised. It looks like the first two until a wrong row has been read by four things before anyone opens it.\n\nDevelopers already have the mental model. Code does not go straight into `main`. It goes through a pull request: a diff of exactly what changes, an author, a place to comment, an approval, and a merge commit that records when it became real.\n\n**Agent writes to data today are the equivalent of giving everyone direct push access to `main`.** The three gates above are each a partial substitute — publication review is a release branch, an audit log is `git log` with no review step, and \"don't connect to production\" is not granting access at all.\n\nWhat none of them is, is a pull request. Applied to data, that means:\n\n| Pull request | Applied to a data write | \n|---|---|\n| The diff | Which fields change, from what to what | \n| The author | Which agent proposed it, on what evidence | \n| Review | A person sees it before it is true, not after | \n| The merge commit | When it became canonical, and who decided | \n\nThe same shape applies to what an agent *knows*, not just what it writes — prompts, instructions and reusable skills drift exactly the way code does, and benefit from exactly the same treatment.\n\nBusabase is the third option — a workspace built so the write path is a pull request by default. Disclosure again: I work on it. It is MIT-licensed and runs locally, so the fastest way to judge it is to run it rather than read about it:\n\n```\nnpx busabase server\n# → http://localhost:15419/dashboard/local\n```\n\nNo signup, no account, no cloud. It starts with an embedded Postgres (PGlite), local file storage, and demo content already in place.\n\nPoint an agent at it — MCP, an Agent Skill, or the OpenAPI surface at `/api/v1` — and have it write something. This is what arrives:\n\nThe changed fields with before and after, which agent proposed it, the source it used, and a comment thread. You approve, request changes, or reject. Approved values become canonical and keep the proposer, reviewer and commit attached.\n\nThe same applies to the agent's skills and instructions, which is the part I did not expect to matter as much as it does: a reusable skill that drifts silently is the same failure as a record that drifts silently, and it responds to the same fix.\n\nTwo honest limits, since this is a post about reading documentation carefully: review is proportional to consequence — low-stakes writes stay fast, and a key with merge rights merges immediately — and if nothing your agents write is worth inspecting, this whole mechanism is overhead you do not need.\n\n*Sources: [Sanity Agent Actions docs](https://www.sanity.io/docs/agent-actions/operations), [Notion 3.6 release notes](https://www.notion.com/releases/2026-07-01), [Supabase — AI Agents Know About Supabase. They Don't Always Use It Right.](https://supabase.com/blog/supabase-agent-skills). Verified 21 September 2026; all three ship frequently.*\n\n*Longer versions of each comparison, with the sources and a section on where the other product is the better choice: [vs Notion](https://busabase.com/compare/busabase-vs-notion) · [vs Sanity](https://busabase.com/compare/busabase-vs-sanity) · [vs Supabase](https://busabase.com/compare/busabase-vs-supabase)*", "url": "https://wpnews.pro/news/drafts-audit-logs-or-don-t-three-ways-platforms-handle-ai-agent-writes", "canonical_source": "https://dev.to/mrkelly/drafts-audit-logs-or-dont-three-ways-platforms-handle-ai-agent-writes-2e1c", "published_at": "2026-09-21 06:24:58+00:00", "updated_at": "2026-09-21 06:53:18.723948+00:00", "lang": "en", "topics": ["ai-agents", "agent-protocols", "ai-tools", "ai-infrastructure"], "entities": ["Sanity", "Notion", "Supabase", "Claude", "Cursor", "Busabase", "MCP"], "alternates": {"html": "https://wpnews.pro/news/drafts-audit-logs-or-don-t-three-ways-platforms-handle-ai-agent-writes", "markdown": "https://wpnews.pro/news/drafts-audit-logs-or-don-t-three-ways-platforms-handle-ai-agent-writes.md", "text": "https://wpnews.pro/news/drafts-audit-logs-or-don-t-three-ways-platforms-handle-ai-agent-writes.txt", "jsonld": "https://wpnews.pro/news/drafts-audit-logs-or-don-t-three-ways-platforms-handle-ai-agent-writes.jsonld"}}