dbx

package module
v0.1.1 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 8, 2026 License: MIT Imports: 12 Imported by: 0

README

dbx

Lightweight SQL toolkit for Go on top of database/sql:

  • query builder (non-ORM)
  • PostgreSQL + SQLite support
  • named parameters
  • model CRUD
  • transactions, savepoints, upsert, returning

Status

Production-oriented, pre-v1 API (v0.x recommended).

Compatibility

  • Go: 1.22+
  • Module path: github.com/pafthang/dbx

Features

  • Core DB wrapper:
    • Open, MustOpen, NewFromDB, WithContext
    • Begin, BeginTx, Transactional, TransactionalContext
    • Savepoint, RollbackTo, Release
  • Query API:
    • NewQuery, Bind, Execute
    • All, One, Row, Rows, Column, Pluck, Map
  • Select builder:
    • Select, From, joins, Where, GroupBy, Having, OrderBy
    • Limit, Offset, Page, PerPage
    • Union, UnionAll
    • CTE: With, WithRecursive, WithRaw
    • analytics helpers: Count, CountDistinct, Exists
  • DML:
    • Insert, InsertMany, Update, Delete, Upsert
    • InsertReturning, InsertManyReturning, UpdateReturning, DeleteReturning
    • UpsertOnConflict via OnConflict DSL
  • Model CRUD:
    • Model(...).Insert/Update/Delete/Save
    • PK tag support (db:"id,pk")
    • auto PK fill on insert
  • Operational tooling:
    • query/exec hooks (QueryLogFunc, ExecLogFunc)
    • trace hook (TraceHook)
    • optional prepared statement cache (EnableStatementCache)
  • Generic helpers:
    • SelectAll[T], SelectOne[T], SelectOneOrZero[T]
    • QueryAll[T], QueryOne[T]

Installation

go get github.com/pafthang/dbx
Drivers

SQLite (CGO-free):

import _ "modernc.org/sqlite"

PostgreSQL:

import _ "github.com/jackc/pgx/v5/stdlib"

Quick Start

Connect
db, err := dbx.Open("sqlite", ":memory:")
if err != nil {
	panic(err)
}
defer db.Close()
Raw query with named params
var names []string
err := db.NewQuery("SELECT name FROM users WHERE status={:status}").
	Bind(dbx.Params{"status": "active"}).
	Column(&names)
Select builder
type User struct {
	ID    int64  `db:"id"`
	Name  string `db:"name"`
	Email string `db:"email"`
}

var users []User
err := db.Select("id", "name", "email").
	From("users").
	Where(dbx.And(
		dbx.HashExp{"status": "active"},
		dbx.Like("name", "al"),
	)).
	OrderBy("id DESC").
	Page(1, 20).
	All(&users)
Model CRUD
type User struct {
	ID    int64  `db:"id,pk"`
	Name  string `db:"name"`
	Email string `db:"email"`
}

func (User) TableName() string { return "users" }

u := &User{Name: "alice", Email: "a@example.com"}
_ = db.Model(u).Insert()
_ = db.Model(u).Update("name")
_ = db.Model(u).Delete()

Query Builder Guide

Joins

Supported join methods:

  • Join
  • InnerJoin
  • LeftJoin
  • RightJoin
  • FullJoin
  • CrossJoin
  • JoinSubquery
  • LeftJoinSubquery
  • InnerJoinSubquery
sub := db.Select("user_id").From("events").Where(dbx.HashExp{"kind": "login"})

err := db.Select("u.id", "u.name").
	From("users u").
	LeftJoin("profiles p", dbx.Raw("p.user_id = u.id")).
	JoinSubquery(sub, "e", dbx.Raw("e.user_id = u.id")).
	Where(dbx.HashExp{"u.status": "active"}).
	All(&users)
CTE
active := db.Select("id", "name").
	From("users").
	Where(dbx.HashExp{"status": "active"})

err := db.Select("id", "name").
	With("active_users", active).
	From("active_users").
	All(&users)
Aggregation helpers
total, _ := db.Select("id").From("users").Count()
distinctNames, _ := db.Select("name").From("users").CountDistinct("name")
exists, _ := db.Select("id").From("users").Where(dbx.HashExp{"email": "a@example.com"}).Exists()
Column and map extraction
var names []string
_ = db.Select("name").From("users").Pluck(&names)

statusByName := map[string]string{}
_ = db.Select("name", "status").From("users").Map(&statusByName)

DML Guide

