Skip to content

Latest commit

 

History

History
189 lines (144 loc) · 4.83 KB

File metadata and controls

189 lines (144 loc) · 4.83 KB

GitDB API

This page documents the public runtime surface exported by @3xhaust/gitdb.

GitDB has two entrypoints:

  • @3xhaust/gitdb/browser: browser/extension/static app surface. Uses fetch, GitHub REST/Git Database APIs, and Web Crypto.
  • @3xhaust/gitdb: Node surface. Includes local filesystem stores, CLI helpers, and Octokit-backed GitHub stores.

GitDB is ESM-only.

Browser GitHub Store

Plaintext GitHub database:

import { defineTable, GitDb, GitHubFetchPlaintextStore } from "@3xhaust/gitdb/browser"
import { z } from "zod"

const TodoRow = z.object({
  id: z.string(),
  title: z.string(),
  done: z.boolean(),
})

const Todo = defineTable({
  columns: { done: "BOOLEAN", id: "STRING", title: "STRING" },
  indexes: [{ columns: ["done"], name: "todos_done_idx" }],
  name: "todos",
  primaryKey: "id",
  row: TodoRow,
})

const db = await GitDb.open({
  store: new GitHubFetchPlaintextStore({
    branch: "main",
    owner: "your-github-user",
    prefix: "gitdb/v1",
    repo: "my-app-db",
    token: userProvidedGithubToken,
  }),
  syncSchema: true,
  tables: [Todo],
})

Encrypted GitHub database:

import {
  createWebAesGcmCipher,
  GitDb,
  GitHubFetchEncryptedStore,
} from "@3xhaust/gitdb/browser"

const cipher = await createWebAesGcmCipher(base64UrlEncoded32ByteKey)
const db = await GitDb.open({
  store: new GitHubFetchEncryptedStore(
    {
      branch: "main",
      owner: "your-github-user",
      prefix: "gitdb/v1",
      repo: "my-private-db",
      token: userProvidedGithubToken,
    },
    cipher,
  ),
})

Both browser stores write through Git tree creation, commit creation, and non-force ref updates. If the target repository is missing, GitDB tries to create a public database repository for the authenticated owner.

Table Handles

const todos = db.table(Todo)

await todos.insert({ done: false, id: "t1", title: "Write docs" })
await todos.insertMany([
  { done: false, id: "t2", title: "Test browser store" },
  { done: true, id: "t3", title: "Ship example" },
])

await todos.upsertMany([{ done: true, id: "t2", title: "Test browser store" }])

const openTodos = await todos.select({ done: false })
const oneTodo = await todos.first({ id: "t2" })
const deleted = await todos.deleteWhere({ id: "t1" })

insertMany() and upsertMany() share one transaction boundary. Prefer them over repeated single-row calls when loading batches.

SQL

await db.execute("CREATE TABLE people (id STRING, name STRING)")
await db.execute("INSERT INTO people VALUES ('p1', 'Lin')")
const rows = await db.query("SELECT * FROM people WHERE id = 'p1'")

The SQL subset currently covers table creation, inserts, deletes, selects, joins, grouping, ordering, and aggregates. Unsupported SQL should fail explicitly rather than pretending to succeed.

Indexes

Indexes are equality-only and rebuildable. Table metadata records intent:

indexes: [{ columns: ["done"], name: "todos_done_idx" }]

The runtime maintains primary/equality indexes from committed rows. Simple table select({ ... }) calls and safe SELECT * FROM table WHERE col = literal queries use the index path. Missing or stale index snapshot files are ignored.

Transactions

await db.transaction(async (tx) => {
  await tx.execute("INSERT INTO todos VALUES ('t4', 'Batch write', false)")
  await tx.execute("INSERT INTO todos VALUES ('t5', 'Commit once', false)")
})

Transactions run on an isolated database copy and persist only after the callback succeeds. Persisted transactions advance the manifest boundary and write GitHub commits when a GitHub store is configured.

Node Stores

Local plaintext:

import { GitDb, LocalPlaintextStore } from "@3xhaust/gitdb"

const db = await GitDb.open({
  store: new LocalPlaintextStore({ root: ".gitdb" }),
})

Local encrypted:

import { GitDb, LocalEncryptedStore, createAesGcmCipher } from "@3xhaust/gitdb"

const db = await GitDb.open({
  store: new LocalEncryptedStore({
    cipher: createAesGcmCipher(process.env.GITDB_KEY ?? ""),
    root: ".gitdb",
  }),
})

Node GitHub stores remain available from the root entrypoint:

import { GitHubPlaintextStore } from "@3xhaust/gitdb"

new GitHubPlaintextStore({
  branch: "main",
  owner: "3x-haust",
  prefix: "gitdb/v1",
  repo: "my-project-db",
  token: process.env.GITDB_GITHUB_TOKEN ?? "",
})

Compaction

const result = await db.compact()

Compaction is currently enabled for local plaintext stores. It writes a matching page snapshot, advances the manifest to an empty logSegments list, then deletes obsolete mutation segments.

Migration

Existing gitdb/v1 repositories remain readable. The next committed write upgrades manifest metadata to v2 while keeping the path layout. Unreferenced mutation files are ignored unless the manifest lists them. See MIGRATION.md for rollback and storage details.