npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@eddacraft/kindling-store-sqljs

v0.1.2

Published

sql.js (WASM) persistence layer for Kindling - browser and cross-platform compatible

Downloads

259

Readme

@eddacraft/kindling-store-sqljs

WASM-based SQLite persistence layer for Kindling using sql.js. This package provides browser and cross-platform compatibility as a drop-in replacement for @eddacraft/kindling-store-sqlite.

When to Use

Use this package when:

  • Running in a browser environment
  • Running in environments without native compilation support (e.g., some serverless platforms)
  • Need a portable solution that works everywhere JavaScript runs

Use @eddacraft/kindling-store-sqlite instead when:

  • Running in Node.js with native compilation available
  • Performance is critical (native is 2-10x faster)
  • Memory usage is a concern (sql.js loads entire DB into memory)

Installation

pnpm add @eddacraft/kindling-store-sqljs

Usage

Basic Usage

import { openDatabase, SqljsKindlingStore } from '@eddacraft/kindling-store-sqljs';

// Open database (async - needs to load WASM)
const db = await openDatabase();
const store = new SqljsKindlingStore(db);

// Use like any KindlingStore
store.insertObservation({
  id: 'obs_1',
  kind: 'tool_call',
  content: 'User ran npm install',
  provenance: { source: 'cli' },
  ts: Date.now(),
  scopeIds: { sessionId: 'session_1' },
  redacted: false,
});

With Browser Persistence (IndexedDB)

import {
  openDatabase,
  SqljsKindlingStore,
  IndexedDBPersistence,
} from '@eddacraft/kindling-store-sqljs';

const persistence = new IndexedDBPersistence({
  dbName: 'my-app', // IndexedDB database name
  storeName: 'databases', // Object store name
  key: 'kindling', // Key for this database
});

// Load existing data or start fresh
const existingData = await persistence.load();
const db = await openDatabase({ data: existingData });
const store = new SqljsKindlingStore(db);

// ... use store ...

// Save changes (call periodically or on important operations)
await persistence.save(db.export());

Custom WASM Location

By default, sql.js loads WASM from its CDN. For production, you should host the WASM files yourself:

const db = await openDatabase({
  locateFile: (file) => `/wasm/${file}`, // Your hosted path
});

Or bundle with your application:

const db = await openDatabase({
  locateFile: (file) => new URL(`./sql-wasm/${file}`, import.meta.url).href,
});

With KindlingService

import { KindlingService } from '@eddacraft/kindling-core';
import { LocalFtsProvider } from '@eddacraft/kindling-provider-local';
import { openDatabase, SqljsKindlingStore } from '@eddacraft/kindling-store-sqljs';

const db = await openDatabase();
const store = new SqljsKindlingStore(db);
const provider = new LocalFtsProvider(db);

const kindling = new KindlingService({
  store,
  provider,
});

// Now use kindling.openCapsule(), kindling.appendObservation(), etc.

API

Database Functions

openDatabase(options?)

Opens and initializes a Kindling database.

interface DatabaseOptions {
  data?: Uint8Array; // Initial database data
  locateFile?: (file: string) => string; // WASM file locator
  skipMigrations?: boolean; // Skip running migrations
  verbose?: boolean; // Enable logging
}

closeDatabase(db)

Closes a database connection.

exportDatabaseToBytes(db)

Exports the database to a Uint8Array for persistence.

Store Class

SqljsKindlingStore implements the KindlingStore interface from @eddacraft/kindling-core:

  • insertObservation(observation) - Insert an observation
  • createCapsule(capsule) - Create a capsule
  • closeCapsule(capsuleId, closedAt?, summaryId?) - Close a capsule
  • attachObservationToCapsule(capsuleId, observationId) - Link observation to capsule
  • insertSummary(summary) - Insert a summary
  • insertPin(pin) / deletePin(pinId) - Manage pins
  • getObservationById(id) - Get observation by ID
  • getCapsule(id) - Get capsule by ID
  • getOpenCapsuleForSession(sessionId) - Find open capsule
  • queryObservations(scopeIds?, fromTs?, toTs?, limit?) - Query observations
  • listActivePins(scopeIds?, now?) - List non-expired pins
  • transaction(fn) - Execute in transaction
  • exportDatabase(options?) - Export all data
  • importDatabase(dataset) - Import data

Persistence Adapters

IndexedDBPersistence

Browser persistence using IndexedDB.

const persistence = new IndexedDBPersistence({
  dbName: 'kindling',
  storeName: 'databases',
  key: 'main',
});

await persistence.save(data); // Save Uint8Array
await persistence.load(); // Load Uint8Array | undefined
await persistence.exists(); // Check if exists
await persistence.delete(); // Delete stored data

MemoryPersistence

In-memory persistence for testing.

const persistence = new MemoryPersistence();

Differences from store-sqlite

| Feature | store-sqlite | store-sqljs | | -------------- | ---------------- | -------------------- | | Environment | Node.js only | Browser + Node.js | | Performance | Native speed | 2-10x slower | | Memory | Memory-mapped | Entire DB in memory | | Persistence | Automatic (file) | Manual (export/save) | | WAL mode | Supported | Not supported | | Initialization | Synchronous | Asynchronous | | Bundle size | Native binary | ~1.5MB WASM |

FTS5 Support

FTS5 support depends on your sql.js build:

  • Standard sql.js: FTS5 is not included. The package auto-detects this and skips FTS migrations.
  • Custom sql.js build: You can compile sql.js with FTS5 enabled for full-text search support.

To explicitly control FTS behavior:

// Force FTS5 (will error if not available)
const db = await openDatabase({ enableFts: true });

// Explicitly disable FTS5
const db = await openDatabase({ enableFts: false });

// Auto-detect (default)
const db = await openDatabase();

When FTS5 is not available, you can still use the store - you just won't have full-text search capabilities. The @eddacraft/kindling-provider-local FTS provider won't work, but you can implement alternative retrieval strategies.

License

Apache-2.0