Upsert
_ = db.Upsert("users", dbx.Params{
	"email": "a@example.com",
	"name":  "alice-updated",
}, "email").Execute()
OnConflict DSL
_ = db.UpsertOnConflict("users", dbx.Params{
	"email": "a@example.com",
	"name":  "alice",
}, dbx.Conflict("email").DoUpdateColumns("name")).Execute()
Returning
var id int64
var name string
_ = db.UpdateReturning("users", dbx.Params{"name": "alice-v2"}, dbx.HashExp{"id": 1}, "id", "name").
	Row(&id, &name)
Bulk insert
_ = db.InsertMany("users", []dbx.Params{
	{"email": "a@example.com", "name": "alice"},
	{"email": "b@example.com", "name": "bob"},
}).Execute()

Bulk insert with returning:

rows, _ := db.InsertManyReturning("users", []dbx.Params{
	{"email": "a@example.com", "name": "alice"},
	{"email": "b@example.com", "name": "bob"},
}, "id", "name").Rows()
defer rows.Close()

Transactions and Savepoints

_ = db.Transactional(func(tx *dbx.Tx) error {
	if err := tx.Savepoint("sp1"); err != nil {
		return err
	}
	if _, err := tx.Insert("users", dbx.Params{"name": "temp"}).Execute(); err != nil {
		return err
	}
	if err := tx.RollbackTo("sp1"); err != nil {
		return err
	}
	return tx.Release("sp1")
})

Generic Helpers

users, _ := dbx.SelectAll[User](db.Select("id", "name").From("users"))
user, _ := dbx.SelectOne[User](db.Select("id", "name").From("users").Where(dbx.HashExp{"id": 1}))

Observability and Performance Features

Query/Exec hooks
  • QueryLogFunc
  • ExecLogFunc
Trace hook
db.TraceHook = func(ctx context.Context, sql string, exec bool) (context.Context, func(error)) {
	start := time.Now()
	return ctx, func(err error) {
		_ = time.Since(start)
		_ = err
		_ = sql
		_ = exec
	}
}
Statement cache
db = db.EnableStatementCache(128)

Dialect Notes

  • Supported dialects:
    • SQLite (sqlite, sqlite3)
    • PostgreSQL (postgres, pgx)
  • Placeholders:
    • SQLite: ?
    • PostgreSQL: $1, $2, ...
  • Quoting:
    • SQLite: backticks
    • PostgreSQL: double quotes
  • FULL JOIN:
    • available in builder API
    • verify target DB support in your deployment
  • RETURNING:
    • supported by this package where DB supports it

Testing

Run all tests:

go test ./...

Run benchmarks:

go test -run '^$' -bench . -benchmem

PostgreSQL integration tests require DBX_PG_DSN.

Local PostgreSQL via Docker:

docker compose up -d postgres
export DBX_PG_DSN='postgres://dbx:dbx@localhost:55432/dbx_test?sslmode=disable'
go test ./... -run PostgresIntegration

License

MIT. See LICENSE.

Documentation

Index

Examples

Constants

This section is empty.

Variables

View Source
var (
	// ErrEmptyColumns indicates that columns map is empty for INSERT/UPDATE.
	ErrEmptyColumns = errors.New("cols cannot be empty")
	// ErrEmptyRows indicates rows slice is empty for batch insert.
	ErrEmptyRows = errors.New("rows cannot be empty")
	// ErrInconsistentColumns indicates batch rows use different column sets.
	ErrInconsistentColumns = errors.New("rows must have identical column keys")
	// ErrInvalidModel indicates model must be pointer to struct.
	ErrInvalidModel = errors.New("model must be a non-nil pointer to struct")
	// MissingPKError indicates no primary key fields are declared.
	MissingPKError = errors.New("missing primary key declaration")
	// CompositePKError indicates composite primary keys are not supported.
	CompositePKError = errors.New("composite primary key is not supported")
	// ErrInvalidSavepointName indicates savepoint name is invalid.
	ErrInvalidSavepointName = errors.New("invalid savepoint name")
)
View Source
var BuilderFuncMap = map[string]BuilderFunc{
	"postgres": NewPgsqlBuilder,
	"pgx":      NewPgsqlBuilder,
	"sqlite":   NewSqliteBuilder,
	"sqlite3":  NewSqliteBuilder,
}

BuilderFuncMap maps driver names to SQL builders.

Functions

func QueryAll

func QueryAll[T any](q *Query) ([]T, error)

QueryAll is a generic helper to fetch all rows into []T.

func QueryOne

func QueryOne[T any](q *Query) (T, error)

QueryOne is a generic helper to fetch first row into T.

func SelectAll

func SelectAll[T any](q *SelectQuery) ([]T, error)

