@hatk/hatk 0.0.1-alpha.43 → 0.0.1-alpha.45

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.js CHANGED
@@ -1,8 +1,8 @@
1
1
  #!/usr/bin/env node
2
- import { mkdirSync, writeFileSync, existsSync, unlinkSync, readdirSync, readFileSync, cpSync } from 'node:fs';
3
- import { resolve, join, dirname } from 'node:path';
2
+ import { mkdirSync, writeFileSync, existsSync, unlinkSync, readdirSync, readFileSync } from 'node:fs';
3
+ import { resolve, join } from 'node:path';
4
4
  import { execSync, spawn } from 'node:child_process';
5
- import { loadLexicons, discoverCollections, buildSchemas } from "./database/schema.js";
5
+ import { loadLexicons } from "./database/schema.js";
6
6
  import { loadConfig } from "./config.js";
7
7
  const args = process.argv.slice(2);
8
8
  const command = args[0];
@@ -69,15 +69,11 @@ function usage() {
69
69
  console.log(`
70
70
  Usage: hatk <command> [options]
71
71
 
72
- Getting Started
73
- new <name> [--svelte] [--duckdb] [--template <t>] Create a new hatk project
74
-
75
72
  Running
76
73
  start Start the hatk server
77
74
  dev Start PDS, seed, and run hatk
78
75
  seed Seed local PDS with fixture data
79
76
  reset Reset database and PDS for a clean slate
80
- schema Show database schema from lexicons
81
77
 
82
78
  Code Quality
83
79
  check Type-check and lint the project
@@ -193,493 +189,12 @@ const dirs = {
193
189
  };
194
190
  // --- Commands ---
195
191
  if (command === 'new') {
196
- const name = args[1];
197
- if (!name) {
198
- console.error('Usage: hatk new <name> [--svelte] [--duckdb] [--template <template-name>]');
199
- process.exit(1);
200
- }
201
- const templateIdx = args.indexOf('--template');
202
- const templateName = templateIdx !== -1 ? args[templateIdx + 1] : null;
203
- if (templateIdx !== -1 && !templateName) {
204
- console.error('Usage: hatk new <name> --template <template-name>');
205
- process.exit(1);
206
- }
207
- const dir = resolve(name);
208
- if (existsSync(dir)) {
209
- console.error(`Directory ${name} already exists`);
210
- process.exit(1);
211
- }
212
- if (templateName) {
213
- const repo = `https://github.com/hatk-dev/hatk-template-${templateName}.git`;
214
- console.log(`Cloning template ${templateName}...`);
215
- try {
216
- execSync(`git clone --depth 1 ${repo} ${dir}`, { stdio: 'inherit' });
217
- }
218
- catch {
219
- console.error(`Failed to clone template: ${repo}`);
220
- process.exit(1);
221
- }
222
- execSync(`rm -rf ${join(dir, '.git')}`);
223
- const pkgPath = join(dir, 'package.json');
224
- if (existsSync(pkgPath)) {
225
- const pkg = JSON.parse(readFileSync(pkgPath, 'utf-8'));
226
- pkg.name = name;
227
- writeFileSync(pkgPath, JSON.stringify(pkg, null, 2) + '\n');
228
- }
229
- console.log(`\nCreated ${name}/ from template ${templateName}`);
230
- console.log(`\n cd ${name}`);
231
- console.log(` npm install`);
232
- console.log(` hatk dev`);
233
- process.exit(0);
234
- }
235
- const withSvelte = args.includes('--svelte');
236
- const withDuckdb = args.includes('--duckdb');
237
- const dbEngine = withDuckdb ? 'duckdb' : 'sqlite';
238
- mkdirSync(dir);
239
- const subs = [
240
- 'lexicons',
241
- 'server',
242
- 'seeds',
243
- 'public',
244
- 'test',
245
- 'test/server',
246
- 'test/integration',
247
- 'test/browser',
248
- 'test/fixtures',
249
- ];
250
- if (withSvelte)
251
- subs.push('src', 'src/routes', 'src/lib');
252
- for (const sub of subs) {
253
- mkdirSync(join(dir, sub));
254
- }
255
- writeFileSync(join(dir, 'hatk.config.ts'), `import { defineConfig } from '@hatk/hatk/config'
256
-
257
- export default defineConfig({
258
- relay: 'ws://localhost:2583',
259
- plc: 'http://localhost:2582',
260
- port: 3000,
261
- databaseEngine: '${dbEngine}',
262
- database: 'data/hatk.db',
263
- admins: [],
264
- backfill: {
265
- parallelism: 10,
266
- },
267
- })
268
- `);
269
- writeFileSync(join(dir, 'public', 'index.html'), `<!DOCTYPE html>
270
- <html><head><title>${name}</title></head>
271
- <body><h1>${name}</h1></body></html>
272
- `);
273
- // Copy core framework lexicons (dev.hatk.* and dependencies like com.atproto.repo.strongRef)
274
- const builtinLexDir = join(import.meta.dirname, 'lexicons');
275
- cpSync(builtinLexDir, join(dir, 'lexicons'), { recursive: true });
276
- writeFileSync(join(dir, 'seeds', 'seed.ts'), loadTemplate('seed.tpl', ''));
277
- writeFileSync(join(dir, 'docker-compose.yml'), `services:
278
- plc:
279
- build:
280
- context: https://github.com/did-method-plc/did-method-plc.git
281
- dockerfile: packages/server/Dockerfile
282
- ports:
283
- - '2582:2582'
284
- environment:
285
- - DATABASE_URL=postgres://plc:plc@postgres:5432/plc
286
- - PORT=2582
287
- command: ['dumb-init', 'node', '--enable-source-maps', '../dist/bin.js']
288
- depends_on:
289
- postgres:
290
- condition: service_healthy
291
- healthcheck:
292
- test: ['CMD-SHELL', 'wget -q --spider http://localhost:2582/_health || exit 1']
293
- interval: 2s
294
- timeout: 5s
295
- retries: 15
296
-
297
- pds:
298
- image: ghcr.io/bluesky-social/pds:latest
299
- ports:
300
- - '2583:2583'
301
- environment:
302
- - PDS_HOSTNAME=localhost
303
- - PDS_PORT=2583
304
- - PDS_DID_PLC_URL=http://plc:2582
305
- - PDS_DATA_DIRECTORY=/pds
306
- - PDS_BLOBSTORE_DISK_LOCATION=/pds/blobs
307
- - PDS_JWT_SECRET=dev-jwt-secret
308
- - PDS_ADMIN_PASSWORD=dev-admin
309
- - PDS_PLC_ROTATION_KEY_K256_PRIVATE_KEY_HEX=0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef
310
- - PDS_INVITE_REQUIRED=false
311
- - PDS_DEV_MODE=true
312
- - LOG_ENABLED=true
313
- volumes:
314
- - pds_data:/pds
315
- depends_on:
316
- plc:
317
- condition: service_healthy
318
- healthcheck:
319
- test: ['CMD-SHELL', 'wget -q --spider http://localhost:2583/xrpc/_health || exit 1']
320
- interval: 2s
321
- timeout: 5s
322
- retries: 15
323
-
324
- postgres:
325
- image: postgres:16-alpine
326
- environment:
327
- - POSTGRES_USER=plc
328
- - POSTGRES_PASSWORD=plc
329
- - POSTGRES_DB=plc
330
- volumes:
331
- - plc_data:/var/lib/postgresql/data
332
- healthcheck:
333
- test: ['CMD-SHELL', 'pg_isready -U plc']
334
- interval: 2s
335
- timeout: 5s
336
- retries: 10
337
-
338
- volumes:
339
- pds_data:
340
- plc_data:
341
- `);
342
- writeFileSync(join(dir, '.dockerignore'), `node_modules
343
- data
344
- .svelte-kit
345
- public
346
- `);
347
- writeFileSync(join(dir, 'Dockerfile'), `FROM node:25-slim
348
- WORKDIR /app
349
- COPY package.json package-lock.json ./
350
- RUN npm ci
351
- COPY . .
352
- RUN node_modules/.bin/hatk build
353
- RUN npm prune --omit=dev
354
- EXPOSE 3000
355
- CMD ["node", "--experimental-strip-types", "--max-old-space-size=512", "node_modules/@hatk/hatk/dist/main.js", "hatk.config.ts"]
356
- `);
357
- const pkgDeps = { '@hatk/oauth-client': '*', hatk: '*' };
358
- if (!withDuckdb) {
359
- pkgDeps['better-sqlite3'] = '^11';
360
- }
361
- const pkgDevDeps = {
362
- '@playwright/test': '^1',
363
- oxfmt: '^0.35.0',
364
- oxlint: '^1',
365
- typescript: '^5',
366
- vite: '^6',
367
- vitest: '^4',
368
- '@types/node': '^22',
369
- };
370
- if (withSvelte) {
371
- pkgDevDeps['@sveltejs/adapter-static'] = '^3';
372
- pkgDevDeps['@sveltejs/kit'] = '^2';
373
- pkgDevDeps['@sveltejs/vite-plugin-svelte'] = '^5';
374
- pkgDevDeps['svelte'] = '^5';
375
- pkgDevDeps['svelte-check'] = '^4';
376
- }
377
- writeFileSync(join(dir, 'package.json'), JSON.stringify({
378
- name,
379
- private: true,
380
- type: 'module',
381
- scripts: {
382
- start: 'hatk start',
383
- dev: 'hatk dev',
384
- build: 'hatk build',
385
- check: 'hatk check',
386
- format: 'hatk format',
387
- },
388
- dependencies: pkgDeps,
389
- devDependencies: pkgDevDeps,
390
- }, null, 2) + '\n');
391
- writeFileSync(join(dir, 'tsconfig.server.json'), JSON.stringify({
392
- compilerOptions: {
393
- target: 'ES2022',
394
- module: 'Node16',
395
- moduleResolution: 'Node16',
396
- strict: true,
397
- esModuleInterop: true,
398
- skipLibCheck: true,
399
- noEmit: true,
400
- allowImportingTsExtensions: true,
401
- resolveJsonModule: true,
402
- },
403
- include: ['server', 'seeds', 'hatk.generated.ts', 'hatk.config.ts'],
404
- }, null, 2) + '\n');
405
- writeFileSync(join(dir, 'playwright.config.ts'), `import { defineConfig } from '@playwright/test'
406
-
407
- export default defineConfig({
408
- testDir: 'test/browser',
409
- use: { baseURL: 'http://127.0.0.1:3000' },
410
- globalSetup: './test/browser/global-setup.ts',
411
- })
412
- `);
413
- writeFileSync(join(dir, 'test/browser/global-setup.ts'), `import { execSync } from 'node:child_process'
414
- import { existsSync } from 'node:fs'
415
-
416
- export default function globalSetup() {
417
- if (existsSync('src/app.html')) {
418
- execSync('npx vite build', { stdio: 'inherit' })
419
- }
420
- }
421
- `);
422
- writeFileSync(join(dir, '.gitignore'), `node_modules/
423
- *.db
424
- data/
425
- test-results/
426
- .svelte-kit/
427
- .DS_Store
428
- public/
429
- `);
430
- writeFileSync(join(dir, '.oxlintrc.json'), `{
431
- "ignorePatterns": ["public", "data", ".svelte-kit", "hatk.generated.ts"]
432
- }
433
- `);
434
- writeFileSync(join(dir, '.oxfmtrc.json'), `{
435
- "semi": false,
436
- "singleQuote": true,
437
- "trailingComma": "all",
438
- "printWidth": 120,
439
- "tabWidth": 2,
440
- "ignorePatterns": ["public", "data", ".svelte-kit", "hatk.generated.ts"]
441
- }
442
- `);
443
- if (withSvelte) {
444
- writeFileSync(join(dir, 'svelte.config.js'), `import adapter from '@sveltejs/adapter-static'
445
-
446
- export default {
447
- kit: {
448
- adapter: adapter({
449
- pages: 'public',
450
- assets: 'public',
451
- fallback: 'index.html',
452
- }),
453
- paths: { base: '' },
454
- alias: {
455
- $hatk: './hatk.generated.ts',
456
- },
457
- },
458
- }
459
- `);
460
- writeFileSync(join(dir, 'vite.config.ts'), `import { sveltekit } from '@sveltejs/kit/vite'
461
- import { hatk } from '@hatk/hatk/vite-plugin'
462
- import { defineConfig } from 'vite'
463
-
464
- export default defineConfig({
465
- plugins: [sveltekit(), hatk()],
466
- })
467
- `);
468
- writeFileSync(join(dir, 'tsconfig.json'), JSON.stringify({
469
- extends: './.svelte-kit/tsconfig.json',
470
- compilerOptions: {
471
- allowJs: true,
472
- checkJs: false,
473
- esModuleInterop: true,
474
- forceConsistentCasingInFileNames: true,
475
- resolveJsonModule: true,
476
- skipLibCheck: true,
477
- sourceMap: true,
478
- strict: true,
479
- moduleResolution: 'bundler',
480
- allowImportingTsExtensions: true,
481
- },
482
- }, null, 2) + '\n');
483
- writeFileSync(join(dir, 'src/app.html'), `<!doctype html>
484
- <html lang="en">
485
- <head>
486
- <meta charset="utf-8" />
487
- <meta name="viewport" content="width=device-width, initial-scale=1" />
488
- <meta name="description" content="${name}" />
489
- <title>${name}</title>
490
- %sveltekit.head%
491
- </head>
492
- <body data-sveltekit-preload-data="hover">
493
- <div style="display: contents">%sveltekit.body%</div>
494
- </body>
495
- </html>
496
- `);
497
- writeFileSync(join(dir, 'src/app.css'), `*,
498
- *::before,
499
- *::after {
500
- box-sizing: border-box;
501
- margin: 0;
502
- padding: 0;
503
- }
504
-
505
- :root {
506
- --bg-root: #080b12;
507
- --bg-surface: #0f1419;
508
- --bg-elevated: #161d27;
509
- --bg-hover: #1c2633;
510
- --border: #1e293b;
511
- --teal: #14b8a6;
512
- --text-primary: #e2e8f0;
513
- --text-secondary: #94a3b8;
514
- --text-muted: #64748b;
515
- }
516
-
517
- html {
518
- background: var(--bg-root);
519
- color: var(--text-primary);
520
- }
521
-
522
- body {
523
- font-family: -apple-system, system-ui, sans-serif;
524
- font-size: 15px;
525
- line-height: 1.5;
526
- min-height: 100vh;
527
- }
528
-
529
- a {
530
- color: inherit;
531
- text-decoration: none;
532
- }
533
- `);
534
- writeFileSync(join(dir, 'src/routes/+layout.svelte'), `<script lang="ts">
535
- import type { Snippet } from 'svelte'
536
- import '../app.css'
537
-
538
- let { children }: { children: Snippet } = $props()
539
- </script>
540
-
541
- {@render children()}
542
- `);
543
- writeFileSync(join(dir, 'src/routes/+page.svelte'), `<h1>${name}</h1>
544
- <p>Your hatk server is running.</p>
545
- `);
546
- writeFileSync(join(dir, 'src/error.html'), `<!doctype html>
547
- <html lang="en">
548
- <head>
549
- <meta charset="utf-8" />
550
- <meta name="viewport" content="width=device-width, initial-scale=1" />
551
- <title>%sveltekit.error.message% — ${name}</title>
552
- <style>
553
- * { box-sizing: border-box; margin: 0; padding: 0; }
554
- body {
555
- font-family: -apple-system, system-ui, sans-serif;
556
- background: #080b12; color: #e2e8f0;
557
- min-height: 100vh; display: flex; align-items: center; justify-content: center;
558
- }
559
- .error-page { display: flex; flex-direction: column; align-items: center; text-align: center; gap: 8px; padding: 24px; }
560
- .error-code { font-size: 72px; font-weight: 800; color: #14b8a6; line-height: 1; }
561
- .error-title { font-size: 24px; font-weight: 800; }
562
- .error-link {
563
- margin-top: 16px; padding: 10px 24px; background: #14b8a6; color: #000;
564
- border-radius: 20px; font-weight: 600; font-size: 14px; text-decoration: none;
565
- }
566
- </style>
567
- </head>
568
- <body>
569
- <div class="error-page">
570
- <span class="error-code">%sveltekit.status%</span>
571
- <h1 class="error-title">%sveltekit.error.message%</h1>
572
- <a href="/" class="error-link">Back to home</a>
573
- </div>
574
- </body>
575
- </html>
576
- `);
577
- writeFileSync(join(dir, 'src/routes/+error.svelte'), `<script lang="ts">
578
- import { page } from '$app/state'
579
- </script>
580
-
581
- <div style="display: flex; flex-direction: column; align-items: center; justify-content: center; min-height: 80vh; gap: 8px;">
582
- <span style="font-size: 72px; font-weight: 800; color: var(--teal);">{page.status}</span>
583
- <h1 style="font-size: 24px; font-weight: 800;">{page.error?.message}</h1>
584
- <a href="/" style="margin-top: 16px; padding: 10px 24px; background: var(--teal); color: #000; border-radius: 20px; font-weight: 600; font-size: 14px;">Back to home</a>
585
- </div>
586
- `);
587
- }
588
- let agentsMd = `# hatk project
589
-
590
- This is an AT Protocol application built with [hatk](https://github.com/hatk-dev/hatk).
591
- Read the project's lexicons in \`lexicons/\` to understand the data model.
592
- Types are generated from lexicons into \`hatk.generated.ts\` — never edit this file directly.
593
-
594
- ## Project structure
595
-
596
- | Directory | Purpose |
597
- |-------------|------------------------------------------------------|
598
- | \`lexicons/\` | AT Protocol lexicon schemas (JSON). Defines collections and XRPC methods |
599
- | \`server/\` | All server-side code: feeds, XRPC handlers, hooks, labels, OG routes, setup scripts |
600
- | \`seeds/\` | Test data seeding scripts for local development |
601
- | \`test/\` | Test files (vitest). Run with \`vp test\` |
602
- | \`public/\` | Static files served at the root |
603
- `;
604
- if (withSvelte) {
605
- agentsMd += `| \`src/\` | SvelteKit frontend (routes, components, styles) |
606
-
607
- `;
608
- }
609
- else {
610
- agentsMd += `
611
- `;
612
- }
613
- agentsMd += `## Key files
614
-
615
- - \`hatk.config.ts\` — project configuration (see \`defineConfig\` for type info)
616
- - \`hatk.generated.ts\` — auto-generated server types and helpers. Regenerate with \`hatk generate types\`
617
- - \`hatk.generated.client.ts\` — auto-generated client-safe types and \`callXrpc\`. Never import \`hatk.generated.ts\` from frontend code
618
-
619
- ## The \`$hatk\` alias
620
-
621
- Server files in \`server/\` import from \`$hatk\`:
622
- \`\`\`ts
623
- import { defineFeed, views, type Status } from "$hatk"
624
- \`\`\`
625
- `;
626
- if (withSvelte) {
627
- agentsMd += `
628
- SvelteKit routes and components import from \`$hatk/client\`:
629
- \`\`\`ts
630
- import { callXrpc, getViewer } from "$hatk/client"
631
- \`\`\`
632
-
633
- \`$hatk\` resolves to \`hatk.generated.ts\` and \`$hatk/client\` to \`hatk.generated.client.ts\`.
634
- The Vite plugin handles this in dev/build. In tests and production, a Node.js module resolve hook handles it.
635
- `;
636
- }
637
- else {
638
- agentsMd += `
639
- \`$hatk\` resolves to \`hatk.generated.ts\`. The Vite plugin handles this in dev/build.
640
- In tests and production, a Node.js module resolve hook handles it.
641
- `;
642
- }
643
- agentsMd += `
644
- ## Commands
645
-
646
- Run \`npx hatk --help\` for the full list of commands.
647
-
648
- Use \`npx hatk generate\` to scaffold new feeds, xrpc handlers, labels, and lexicons
649
- rather than creating files manually. These generate files with the correct imports.
650
-
651
- After modifying lexicons, always run \`npx hatk generate types\` to update the generated types.
652
- `;
653
- if (withSvelte) {
654
- agentsMd += `
655
- ## Running
656
-
657
- - \`vp dev\` — start dev server (hatk + SvelteKit + PDS)
658
- - \`vp build\` — build for production (SvelteKit outputs to \`build/\`)
659
- - \`hatk start\` — start production server (hatk + SvelteKit via \`build/handler.js\`)
660
- - \`vp test\` — run tests
661
- `;
662
- }
663
- writeFileSync(join(dir, 'AGENTS.md'), agentsMd);
664
- console.log(`Created ${name}/`);
665
- console.log(` hatk.config.ts`);
666
- console.log(` lexicons/ — lexicon JSON files (core + your own)`);
667
- console.log(` server/ — feeds, XRPC handlers, hooks, labels, OG routes, setup`);
668
- console.log(` seeds/ — seed fixture data (hatk seed)`);
669
- console.log(` test/ — test files (hatk test)`);
670
- console.log(` public/ — static files`);
671
- console.log(` docker-compose.yml — local PDS for development`);
672
- console.log(` Dockerfile — production container`);
673
- if (withSvelte) {
674
- console.log(` src/ — SvelteKit frontend`);
675
- console.log(` svelte.config.js`);
676
- console.log(` vite.config.ts`);
677
- }
678
- // Generate types so the project is ready to go
679
- execSync('npx hatk generate types', { stdio: 'inherit', cwd: dir });
680
- if (withSvelte) {
681
- execSync('npx svelte-kit sync', { stdio: 'inherit', cwd: dir });
682
- }
192
+ console.error('`hatk new` has been removed. Create a new project with:');
193
+ console.error('');
194
+ console.error(' vp create github:hatk-dev/hatk-template-starter');
195
+ console.error('');
196
+ console.error('Install vp first: curl -fsSL https://vite.plus | bash');
197
+ process.exit(1);
683
198
  }
