The ORM that shows its work

Type-safe queries that compile to SQL you can see, debug, and trust. Blocks UPDATE without WHERE at compile time. Built for developers who refuse to debug production at 2am.

Detailed description of ChameleonDB

ChameleonDB is a strongly-typed, graph-oriented database abstraction layer built for developers who demand control. Unlike traditional ORMs that hide SQL behind magic, ChameleonDB gives you full transparency: you write natural graph queries and always see the generated SQL before execution. Import existing PostgreSQL databases automatically, define type-safe schemas, and navigate relationships like user.posts without writing JOINs or facing N+1 problems. Catch errors at compile time—like DELETE without WHERE—with clear, actionable messages. Built with a Rust core and Go runtime (with more languages on the roadmap).

GitHub stars · Join 100+ developers · Discord community →

Your 2am self will thank you

Ever run UPDATE without WHERE in production? ChameleonDB blocks it at compile time.

Other ORMs (Runtime disaster)
// Runs. Wipes everything. Oops.
db.Update("User").
   Set("verified", true).
   Execute(ctx)

// ✓ Updated 1,847,392 rows
// Your database is now gone.
ChameleonDB (Compile error)
// Compiler blocks it
db.Update("User").
   Set("verified", true).
   Execute(ctx)

// ❌ Error: UPDATE requires Filter()
// Hint: Add .Filter("id", "eq", userId)
//    or .ForceUpdateAll() for bulk ops

ChameleonDB blocks dangerous operations at compile time, not 2am in production.

Detailed description of ChameleonDB

ChameleonDB is a schema-first database toolkit built for developers who demand control without magic. Unlike traditional ORMs that hide SQL behind abstraction layers, ChameleonDB gives you full transparency: you write type-safe queries in Go and always see the generated SQL before execution.

What makes it different: Immutable schema versioning with cryptographic hashing means every schema change is auditable and impossible to lose. Integrity modes (inspired by OS protection rings) control who can modify what and when. Safety features like blocking UPDATE/DELETE without WHERE prevent production disasters at compile time, not 2am.

Import existing PostgreSQL databases automatically, define relationships in a clean .cham DSL, and navigate relations like user.posts without writing JOINs or facing N+1 problems. Built with a Rust core (performance + safety) and Go runtime (ergonomics). Python and Node.js on the roadmap.

Requires PostgreSQL · Open Source (Apache 2.0) · Learn more →

From schema to queries in 30 seconds

1. Define your schema
entity User {
    id: uuid primary,
    email: string unique,
    posts: [Post] via author_id,
}

entity Post {
    id: uuid primary,
    title: string,
    author_id: uuid,
    author: User,
}
2. Write natural queries
// Get user with all posts
user := db.Query("User").
    Filter("email", "eq", "ana@mail.com").
    Include("posts").
    Execute(ctx)

// No N+1 queries
// No manual JOINs
// Just works
3. See what runs (always)
-- Main query
SELECT id, email 
FROM users 
WHERE email = 'ana@mail.com';

-- Eager load (efficient)
SELECT id, title 
FROM posts 
WHERE author_id IN (...);

Visualize your schema

Paste your schema and see the entity relationships as a diagram. Powered by Mermaid.js, validate your design before writing code.

Schema Visualizer Preview
Open Visualizer →

See your database design in real-time

Built for developers who want control

Type-Safe Schema Ready

Catch errors at compile-time. Rich error messages point you exactly where the problem is, with suggestions to fix it.

🔍

Full SQL Transparency Ready

Always see the generated SQL. Debug mode shows queries before execution. No magic, no surprises, full control.

🚀

Graph Navigation Ready

Navigate relations naturally. Include nested data without writing JOINs. Eager loading prevents N+1 automatically.

🎨

Editor Integration Ready

VSCode extension with syntax highlighting, real-time diagnostics, and auto-completion. Available in the marketplace.

Install Extension →
📥

Database Introspection Ready

Import existing PostgreSQL databases automatically. No manual schema rewriting — get started in seconds.

🔄

Multi-Database Planned

Route different fields to different backends. PostgreSQL for data, Redis for cache, DuckDB for analytics — one schema.

ChameleonDB vs The Competition

Here's how ChameleonDB compares to other popular database tools

Feature Prisma GORM ChameleonDB
See generated SQL ❌ Log only ❌ Log only ✅ Built-in .Debug()
Blocks UPDATE without WHERE ❌ No ❌ No ✅ Compile error
Schema versioning ⚠️ Migrations only ⚠️ Manual ✅ Immutable + audited
N+1 query prevention ⚠️ Manual includes ⚠️ Preload needed ✅ Automatic
Runtime performance ~2ms overhead ~500μs overhead ~100ns overhead

Roadmap