SelectAll is a generic helper to fetch all rows into []T.

func SelectOne

func SelectOne[T any](q *SelectQuery) (T, error)

SelectOne is a generic helper to fetch first row into T.

func SelectOneOrZero

func SelectOneOrZero[T any](q *SelectQuery) (T, error)

SelectOneOrZero fetches first row into T and returns zero value with nil when query is empty.

Types

type BaseBuilder

type BaseBuilder struct {
	// contains filtered or unexported fields
}

BaseBuilder provides default builder behavior.

func NewBaseBuilder

func NewBaseBuilder(db *DB, executor Executor) *BaseBuilder

NewBaseBuilder creates a BaseBuilder.

func (*BaseBuilder) Delete

func (b *BaseBuilder) Delete(table string, where Expression) *Query

Delete creates DELETE query.

func (*BaseBuilder) DeleteReturning

func (b *BaseBuilder) DeleteReturning(table string, where Expression, returning ...string) *Query

DeleteReturning creates DELETE ... RETURNING query.

func (*BaseBuilder) GeneratePlaceholder

func (b *BaseBuilder) GeneratePlaceholder(_ int) string

GeneratePlaceholder generates positional placeholders.

func (*BaseBuilder) Insert

func (b *BaseBuilder) Insert(table string, cols Params) *Query

Insert creates INSERT query.

func (*BaseBuilder) InsertMany

func (b *BaseBuilder) InsertMany(table string, rows []Params) *Query

InsertMany creates a multi-row INSERT query.

func (*BaseBuilder) InsertManyReturning

func (b *BaseBuilder) InsertManyReturning(table string, rows []Params, returning ...string) *Query

InsertManyReturning creates multi-row INSERT ... RETURNING query.

func (*BaseBuilder) InsertReturning

func (b *BaseBuilder) InsertReturning(table string, cols Params, returning ...string) *Query

InsertReturning creates INSERT query with optional RETURNING columns.

func (*BaseBuilder) Model

func (b *BaseBuilder) Model(model any) *ModelQuery

Model creates model query helper for struct model.

func (*BaseBuilder) NewQuery

func (b *BaseBuilder) NewQuery(sql string) *Query

NewQuery creates a new query.

func (*BaseBuilder) QueryBuilder

func (b *BaseBuilder) QueryBuilder() QueryBuilder

QueryBuilder returns active SQL clause builder.

func (*BaseBuilder) QuoteSimpleColumnName

func (b *BaseBuilder) QuoteSimpleColumnName(s string) string

QuoteSimpleColumnName quotes column name without table parsing.

func (*BaseBuilder) QuoteSimpleTableName

func (b *BaseBuilder) QuoteSimpleTableName(s string) string

QuoteSimpleTableName quotes table name without schema parsing.

func (*BaseBuilder) Select

func (b *BaseBuilder) Select(cols ...string) *SelectQuery

Select creates SELECT query builder.

func (*BaseBuilder) Update

func (b *BaseBuilder) Update(table string, cols Params, where Expression) *Query

Update creates UPDATE query.

func (*BaseBuilder) UpdateReturning

func (b *BaseBuilder) UpdateReturning(table string, cols Params, where Expression, returning ...string) *Query

UpdateReturning creates UPDATE ... RETURNING query.

func (*BaseBuilder) Upsert

func (b *BaseBuilder) Upsert(table string, cols Params, constraints ...string) *Query

Upsert default implementation maps to INSERT.

func (*BaseBuilder) UpsertOnConflict

func (b *BaseBuilder) UpsertOnConflict(table string, cols Params, conflict OnConflict) *Query

UpsertOnConflict creates UPSERT query with conflict DSL.

type BaseQueryBuilder

type BaseQueryBuilder struct {
	// contains filtered or unexported fields
}

BaseQueryBuilder provides generic SQL clause generation.

func NewBaseQueryBuilder

func NewBaseQueryBuilder(db *DB) *BaseQueryBuilder

NewBaseQueryBuilder creates clause builder.

func (*BaseQueryBuilder) BuildFrom

func (b *BaseQueryBuilder) BuildFrom(tables []string) string

func (*BaseQueryBuilder) BuildGroupBy

func (b *BaseQueryBuilder) BuildGroupBy(cols []string) string

func (*BaseQueryBuilder) BuildHaving

func (b *BaseQueryBuilder) BuildHaving(e Expression, params Params) string

func (*BaseQueryBuilder) BuildJoin

func (b *BaseQueryBuilder) BuildJoin(joins []JoinInfo, params Params) string

