Skip to content

Commit 66dfb18

Browse files
Copilothotlong
andcommitted
docs: add SQLite WASM, PG WASM, plugin dev, driver dev, and v5 migration docs
Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
1 parent b813785 commit 66dfb18

8 files changed

Lines changed: 1198 additions & 3 deletions

File tree

content/docs/drivers/meta.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88
"fs",
99
"excel",
1010
"redis",
11-
"sdk"
11+
"sdk",
12+
"sqlite-wasm",
13+
"pg-wasm"
1214
]
1315
}

content/docs/drivers/pg-wasm.mdx

Lines changed: 229 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,229 @@
1+
---
2+
title: PG WASM Driver
3+
description: Full PostgreSQL in the browser via PGlite WASM with IndexedDB, OPFS, and in-memory storage
4+
---
5+
6+
# PG WASM Driver
7+
8+
The PG WASM Driver (`@objectql/driver-pg-wasm`) embeds a complete PostgreSQL instance inside the browser using [PGlite](https://pglite.dev/) — a WASM build of Postgres. It supports JSONB, full-text search, transactions, and array fields with no server required.
9+
10+
## Features
11+
12+
-**Full PostgreSQL**: Real Postgres query engine compiled to WebAssembly
13+
-**Multiple Storage Backends**: IndexedDB, OPFS, or in-memory
14+
-**Transactions**: Full ACID transaction support with begin/commit/rollback
15+
-**JSONB**: Native JSON document queries
16+
-**Full-Text Search**: Built-in `tsvector` / `tsquery` support
17+
-**Array Fields**: Native PostgreSQL array column types
18+
-**Knex Pipeline**: Reuses `@objectql/driver-sql` Knex codegen (`client: 'pg'`)
19+
-**Extensions**: Load PGlite extensions (e.g., `pgvector`)
20+
21+
## Architecture
22+
23+
```
24+
QueryAST → Knex (client: 'pg') → SQL string → PGlite WASM → IndexedDB / OPFS / Memory
25+
```
26+
27+
The driver compiles queries through the same Knex `pg` pipeline used by the server-side SQL driver, then executes the SQL against a PGlite WASM instance. The result is full PostgreSQL semantics — including window functions, CTEs, and JSONB operators — running entirely client-side.
28+
29+
## Installation
30+
31+
```bash
32+
pnpm add @objectql/driver-pg-wasm
33+
```
34+
35+
## Configuration
36+
37+
```typescript
38+
interface PgWasmDriverConfig {
39+
/** Storage backend */
40+
storage: 'idb' | 'opfs' | 'memory';
41+
/** Database name (IndexedDB database or OPFS directory). Default: 'objectql' */
42+
database?: string;
43+
/** PGlite extensions to load */
44+
extensions?: Record<string, unknown>;
45+
}
46+
```
47+
48+
| Option | Type | Default | Description |
49+
|--------|------|---------|-------------|
50+
| `storage` | `'idb' \| 'opfs' \| 'memory'` | `'idb'` | Persistence backend |
51+
| `database` | `string` | `'objectql'` | Database / namespace identifier |
52+
| `extensions` | `Record<string, unknown>` | `{}` | PGlite extensions to load |
53+
54+
## Quick Start
55+
56+
```typescript
57+
import { ObjectStackKernel } from '@objectstack/runtime';
58+
import { PgWasmDriver } from '@objectql/driver-pg-wasm';
59+
60+
const kernel = new ObjectStackKernel([
61+
new PgWasmDriver({
62+
storage: 'idb',
63+
database: 'my-app'
64+
})
65+
]);
66+
67+
await kernel.start();
68+
```
69+
70+
## Storage Backends
71+
72+
| Backend | Persistence | Capacity | Best For |
73+
|---------|-------------|----------|----------|
74+
| `idb` (IndexedDB) | ✅ Persistent | Hundreds of MB (quota-dependent) | Default — widest browser support |
75+
| `opfs` (Origin Private File System) | ✅ Persistent | GB-scale | Large datasets, near-native I/O |
76+
| `memory` | ❌ Ephemeral | WASM heap only | Unit tests, SSR, throwaway sessions |
77+
78+
```typescript
79+
// IndexedDB (default, broadest support)
80+
new PgWasmDriver({ storage: 'idb' });
81+
82+
// OPFS (best performance for large datasets)
83+
new PgWasmDriver({ storage: 'opfs' });
84+
85+
// Memory (testing)
86+
new PgWasmDriver({ storage: 'memory' });
87+
```
88+
89+
## PostgreSQL-Specific Features
90+
91+
### JSONB Queries
92+
93+
```typescript
94+
const ctx = kernel.createContext({ isSystem: true });
95+
const settings = ctx.object('settings');
96+
97+
// Create a record with JSONB data
98+
await settings.create({
99+
userId: 'user-1',
100+
preferences: { theme: 'dark', locale: 'en', notifications: true }
101+
});
102+
103+
// Query nested JSONB fields
104+
const darkThemeUsers = await settings.find({
105+
filters: [['preferences.theme', '=', 'dark']]
106+
});
107+
```
108+
109+
### Full-Text Search
110+
111+
```typescript
112+
const articles = ctx.object('articles');
113+
114+
// Full-text search using PostgreSQL tsvector
115+
const results = await articles.find({
116+
filters: [['content', 'contains', 'ObjectQL migration guide']]
117+
});
118+
```
119+
120+
### Transactions
121+
122+
```typescript
123+
const driver = kernel.getDriver();
124+
const trx = await driver.beginTransaction();
125+
126+
try {
127+
await driver.create('orders', { total: 99.99, status: 'pending' }, { transaction: trx });
128+
await driver.update('inventory', 'item-1', { stock: 49 }, { transaction: trx });
129+
await driver.commit(trx);
130+
} catch (error) {
131+
await driver.rollback(trx);
132+
throw error;
133+
}
134+
```
135+
136+
### Extensions
137+
138+
```typescript
139+
import { vector } from '@electric-sql/pglite/vector';
140+
141+
const driver = new PgWasmDriver({
142+
storage: 'idb',
143+
extensions: { vector }
144+
});
145+
```
146+
147+
## Browser Requirements
148+
149+
| Requirement | Fallback |
150+
|-------------|----------|
151+
| WebAssembly | Required — no fallback |
152+
| IndexedDB | Required for `idb` storage |
153+
| OPFS | Required for `opfs` storage; needs `Cross-Origin-Isolated` headers |
154+
| `SharedArrayBuffer` | Required for OPFS sync access |
155+
156+
For OPFS storage, set these HTTP headers:
157+
158+
```
159+
Cross-Origin-Opener-Policy: same-origin
160+
Cross-Origin-Embedder-Policy: require-corp
161+
```
162+
163+
## Capabilities
164+
165+
```typescript
166+
{
167+
transactions: true,
168+
joins: true,
169+
aggregations: true,
170+
fullTextSearch: true,
171+
jsonFields: true,
172+
arrayFields: true,
173+
queryFilters: true,
174+
querySorting: true,
175+
queryPagination: true,
176+
bulkOperations: true,
177+
schemaSync: true
178+
}
179+
```
180+
181+
## Usage
182+
183+
```typescript
184+
const ctx = kernel.createContext({ isSystem: true });
185+
const projects = ctx.object('projects');
186+
187+
// Create
188+
const project = await projects.create({
189+
name: 'ObjectQL v5',
190+
tags: ['typescript', 'wasm'],
191+
metadata: { priority: 'high', milestone: 'Q3' }
192+
});
193+
194+
// Query with filters, sort, and pagination
195+
const active = await projects.find({
196+
filters: [['metadata.priority', '=', 'high']],
197+
sort: [['created_at', 'desc']],
198+
limit: 20
199+
});
200+
201+
// Aggregations
202+
const stats = await projects.aggregate({
203+
aggregations: [
204+
{ function: 'count', field: '*', alias: 'total' }
205+
],
206+
groupBy: ['status']
207+
});
208+
```
209+
210+
## Bundle Size
211+
212+
| Component | Size (gzip) |
213+
|-----------|-------------|
214+
| PGlite WASM binary | ~2.8 MB |
215+
| Driver + Knex pg codegen | ~200 KB |
216+
| **Total** | **~3 MB** |
217+
218+
Consider lazy-loading the driver to keep initial bundle size small:
219+
220+
```typescript
221+
const { PgWasmDriver } = await import('@objectql/driver-pg-wasm');
222+
```
223+
224+
## Related Documentation
225+
226+
- [SQL Driver](/docs/drivers/sql) — Server-side Knex driver with native PostgreSQL
227+
- [SQLite WASM Driver](/docs/drivers/sqlite-wasm) — Lighter-weight browser SQL alternative
228+
- [Memory Driver](/docs/drivers/memory) — Lightweight in-memory driver
229+
- [Driver Overview](/docs/drivers)

0 commit comments

Comments
 (0)