Documentation
¶
Index ¶
- Constants
- func Drivers() []string
- func Expired(deadline time.Time) bool
- func ExpiryFor(ttl time.Duration) time.Time
- func FormatDeadline(deadline time.Time) string
- func NewStruct(typ reflect.Type) reflect.Value
- func ParseDeadline(s string) time.Time
- func Register(name string, dbType DbType)
- func ScanRows[T any](rows *sql.Rows, schema *CachedSchema) ([]T, error)
- func TypeOf(v any) reflect.Type
- func TypeOfT[T any]() reflect.Type
- func UnwrapValueOf(v any) reflect.Value
- type CachedSchema
- func (s *CachedSchema) BuildAssignments(v reflect.Value, fields []string, quote func(string) string, paramStyle string, ...) ([]string, []any, error)
- func (s *CachedSchema) BuildInsertQueryMysql(tableName string) string
- func (s *CachedSchema) BuildInsertQueryPG(tableName string) string
- func (s *CachedSchema) BuildWhereClause(val reflect.Value, whereFields []string, paramStyle string) (string, []any, error)
- func (s *CachedSchema) ExtractValues(val reflect.Value) []any
- type Config
- type Database
- type DbType
- type FieldInfo
- type FieldNotFoundError
- type Options
- type Order
- type ScanTypeError
- type Table
Constants ¶
const KindStruct = reflect.Struct
Variables ¶
This section is empty.
Functions ¶
func FormatDeadline ¶
FormatDeadline renders a deadline for a string-typed store.
func ParseDeadline ¶
ParseDeadline is the inverse of FormatDeadline. An empty or unparsable value means no deadline, so a corrupt companion entry cannot hide the data.
func Register ¶
Register associates a driver name with a DbType. It is intended to be called from a backend package's init function. Registering the same name twice is a no-op; registering a name that maps to a different DbType panics, since that indicates a programming error rather than a runtime condition.
func ScanRows ¶
func ScanRows[T any](rows *sql.Rows, schema *CachedSchema) ([]T, error)
ScanRows reads every row into a T. T may be the struct type or a pointer to it. Columns absent from the schema are discarded.
func TypeOfT ¶
TypeOfT returns the struct type of T, dereferencing pointer types. It is the type-safe counterpart of TypeOf for generic code paths.
func UnwrapValueOf ¶
Types ¶
type CachedSchema ¶
type CachedSchema struct {
Type reflect.Type
Fields []FieldInfo
Insertable []FieldInfo
PKIndex int
FieldMap map[string]FieldInfo
InsertColsMysql string
InsertPlaceMysql string
InsertColsPG string
InsertPlacePG string
}
func GetOrBuildSchema ¶
func GetOrBuildSchema(typ reflect.Type) *CachedSchema
func SchemaOfT ¶
func SchemaOfT[T any]() *CachedSchema
SchemaOfT returns the cached schema for T, building it on first use.
func (*CachedSchema) BuildAssignments ¶
func (s *CachedSchema) BuildAssignments(v reflect.Value, fields []string, quote func(string) string, paramStyle string, startIdx int) ([]string, []any, error)
BuildAssignments renders the SET clause assigning the named fields from v.
paramStyle "pg" numbers placeholders from startIdx, because a PostgreSQL UPDATE binds the SET arguments before the WHERE ones. Other styles use a bare "?" and ignore startIdx.
func (*CachedSchema) BuildInsertQueryMysql ¶
func (s *CachedSchema) BuildInsertQueryMysql(tableName string) string
func (*CachedSchema) BuildInsertQueryPG ¶
func (s *CachedSchema) BuildInsertQueryPG(tableName string) string
func (*CachedSchema) BuildWhereClause ¶
func (*CachedSchema) ExtractValues ¶
func (s *CachedSchema) ExtractValues(val reflect.Value) []any
type FieldNotFoundError ¶
type FieldNotFoundError struct {
Name string
}
func (*FieldNotFoundError) Error ¶
func (e *FieldNotFoundError) Error() string
type Options ¶
type Options struct {
// Order sorts the result, applied in the order given.
Order []Order
// Limit caps the row count; zero or less means no cap.
Limit int
// Offset skips rows.
Offset int
}
Options narrows and orders a read. The zero value means "everything".
func (Options) LimitClause ¶
LimitClause renders the LIMIT/OFFSET pair, which every SQL dialect here spells the same way.
func (Options) Validate ¶
func (o Options) Validate(schema *CachedSchema) error
Validate rejects names that are not real columns. Sort keys and limits cannot be bound as parameters, so this is what keeps a caller-supplied name out of the query as raw SQL.
type Order ¶
Order is one sort key.
func Descending ¶
type ScanTypeError ¶
ScanTypeError reports rows that could not be materialised into T.
func (*ScanTypeError) Error ¶
func (e *ScanTypeError) Error() string
type Table ¶
type Table[T any] interface { // Ins inserts one row. Ins(val T, ttl time.Duration) error // Get reads the rows matching whereFields, whose values are taken from // val. An empty whereFields matches every row. opts narrows and orders the // result. Get(val T, whereFields []string, opts Options, ttl time.Duration) ([]T, error) // Set updates rows where the columns named in whereFields equal their // values in old, assigning the columns named in setFields the values in // updated. Passing the same model for both is the common case. Set(old, updated T, whereFields, setFields []string, ttl time.Duration) error // Del removes the rows matching whereFields, whose values are taken from // val. Del(val T, whereFields []string, ttl time.Duration) error }
Table is the CRUD surface of one table.
Read and write options are kept separate on purpose: whereFields name the columns whose values come from the passed model, while setFields name the columns to assign. That split is what lets Set distinguish "match on the old value" from "write the new one" without the caller having to remember which fields to exclude.
The ttl argument of Ins and Set sets a deadline; see ExpiryFor for the semantics. It is ignored on reads and on Del.