func (*BaseQueryBuilder) BuildOrderByAndLimit

func (b *BaseQueryBuilder) BuildOrderByAndLimit(sql string, cols []string, limit int64, offset int64) string

func (*BaseQueryBuilder) BuildSelect

func (b *BaseQueryBuilder) BuildSelect(cols []string, distinct bool, option string) string

func (*BaseQueryBuilder) BuildUnion

func (b *BaseQueryBuilder) BuildUnion(unions []UnionInfo, params Params) string

func (*BaseQueryBuilder) BuildWhere

func (b *BaseQueryBuilder) BuildWhere(e Expression, params Params) string

func (*BaseQueryBuilder) CombineUnion

func (b *BaseQueryBuilder) CombineUnion(sql string, unionClause string) string

type Builder

type Builder interface {
	NewQuery(sql string) *Query
	GeneratePlaceholder(i int) string
	QuoteSimpleTableName(s string) string
	QuoteSimpleColumnName(s string) string
	QueryBuilder() QueryBuilder
	Select(cols ...string) *SelectQuery
	Insert(table string, cols Params) *Query
	InsertMany(table string, rows []Params) *Query
	InsertReturning(table string, cols Params, returning ...string) *Query
	InsertManyReturning(table string, rows []Params, returning ...string) *Query
	Update(table string, cols Params, where Expression) *Query
	UpdateReturning(table string, cols Params, where Expression, returning ...string) *Query
	Delete(table string, where Expression) *Query
	DeleteReturning(table string, where Expression, returning ...string) *Query
	Upsert(table string, cols Params, constraints ...string) *Query
	UpsertOnConflict(table string, cols Params, conflict OnConflict) *Query
	Model(model any) *ModelQuery
}

Builder creates queries for a specific SQL dialect.

func NewPgsqlBuilder

func NewPgsqlBuilder(db *DB, executor Executor) Builder

NewPgsqlBuilder creates PgsqlBuilder.

func NewSqliteBuilder

func NewSqliteBuilder(db *DB, executor Executor) Builder

NewSqliteBuilder creates SqliteBuilder.

func NewStandardBuilder

func NewStandardBuilder(db *DB, executor Executor) Builder

NewStandardBuilder creates StandardBuilder.

type BuilderFunc

type BuilderFunc func(*DB, Executor) Builder

BuilderFunc creates a builder instance for a DB/executor pair.

type DB

type DB struct {
	Builder

	QueryLogFunc QueryLogFunc
	ExecLogFunc  ExecLogFunc
	TraceHook    TraceHook

	StmtCacheSize int
	// contains filtered or unexported fields
}

DB is a thin wrapper over sql.DB with query helpers.

func MustOpen

func MustOpen(driverName, dsn string) (*DB, error)

MustOpen opens and validates connectivity.

func NewFromDB

func NewFromDB(sqlDB *sql.DB, driverName string) *DB

NewFromDB wraps existing sql.DB.

func Open

func Open(driverName, dsn string) (*DB, error)

Open creates a DB wrapper over sql.Open.

func (*DB) Begin

func (db *DB) Begin() (*Tx, error)

Begin starts a transaction.

func (*DB) BeginTx

func (db *DB) BeginTx(ctx context.Context, opts *sql.TxOptions) (*Tx, error)

BeginTx starts a transaction with context/options.

func (*DB) Clone

func (db *DB) Clone() *DB

Clone creates a shallow copy.

func (*DB) Close

func (db *DB) Close() error

Close closes underlying sql.DB.

func (*DB) Context

func (db *DB) Context() context.Context

Context returns associated context.

func (*DB) DB

func (db *DB) DB() *sql.DB

DB returns wrapped sql.DB.

func (*DB) DriverName

func (db *DB) DriverName() string

DriverName returns underlying driver name.

func (*DB) EnableStatementCache

func (db *DB) EnableStatementCache(size int) *DB

EnableStatementCache enables prepared statement cache for sql.DB executor paths. size <= 0 disables cache.

func (*DB) NewQuery

func (db *DB) NewQuery(sql string) *Query

NewQuery creates a query from raw SQL.

func (*DB) QuoteColumnName

func (db *DB) QuoteColumnName(name string) string

QuoteColumnName quotes column names, including dotted names.

func (*DB) QuoteTableName

func (db *DB) QuoteTableName(name string) string

QuoteTableName quotes table names, including dotted names.

func (*DB) Transactional

func (db *DB) Transactional(f func(tx *Tx) error) (err error)

Transactional executes f in a transaction.

func (*DB) TransactionalContext

