# README
PostgreSQL client and ORM for Golang
Maintenance mode
go-pg is in a maintenance mode and only critical issues are addressed. New development happens in Bun repo which offers similar functionality but works with PostgreSQL, MySQL, MariaDB, and SQLite.
Golang ORM
- Documentation
- Reference
- Examples
- Example projects:
- monetr - budgeting application focused on planning for recurring expenses
- bunrouter
- gin
- go-kit
- aah framework
Tutorials
Ecosystem
- Migrations by vmihailenco and robinjoseph08.
- Genna - cli tool for generating go-pg models.
- bigint - big.Int type for go-pg.
- urlstruct to decode
url.Values
into structs. - Sharding.
- go-pg-monitor - Prometheus metrics based on go-pg client stats.
Features
- Basic types: integers, floats, string, bool, time.Time, net.IP, net.IPNet.
- sql.NullBool, sql.NullString, sql.NullInt64, sql.NullFloat64 and pg.NullTime.
- sql.Scanner and sql/driver.Valuer interfaces.
- Structs, maps and arrays are marshalled as JSON by default.
- PostgreSQL multidimensional Arrays using array tag and Array wrapper.
- Hstore using hstore tag and Hstore wrapper.
- Composite types.
- All struct fields are nullable by default and zero values (empty string, 0, zero time, empty map
or slice, nil ptr) are marshalled as SQL
NULL
.pg:",notnull"
is used to add SQLNOT NULL
constraint andpg:",use_zero"
to allow Go zero values. - Transactions.
- Prepared statements.
- Notifications using
LISTEN
andNOTIFY
. - Copying data using
COPY FROM
andCOPY TO
. - Timeouts and canceling queries using context.Context.
- Automatic connection pooling with circuit breaker support.
- Queries retry on network errors.
- Working with models using ORM and SQL.
- Scanning variables using ORM and SQL.
- SelectOrInsert using on-conflict.
- INSERT ... ON CONFLICT DO UPDATE using ORM.
- Bulk/batch inserts, updates, and deletes.
- Common table expressions using WITH and WrapWith.
- CountEstimate
using
EXPLAIN
to get estimated number of matching rows. - ORM supports has one, belongs to, has many, and many to many with composite/multi-column primary keys.
- Soft deletes.
- Creating tables from structs.
- ForEach that calls a function for each row returned by the query without loading all rows into the memory.
Installation
go-pg supports 2 last Go versions and requires a Go version with modules support. So make sure to initialize a Go module:
go mod init github.com/my/repo
And then install go-pg (note v10 in the import; omitting it is a popular mistake):
go get github.com/go-pg/pg/v10
Quickstart
package pg_test
import (
"fmt"
"github.com/go-pg/pg/v10"
"github.com/go-pg/pg/v10/orm"
)
type User struct {
Id int64
Name string
Emails []string
}
func (u User) String() string {
return fmt.Sprintf("User<%d %s %v>", u.Id, u.Name, u.Emails)
}
type Story struct {
Id int64
Title string
AuthorId int64
Author *User `pg:"rel:has-one"`
}
func (s Story) String() string {
return fmt.Sprintf("Story<%d %s %s>", s.Id, s.Title, s.Author)
}
func ExampleDB_Model() {
db := pg.Connect(&pg.Options{
User: "postgres",
})
defer db.Close()
err := createSchema(db)
if err != nil {
panic(err)
}
user1 := &User{
Name: "admin",
Emails: []string{"admin1@admin", "admin2@admin"},
}
_, err = db.Model(user1).Insert()
if err != nil {
panic(err)
}
_, err = db.Model(&User{
Name: "root",
Emails: []string{"root1@root", "root2@root"},
}).Insert()
if err != nil {
panic(err)
}
story1 := &Story{
Title: "Cool story",
AuthorId: user1.Id,
}
_, err = db.Model(story1).Insert()
if err != nil {
panic(err)
}
// Select user by primary key.
user := &User{Id: user1.Id}
err = db.Model(user).WherePK().Select()
if err != nil {
panic(err)
}
// Select all users.
var users []User
err = db.Model(&users).Select()
if err != nil {
panic(err)
}
// Select story and associated author in one query.
story := new(Story)
err = db.Model(story).
Relation("Author").
Where("story.id = ?", story1.Id).
Select()
if err != nil {
panic(err)
}
fmt.Println(user)
fmt.Println(users)
fmt.Println(story)
// Output: User<1 admin [admin1@admin admin2@admin]>
// [User<1 admin [admin1@admin admin2@admin]> User<2 root [root1@root root2@root]>]
// Story<1 Cool story User<1 admin [admin1@admin admin2@admin]>>
}
// createSchema creates database schema for User and Story models.
func createSchema(db *pg.DB) error {
models := []interface{}{
(*User)(nil),
(*Story)(nil),
}
for _, model := range models {
err := db.Model(model).CreateTable(&orm.CreateTableOptions{
Temp: true,
})
if err != nil {
return err
}
}
return nil
}
See also
# Functions
Array accepts a slice and returns a wrapper for working with PostgreSQL array data type.
Connect connects to a database using provided options.
Hstore accepts a map and returns a wrapper for working with hstore data type.
In accepts a slice and returns a wrapper that can be used with PostgreSQL IN operator:
Where("id IN (?)", pg.In([]int{1, 2, 3, 4}))
produces
WHERE id IN (1, 2, 3, 4).
InMulti accepts multiple values and returns a wrapper that can be used with PostgreSQL IN operator:
Where("(id1, id2) IN (?)", pg.InMulti([]int{1, 2}, []int{3, 4}))
produces
WHERE (id1, id2) IN ((1, 2), (3, 4)).
Model returns a new query for the optional model.
ModelContext returns a new query for the optional model with a context.
ParseURL parses an URL into options that can be used to connect to PostgreSQL.
SafeQuery replaces any placeholders found in the query.
Scan returns ColumnScanner that copies the columns in the row into the values.
SetLogger sets the logger to the given one.
Version is the current release version.
# Variables
Discard is used with Query and QueryOne to discard rows.
ErrMultiRows is returned by QueryOne and ExecOne when query returned multiple rows but exactly one row is expected.
ErrNoRows is returned by QueryOne and ExecOne when query returned zero rows but at least one row is expected.
ErrTxDone is returned by any operation that is performed on a transaction that has already been committed or rolled back.
# Structs
Conn represents a single database connection rather than a pool of database connections.
DB is a database handle representing a pool of zero or more underlying connections.
Listener listens for notifications sent with NOTIFY command.
Notification which is received with LISTEN command.
Options contains database connection options.
QueryEvent ...
Stmt is a prepared statement.
Tx is an in-progress database transaction.
# Type aliases
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
No description provided by the author
Ident represents a SQL identifier, e.g.
Ints is a type alias for a slice of int64 values.
IntSet is a set of int64 values.
NullTime is a time.Time wrapper that marshals zero time as JSON null and PostgreSQL NULL.
PoolStats contains the stats of a connection pool.
No description provided by the author
Result summarizes an executed SQL command.
Safe represents a safe SQL query.
Strings is a type alias for a slice of strings.