goose

package module
v3.0.1 Latest Latest
Warning

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

Go to latest
Published: Nov 20, 2023 License: MIT Imports: 27 Imported by: 0

README

goose Goose CI Go Reference Go Report Card

Goose is a database migration tool. Manage your database schema by creating incremental SQL changes or Go functions.

Starting with v3.0.0 this project adds Go module support, but maintains backwards compatibility with older v2.x.y tags.

Goose supports embedding SQL migrations, which means you'll need go1.16 and up. If using go1.15 or lower, then pin v3.0.1.

Goals of this fork

github.com/agrantis/goose is a fork of bitbucket.org/liamstask/goose with the following changes:

  • No config files
  • Default goose binary can migrate SQL files only
  • Go migrations:
    • We don't go build Go migrations functions on-the-fly from within the goose binary
    • Instead, we let you create your own custom goose binary, register your Go migration functions explicitly and run complex migrations with your own *sql.DB connection
    • Go migration functions let you run your code within an SQL transaction, if you use the *sql.Tx argument
  • The goose pkg is decoupled from the binary:
    • goose pkg doesn't register any SQL drivers anymore, thus no driver panic() conflict within your codebase!
    • goose pkg doesn't have any vendor dependencies anymore
  • We use timestamped migrations by default but recommend a hybrid approach of using timestamps in the development process and sequential versions in production.
  • Supports missing (out-of-order) migrations with the -allow-missing flag, or if using as a library supply the functional option goose.WithAllowMissing() to Up, UpTo or UpByOne.
  • Supports applying ad-hoc migrations without tracking them in the schema table. Useful for seeding a database after migrations have been applied. Use -no-versioning flag or the functional option goose.WithNoVersioning().

Install

go install github.com/agrantis/goose/v3/cmd/goose@latest

This will install the goose binary to your $GOPATH/bin directory.

For a lite version of the binary without DB connection dependent commands, use the exclusive build tags:

go build -tags='no_postgres no_mysql no_sqlite3 no_ydb' -o goose ./cmd/goose

For macOS users goose is available as a Homebrew Formulae:

brew install goose

See the docs for more installation instructions.

Usage

Usage: goose [OPTIONS] DRIVER DBSTRING COMMAND

Drivers:
    postgres
    mysql
    sqlite3
    mssql
    redshift
    tidb
    clickhouse
    vertica
    ydb

Examples:
    goose sqlite3 ./foo.db status
    goose sqlite3 ./foo.db create init sql
    goose sqlite3 ./foo.db create add_some_column sql
    goose sqlite3 ./foo.db create fetch_user_data go
    goose sqlite3 ./foo.db up

    goose postgres "user=postgres password=postgres dbname=postgres sslmode=disable" status
    goose mysql "user:password@/dbname?parseTime=true" status
    goose redshift "postgres://user:password@qwerty.us-east-1.redshift.amazonaws.com:5439/db" status
    goose tidb "user:password@/dbname?parseTime=true" status
    goose mssql "sqlserver://user:password@dbname:1433?database=master" status
    goose clickhouse "tcp://127.0.0.1:9000" status
    goose vertica "vertica://user:password@localhost:5433/dbname?connection_load_balance=1" status
    goose ydb "grpc://localhost:2136/local?go_query_mode=scripting&go_fake_tx=scripting&go_query_bind=declare,numeric" status

Options:

  -allow-missing
    	applies missing (out-of-order) migrations
  -certfile string
    	file path to root CA's certificates in pem format (only supported on mysql)
  -dir string
    	directory with migration files (default ".")
  -h	print help
  -no-versioning
    	apply migration commands with no versioning, in file order, from directory pointed to
  -s	use sequential numbering for new migrations
  -ssl-cert string
    	file path to SSL certificates in pem format (only supported on mysql)
  -ssl-key string
    	file path to SSL key in pem format (only supported on mysql)
  -table string
    	migrations table name (default "goose_db_version")
  -v	enable verbose mode
  -version
    	print version

Commands:
    up                   Migrate the DB to the most recent version available
    up-by-one            Migrate the DB up by 1
    up-to VERSION        Migrate the DB to a specific VERSION
    down                 Roll back the version by 1
    down-to VERSION      Roll back to a specific VERSION
    redo                 Re-run the latest migration
    reset                Roll back all migrations
    status               Dump the migration status for the current DB
    version              Print the current version of the database
    create NAME [sql|go] Creates new migration file with the current timestamp
    fix                  Apply sequential ordering to migrations
    validate             Check migration files without running them