func (db *DB) TransactionalContext(ctx context.Context, opts *sql.TxOptions, f func(tx *Tx) error) (err error)

TransactionalContext executes f in a context-bound transaction.

func (*DB) WithContext

func (db *DB) WithContext(ctx context.Context) *DB

WithContext returns a cloned DB with context.

func (*DB) Wrap

func (db *DB) Wrap(tx *sql.Tx) *Tx

Wrap wraps an existing sql.Tx.

type ExecLogFunc

type ExecLogFunc func(ctx context.Context, d time.Duration, sql string, result sql.Result, err error)

ExecLogFunc logs execute-like query calls.

type Executor

type Executor interface {
	Exec(query string, args ...any) (sql.Result, error)
	Query(query string, args ...any) (*sql.Rows, error)
}

Executor is the common interface for sql.DB and sql.Tx.

type Expression

type Expression interface {
	Build(db *DB, params Params) string
}

Expression can build SQL and bind parameters.

func And

func And(exprs ...Expression) Expression

And joins expressions with AND.

func Between

func Between(col string, start, end any) Expression

Between creates BETWEEN expression.

func Exists

func Exists(q *SelectQuery) Expression

Exists creates EXISTS (subquery).

func In

func In(col string, values any) Expression

In creates column IN (...) expression.

func Like

func Like(col string, value any) Expression

Like creates column LIKE '%value%' expression.

func Not

func Not(e Expression) Expression

Not negates expression.

func NotIn

func NotIn(col string, values any) Expression

NotIn creates column NOT IN (...) expression.

func Or

func Or(exprs ...Expression) Expression

Or joins expressions with OR.

func Raw

func Raw(sql string, params ...Params) Expression

Raw builds SQL expression from raw SQL with optional params.

type HashExp

type HashExp map[string]any

HashExp builds conjunction: col1=val1 AND col2=val2...

func (HashExp) Build

func (e HashExp) Build(db *DB, params Params) string

type JoinInfo

type JoinInfo struct {
	Join  string
	Table string
	On    Expression
}

JoinInfo describes JOIN clause parts.

type ModelQuery

type ModelQuery struct {
	// contains filtered or unexported fields
}

ModelQuery performs model-based CRUD.

func NewModelQuery

func NewModelQuery(model any, db *DB, builder Builder) *ModelQuery

NewModelQuery creates model query wrapper.

func (*ModelQuery) Delete

func (q *ModelQuery) Delete() error

Delete deletes model row by PK.

func (*ModelQuery) Exclude

func (q *ModelQuery) Exclude(attrs ...string) *ModelQuery

Exclude excludes fields from Insert/Update payload.

func (*ModelQuery) Insert

func (q *ModelQuery) Insert(attrs ...string) error

Insert inserts model into DB and sets auto-increment PK when possible.

func (*ModelQuery) Save

func (q *ModelQuery) Save(attrs ...string) error

Save inserts model when PK is zero, otherwise updates it.

func (*ModelQuery) Update

func (q *ModelQuery) Update(attrs ...string) error

Update updates model row by PK.

func (*ModelQuery) WithContext

func (q *ModelQuery) WithContext(ctx context.Context) *ModelQuery

WithContext associates context with this model query.

type NullStringMap

type NullStringMap map[string]sql.NullString

NullStringMap is a map that stores row data as nullable strings.

type OnConflict

type OnConflict struct {
	Target         []string
	DoNothingFlag  bool
	UpdateSet      Params
	UpdateColumns  []string
	WhereCondition Expression
}

OnConflict describes UPSERT conflict strategy.

func Conflict

func Conflict(cols ...string) OnConflict

Conflict creates OnConflict for specified unique/PK columns.

func (OnConflict) DoNothing

func (c OnConflict) DoNothing() OnConflict

DoNothing sets conflict action to DO NOTHING.

func (OnConflict) DoUpdateColumns

func (c OnConflict) DoUpdateColumns(cols ...string) OnConflict

DoUpdateColumns sets update action to use EXCLUDED values for listed columns.

func (OnConflict) DoUpdateSet

func (c OnConflict) DoUpdateSet(set Params) OnConflict

DoUpdateSet sets update action with explicit assignments.

func (OnConflict) Where

func (c OnConflict) Where(e Expression) OnConflict

Where applies optional WHERE to DO UPDATE action.

type Params

type Params map[string]any

Params represents named query parameters.

type PgsqlBuilder

type PgsqlBuilder struct {
	*BaseBuilder
}

PgsqlBuilder is PostgreSQL builder.

func (*PgsqlBuilder) GeneratePlaceholder

