gastownhall/beads · error

checkout branch %s: %w

Error message

checkout branch %s: %w

What it means

CheckoutBranch runs CALL DOLT_CHECKOUT(?) to switch the session's active branch and wraps failures as 'checkout branch <name>: %w'. Because Dolt checkout is session-scoped, failure means the session stays on the old branch. Dolt rejects checkout when the branch doesn't exist or when uncommitted working-set changes would conflict with the switch.

Source

Thrown at internal/storage/versioncontrolops/branches.go:55

func CreateBranch(ctx context.Context, db DBConn, name string) error {
	if _, err := db.ExecContext(ctx, "CALL DOLT_BRANCH(?)", name); err != nil {
		return fmt.Errorf("create branch %s: %w", name, err)
	}
	return nil
}

// DeleteBranch force-deletes a Dolt branch.
func DeleteBranch(ctx context.Context, db DBConn, name string) error {
	if _, err := db.ExecContext(ctx, "CALL DOLT_BRANCH('-D', ?)", name); err != nil {
		return fmt.Errorf("delete branch %s: %w", name, err)
	}
	return nil
}

// CheckoutBranch switches the active session to the named branch.
func CheckoutBranch(ctx context.Context, db DBConn, name string) error {
	if _, err := db.ExecContext(ctx, "CALL DOLT_CHECKOUT(?)", name); err != nil {
		return fmt.Errorf("checkout branch %s: %w", name, err)
	}
	return nil
}

View on GitHub (pinned to 71377f2769)

Solutions

  1. Commit or stash pending changes (StageAndCommit / DOLT_RESET) before checkout
  2. Confirm the branch exists (query dolt_branches) before checkout
  3. Use a single dedicated connection for checkout and subsequent session-scoped operations, not a pooled *sql.DB

Example fix

// before
err := versioncontrolops.CheckoutBranch(ctx, pooledDB, "feature")
// after
conn := db.Conn(ctx) // dedicated session
_, _ = conn.ExecContext(ctx, "CALL DOLT_ADD('-A')")
err := versioncontrolops.CheckoutBranch(ctx, conn, "feature")
Defensive patterns

Strategy: validation

Validate before calling

var exists int
_ = db.QueryRowContext(ctx,
    "SELECT COUNT(*) FROM dolt_branches WHERE name = ?", name).Scan(&exists)
// require exists == 1 before checkout

Prevention

When it happens

Trigger: Calling CheckoutBranch for a branch that doesn't exist; switching while the session has dirty working-set changes that block the switch; using a pooled connection so the checkout affects the wrong session or the error arises from a dead connection.

Common situations: Typo in branch name; dirty tables from an earlier failed commit; running against a connection pool instead of a single dedicated connection (session state mismatch); branch deleted by another process.

Related errors


AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30). Data as JSON: /api/errors/dc1727ee22b20221. Report an issue: GitHub.