golang-migrate/migrate · error
no schema
Error message
no schema
What it means
ErrNoSchema is the sentinel error returned by the pgx (and pgx v5) drivers when a schema name is required but empty. In pgx, Open/WithInstance derive the schema from Config.SchemaName or the `search_path`/x-no-lock-etc DSN settings; if no schema can be determined, the driver returns ErrNoSchema because migrations must be scoped to a known schema.
Source
Thrown at database/pgx/v5/pgx.go:41
_ "github.com/jackc/pgx/v5/stdlib"
)
func init() {
db := Postgres{}
database.Register("pgx5", &db)
}
var (
multiStmtDelimiter = []byte(";")
DefaultMigrationsTable = "schema_migrations"
DefaultMultiStatementMaxSize = 10 * 1 << 20 // 10 MB
)
var (
ErrNilConfig = fmt.Errorf("no config")
ErrNoDatabaseName = fmt.Errorf("no database name")
ErrNoSchema = fmt.Errorf("no schema")
)
type Config struct {
MigrationsTable string
DatabaseName string
SchemaName string
migrationsSchemaName string
migrationsTableName string
StatementTimeout time.Duration
MigrationsTableQuoted bool
MultiStatementEnabled bool
MultiStatementMaxSize int
}
type Postgres struct {
// Locking and unlocking need to use the same connection
conn *sql.Conn
db *sql.DBView on GitHub (pinned to 01a9643f14)
Solutions
- Set Config.SchemaName explicitly (e.g. "public") or include search_path in the DSN: postgres://.../db?search_path=myschema.
- If relying on search_path, add it to the connection string's options parameter so Open can derive the schema.
- Validate that the schema value is non-empty before constructing Config in multi-tenant code paths.
- Match with errors.Is(err, pgx.ErrNoSchema) and surface a clear message about which schema setting is missing.
Example fix
// before dsn := "postgres://user:pass@host/db" drv, err := pgx.Open(dsn) // ErrNoSchema if search_path absent // after dsn := "postgres://user:pass@host/db?search_path=myschema"
Defensive patterns
Strategy: validation
Validate before calling
if cfg.SchemaName == "" && !strings.Contains(dsn, "search_path") {
cfg.SchemaName = "public"
} Type guard
func hasSchema(c *pgx.Config) bool { return c != nil && c.SchemaName != "" } Try / catch
drv, err := pgx.Open(dsn)
if err != nil {
if errors.Is(err, pgx.ErrNoSchema) {
return fmt.Errorf("set SchemaName or add ?search_path=<schema> to the DSN: %w", err)
}
return err
} Prevention
- Set SchemaName explicitly in multi-tenant environments rather than relying on server defaults
- Include search_path in the migrate DSN, not just the application connection
- Validate schema presence per tenant before running migrations
When it happens
Trigger: Calling pgx.Open/WithInstance with a Config whose SchemaName is empty and a DSN that does not carry a schema (no search_path in the options and no x-schema-name-style parameter), e.g. `postgres://user:pass@host/db` with &Config{}.
Common situations: Deployments where the app connects with search_path set server-side per role but the migrate DSN is built independently and loses it; forgetting to set SchemaName when the database user's default schema (public) was intentionally renamed; multi-tenant setups where the schema comes from the request context and is sometimes empty.
Understand the failure class
Background: "is required", "must be set", "missing required field": configuration validation errors across open-source libraries — this error's family across 36 libraries.
Related errors
- no database name
- unable to parse option x-migrations-table-quoted: %w
- x-migrations-table must be quoted (for instance '"migrate"."
- unable to parse option x-multi-statement: %w
- unknown lock strategy "%s"
AI-assisted analysis of golang-migrate/migrate@01a9643f14 (2026-09-02).
Data as JSON: /api/errors/abc06797170f3719.
Report an issue: GitHub.