func (b *PgsqlBuilder) GeneratePlaceholder(i int) string

GeneratePlaceholder generates postgres placeholders.

func (*PgsqlBuilder) QuoteSimpleColumnName

func (b *PgsqlBuilder) QuoteSimpleColumnName(s string) string

QuoteSimpleColumnName quotes column name for postgres.

func (*PgsqlBuilder) QuoteSimpleTableName

func (b *PgsqlBuilder) QuoteSimpleTableName(s string) string

QuoteSimpleTableName quotes table name for postgres.

func (*PgsqlBuilder) Upsert

func (b *PgsqlBuilder) Upsert(table string, cols Params, constraints ...string) *Query

Upsert creates PostgreSQL ON CONFLICT upsert query.

type Query

type Query struct {
	LastError error
	// contains filtered or unexported fields
}

Query is an executable SQL query.

func (*Query) All

func (q *Query) All(dest any) error

All scans all query rows into dest pointer to slice.

func (*Query) Bind

func (q *Query) Bind(params Params) *Query

Bind merges named params into query parameters.

Example
db, err := Open("sqlite", ":memory:")
if err != nil {
	log.Fatal(err)
}
defer db.Close()

_, _ = db.NewQuery(`CREATE TABLE users (id INTEGER PRIMARY KEY AUTOINCREMENT, name TEXT, status TEXT)`).Execute()
_, _ = db.Insert("users", Params{"name": "alice", "status": "active"}).Execute()
_, _ = db.Insert("users", Params{"name": "bob", "status": "disabled"}).Execute()

var names []string
err = db.NewQuery(`SELECT name FROM users WHERE status={:status} ORDER BY id`).
	Bind(Params{"status": "active"}).
	Column(&names)
if err != nil {
	log.Fatal(err)
}

fmt.Println(names)
Output:
[alice]

func (*Query) Column

func (q *Query) Column(dest any) error

Column scans first column into a slice pointer.

func (*Query) Execute

func (q *Query) Execute() (sql.Result, error)

Execute runs query as Exec.

func (*Query) Map

func (q *Query) Map(dest any) error

Map scans query result into a map pointer. Query must return exactly 2 columns: key and value.

func (*Query) One

func (q *Query) One(dest any) error

One scans first row into dest and returns sql.ErrNoRows when empty.

func (*Query) Pluck

func (q *Query) Pluck(dest any) error

Pluck is an alias of Column.

func (*Query) Row

func (q *Query) Row(dest ...any) error

Row scans first row by positional targets.

func (*Query) Rows

func (q *Query) Rows() (*Rows, error)

Rows executes query and returns rows wrapper.

func (*Query) SQL

func (q *Query) SQL() string

SQL returns currently compiled SQL template.

func (*Query) WithContext

func (q *Query) WithContext(ctx context.Context) *Query

WithContext sets context for this query.

type QueryBuilder

type QueryBuilder interface {
	BuildSelect(cols []string, distinct bool, option string) string
	BuildFrom(tables []string) string
	BuildJoin(joins []JoinInfo, params Params) string
	BuildWhere(e Expression, params Params) string
	BuildGroupBy(cols []string) string
	BuildHaving(e Expression, params Params) string
	BuildOrderByAndLimit(sql string, cols []string, limit int64, offset int64) string
	BuildUnion(unions []UnionInfo, params Params) string
	CombineUnion(sql string, unionClause string) string
}

QueryBuilder builds SQL clauses for SelectQuery.

type QueryLogFunc

type QueryLogFunc func(ctx context.Context, d time.Duration, sql string, rows *sql.Rows, err error)

QueryLogFunc logs select-like query calls.

type Rows

type Rows struct {
	*sql.Rows
	// contains filtered or unexported fields
}

Rows wraps sql.Rows with struct/map scanning helpers.

func (*Rows) Close

func (r *Rows) Close() error

Close closes underlying rows and releases temporary buffers.

func (*Rows) ScanMap

func (r *Rows) ScanMap(dest any) error

ScanMap scans current row into map pointer or NullStringMap.

func (*Rows) ScanStruct

func (r *Rows) ScanStruct(dest any) error

ScanStruct scans current row into struct pointer.

type SelectQuery

type SelectQuery struct {
	// contains filtered or unexported fields
}

SelectQuery builds SELECT statements.

func NewSelectQuery

func NewSelectQuery(builder Builder, db *DB) *SelectQuery

NewSelectQuery creates a SELECT query builder.

func (*SelectQuery) All

func (q *SelectQuery) All(dest any) error

All fetches all rows.

func (*SelectQuery) AndWhere