create

Create a new SQL migration.

$ goose create add_some_column sql
$ Created new file: 20170506082420_add_some_column.sql

Edit the newly created file to define the behavior of your migration.

You can also create a Go migration, if you then invoke it with your own goose binary:

$ goose create fetch_user_data go
$ Created new file: 20170506082421_fetch_user_data.go

up

Apply all available migrations.

$ goose up
$ OK    001_basics.sql
$ OK    002_next.sql
$ OK    003_and_again.go

up-to

Migrate up to a specific version.

$ goose up-to 20170506082420
$ OK    20170506082420_create_table.sql

up-by-one

Migrate up a single migration from the current version

$ goose up-by-one
$ OK    20170614145246_change_type.sql

down

Roll back a single migration from the current version.

$ goose down
$ OK    003_and_again.go

down-to

Roll back migrations to a specific version.

$ goose down-to 20170506082527
$ OK    20170506082527_alter_column.sql

redo

Roll back the most recently applied migration, then run it again.

$ goose redo
$ OK    003_and_again.go
$ OK    003_and_again.go

status

Print the status of all migrations:

$ goose status
$   Applied At                  Migration
$   =======================================
$   Sun Jan  6 11:25:03 2013 -- 001_basics.sql
$   Sun Jan  6 11:25:03 2013 -- 002_next.sql
$   Pending                  -- 003_and_again.go

Note: for MySQL parseTime flag must be enabled.

Note: for MySQL multiStatements must be enabled. This is required when writing multiple queries separated by ';' characters in a single sql file.

version

Print the current version of the database:

$ goose version
$ goose: version 002

Migrations

goose supports migrations written in SQL or in Go.

SQL Migrations

A sample SQL migration looks like:

-- +goose Up
CREATE TABLE post (
    id int NOT NULL,
    title text,
    body text,
    PRIMARY KEY(id)
);

-- +goose Down
DROP TABLE post;

Each migration file must have exactly one -- +goose Up annotation. The -- +goose Down annotation is optional. If the file has both annotations, then the -- +goose Up annotation must come first.

Notice the annotations in the comments. Any statements following -- +goose Up will be executed as part of a forward migration, and any statements following -- +goose Down will be executed as part of a rollback.

By default, all migrations are run within a transaction. Some statements like CREATE DATABASE, however, cannot be run within a transaction. You may optionally add -- +goose NO TRANSACTION to the top of your migration file in order to skip transactions within that specific migration file. Both Up and Down migrations within this file will be run without transactions.

By default, SQL statements are delimited by semicolons - in fact, query statements must end with a semicolon to be properly recognized by goose.

More complex statements (PL/pgSQL) that have semicolons within them must be annotated with -- +goose StatementBegin and -- +goose StatementEnd to be properly recognized. For example:

-- +goose Up
-- +goose StatementBegin
CREATE OR REPLACE FUNCTION histories_partition_creation( DATE, DATE )
returns void AS $$
DECLARE
  create_query text;
