Dew

A lightweight, type-safe query builder for Go.
No ORM magic, no repo layers — just queries.

go get github.com/dr3dnought/dew

Write queries, not abstractions

Define your schema once with typed columns. Query anywhere with full compile-time safety — no strings, no guessing.

// Define oncevar Users = dew.DefineSchema("users", dew.PostgreSQLDialect{}, func(t dew.Table[User]) struct {    dew.Table[User]    ID   dew.IntColumn    Name dew.StringColumn    Age  dew.IntColumn} {    return struct {        dew.Table[User]        ID   dew.IntColumn        Name dew.StringColumn        Age  dew.IntColumn    }{        Table: t,        ID:    t.IntColumn("id"),        Name:  t.StringColumn("name"),        Age:   t.IntColumn("age"),    }})// Query anywhere — type-safe, composable, no repo neededadults, err := Users.From(db).    Where(Users.Age.Gte(18)).    OrderBy(dew.Desc(Users.Name)).    Limit(10).    All(ctx)

Before and after

Same query. Less code. Type-safe. No manual scanning.

Raw database/sql — 14 lines

rows, err := db.QueryContext(ctx,    "SELECT * FROM users WHERE age >= $1 AND role = $2 ORDER BY name LIMIT $3",    18, "admin", 10,)if err != nil {    return nil, err}defer rows.Close()var users []Userfor rows.Next() {    var u User    err := rows.Scan(&u.ID, &u.Name, &u.Email, &u.Age, &u.Role)    if err != nil {        return nil, err    }    users = append(users, u)}

With dew — 5 lines

users, err := Users.From(db).    Where(Users.Age.Gte(18), Users.Role.Eq("admin")).    OrderBy(dew.Asc(Users.Name)).    Limit(10).    All(ctx)

The compiler checks every column name.

Why dew?

There are great tools out there. Here's where dew fits.

ToolApproachDew
GORMFull ORM with auto-migrations, hooks, associations. Heavy abstraction — magic behind the scenes, hard to debug generated SQL, interface{} everywhere.Dew is just a query builder. No magic, no auto-migration, no hooks. You see exactly what SQL runs. Type-safe columns instead of string-based field names.
sqlxThin wrapper over database/sql with struct scanning. Great, but queries are raw strings — no compile-time safety, no composability.Dew gives you the same directness as sqlx but with typed columns and composable builders. Refactor a column name and the compiler catches every usage.
entCode-generated type-safe ORM. Powerful, but requires a build step, generates thousands of lines, and owns your schema.Dew achieves type safety through generics alone — zero code generation. Your schema is plain Go code. No build step, no generated files.

Ready to drop the boilerplate?

Get started in under 5 minutes.

Read the Docs