func (q *SelectQuery) AndWhere(e Expression) *SelectQuery

AndWhere combines existing WHERE with AND.

func (*SelectQuery) Bind

func (q *SelectQuery) Bind(params Params) *SelectQuery

Bind adds named parameters.

func (*SelectQuery) Build

func (q *SelectQuery) Build() (string, Params)

Build creates SQL string and collected params.

func (*SelectQuery) Column

func (q *SelectQuery) Column(dest any) error

Column fetches first column into slice pointer.

func (*SelectQuery) Count

func (q *SelectQuery) Count() (int64, error)

Count executes COUNT(*) over current query shape (without ORDER/LIMIT/OFFSET).

func (*SelectQuery) CountDistinct

func (q *SelectQuery) CountDistinct(cols ...string) (int64, error)

CountDistinct executes count of distinct value combinations for selected columns. When no columns are provided it defaults to currently selected columns.

func (*SelectQuery) CrossJoin

func (q *SelectQuery) CrossJoin(table string) *SelectQuery

CrossJoin appends CROSS JOIN table.

func (*SelectQuery) Distinct

func (q *SelectQuery) Distinct(v ...bool) *SelectQuery

Distinct sets DISTINCT mode.

func (*SelectQuery) Execute

func (q *SelectQuery) Execute() error

Execute runs query via Exec (mostly useful with SELECT ... FOR UPDATE etc).

func (*SelectQuery) Exists

func (q *SelectQuery) Exists() (bool, error)

Exists checks whether current query returns at least one row.

func (*SelectQuery) From

func (q *SelectQuery) From(tables ...string) *SelectQuery

From sets FROM tables.

func (*SelectQuery) FullJoin

func (q *SelectQuery) FullJoin(table string, on Expression) *SelectQuery

FullJoin appends FULL JOIN table ON condition.

func (*SelectQuery) GroupBy

func (q *SelectQuery) GroupBy(cols ...string) *SelectQuery

GroupBy sets GROUP BY columns.

func (*SelectQuery) Having

func (q *SelectQuery) Having(e Expression) *SelectQuery

Having sets HAVING expression.

func (*SelectQuery) InnerJoin

func (q *SelectQuery) InnerJoin(table string, on Expression) *SelectQuery

InnerJoin appends INNER JOIN table ON condition.

func (*SelectQuery) InnerJoinSubquery

func (q *SelectQuery) InnerJoinSubquery(sub *SelectQuery, alias string, on Expression) *SelectQuery

InnerJoinSubquery appends INNER JOIN (subquery) alias ON condition.

func (*SelectQuery) Join

func (q *SelectQuery) Join(table string, on Expression) *SelectQuery

Join appends JOIN table ON condition.

func (*SelectQuery) JoinSubquery

func (q *SelectQuery) JoinSubquery(sub *SelectQuery, alias string, on Expression) *SelectQuery

JoinSubquery appends JOIN (subquery) alias ON condition with safe parameter rebinding.

func (*SelectQuery) LeftJoin

func (q *SelectQuery) LeftJoin(table string, on Expression) *SelectQuery

LeftJoin appends LEFT JOIN table ON condition.

func (*SelectQuery) LeftJoinSubquery

func (q *SelectQuery) LeftJoinSubquery(sub *SelectQuery, alias string, on Expression) *SelectQuery

LeftJoinSubquery appends LEFT JOIN (subquery) alias ON condition.

func (*SelectQuery) Limit

func (q *SelectQuery) Limit(v int64) *SelectQuery

Limit sets LIMIT.

func (*SelectQuery) Map

func (q *SelectQuery) Map(dest any) error

Map scans 2-column query results into a map pointer.

func (*SelectQuery) Offset

func (q *SelectQuery) Offset(v int64) *SelectQuery

Offset sets OFFSET.

func (*SelectQuery) One

func (q *SelectQuery) One(dest any) error

One fetches first row.

func (*SelectQuery) Option

func (q *SelectQuery) Option(option string) *SelectQuery

Option sets custom select option (eg SQL_CALC_FOUND_ROWS).

func (*SelectQuery) OrWhere

func (q *SelectQuery) OrWhere(e Expression) *SelectQuery

OrWhere combines existing WHERE with OR.

func (*SelectQuery) OrderBy

func (q *SelectQuery) OrderBy(cols ...string) *SelectQuery

OrderBy sets ORDER BY columns.

func (*SelectQuery) Page

func (q *SelectQuery) Page(page, perPage int64) *SelectQuery

Page configures pagination using 1-based page number and per-page size. Invalid values are clamped to page=1 and perPage=20.