BEGIN
  FOR create_query IN SELECT
      'CREATE TABLE IF NOT EXISTS histories_'
      || TO_CHAR( d, 'YYYY_MM' )
      || ' ( CHECK( created_at >= timestamp '''
      || TO_CHAR( d, 'YYYY-MM-DD 00:00:00' )
      || ''' AND created_at < timestamp '''
      || TO_CHAR( d + INTERVAL '1 month', 'YYYY-MM-DD 00:00:00' )
      || ''' ) ) inherits ( histories );'
    FROM generate_series( $1, $2, '1 month' ) AS d
  LOOP
    EXECUTE create_query;
  END LOOP;  -- LOOP END
END;         -- FUNCTION END
$$
language plpgsql;
-- +goose StatementEnd

Embedded sql migrations

Go 1.16 introduced new feature: compile-time embedding files into binary and corresponding filesystem abstraction.

This feature can be used only for applying existing migrations. Modifying operations such as fix and create will continue to operate on OS filesystem even if using embedded files. This is expected behaviour because io/fs interfaces allows read-only access.

Make sure to configure the correct SQL dialect, see dialect.go for supported SQL dialects.

Example usage, assuming that SQL migrations are placed in the migrations directory:

package main

import (
    "database/sql"
    "embed"

    "github.com/agrantis/goose/v3"
)

//go:embed migrations/*.sql
var embedMigrations embed.FS

func main() {
    var db *sql.DB
    // setup database

    goose.SetBaseFS(embedMigrations)

    if err := goose.SetDialect("postgres"); err != nil {
        panic(err)
    }

    if err := goose.Up(db, "migrations"); err != nil {
        panic(err)
    }

    // run app
}

Note that we pass "migrations" as directory argument in Up because embedding saves directory structure.

Go Migrations

  1. Create your own goose binary, see example
  2. Import github.com/agrantis/goose
  3. Register your migration functions
  4. Run goose command, ie. goose.Up(db *sql.DB, dir string)

A sample Go migration 00002_users_add_email.go file looks like:

package migrations

import (
	"database/sql"

	"github.com/agrantis/goose/v3"
)

func init() {
	goose.AddMigration(Up, Down)
}

func Up(tx *sql.Tx) error {
	_, err := tx.Exec("UPDATE users SET username='admin' WHERE username='root';")
	if err != nil {
		return err
	}
	return nil
}

func Down(tx *sql.Tx) error {
	_, err := tx.Exec("UPDATE users SET username='root' WHERE username='admin';")
	if err != nil {
		return err
	}
	return nil
}

Note that Go migration files must begin with a numeric value, followed by an underscore, and must not end with *_test.go.

Development

This can be used to build local goose binaries without having the latest Go version installed locally.

DOCKER_BUILDKIT=1  docker build -f Dockerfile.local --output bin .

Hybrid Versioning

Please, read the versioning problem first.

By default, if you attempt to apply missing (out-of-order) migrations goose will raise an error. However, If you want to apply these missing migrations pass goose the -allow-missing flag, or if using as a library supply the functional option goose.WithAllowMissing() to Up, UpTo or UpByOne.

However, we strongly recommend adopting a hybrid versioning approach, using both timestamps and sequential numbers. Migrations created during the development process are timestamped and sequential versions are ran on production. We believe this method will prevent the problem of conflicting versions when writing software in a team environment.

To help you adopt this approach, create will use the current timestamp as the migration version. When you're ready to deploy your migrations in a production environment, we also provide a helpful fix command to convert your migrations into sequential order, while preserving the timestamp ordering. We recommend running fix in the CI pipeline, and only when the migrations are ready for production.

Credit

The gopher mascot was designed by Renée French / CC 3.0. For more info check out the Go Blog. Adapted by Ellen.

License

Licensed under MIT License

Documentation

Index

Constants

View Source
const (
	// DefaultTablename is the default name of the database table used to track history of applied
	// migrations.
	DefaultTablename = "goose_db_version"
)
View Source
const VERSION = "v3.2.0"

Deprecated: VERSION will no longer be supported in the next major release.

Variables

View Source
var (
	// ErrNoMigrationFiles when no migration files have been found.
	ErrNoMigrationFiles = errors.New("no migration files found")
	// ErrNoCurrentVersion when a current migration version is not found.
	ErrNoCurrentVersion = errors.New("no current version found")
	// ErrNoNextVersion when the next migration version is not found.
	ErrNoNextVersion = errors.New("no next version found")
	// MaxVersion is the maximum allowed version.
	MaxVersion int64 = math.MaxInt64
)
View Source
var (
	// ErrVersionNotFound when a migration version is not found.
	ErrVersionNotFound = errors.New("version not found")

	// ErrAlreadyApplied when a migration has already been applied.
	ErrAlreadyApplied = errors.New("already applied")

	// ErrNoMigrations is returned by [NewProvider] when no migrations are found.
	ErrNoMigrations = errors.New("no migrations found")
)

Functions

func AddMigration deprecated

func AddMigration(up, down GoMigration)

AddMigration adds Go migrations.

Deprecated: Use AddMigrationContext.

func AddMigrationContext

func AddMigrationContext(up, down GoMigrationContext)

AddMigrationContext adds Go migrations.

func AddMigrationNoTx deprecated

func AddMigrationNoTx(up, down GoMigrationNoTx)

AddMigrationNoTx adds Go migrations that will be run outside transaction.

Deprecated: Use AddMigrationNoTxContext.

func AddMigrationNoTxContext

func AddMigrationNoTxContext(up, down GoMigrationNoTxContext)

AddMigrationNoTxContext adds Go migrations that will be run outside transaction.

func AddNamedMigration deprecated

func AddNamedMigration(filename string, up, down GoMigration)

AddNamedMigration adds named Go migrations.

Deprecated: Use AddNamedMigrationContext.

func AddNamedMigrationContext

func AddNamedMigrationContext(filename string, up, down GoMigrationContext)

AddNamedMigrationContext adds named Go migrations.

func AddNamedMigrationNoTx deprecated

func AddNamedMigrationNoTx(filename string, up, down GoMigrationNoTx)

AddNamedMigrationNoTx adds named Go migrations that will be run outside transaction.

Deprecated: Use AddNamedMigrationNoTxContext.

func AddNamedMigrationNoTxContext

func AddNamedMigrationNoTxContext(filename string, up, down GoMigrationNoTxContext)

AddNamedMigrationNoTxContext adds named Go migrations that will be run outside transaction.

func Create

func Create(db *sql.DB, dir, name, migrationType string) error

Create writes a new blank migration file.

func CreateWithTemplate

func CreateWithTemplate(db *sql.DB, dir string, tmpl *template.Template, name, migrationType string) error

Create writes a new blank migration file.

func Down

func Down(db *sql.DB, dir string, opts ...OptionsFunc) error

Down rolls back a single migration from the current version.

func DownContext

func DownContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

DownContext rolls back a single migration from the current version.

func DownTo

func DownTo(db *sql.DB, dir string, version int64, opts ...OptionsFunc) error

DownTo rolls back migrations to a specific version.

func DownToContext

func DownToContext(ctx context.Context, db *sql.DB, dir string, version int64, opts ...OptionsFunc) error

DownToContext rolls back migrations to a specific version.

func EnsureDBVersion

func EnsureDBVersion(db *sql.DB) (int64, error)

EnsureDBVersion retrieves the current version for this DB. Create and initialize the DB version table if it doesn't exist.

func EnsureDBVersionContext

func EnsureDBVersionContext(ctx context.Context, db *sql.DB) (int64, error)

EnsureDBVersionContext retrieves the current version for this DB. Create and initialize the DB version table if it doesn't exist.

func Fix

func Fix(dir string) error

func GetDBVersion

func GetDBVersion(db *sql.DB) (int64, error)

GetDBVersion is an alias for EnsureDBVersion, but returns -1 in error.

func GetDBVersionContext

func GetDBVersionContext(ctx context.Context, db *sql.DB) (int64, error)

GetDBVersionContext is an alias for EnsureDBVersion, but returns -1 in error.

func NumericComponent

func NumericComponent(filename string) (int64, error)

NumericComponent parses the version from the migration file name.

XXX_descriptivename.ext where XXX specifies the version number and ext specifies the type of migration, either .sql or .go.

func OpenDBWithDriver

func OpenDBWithDriver(driver string, dbstring string) (*sql.DB, error)

OpenDBWithDriver creates a connection to a database, and modifies goose internals to be compatible with the supplied driver by calling SetDialect.

func Redo

func Redo(db *sql.DB, dir string, opts ...OptionsFunc) error

Redo rolls back the most recently applied migration, then runs it again.

func RedoContext

func RedoContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

RedoContext rolls back the most recently applied migration, then runs it again.

func Reset

func Reset(db *sql.DB, dir string, opts ...OptionsFunc) error

Reset rolls back all migrations

func ResetContext

func ResetContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

ResetContext rolls back all migrations

func ResetGlobalMigrations

func ResetGlobalMigrations()

ResetGlobalMigrations resets the global Go migrations registry.

Not safe for concurrent use.

func Run

func Run(command string, db *sql.DB, dir string, args ...string) error

Run runs a goose command.

func RunContext

func RunContext(ctx context.Context, command string, db *sql.DB, dir string, args ...string) error

RunContext runs a goose command.

func RunWithOptions

func RunWithOptions(command string, db *sql.DB, dir string, args []string, options ...OptionsFunc) error

RunWithOptions runs a goose command with options.

func RunWithOptionsContext

func RunWithOptionsContext(ctx context.Context, command string, db *sql.DB, dir string, args []string, options ...OptionsFunc) error

RunWithOptionsContext runs a goose command with options.

func SetBaseFS

func SetBaseFS(fsys fs.FS)

SetBaseFS sets a base FS to discover migrations. It can be used with 'embed' package. Calling with 'nil' argument leads to default behaviour: discovering migrations from os filesystem. Note that modifying operations like Create will use os filesystem anyway.

func SetDialect

func SetDialect(s string) error

SetDialect sets the dialect to use for the goose package.

func SetGlobalMigrations

func SetGlobalMigrations(migrations ...*Migration) error

SetGlobalMigrations registers Go migrations globally. It returns an error if a migration with the same version has already been registered. Go migrations must be constructed using the NewGoMigration function.

Not safe for concurrent use.

func SetLogger

func SetLogger(l Logger)

SetLogger sets the logger for package output

func SetSequential

func SetSequential(s bool)

SetSequential set whether to use sequential versioning instead of timestamp based versioning

func SetTableName

func SetTableName(n string)

SetTableName set goose db version table name

func SetVerbose

func SetVerbose(v bool)

SetVerbose set the goose verbosity mode

func Status

func Status(db *sql.DB, dir string, opts ...OptionsFunc) error

Status prints the status of all migrations.

func StatusContext

func StatusContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

StatusContext prints the status of all migrations.

func TableName

func TableName() string

TableName returns goose db version table name

func Up

func Up(db *sql.DB, dir string, opts ...OptionsFunc) error

Up applies all available migrations.

func UpByOne

func UpByOne(db *sql.DB, dir string, opts ...OptionsFunc) error

UpByOne migrates up by a single version.

func UpByOneContext

func UpByOneContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

UpByOneContext migrates up by a single version.

func UpContext

func UpContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

UpContext applies all available migrations.

func UpTo

func UpTo(db *sql.DB, dir string, version int64, opts ...OptionsFunc) error

UpTo migrates up to a specific version.

func UpToContext

func UpToContext(ctx context.Context, db *sql.DB, dir string, version int64, opts ...OptionsFunc) error

func Version

func Version(db *sql.DB, dir string, opts ...OptionsFunc) error

Version prints the current version of the database.

func VersionContext

func VersionContext(ctx context.Context, db *sql.DB, dir string, opts ...OptionsFunc) error

VersionContext prints the current version of the database.

Types

type Dialect

type Dialect = database.Dialect

Dialect is the type of database dialect. It is an alias for database.Dialect.

const (
	DialectClickHouse  Dialect = database.DialectClickHouse
	DialectMSSQL       Dialect = database.DialectMSSQL
	DialectMySQL       Dialect = database.DialectMySQL
	DialectPostgres    Dialect = database.DialectPostgres
	DialectRedshift    Dialect = database.DialectRedshift
	DialectSQLite3     Dialect = database.DialectSQLite3
	DialectTiDB        Dialect = database.DialectTiDB
	DialectVertica     Dialect = database.DialectVertica
	DialectYdB         Dialect = database.DialectYdB
	DialectSQLAnywhere Dialect = database.DialectSQLAnywhere
)

type GoFunc

type GoFunc struct {
	// Exactly one of these must be set, or both must be nil.
	RunTx func(ctx context.Context, tx *sql.Tx) error
	// -- OR --
	RunDB func(ctx context.Context, db *sql.DB) error

	// Mode is the transaction mode for the migration. When one of the run functions is set, the
	// mode will be inferred from the function and the field is ignored. Users do not need to set
	// this field when supplying a run function.
	//
	// If both run functions are nil, the mode defaults to TransactionEnabled. The use case for nil
	// functions is to record a version in the version table without invoking a Go migration
	// function.
	//
	// The only time this field is required is if BOTH run functions are nil AND you want to
	// override the default transaction mode.
	Mode TransactionMode
}

GoFunc represents a Go migration function.

type GoMigration deprecated

type GoMigration func(tx *sql.Tx) error

GoMigration is a Go migration func that is run within a transaction.

Deprecated: Use GoMigrationContext.

type GoMigrationContext

type GoMigrationContext func(ctx context.Context, tx *sql.Tx) error

GoMigrationContext is a Go migration func that is run within a transaction and receives a context.

type GoMigrationNoTx deprecated

type GoMigrationNoTx func(db *sql.DB) error

GoMigrationNoTx is a Go migration func that is run outside a transaction.

Deprecated: Use GoMigrationNoTxContext.

type GoMigrationNoTxContext

type GoMigrationNoTxContext func(ctx context.Context, db *sql.DB) error

GoMigrationNoTxContext is a Go migration func that is run outside a transaction and receives a context.

type Logger

type Logger interface {
	Fatalf(format string, v ...interface{})
	Printf(format string, v ...interface{})
}

Logger is standard logger interface

func NopLogger

func NopLogger() Logger

NopLogger returns a logger that discards all logged output.

type Migration

type Migration struct {
	Type    MigrationType
	Version int64
	// Source is the path to the .sql script or .go file. It may be empty for Go migrations that
	// have been registered globally and don't have a source file.
	Source string

	UpFnContext, DownFnContext         GoMigrationContext
	UpFnNoTxContext, DownFnNoTxContext GoMigrationNoTxContext

	// These fields will be removed in a future major version. They are here for backwards
	// compatibility and are an implementation detail.
	Registered bool
	UseTx      bool
	Next       int64 // next version, or -1 if none
	Previous   int64 // previous version, -1 if none

	UpFn       GoMigration     // Deprecated: use UpFnContext instead.
	DownFn     GoMigration     // Deprecated: use DownFnContext instead.
	UpFnNoTx   GoMigrationNoTx // Deprecated: use UpFnNoTxContext instead.
	DownFnNoTx GoMigrationNoTx // Deprecated: use DownFnNoTxContext instead.
	// contains filtered or unexported fields
}

Migration struct represents either a SQL or Go migration.

Avoid constructing migrations manually, use NewGoMigration function.

func NewGoMigration

func NewGoMigration(version int64, up, down *GoFunc) *Migration

NewGoMigration creates a new Go migration.

Both up and down functions may be nil, in which case the migration will be recorded in the versions table but no functions will be run. This is useful for recording (up) or deleting (down) a version without running any functions. See GoFunc for more details.

func (*Migration) Down

func (m *Migration) Down(db *sql.DB) error

Down runs a down migration.

func (*Migration) DownContext

func (m *Migration) DownContext(ctx context.Context, db *sql.DB) error

DownContext runs a down migration.

func (*Migration) String

func (m *Migration) String() string

func (*Migration) Up

func (m *Migration) Up(db *sql.DB) error

Up runs an up migration.

func (*Migration) UpContext

func (m *Migration) UpContext(ctx context.Context, db *sql.DB) error

UpContext runs an up migration.

type MigrationRecord deprecated

type MigrationRecord struct {
	VersionID int64
	TStamp    time.Time
	IsApplied bool // was this a result of up() or down()
}

MigrationRecord struct.

Deprecated: unused and will be removed in a future major version.

type MigrationResult

type MigrationResult struct {
	Source    *Source
	Duration  time.Duration
	Direction string
	// Empty indicates no action was taken during the migration, but it was still versioned. For
	// SQL, it means no statements; for Go, it's a nil function.
	Empty bool
	// Error is only set if the migration failed.
	Error error
}

MigrationResult is the result of a single migration operation.

type MigrationStatus

type MigrationStatus struct {
	Source    *Source
	State     State
	AppliedAt time.Time
}

MigrationStatus represents the status of a single migration.

type MigrationType

type MigrationType string

MigrationType is the type of migration.

const (
	TypeGo  MigrationType = "go"
	TypeSQL MigrationType = "sql"
)

type Migrations

type Migrations []*Migration

Migrations slice.

func CollectMigrations

func CollectMigrations(dirpath string, current, target int64) (Migrations, error)

CollectMigrations returns all the valid looking migration scripts in the migrations folder and go func registry, and key them by version.

func (Migrations) Current

func (ms Migrations) Current(current int64) (*Migration, error)

Current gets the current migration.

func (Migrations) Last

func (ms Migrations) Last() (*Migration, error)

Last gets the last migration.

func (Migrations) Len

func (ms Migrations) Len() int

helpers so we can use pkg sort

func (Migrations) Less

func (ms Migrations) Less(i, j int) bool

func (Migrations) Next

func (ms Migrations) Next(current int64) (*Migration, error)

Next gets the next migration.

func (Migrations) Previous

func (ms Migrations) Previous(current int64) (*Migration, error)

Previous : Get the previous migration.

func (Migrations) String

func (ms Migrations) String() string

func (Migrations) Swap

func (ms Migrations) Swap(i, j int)

type OptionsFunc

type OptionsFunc func(o *options)

func WithAllowMissing

func WithAllowMissing() OptionsFunc

func WithNoColor

func WithNoColor(b bool) OptionsFunc

func WithNoVersioning

func WithNoVersioning() OptionsFunc

type PartialError

type PartialError struct {
	// Applied are migrations that were applied successfully before the error occurred. May be
	// empty.
	Applied []*MigrationResult
	// Failed contains the result of the migration that failed. Cannot be nil.
	Failed *MigrationResult
	// Err is the error that occurred while running the migration and caused the failure.
	Err error
}

PartialError is returned when a migration fails, but some migrations already got applied.

func (*PartialError) Error

func (e *PartialError) Error() string

type Provider

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

Provider is a goose migration provider.

func NewProvider

func NewProvider(dialect Dialect, db *sql.DB, fsys fs.FS, opts ...ProviderOption) (*Provider, error)

NewProvider returns a new goose provider.

The caller is responsible for matching the database dialect with the database/sql driver. For example, if the database dialect is "postgres", the database/sql driver could be github.com/lib/pq or github.com/jackc/pgx. Each dialect has a corresponding database.Dialect constant backed by a default database.Store implementation. For more advanced use cases, such as using a custom table name or supplying a custom store implementation, see WithStore.

fsys is the filesystem used to read migration files, but may be nil. Most users will want to use os.DirFS, os.DirFS("path/to/migrations"), to read migrations from the local filesystem. However, it is possible to use a different "filesystem", such as embed.FS or filter out migrations using fs.Sub.

See ProviderOption for more information on configuring the provider.

Unless otherwise specified, all methods on Provider are safe for concurrent use.

Experimental: This API is experimental and may change in the future.

func (*Provider) ApplyVersion

func (p *Provider) ApplyVersion(ctx context.Context, version int64, direction bool) (*MigrationResult, error)

ApplyVersion applies exactly one migration for the specified version. If there is no migration available for the specified version, this method returns ErrVersionNotFound. If the migration has already been applied, this method returns ErrAlreadyApplied.

The direction parameter determines the migration direction: true for up migration and false for down migration.

func (*Provider) Close

func (p *Provider) Close() error

Close closes the database connection initially supplied to the provider.

func (*Provider) Down

func (p *Provider) Down(ctx context.Context) (*MigrationResult, error)

Down rolls back the most recently applied migration. If there are no migrations to rollback, this method returns ErrNoNextVersion.

Note, migrations are rolled back in the order they were applied. And not in the reverse order of the migration version. This only applies in scenarios where migrations are allowed to be applied out of order.

func (*Provider) DownTo

func (p *Provider) DownTo(ctx context.Context, version int64) ([]*MigrationResult, error)

DownTo rolls back all migrations down to, but not including, the specified version.

For example, if the current database version is 11,10,9... and the requested version is 9, only migrations 11, 10 will be rolled back.

Note, migrations are rolled back in the order they were applied. And not in the reverse order of the migration version. This only applies in scenarios where migrations are allowed to be applied out of order.

func (*Provider) GetDBVersion

func (p *Provider) GetDBVersion(ctx context.Context) (int64, error)

GetDBVersion returns the highest version recorded in the database, regardless of the order in which migrations were applied. For example, if migrations were applied out of order (1,4,2,3), this method returns 4. If no migrations have been applied, it returns 0.

func (*Provider) ListSources

func (p *Provider) ListSources() []*Source

ListSources returns a list of all migration sources known to the provider, sorted in ascending order by version. The path field may be empty for manually registered migrations, such as Go migrations registered using the WithGoMigrations option.

func (*Provider) Ping

func (p *Provider) Ping(ctx context.Context) error

Ping attempts to ping the database to verify a connection is available.

func (*Provider) Status

func (p *Provider) Status(ctx context.Context) ([]*MigrationStatus, error)

Status returns the status of all migrations, merging the list of migrations from the database and filesystem. The returned items are ordered by version, in ascending order.

func (*Provider) Up

func (p *Provider) Up(ctx context.Context) ([]*MigrationResult, error)

Up applies all pending migrations. If there are no new migrations to apply, this method returns empty list and nil error.

func (*Provider) UpByOne

func (p *Provider) UpByOne(ctx context.Context) (*MigrationResult, error)

UpByOne applies the next pending migration. If there is no next migration to apply, this method returns ErrNoNextVersion. The returned list will always have exactly one migration result.

func (*Provider) UpTo

func (p *Provider) UpTo(ctx context.Context, version int64) ([]*MigrationResult, error)

UpTo applies all pending migrations up to, and including, the specified version. If there are no migrations to apply, this method returns empty list and nil error.

For example, if there are three new migrations (9,10,11) and the current database version is 8 with a requested version of 10, only versions 9,10 will be applied.

type ProviderOption

type ProviderOption interface {
	// contains filtered or unexported methods
}

ProviderOption is a configuration option for a goose goose.

func WithAllowOutofOrder

func WithAllowOutofOrder(b bool) ProviderOption

WithAllowOutofOrder allows the provider to apply missing (out-of-order) migrations. By default, goose will raise an error if it encounters a missing migration.

For example: migrations 1,3 are applied and then version 2,6 are introduced. If this option is true, then goose will apply 2 (missing) and 6 (new) instead of raising an error. The final order of applied migrations will be: 1,3,2,6. Out-of-order migrations are always applied first, followed by new migrations.

func WithDisableGlobalRegistry

func WithDisableGlobalRegistry(b bool) ProviderOption

WithDisableGlobalRegistry prevents the provider from registering Go migrations from the global registry. By default, goose will register all Go migrations including those registered globally.

func WithDisableVersioning

func WithDisableVersioning(b bool) ProviderOption

WithDisableVersioning disables versioning. Disabling versioning allows applying migrations without tracking the versions in the database schema table. Useful for tests, seeding a database or running ad-hoc queries. By default, goose will track all versions in the database schema table.

func WithExcludeNames

func WithExcludeNames(excludes []string) ProviderOption

WithExcludeNames excludes the given file name from the list of migrations. If called multiple times, the list of excludes is merged.

func WithExcludeVersions

func WithExcludeVersions(versions []int64) ProviderOption

WithExcludeVersions excludes the given versions from the list of migrations. If called multiple times, the list of excludes is merged.

func WithGoMigrations

func WithGoMigrations(migrations ...*Migration) ProviderOption

WithGoMigrations registers Go migrations with the provider. If a Go migration with the same version has already been registered, an error will be returned.

Go migrations must be constructed using the NewGoMigration function.

func WithSessionLocker

func WithSessionLocker(locker lock.SessionLocker) ProviderOption

WithSessionLocker enables locking using the provided SessionLocker.

If WithSessionLocker is not called, locking is disabled.

func WithStore

func WithStore(store database.Store) ProviderOption

WithStore configures the provider with a custom database.Store implementation.

By default, the provider uses the database.NewStore function to create a store backed by the given dialect. However, this option allows users to provide their own implementation or call database.NewStore with custom options, such as setting the table name.

Example:

// Create a store with a custom table name.
store, err := database.NewStore(database.DialectPostgres, "my_custom_table_name")
if err != nil {
    return err
}
// Create a provider with the custom store.
provider, err := goose.NewProvider("", db, nil, goose.WithStore(store))
if err != nil {
    return err
}

func WithVerbose

func WithVerbose(b bool) ProviderOption

WithVerbose enables verbose logging.

type Source

type Source struct {
	Type    MigrationType
	Path    string
	Version int64
}

Source represents a single migration source.

The Path field may be empty if the migration was registered manually. This is typically the case for Go migrations registered using the [WithGoMigration] option.

type State

type State string

State represents the state of a migration.

const (
	// StatePending is a migration that exists on the filesystem, but not in the database.
	StatePending State = "pending"
	// StateApplied is a migration that has been applied to the database and exists on the
	// filesystem.
	StateApplied State = "applied"
)

type TransactionMode

type TransactionMode int

TransactionMode represents the possible transaction modes for a migration.

const (
	TransactionEnabled TransactionMode = iota + 1
	TransactionDisabled
)

func (TransactionMode) String

func (m TransactionMode) String() string

Directories

Path Synopsis
cmd
Package database defines a generic [Store] interface for goose to use when interacting with the database.
Package database defines a generic [Store] interface for goose to use when interacting with the database.
examples
internal
cfg
Package lock defines the Locker interface and implements the locking logic.
Package lock defines the Locker interface and implements the locking logic.

Jump to

Keyboard shortcuts

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