8000 GitHub - janwilmake/dorm: Unlimited SQLite DBs Directly In Your Worker - OSS Turso Alternative
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

Unlimited SQLite DBs Directly In Your Worker - OSS Turso Alternative

License

Notifications You must be signed in to change notification settings

janwilmake/dorm

Repository files navigation

πŸ›οΈ DORM - Unlimited SQLite DBs Directly In Your Worker

janwilmake/dorm context

DORM makes building multi-tenant applications on Cloudflare ridiculously easy by letting you:

  1. Create unlimited SQLite DBs on the fly (up to 10GB each)
  2. Query them directly from anywhere in your worker (not just inside DOs)
  3. Explore and manage your data with built-in Outerbase integration
  4. Migrate once, everywhere with built-in JIT migration-support

Perfect for SaaS applications, user profiles, rate limiting, or any case where you need isolated data stores that are lightning fast at the edge.

Demo app: https://dorm.wilmake.com | Give me a like/share on X

⚑ Key Benefits vs Alternatives

Feature Vanilla DOs DORM πŸ›οΈ D1 Turso
Multi-tenant βœ… Unlimited βœ… Unlimited ❌ One DB Pricey
Query from worker ❌ Only in DO βœ… βœ… βœ…
Data Explorer ❌ βœ… Outerbase βœ… βœ…
Migrations ❌ βœ… βœ… βœ…
Edge Performance Closest to user Closest to user Global edge Global edge
Developer Experience ❌ Verbose, complex βœ… Clean, low verbosity βœ… Good Good, not CF native

See Turso vs DORM and DORM vs D1 for a more in-depth comparison with these alternatives. Also, see the pricing comparison here

πŸš€ Quick Start

Check out the live TODO app demo showing multi-tenant capabilities.

Install dormroom as dependency...

npm i dormroom@next

...or fork this repo, and use template.ts as a starting point.

View your data with Outerbase Studio:

Local Development:

  1. Install: https://github.com/outerbase/studio
  2. Create starbase connecting to: http://localhost:8787/db (or your port, your prefix)

Production: Use https://studio.outerbase.com

πŸ”₯ Top Use Cases

1. Multi-tenant SaaS applications

Create a separate database for each customer/organization:

const client = createClient({
  doNamespace: env.MY_DO_NAMESPACE,
  version: "v1",
  name: `tenant:${tenantId}`, // One DB per tenant
  migrations: {
    1: [
      /* Your sql statements to create tables or alter them. Migrations are applied just once. */
    ],
  },
});

2. Global user profiles with edge latency

Store user data closest to where they access it:

const client = createClient({
  doNamespace: env.MY_DO_NAMESPACE,
  version: "v1",
  name: `user:${userId}`, // One DB per user
});

3. Data aggregation with mirroring

Mirror tenant operations to a central database for analytics:

const client = createClient({
  doNamespace: env.MY_DO_NAMESPACE,
  name: `tenant:${tenantId}`,
  mirrorName: "aggregate", // Mirror operations to an aggregate DB
});

When creating mirrors, be wary of naming collisions and database size:

  • Unique id collisions: when you use auto-increment and unique IDs (or columns in general), you may run into the issue that the value is unique in the main DB, but not in the mirror. This is currently not handled and your mirror query will silently fail! To prevent this issue I recommend not using auto increment or random in the query, and generate unique IDs beforehand when doing a query, so the data remains the same.

  • Size: You have max 10GB. When executing a query, you can choose to use skipMirror:true to not perform the same query in the mirror db, to save on size for DBs with larger tables.

✨ Key Features

  • Direct SQL anywhere: No need to write DO handler code - query from your worker
  • Outerbase integration: Explore and manage your data with built-in tools
  • JSON Schema support: Define tables using JSON Schema with automatic SQL translation
  • Streaming queries: Efficient cursor implementation for large result sets
  • JIT Migrations: Migrations are applied when needed, just once, right before a DO gets accessed.
  • Data mirroring: Mirror operations to aggregate databases for analytics
  • Low verbosity: Clean API that hides Durable Object complexity

πŸ› οΈ Advanced Features

JSONSchema to SQL Conversion

import { jsonSchemaToSql, TableSchema } from "dormroom";

const userSchema: TableSchema = {
  $id: "users",
  properties: {
    id: { type: "string", "x-dorm-primary-key": true },
    name: { type: "string", maxLength: 100 },
    email: { type: "string", "x-dorm-unique": true },
  },
  required: ["id", "name"],
};

const sqlStatements = jsonSchemaToSql(userSchema);

Streaming Query Results

// Get a cursor for working with large datasets
const cursor = client.exec<UserRecord>("SELECT * FROM users");

// Stream results without loading everything into memory
for await (const user of cursor) {
  // Process each user individually
}

REST API for Data Access

// Access your database via REST API
const middlewareResponse = await client.middleware(request, {
  prefix: "/api/db",
  secret: "my-secret-key",
});

πŸ“Š Performance & Limitations

  • βœ… Nearly zero overhead: Thin abstraction over DO's SQLite
  • βœ… Edge-localized: Data stored closest to where it's accessed
  • βœ… Up to 10GB per DB: Sufficient for most application needs
  • ❓ Localhost isn't easily accessible YET in https://studio.outerbase.com so you need to deploy first, use a tunnel, or run the outerbase client on localhost.

πŸ”— Links & Resources

🚧 Status: Beta

DORM is currently in beta. API may change, but core functionality is stable.

Deploy to Cloudflare Workers

About

Unlimited SQLite DBs Directly In Your Worker - OSS Turso Alternative

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published
0