func (*SelectQuery) PerPage

func (q *SelectQuery) PerPage(v int64) *SelectQuery

PerPage sets LIMIT for pagination and keeps existing OFFSET. Values <= 0 disable LIMIT.

func (*SelectQuery) Pluck

func (q *SelectQuery) Pluck(dest any) error

Pluck is an alias of Column.

func (*SelectQuery) Query

func (q *SelectQuery) Query() *Query

Query converts SelectQuery to executable Query.

func (*SelectQuery) RightJoin

func (q *SelectQuery) RightJoin(table string, on Expression) *SelectQuery

RightJoin appends RIGHT JOIN table ON condition.

func (*SelectQuery) Row

func (q *SelectQuery) Row(dest ...any) error

Row fetches first row into positional targets.

func (*SelectQuery) Rows

func (q *SelectQuery) Rows() (*Rows, error)

Rows returns streaming rows.

func (*SelectQuery) SQL

func (q *SelectQuery) SQL() string

SQL returns SQL string only.

func (*SelectQuery) Select

func (q *SelectQuery) Select(cols ...string) *SelectQuery

Select sets selected columns.

func (*SelectQuery) Union

func (q *SelectQuery) Union(other *SelectQuery) *SelectQuery

Union appends UNION query.

func (*SelectQuery) UnionAll

func (q *SelectQuery) UnionAll(other *SelectQuery) *SelectQuery

UnionAll appends UNION ALL query.

func (*SelectQuery) Where

func (q *SelectQuery) Where(e Expression) *SelectQuery

Where sets WHERE expression.

func (*SelectQuery) With

func (q *SelectQuery) With(name string, sub *SelectQuery) *SelectQuery

With appends a CTE: WITH name AS (subquery).

func (*SelectQuery) WithContext

func (q *SelectQuery) WithContext(ctx context.Context) *SelectQuery

WithContext associates context with this query.

func (*SelectQuery) WithRaw

func (q *SelectQuery) WithRaw(name string, sql string, params ...Params) *SelectQuery

WithRaw appends a raw CTE SQL snippet with optional params.

func (*SelectQuery) WithRecursive

func (q *SelectQuery) WithRecursive(name string, sub *SelectQuery) *SelectQuery

WithRecursive appends a recursive CTE and marks WITH RECURSIVE.

type SqliteBuilder

type SqliteBuilder struct {
	*BaseBuilder
}

SqliteBuilder is SQLite builder.

func (*SqliteBuilder) Upsert

func (b *SqliteBuilder) Upsert(table string, cols Params, constraints ...string) *Query

Upsert creates SQLite ON CONFLICT upsert query.

type SqliteQueryBuilder

type SqliteQueryBuilder struct {
	*BaseQueryBuilder
}

SqliteQueryBuilder adapts union syntax for sqlite.

func NewSqliteQueryBuilder

func NewSqliteQueryBuilder(db *DB) *SqliteQueryBuilder

NewSqliteQueryBuilder creates sqlite clause builder.

func (*SqliteQueryBuilder) BuildUnion

func (b *SqliteQueryBuilder) BuildUnion(unions []UnionInfo, params Params) string

func (*SqliteQueryBuilder) CombineUnion

func (b *SqliteQueryBuilder) CombineUnion(sql string, unionClause string) string

type StandardBuilder

type StandardBuilder struct {
	*BaseBuilder
}

StandardBuilder is default ANSI-like builder.

type TableModel

type TableModel interface {
	TableName() string
}

TableModel allows overriding table name.

type TraceHook

type TraceHook func(ctx context.Context, sql string, execute bool) (context.Context, func(error))

TraceHook allows attaching tracing lifecycle around query execution. Returned end func is always called with execution error (or nil).

type Tx

type Tx struct {
	Builder
	*sql.Tx
}

Tx wraps sql.Tx and exposes the same query builder API.

func (*Tx) Release

func (tx *Tx) Release(name string) error

Release is an alias for ReleaseSavepoint.

func (*Tx) ReleaseSavepoint

func (tx *Tx) ReleaseSavepoint(name string) error

ReleaseSavepoint releases a savepoint.

func (*Tx) RollbackTo

func (tx *Tx) RollbackTo(name string) error

RollbackTo rolls back transaction state to a savepoint.

func (*Tx) Savepoint

func (tx *Tx) Savepoint(name string) error

Savepoint creates a named savepoint in current transaction.

type UnionInfo

type UnionInfo struct {
	Query *SelectQuery
	All   bool
}

UnionInfo describes UNION/UNION ALL parts.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL