gastownhall/beads · error
ErrScan
ErrScan
Error message
scan error
What it means
ErrScan is the dolt storage layer's sentinel for failures converting database rows into Go values — rows.Scan failing because column types or count don't match the destination (e.g. NULL into a non-nullable field, column added/renamed by a schema change). wrapScanError embeds it in the chain for errors.Is classification.
Source
Thrown at internal/storage/dolt/errors.go:28
mysql "github.com/go-sql-driver/mysql"
"github.com/steveyegge/beads/internal/storage"
"github.com/steveyegge/beads/internal/storage/dberrors"
)
// Sentinel errors for the dolt storage layer.
// These complement the storage-level sentinels (storage.ErrNotFound, etc.)
// with dolt-specific error types.
var (
// ErrTransaction indicates a transaction begin/commit/rollback failure.
ErrTransaction = errors.New("transaction error")
// ErrQuery indicates a database query failure.
ErrQuery = errors.New("query error")
// ErrScan indicates a failure scanning database rows into Go values.
ErrScan = errors.New("scan error")
// ErrExec indicates a database exec (INSERT/UPDATE/DELETE) failure.
ErrExec = errors.New("exec error")
// ErrDanglingReference indicates that the pre-push integrity check detected
// missing chunks in the local Dolt noms store. The push was aborted to
// prevent propagating the corruption to the remote. Run bd dolt verify
// to diagnose and recover.
ErrDanglingReference = errors.New("dangling chunk reference")
// ErrFSCKTimeout indicates that the pre-push integrity check (dolt fsck) did
// not complete within the configured timeout. The push was aborted without
// verifying chunk integrity — the store is not necessarily corrupt. Large
// stores can be shrunk with `dolt gc` (or `CALL DOLT_GC()` on a running
// sql-server); the timeout can be raised via the BEADS_FSCK_TIMEOUT
// environment variable.
ErrFSCKTimeout = errors.New("pre-push integrity check timed out")
View on GitHub (pinned to 71377f2769)
Solutions
- Compare your bd binary version with the database schema version (bd doctor) — upgrade or migrate so they match
- Read the wrapped error for the exact column mismatch: errors.Is(err, dolt.ErrScan) then unwrap
- If caused by version rollback, re-upgrade the binary or restore a matching backup (bd backup restore)
- Fix the NULL source or change the scan destination to a pointer/sql.Null* type if you own the query
Example fix
// before
var assignee string
if err := row.Scan(&id, &assignee); err != nil { return err } // fails on NULL assignee
// after
var assignee sql.NullString
if err := row.Scan(&id, &assignee); err != nil {
if errors.Is(err, dolt.ErrScan) { /* schema drift: check bd doctor */ }
return err
}
a := assignee.String // empty when NULL Defensive patterns
Strategy: type-guard
Type guard
func isScanError(err error) bool {
return errors.Is(err, dolt.ErrScan)
} Try / catch
if err := store.List(ctx); err != nil {
if errors.Is(err, dolt.ErrScan) {
return fmt.Errorf("schema mismatch between binary and database; run bd doctor / re-migrate: %w", err)
}
return err
} Prevention
- Keep the bd binary and database schema versions in sync — never roll back the binary across migrations
- Run bd doctor after version changes to detect schema drift early
- Scan nullable columns into sql.Null* types or pointers
- Let migrations own all schema changes; avoid hand-editing the database
- Back up before upgrades so a bad migration can be restored (bd backup restore)
When it happens
Trigger: Any dolt-backed read where rows.Scan fails after a successful query: schema drift between the running code and the database (a column added, removed, or type-changed), unexpected NULL in a column scanned into a non-pointer type, or a column order/count mismatch in hand-written SELECTs.
Common situations: Rolling back the bd binary to an older version against a newer migrated database; a partially applied or failed migration; manually editing the schema; database written by a newer bd version and read by an older one.
Related errors
- ErrTransaction
- ErrQuery
- failed to get current commit: %w
- failed to open database: %w Hint: %s
- failed to begin transaction: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/ec87b1d2a1ef503d.
Report an issue: GitHub.