gastownhall/beads · error
committing migrations: %w
Error message
committing migrations: %w
What it means
This error wraps a failure from `CALL DOLT_COMMIT('-m', 'schema: apply migrations')` at the end of MigrateUp. After schema migrations have applied and staged changes were detected (stageSchemaTables returned true), the library attempts to commit the migration work so the database converges to a clean working set. If Dolt rejects the commit for any reason other than "nothing to commit" (which is tolerated and swallowed), the underlying driver error is wrapped as "committing migrations: %w".
Source
Thrown at internal/storage/schema/schema.go:739
}
changedDirtyTables, err := changedDirtyTableSignatures(ctx, db, dirtyBeforeSignatures)
if err != nil {
return applied, fmt.Errorf("checking pre-existing dirty table diffs: %w", err)
}
if len(changedDirtyTables) > 0 {
return applied, fmt.Errorf("pre-existing dirty tables changed during schema migration: %s", strings.Join(changedDirtyTables, ", "))
}
staged, err := stageSchemaTables(ctx, db, dirtyBefore)
if err != nil {
return applied, fmt.Errorf("staging migrations: %w", err)
}
if !staged {
return applied, nil
}
if err := DrainCall(ctx, db, "CALL DOLT_COMMIT('-m', 'schema: apply migrations')"); err != nil {
if !strings.Contains(strings.ToLower(err.Error()), "nothing to commit") {
return applied, fmt.Errorf("committing migrations: %w", err)
}
}
return applied, nil
}
func migrationWorkNeeded(ctx context.Context, db DBConn) (bool, error) {
if !mainSource.atLatest(ctx, db) || !ignoredSource.atLatest(ctx, db) {
return true, nil
}
// A database already at the latest numbered migration still needs work if it
// predates the content_hash column (gastownhall/beads#4259 reporter fix No.2).
// Without this, MigrateUp short-circuits before migrate() runs the idempotent
// ALTER, so the recording/detection surface is never installed on exactly the
// already-upgraded databases the fix is meant to protect.
hasMainHash, err := mainSource.hasContentHashColumn(ctx, db)
if err != nil {
return false, errView on GitHub (pinned to 71377f2769)
Solutions
- Inspect the wrapped cause (%w) printed after "committing migrations:" — it names the actual Dolt failure; fix that condition first.
- Run `bd doctor` (or `dolt status` in the .beads database dir) to check for a dirty/conflicting working set, then resolve or reset the conflicted tables.
- Retry the open/migration after ensuring the database directory is writable and no other process holds the DB lock (MigrateUpWithLock takes the advisory lock for you).
- If the working set is corrupted by a crashed pass, verify the migration self-heal path: re-run MigrateUp — the #4566 contract expects a retry from a clean working set to converge.
- Check the installed Dolt/embedded-dolt version against the version beads was built for; upgrade or downgrade to a compatible release.
Example fix
// before: opaque failure at open time
if err := DrainCall(ctx, db, "CALL DOLT_COMMIT('-m', 'schema: apply migrations')"); err != nil {
return applied, fmt.Errorf("committing migrations: %w", err)
}
// after: caller-side handling that inspects the cause and retries once
var openErr error
for i := 0; i < 2; i++ {
_, openErr = storage.Open(ctx, dbPath)
if openErr == nil || !strings.Contains(openErr.Error(), "committing migrations") {
break
}
time.Sleep(500 * time.Millisecond) // transient engine/lock condition
} Defensive patterns
Strategy: try-catch
Validate before calling
// Go: ensure the database dir is writable and no merge state before migrating
func canCommit(dbPath string) error {
fi, err := os.Stat(dbPath)
if err != nil || !fi.IsDir() {
return fmt.Errorf("db path missing: %s", dbPath)
}
if err := unix.Access(dbPath, unix.W_OK); err != nil {
return fmt.Errorf("db not writable: %w", err)
}
return nil
} Type guard
// Go: the wrapped error is opaque (%w of a driver error); narrow by message
func isMigrationCommitError(err error) bool {
return err != nil && strings.Contains(err.Error(), "committing migrations:")
} Try / catch
_, err := schema.MigrateUp(ctx, db)
if err != nil {
var pathErr *os.PathError
switch {
case isMigrationCommitError(err):
// inspect wrapped cause, check `dolt status`, retry once
case errors.As(err, &pathErr):
// fix filesystem permission
default:
return err
}
} Prevention
- Always migrate via MigrateUpWithLock so no competing process mutates the working set mid-commit
- Keep the .beads database directory writable by the running user
- Commit or clean user-staged changes before running migrations
- Pin/verify the Dolt engine version beads was built against
When it happens
Trigger: Calling MigrateUp (directly or via MigrateUpWithLock) when stageSchemaTables staged migration changes but the subsequent DOLT_COMMIT fails — e.g. Dolt server refused the commit, a merge/conflict state exists, the DB is read-only, or the connection dropped mid-commit. Only non-"nothing to commit" errors produce this.
Common situations: Running `bd` against an embedded Dolt database whose working set entered a conflicting state between staging and commit; opening a database on a read-only filesystem; an interrupted earlier migration pass leaving the repo in a state Dolt refuses to commit; Dolt version differences changing DOLT_COMMIT behavior; transient connection loss to the storage engine.
Related errors
- committing migration %s: %w
- committing migration step: %w
- failed to commit is_blocked repairs to Dolt: %w
- failed to commit dependency key repairs: %w
- failed to commit orphaned dependency removals: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/573eb35a2042004e.
Report an issue: GitHub.