684
199
  else if (command === 'generate') {
685
200
  const type = args[1];
@@ -1059,6 +574,7 @@ else if (command === 'generate') {
1059
574
  clientOut += ` const blob = arg as Blob | ArrayBuffer\n`;
1060
575
  clientOut += ` const ct = blob instanceof Blob ? blob.type : 'application/octet-stream'\n`;
1061
576
  clientOut += ` const res = await _fetch(path, { method: 'POST', headers: { 'Content-Type': ct }, body: blob })\n`;
577
+ clientOut += ` if (typeof window !== 'undefined' && res.status === 401) { const _b = await res.json().catch(() => ({})); const _h = _b.handle ?? getViewer()?.handle; window.location.href = _h ? \`/oauth/login?handle=\${encodeURIComponent(_h)}\` : '/oauth/login'; return new Promise(() => {}) as any }\n`;
1062
578
  clientOut += ` if (!res.ok) throw new Error(\`XRPC \${nsid} failed: \${res.status}\`)\n`;
1063
579
  clientOut += ` return res.json() as Promise<OutputOf<K>>\n`;
1064
580
  clientOut += ` }\n`;
@@ -1395,22 +911,6 @@ else if (command === 'resolve') {
1395
911
  console.log(`\nResolved ${resolved.size} lexicon(s). Regenerating types...`);
1396
912
  execSync('npx hatk generate types', { stdio: 'inherit', cwd: process.cwd() });
1397
913
  }
1398
- else if (command === 'schema') {
1399
- const config = await loadConfig(resolve('hatk.config.ts'));
1400
- const { initDatabase, getSchemaDump } = await import("./database/db.js");
1401
- const { createAdapter } = await import("./database/adapter-factory.js");
1402
- const { getDialect } = await import("./database/dialect.js");
1403
- const configDir2 = resolve('.');
1404
- const lexicons2 = loadLexicons(resolve(configDir2, 'lexicons'));
1405
- const collections2 = config.collections.length > 0 ? config.collections : discoverCollections(lexicons2);
1406
- const { schemas: schemas2, ddlStatements: ddl2 } = buildSchemas(lexicons2, collections2, getDialect(config.databaseEngine));
1407
- if (config.database !== ':memory:') {
1408
- mkdirSync(dirname(config.database), { recursive: true });
1409
- }
1410
- const { adapter: adapter2 } = await createAdapter(config.databaseEngine);
1411
- await initDatabase(adapter2, config.database, schemas2, ddl2);
1412
- console.log(await getSchemaDump());
1413
- }
1414
914
  else if (command === 'start') {
1415
915
  const mainPath = resolve(import.meta.dirname, 'main.js');
1416
916
  await spawnForward('npx', ['tsx', mainPath, 'hatk.config.ts']);
@@ -25,6 +25,8 @@ export declare function setRepoStatus(did: string, status: string, rev?: string,
25
25
  retryAfter?: number;
26
26
  handle?: string | null;
27
27
  }): Promise<void>;
28
+ /** Update the handle for a DID if it exists in _repos. */
29
+ export declare function updateRepoHandle(did: string, handle: string): Promise<void>;
28
30
  export declare function getRepoRev(did: string): Promise<string | null>;
29
31
  export declare function getRepoRetryInfo(did: string): Promise<{
30
32
  retryCount: number;
@@ -1 +1 @@
1
- {"version":3,"file":"db.d.ts","sourceRoot":"","sources":["../../src/database/db.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"db.d.ts","sourceRoot":"","sources":["../../src/database/db.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,4 @@
1
- import { toSnakeCase } from "./schema.js";
1
+ import { toSnakeCase, q } from "./schema.js";
2
2
  import { getSearchColumns, stripStopWords, getSearchPort, updateFtsRecord, deleteFtsRecord } from "./fts.js";
3
3
  import { emit, timer } from "../logger.js";
4
4
  import { OAUTH_DDL } from "../oauth/db.js";
@@ -354,6 +354,10 @@ export async function setRepoStatus(did, status, rev, opts) {
354
354
  await run(`INSERT OR IGNORE INTO _repos (did, status) VALUES ($1, $2)`, [did, status]);
355
355
  }
356
356
  }
357
+ /** Update the handle for a DID if it exists in _repos. */
358
+ export async function updateRepoHandle(did, handle) {
359
+ await run(`UPDATE _repos SET handle = $1 WHERE did = $2`, [handle, did]);
360
+ }
357
361
  export async function getRepoRev(did) {
358
362
  const rows = await all(`SELECT rev FROM _repos WHERE did = $1`, [did]);
359
363
  return rows[0]?.rev ?? null;
@@ -508,7 +512,7 @@ export function buildInsertOp(collection, uri, cid, authorDid, record) {
508
512
  else if (col.originalName.endsWith('__cid') && record[col.originalName.replace('__cid', '')]) {
509
513
  rawValue = record[col.originalName.replace('__cid', '')].cid;
510
514
  }
511
- colNames.push(col.name);
515
+ colNames.push(q(col.name));
512
516
  placeholders.push(`$${paramIdx++}`);
513
517
  if (rawValue === undefined || rawValue === null) {
514
518
  values.push(null);
@@ -542,7 +546,7 @@ export async function insertRecord(collection, uri, cid, authorDid, record) {
542
546
  const values = [uri, authorDid];
543
547
  let idx = 3;
544
548
  for (const col of child.columns) {
545
- colNames.push(col.name);
549
+ colNames.push(q(col.name));
546
550
  placeholders.push(`$${idx++}`);
547
551
  const raw = item[col.originalName];
548
552
  if (raw === undefined || raw === null) {
@@ -581,7 +585,7 @@ export async function insertRecord(collection, uri, cid, authorDid, record) {
581
585
  const values = [uri, authorDid];
582
586
  let idx = 3;
583
587
  for (const col of branch.columns) {
584
- colNames.push(col.name);
588
+ colNames.push(q(col.name));
585
589
  placeholders.push(`$${idx++}`);
586
590
  const raw = item[col.originalName];
587
591
  if (raw === undefined || raw === null) {
@@ -605,7 +609,7 @@ export async function insertRecord(collection, uri, cid, authorDid, record) {
605
609
  const values = [uri, authorDid];
606
610
  let idx = 3;
607
611
  for (const col of branch.columns) {
608
- colNames.push(col.name);
612
+ colNames.push(q(col.name));
609
613
  placeholders.push(`$${idx++}`);
610
614
  const raw = branchData[col.originalName];
611
615
  if (raw === undefined || raw === null) {
@@ -704,7 +708,7 @@ export async function bulkInsertRecords(records) {
704
708
  if (!schema)
705
709
  continue;
706
710
  const stagingTable = `_staging_${collection.replace(/\./g, '_')}`;
707
- const allCols = ['uri', 'cid', 'did', 'indexed_at', ...schema.columns.map((c) => c.name)];
711
+ const allCols = ['uri', 'cid', 'did', 'indexed_at', ...schema.columns.map((c) => q(c.name))];
708
712
  const colDefs = [
709
713
  'uri TEXT',
710
714
  'cid TEXT',
@@ -713,7 +717,7 @@ export async function bulkInsertRecords(records) {
713
717
  ...schema.columns.map((c) => {
714
718
  const t = c.sqlType;
715
719
  // Use TEXT for timestamp columns in staging (will cast on merge)
716
- return `${c.name} ${t === 'TIMESTAMP' || t === 'TIMESTAMPTZ' ? 'TEXT' : t}`;
720
+ return `${q(c.name)} ${t === 'TIMESTAMP' || t === 'TIMESTAMPTZ' ? 'TEXT' : t}`;
717
721
  }),
718
722
  ];
719
723
  await port.execute(`DROP TABLE IF EXISTS ${stagingTable}`, []);
@@ -736,7 +740,7 @@ export async function bulkInsertRecords(records) {
736
740
  await inserter.close();
737
741
  // Merge into target, filtering rows that would violate NOT NULL
738
742
  const selectCols = allCols.map((name) => {
739
- const col = schema.columns.find((c) => c.name === name);
743
+ const col = schema.columns.find((c) => q(c.name) === name);
740
744
  if (name === 'indexed_at' || (col && (col.sqlType === 'TIMESTAMP' || col.sqlType === 'TIMESTAMPTZ'))) {
741
745
  return `${dialect.tryCastTimestamp(name)} AS ${name}`;
742
746
  }
@@ -746,10 +750,10 @@ export async function bulkInsertRecords(records) {
746
750
  for (const col of schema.columns) {
747
751
  if (col.notNull) {
748
752
  if (col.sqlType === 'TIMESTAMP' || col.sqlType === 'TIMESTAMPTZ') {
749
- notNullChecks.push(`${dialect.tryCastTimestamp(col.name)} IS NOT NULL`);
753
+ notNullChecks.push(`${dialect.tryCastTimestamp(q(col.name))} IS NOT NULL`);
750
754
  }
751
755
  else {
752
- notNullChecks.push(`${col.name} IS NOT NULL`);
756
+ notNullChecks.push(`${q(col.name)} IS NOT NULL`);
753
757
  }
754
758
  }
755
759
  }
@@ -764,10 +768,10 @@ export async function bulkInsertRecords(records) {
764
768
  'parent_did TEXT',
765
769
  ...child.columns.map((c) => {
766
770
  const t = c.sqlType;
767
- return `${c.name} ${t === 'TIMESTAMP' || t === 'TIMESTAMPTZ' ? 'TEXT' : t}`;
771
+ return `${q(c.name)} ${t === 'TIMESTAMP' || t === 'TIMESTAMPTZ' ? 'TEXT' : t}`;
768
772
  }),
769
773
  ];
770
- const childAllCols = ['parent_uri', 'parent_did', ...child.columns.map((c) => c.name)];
774
+ const childAllCols = ['parent_uri', 'parent_did', ...child.columns.map((c) => q(c.name))];
771
775
  await port.execute(`DROP TABLE IF EXISTS ${childStagingTable}`, []);
772
776
  await port.execute(`CREATE TABLE ${childStagingTable} (${childColDefs.join(', ')})`, []);
773
777
  const childInserter = await port.createBulkInserter(childStagingTable, childAllCols);
@@ -793,7 +797,7 @@ export async function bulkInsertRecords(records) {
793
797
  const uriPlaceholders = recs.map((_, i) => `$${i + 1}`).join(',');
794
798
  await port.execute(`DELETE FROM ${child.tableName} WHERE parent_uri IN (${uriPlaceholders})`, recs.map((r) => r.uri));
795
799
  const childSelectCols = childAllCols.map((name) => {
796
- const col = child.columns.find((c) => c.name === name);
800
+ const col = child.columns.find((c) => q(c.name) === name);
797
801
  if (col && (col.sqlType === 'TIMESTAMP' || col.sqlType === 'TIMESTAMPTZ')) {
798
802
  return `${dialect.tryCastTimestamp(name)} AS ${name}`;
799
803
  }
@@ -811,10 +815,10 @@ export async function bulkInsertRecords(records) {
811
815
  'parent_did TEXT',
812
816
  ...branch.columns.map((c) => {
813
817
  const t = c.sqlType;
814
- return `${c.name} ${t === 'TIMESTAMP' || t === 'TIMESTAMPTZ' ? 'TEXT' : t}`;
818
+ return `${q(c.name)} ${t === 'TIMESTAMP' || t === 'TIMESTAMPTZ' ? 'TEXT' : t}`;
815
819
  }),
816
820
  ];
817
- const branchAllCols = ['parent_uri', 'parent_did', ...branch.columns.map((c) => c.name)];
821
+ const branchAllCols = ['parent_uri', 'parent_did', ...branch.columns.map((c) => q(c.name))];
818
822
  await port.execute(`DROP TABLE IF EXISTS ${branchStagingTable}`, []);
819
823
  await port.execute(`CREATE TABLE ${branchStagingTable} (${branchColDefs.join(', ')})`, []);
820
824
  const branchInserter = await port.createBulkInserter(branchStagingTable, branchAllCols);
@@ -860,7 +864,7 @@ export async function bulkInsertRecords(records) {
860
864
  const uriPlaceholders = recs.map((_, i) => `$${i + 1}`).join(',');
861
865
  await port.execute(`DELETE FROM ${branch.tableName} WHERE parent_uri IN (${uriPlaceholders})`, recs.map((r) => r.uri));
862
866
  const branchSelectCols = branchAllCols.map((name) => {
863
- const col = branch.columns.find((c) => c.name === name);
867
+ const col = branch.columns.find((c) => q(c.name) === name);
864
868
  if (col && (col.sqlType === 'TIMESTAMP' || col.sqlType === 'TIMESTAMPTZ')) {
865
869
  return `${dialect.tryCastTimestamp(name)} AS ${name}`;
866
870
  }
@@ -1138,14 +1142,14 @@ export async function searchRecords(collection, query, opts = {}) {
1138
1142
  const remaining = limit - bm25Results.length;
1139
1143
  const jwFn = dialect.jaroWinklerSimilarity;
1140
1144
  const simExprs = [
1141
- ...textCols.map((c) => `${jwFn}(lower(t.${c.name}), lower($1))`),
1145
+ ...textCols.map((c) => `${jwFn}(lower(t.${q(c.name)}), lower($1))`),
1142
1146
  `${jwFn}(lower(r.handle), lower($1))`,
1143
1147
  ];
1144
1148
  // Include child table TEXT columns via correlated subquery
1145
1149
  for (const child of schema.children) {
1146
1150
  for (const col of child.columns) {
1147
1151
  if (col.sqlType === 'TEXT') {
1148
- simExprs.push(`COALESCE((SELECT MAX(${jwFn}(lower(c.${col.name}), lower($1))) FROM ${child.tableName} c WHERE c.parent_uri = t.uri), 0)`);
1152
+ simExprs.push(`COALESCE((SELECT MAX(${jwFn}(lower(c.${q(col.name)}), lower($1))) FROM ${child.tableName} c WHERE c.parent_uri = t.uri), 0)`);
1149
1153
  }
1150
1154
  }
1151
1155
  }
@@ -1,5 +1,5 @@
1
1
  import { getSchema, runSQL, getSqlDialect, querySQL } from "./db.js";
2
- import { getLexicon } from "./schema.js";
2
+ import { getLexicon, q } from "./schema.js";
3
3
  import { emit, timer } from "../logger.js";
4
4
  /**
5
5
  * Resolve a lexicon ref like "#artist" to its definition.
@@ -103,7 +103,7 @@ function computeFtsSchema(collection) {
103
103
  const searchColNames = [];
104
104
  for (const col of schema.columns) {
105
105
  if (col.sqlType === 'TEXT') {
106
- selectExprs.push(`t.${col.name}`);
106
+ selectExprs.push(`t.${q(col.name)}`);
107
107
  searchColNames.push(col.name);
108
108
  }
109
109
  else if (col.isJson && record?.properties) {
@@ -111,7 +111,7 @@ function computeFtsSchema(collection) {
111
111
  if (prop?.type === 'blob')
112
112
  continue; // skip blobs
113
113
  if (prop && lexicon) {
114
- const derived = jsonSearchColumns(`t.${col.name}`, prop, lexicon, dialect);
114
+ const derived = jsonSearchColumns(`t.${q(col.name)}`, prop, lexicon, dialect);
115
115
  if (derived.length > 0) {
116
116
  for (const d of derived) {
117
117
  selectExprs.push(`${d.expr} AS ${d.alias}`);
@@ -121,7 +121,7 @@ function computeFtsSchema(collection) {
121
121
  }
122
122
  }
123
123
  // Fallback: cast JSON to TEXT
124
- selectExprs.push(`CAST(t.${col.name} AS TEXT) AS ${col.name}`);
124
+ selectExprs.push(`CAST(t.${q(col.name)} AS TEXT) AS ${q(col.name)}`);
125
125
  searchColNames.push(col.name);
126
126
  }
127
127
  }
@@ -130,7 +130,7 @@ function computeFtsSchema(collection) {
130
130
  for (const col of child.columns) {
131
131
  if (col.sqlType === 'TEXT') {
132
132
  const alias = `${child.fieldName}_${col.name}`;
133
- const agg = dialect.stringAgg(`c.${col.name}`, "' '");
133
+ const agg = dialect.stringAgg(`c.${q(col.name)}`, "' '");
134
134
  selectExprs.push(`(SELECT ${agg} FROM ${child.tableName} c WHERE c.parent_uri = t.uri) AS ${alias}`);
135
135
  searchColNames.push(alias);
136
136
  }
@@ -142,7 +142,7 @@ function computeFtsSchema(collection) {
142
142
  for (const col of branch.columns) {
143
143
  if (col.sqlType === 'TEXT') {
144
144
  const alias = `${union.fieldName}_${branch.branchName}_${col.name}`;
145
- const agg = dialect.stringAgg(`c.${col.name}`, "' '");
145
+ const agg = dialect.stringAgg(`c.${q(col.name)}`, "' '");
146
146
  selectExprs.push(`(SELECT ${agg} FROM ${branch.tableName} c WHERE c.parent_uri = t.uri) AS ${alias}`);
147
147
  searchColNames.push(alias);
148
148
  }
@@ -35,6 +35,7 @@ export interface ChildTableSchema {
35
35
  columns: ColumnDef[];
36
36
  }
37
37
  export declare function toSnakeCase(str: string): string;
38
+ export declare function q(name: string): string;
38
39
  export declare function loadLexicons(lexiconsDir: string): Map<string, any>;
39
40
  /**
40
41
  * Discover collections by scanning lexicons for record-type definitions.
@@ -1 +1 @@
1
- {"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../../src/database/schema.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAA;AAG9C,MAAM,WAAW,SAAS;IACxB,IAAI,EAAE,MAAM,CAAA;IACZ,YAAY,EAAE,MAAM,CAAA;IACpB,OAAO,EAAE,MAAM,CAAA;IACf,OAAO,EAAE,OAAO,CAAA;IAChB,KAAK,EAAE,OAAO,CAAA;IACd,MAAM,EAAE,OAAO,CAAA;CAChB;AAED,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,MAAM,CAAA;IACZ,UAAU,EAAE,MAAM,CAAA;IAClB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,SAAS,EAAE,CAAA;IACpB,OAAO,EAAE,OAAO,CAAA;IAChB,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,YAAY,CAAC,EAAE,MAAM,CAAA;CACtB;AAED,MAAM,WAAW,gBAAgB;IAC/B,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,iBAAiB,EAAE,CAAA;CAC9B;AAED,MAAM,WAAW,WAAW;IAC1B,UAAU,EAAE,MAAM,CAAA;IAClB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,SAAS,EAAE,CAAA;IACpB,UAAU,EAAE,MAAM,EAAE,CAAA;IACpB,QAAQ,EAAE,gBAAgB,EAAE,CAAA;IAC5B,MAAM,EAAE,gBAAgB,EAAE,CAAA;CAC3B;AAED,MAAM,WAAW,gBAAgB;IAC/B,gBAAgB,EAAE,MAAM,CAAA;IACxB,SAAS,EAAE,MAAM,CAAA;IACjB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,SAAS,EAAE,CAAA;CACrB;AAGD,wBAAgB,WAAW,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAE/C;AA+CD,wBAAgB,YAAY,CAAC,WAAW,EAAE,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,CASlE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,MAAM,EAAE,CASxE;AAID,wBAAgB,aAAa,CAAC,QAAQ,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAI9D;AAED,wBAAgB,UAAU,CAAC,IAAI,EAAE,MAAM,GAAG,GAAG,GAAG,SAAS,CAExD;AAED,wBAAgB,cAAc,IAAI,KAAK,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,GAAG,CAAA;CAAE,CAAC,CAEtE;AAED,iFAAiF;AACjF,wBAAgB,eAAe,IAAI,GAAG,EAAE,CAEvC;AAyHD,wBAAgB,mBAAmB,CACjC,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,GAAG,EACZ,QAAQ,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,EAC3B,OAAO,GAAE,UAA2B,GACnC,WAAW,CA+Gb;AAGD,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,WAAW,EAAE,OAAO,GAAE,UAA2B,GAAG,MAAM,CAoExG;AAED;;;GAGG;AACH,wBAAgB,YAAY,CAC1B,QAAQ,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,EAC1B,WAAW,EAAE,MAAM,EAAE,EACrB,OAAO,GAAE,UAA2B,GACnC;IAAE,OAAO,EAAE,WAAW,EAAE,CAAC;IAAC,aAAa,EAAE,MAAM,EAAE,CAAA;CAAE,CA2BrD"}
1
+ {"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../../src/database/schema.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAA;AAG9C,MAAM,WAAW,SAAS;IACxB,IAAI,EAAE,MAAM,CAAA;IACZ,YAAY,EAAE,MAAM,CAAA;IACpB,OAAO,EAAE,MAAM,CAAA;IACf,OAAO,EAAE,OAAO,CAAA;IAChB,KAAK,EAAE,OAAO,CAAA;IACd,MAAM,EAAE,OAAO,CAAA;CAChB;AAED,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,MAAM,CAAA;IACZ,UAAU,EAAE,MAAM,CAAA;IAClB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,SAAS,EAAE,CAAA;IACpB,OAAO,EAAE,OAAO,CAAA;IAChB,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,YAAY,CAAC,EAAE,MAAM,CAAA;CACtB;AAED,MAAM,WAAW,gBAAgB;IAC/B,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,iBAAiB,EAAE,CAAA;CAC9B;AAED,MAAM,WAAW,WAAW;IAC1B,UAAU,EAAE,MAAM,CAAA;IAClB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,SAAS,EAAE,CAAA;IACpB,UAAU,EAAE,MAAM,EAAE,CAAA;IACpB,QAAQ,EAAE,gBAAgB,EAAE,CAAA;IAC5B,MAAM,EAAE,gBAAgB,EAAE,CAAA;CAC3B;AAED,MAAM,WAAW,gBAAgB;IAC/B,gBAAgB,EAAE,MAAM,CAAA;IACxB,SAAS,EAAE,MAAM,CAAA;IACjB,SAAS,EAAE,MAAM,CAAA;IACjB,OAAO,EAAE,SAAS,EAAE,CAAA;CACrB;AAGD,wBAAgB,WAAW,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAE/C;AAGD,wBAAgB,CAAC,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAEtC;AA+CD,wBAAgB,YAAY,CAAC,WAAW,EAAE,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,CASlE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,MAAM,EAAE,CASxE;AAID,wBAAgB,aAAa,CAAC,QAAQ,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAI9D;AAED,wBAAgB,UAAU,CAAC,IAAI,EAAE,MAAM,GAAG,GAAG,GAAG,SAAS,CAExD;AAED,wBAAgB,cAAc,IAAI,KAAK,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,GAAG,CAAA;CAAE,CAAC,CAEtE;AAED,iFAAiF;AACjF,wBAAgB,eAAe,IAAI,GAAG,EAAE,CAEvC;AAyHD,wBAAgB,mBAAmB,CACjC,IAAI,EAAE,MAAM,EACZ,OAAO,EAAE,GAAG,EACZ,QAAQ,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,EAC3B,OAAO,GAAE,UAA2B,GACnC,WAAW,CA+Gb;AAGD,wBAAgB,sBAAsB,CAAC,MAAM,EAAE,WAAW,EAAE,OAAO,GAAE,UAA2B,GAAG,MAAM,CAoExG;AAED;;;GAGG;AACH,wBAAgB,YAAY,CAC1B,QAAQ,EAAE,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,EAC1B,WAAW,EAAE,MAAM,EAAE,EACrB,OAAO,GAAE,UAA2B,GACnC;IAAE,OAAO,EAAE,WAAW,EAAE,CAAC;IAAC,aAAa,EAAE,MAAM,EAAE,CAAA;CAAE,CA2BrD"}
@@ -5,6 +5,10 @@ import { DUCKDB_DIALECT } from "./dialect.js";
5
5
  export function toSnakeCase(str) {
6
6
  return str.replace(/([A-Z])/g, '_$1').toLowerCase();
7
7
  }
8
+ // Quote a column name to avoid conflicts with SQL reserved words
9
+ export function q(name) {
10
+ return `"${name}"`;
11
+ }
8
12
  function mapType(prop, dialect) {
9
13
  if (prop.type === 'string') {
10
14
  if (prop.format === 'datetime')
@@ -312,7 +316,7 @@ export function generateCreateTableSQL(schema, dialect = DUCKDB_DIALECT) {
312
316
  ];
313
317
  for (const col of schema.columns) {
314
318
  const nullable = col.notNull ? ' NOT NULL' : '';
315
- lines.push(` ${col.name} ${col.sqlType}${nullable}`);
319
+ lines.push(` ${q(col.name)} ${col.sqlType}${nullable}`);
316
320
  }
317
321
  const createTable = `CREATE TABLE IF NOT EXISTS ${schema.tableName} (\n${lines.join(',\n')}\n);`;
318
322
  const prefix = schema.collection.replace(/\./g, '_');
@@ -322,7 +326,7 @@ export function generateCreateTableSQL(schema, dialect = DUCKDB_DIALECT) {
322
326
  ];
323
327
  // Index ref columns for hydration lookups
324
328
  for (const refCol of schema.refColumns) {
325
- indexes.push(`CREATE INDEX IF NOT EXISTS idx_${prefix}_${refCol} ON ${schema.tableName}(${refCol});`);
329
+ indexes.push(`CREATE INDEX IF NOT EXISTS idx_${prefix}_${refCol} ON ${schema.tableName}(${q(refCol)});`);
326
330
  }
327
331
  // Child table DDL
328
332
  const childDDL = [];
@@ -330,7 +334,7 @@ export function generateCreateTableSQL(schema, dialect = DUCKDB_DIALECT) {
330
334
  const childLines = [' parent_uri TEXT NOT NULL', ' parent_did TEXT NOT NULL'];
331
335
  for (const col of child.columns) {
332
336
  const nullable = col.notNull ? ' NOT NULL' : '';
333
- childLines.push(` ${col.name} ${col.sqlType}${nullable}`);
337
+ childLines.push(` ${q(col.name)} ${col.sqlType}${nullable}`);
334
338
  }
335
339
  childDDL.push(`CREATE TABLE IF NOT EXISTS ${child.tableName} (\n${childLines.join(',\n')}\n);`);
336
340
  const childPrefix = `${prefix}__${toSnakeCase(child.fieldName)}`;
@@ -339,7 +343,7 @@ export function generateCreateTableSQL(schema, dialect = DUCKDB_DIALECT) {
339
343
  for (const col of child.columns) {
340
344
  if (col.isJson || col.sqlType === 'BLOB')
341
345
  continue;
342
- childDDL.push(`CREATE INDEX IF NOT EXISTS idx_${childPrefix}_${col.name} ON ${child.tableName}(${col.name});`);
346
+ childDDL.push(`CREATE INDEX IF NOT EXISTS idx_${childPrefix}_${col.name} ON ${child.tableName}(${q(col.name)});`);
343
347
  }
344
348
  }
345
349
  // Union branch table DDL
@@ -348,7 +352,7 @@ export function generateCreateTableSQL(schema, dialect = DUCKDB_DIALECT) {
348
352
  const branchLines = [' parent_uri TEXT NOT NULL', ' parent_did TEXT NOT NULL'];
349
353
  for (const col of branch.columns) {
350
354
  const nullable = col.notNull ? ' NOT NULL' : '';
351
- branchLines.push(` ${col.name} ${col.sqlType}${nullable}`);
355
+ branchLines.push(` ${q(col.name)} ${col.sqlType}${nullable}`);
352
356
  }
353
357
  childDDL.push(`CREATE TABLE IF NOT EXISTS ${branch.tableName} (\n${branchLines.join(',\n')}\n);`);
354
358
  const branchPrefix = branch.tableName.replace(/"/g, '').replace(/\./g, '_');
@@ -357,7 +361,7 @@ export function generateCreateTableSQL(schema, dialect = DUCKDB_DIALECT) {
357
361
  for (const col of branch.columns) {
358
362
  if (col.isJson || col.sqlType === 'BLOB')
359
363
  continue;
360
- childDDL.push(`CREATE INDEX IF NOT EXISTS idx_${branchPrefix}_${col.name} ON ${branch.tableName}(${col.name});`);
364
+ childDDL.push(`CREATE INDEX IF NOT EXISTS idx_${branchPrefix}_${col.name} ON ${branch.tableName}(${q(col.name)});`);
361
365
  }
362
366
  }
363
367
  }
@@ -1 +1 @@
1
- {"version":3,"file":"indexer.d.ts","sourceRoot":"","sources":["../src/indexer.ts"],"names":[],"mappings":"AAwJA;;;;;;;GAOG;AACH,iEAAiE;AACjE,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAGxD;AAED,wBAAsB,mBAAmB,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,SAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CA4EjF;AAED,8CAA8C;AAC9C,UAAU,WAAW;IACnB,QAAQ,EAAE,MAAM,CAAA;IAChB,WAAW,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IACxB,iBAAiB,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IAC/B,WAAW,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IACzB,MAAM,CAAC,EAAE,MAAM,GAAG,IAAI,CAAA;IACtB,YAAY,EAAE,MAAM,CAAA;IACpB,UAAU,EAAE,MAAM,CAAA;IAClB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,kBAAkB,CAAC,EAAE,MAAM,CAAA;CAC5B;AAyBD;;;;;;;;;GASG;AACH,wBAAsB,YAAY,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,SAAS,CAAC,CAmDxE"}
1
+ {"version":3,"file":"indexer.d.ts","sourceRoot":"","sources":["../src/indexer.ts"],"names":[],"mappings":"AAyJA;;;;;;;GAOG;AACH,iEAAiE;AACjE,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAGxD;AAED,wBAAsB,mBAAmB,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,SAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CA4EjF;AAED,8CAA8C;AAC9C,UAAU,WAAW;IACnB,QAAQ,EAAE,MAAM,CAAA;IAChB,WAAW,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IACxB,iBAAiB,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IAC/B,WAAW,CAAC,EAAE,GAAG,CAAC,MAAM,CAAC,CAAA;IACzB,MAAM,CAAC,EAAE,MAAM,GAAG,IAAI,CAAA;IACtB,YAAY,EAAE,MAAM,CAAA;IACpB,UAAU,EAAE,MAAM,CAAA;IAClB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,kBAAkB,CAAC,EAAE,MAAM,CAAA;CAC5B;AAyBD;;;;;;;;;GASG;AACH,wBAAsB,YAAY,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,SAAS,CAAC,CAmDxE"}
package/dist/indexer.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import { cborDecode } from "./cbor.js";
2
2
  import { parseCarFrame } from "./car.js";
3
- import { insertRecord, deleteRecord, setCursor, setRepoStatus, getRepoRetryInfo, listAllRepoStatuses, getDatabasePort, } from "./database/db.js";
3
+ import { insertRecord, deleteRecord, setCursor, setRepoStatus, getRepoRetryInfo, listAllRepoStatuses, getDatabasePort, updateRepoHandle, } from "./database/db.js";
4
4
  import { backfillRepo } from "./backfill.js";
5
5
  import { rebuildAllIndexes } from "./database/fts.js";
6
6
  import { log, emit, timer } from "./logger.js";
@@ -260,7 +260,7 @@ export async function startIndexer(opts) {
260
260
  }
261
261
  log(`[indexer] Warmed repo status cache with ${statuses.length} entries`);
262
262
  }
263
- startMemoryDiagnostics();
263
+ // startMemoryDiagnostics()
264
264
  let wsUrl = `${relayUrl}/xrpc/com.atproto.sync.subscribeRepos`;
265
265
  if (cursor) {
266
266
  wsUrl += `?cursor=${cursor}`;
@@ -297,6 +297,15 @@ export async function startIndexer(opts) {
297
297
  function processMessage(bytes, collections) {
298
298
  const header = cborDecode(bytes, 0);
299
299
  const body = cborDecode(bytes, header.offset);
300
+ // Handle identity events (handle changes)
301
+ if (header.value.t === '#identity') {
302
+ const did = body.value.did;
303
+ const handle = body.value.handle;
304
+ if (did && handle && repoStatusCache.has(did)) {
305
+ updateRepoHandle(did, handle).catch(() => { });
306
+ }
307
+ return;
308
+ }
300
309
  if (header.value.op !== 1 || header.value.t !== '#commit')
301
310
  return;
302
311
  if (!body.value.blocks || !body.value.ops)
package/dist/main.js CHANGED
@@ -34,14 +34,9 @@ import { parseSessionCookie, getSessionCookieName } from "./oauth/session.js";
34
34
  import { loadOnLoginHook } from "./hooks.js";
35
35
  import { initSetup } from "./setup.js";
36
36
  import { initServer } from "./server-init.js";
37
- function logMemory(phase) {
38
- const mem = process.memoryUsage();
39
- log(`[mem] ${phase}: heap=${Math.round(mem.heapUsed / 1024 / 1024)}MB rss=${Math.round(mem.rss / 1024 / 1024)}MB external=${Math.round(mem.external / 1024 / 1024)}MB arrayBuffers=${Math.round(mem.arrayBuffers / 1024 / 1024)}MB`);
40
- }
41
37
  const configPath = process.argv[2] || 'hatk.config.ts';
42
38
  const configDir = dirname(resolve(configPath));
43
39
  registerHatkResolveHook();
44
- logMemory('startup');
45
40
  // 1. Load config
46
41
  const config = await loadConfig(configPath);
47
42
  configureRelay(config.relay);
@@ -82,7 +77,6 @@ if (config.database !== ':memory:') {
82
77
  const { adapter, searchPort } = await createAdapter(config.databaseEngine);
83
78
  setSearchPort(searchPort);
84
79
  await initDatabase(adapter, config.database, schemas, ddlStatements);
85
- logMemory('after-db-init');
86
80
  log(`[main] Database initialized (${config.databaseEngine}, ${config.database === ':memory:' ? 'in-memory' : config.database})`);
87
81
  // Auto-migrate schema if lexicons changed
88
82
  const migrationChanges = await migrateSchema(schemas);
@@ -138,7 +132,6 @@ if (config.oauth) {
138
132
  await initOAuth(config.oauth, config.plc, config.relay);
139
133
  log(`[main] OAuth initialized (issuer: ${config.oauth.issuer})`);
140
134
  }
141
- logMemory('before-server');
142
135
  // 5. Start server immediately (don't wait for backfill)
143
136
  const collectionSet = new Set(collections);
144
137
  const backfillOpts = {
@@ -157,7 +150,6 @@ function runBackfillAndRestart() {
157
150
  })
158
151
  .then((recordCount) => {
159
152
  if (recordCount > 0 && !process.env.DEV_MODE) {
160
- logMemory('after-backfill');
161
153
  log('[main] Restarting to reclaim memory...');
162
154
  process.exit(1);
163
155
  }
@@ -193,7 +185,6 @@ log(` Collections: ${collections.join(', ')}`);
193
185
  log(` Feeds: ${listFeeds()
194
186
  .map((f) => f.name)
195
187
  .join(', ')}`);
196
- logMemory('after-server');
197
188
  // 6. Start indexer with cursor
198
189
  const cursor = await getCursor('relay');
199
190
  startIndexer({
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hatk/hatk",
3
- "version": "0.0.1-alpha.43",
3
+ "version": "0.0.1-alpha.45",
4
4
  "license": "MIT",
5
5
  "bin": {
6
6
  "hatk": "dist/cli.js"