A capability-driven view of ChameleonDB evolution. Older milestones fade as focus moves forward.

Schema & Parsing

DONE
  • ✓ LALRPOP parser
  • ✓ AST generation
  • ✓ Schema validation

Type Checker

DONE
  • ✓ Relations & constraints
  • ✓ Cycle detection
  • ✓ Structured errors

FFI Layer

DONE
  • ✓ C ABI boundary
  • ✓ JSON serialization
  • ✓ Rust ↔ Go bridge

Runtime & Execution

DONE
  • ✓ Go runtime engine
  • ✓ Query builder
  • ✓ PostgreSQL backend

Developer Experience

PLANNED
  • ✓ Migrations
  • 🔄 Code generation
  • 🔄 Performance benchmarks

Get Started

# Quick install (macOS, Linux)
curl -sSL https://chameleondb.dev/install | sh

Download Windows version →

# Try the examples
git clone https://github.com/chameleon-db/chameleon-examples
cd chameleon-examples/01-hello-world
chameleon migrate --apply

Requires PostgreSQL. View full installation guide →

Frequently Asked Questions

Everything you need to know about ChameleonDB. Still have questions? Join our Discord.

ChameleonDB is a graph-oriented, strongly-typed database access layer built on a Rust core with Go bindings. You define your schema once in a .cham file, and ChameleonDB generates type-safe queries, validates them at schema load time, and shows you the exact SQL that runs. No hidden behavior, no N+1 surprises, no runtime magic.

Three key differences:

  • Full SQL visibility. Add .Debug() to any query or mutation and see the exact SQL before it executes. No black boxes.
  • Schema validation at load time, not runtime. Errors like unknown fields or broken relations are caught when the schema loads, not when a user hits a broken endpoint.
  • Safety by default. Operations like UPDATE or DELETE without a WHERE clause are blocked at the API level. You must explicitly opt in to bulk operations.

Yes. Database introspection (chameleon introspect) is on the immediate roadmap — it will connect to your existing PostgreSQL database and generate the .cham schema file automatically. In the meantime, writing the schema manually from an existing database is straightforward: the DSL maps directly to standard SQL types and constraints.

Yes, always. Chain .Debug() on any query or mutation and ChameleonDB prints the exact SQL it will send to the database, along with execution time and row count. Works on both reads and writes:

db.Query("User").Select("id", "name").Filter("age", "gt", 25).Debug().Execute(ctx)
// [SQL] SELECT id, name FROM users WHERE age > 25
// [TRACE] 1.2ms · 42 rows

db.Insert("User").Set("email", "ana@mail.com").Debug().Execute(ctx)
// [SQL] INSERT INTO users (email) VALUES ($1) RETURNING *
// [TRACE] 0.8ms · 1 row

Yes, by default. Both Update and Delete require a .Filter() call. Attempting to run either without one returns a descriptive error. When a bulk operation is intentional, you explicitly opt in:

// ❌ Blocked — returns error: "UPDATE requires a WHERE clause"
db.Update("User").Set("verified", true).Execute(ctx)

// Explicit opt-in for bulk operations
db.Update("User").Set("verified", true).ForceUpdateAll().Execute(ctx)
db.Delete("Session").ForceDeleteAll().Execute(ctx)

Currently: Go with PostgreSQL. The core is written in Rust and exposes a C FFI layer, which makes adding language bindings straightforward. Python and Node.js are on the roadmap. Future database backends include Redis (for caching via @cache annotations) and DuckDB (for analytics via @olap), all from a single schema definition.

ChameleonDB exposes the underlying pgx connection pool directly, so you always have a raw SQL escape hatch for complex aggregations, CTEs, full-text search, or any database-specific feature:

pool := engine.Connector().Pool()
rows, err := pool.Query(ctx, `
    SELECT u.name, COUNT(p.id) AS post_count
    FROM users u
    LEFT JOIN posts p ON p.author_id = u.id
    GROUP BY u.id
    HAVING COUNT(p.id) > 5
`)

No abstraction leakage — you drop down to pgx and get full control.

The overhead is negligible in practice. SQL generation happens in the Rust core via FFI — roughly ~100ns per call. Schema validation runs once at load time, not per query. The generated SQL goes directly to pgx, the same driver you'd use with raw queries. For most applications, the bottleneck is the database, not ChameleonDB. Formal benchmarks vs Prisma/GORM are in progress for v1.1.

v1.0-beta is stable for evaluation and non-critical workloads. Core features — schema parsing, query generation, mutations, eager loading, field projection, and debug mode — are covered by 80+ integration tests. Features that are still missing (transaction support, IdentityMap, introspection) are tracked openly on the roadmap. We recommend v1.0-beta for new side projects and internal tools, and waiting for v1.1 for high-traffic production systems.