gastownhall/beads · error
checking constraint %s on %s: %w
Error message
checking constraint %s on %s: %w
What it means
Wraps a failure from schemaConstraintExists, which probes INFORMATION_SCHEMA.TABLE_CONSTRAINTS for a named foreign-key or check constraint (used by wispDepMissingAnyFinalConstraint, dropWispDepLegacyShape, ensureWispDepFinalKeysAndConstraints). Unlike schemaHasPrimaryKey it asks about one specific name, which add-if-absent steps need. Thrown only on query failure; a missing constraint is a normal result.
Source
Thrown at internal/storage/schema/migration_repairs.go:731
if err := db.QueryRowContext(ctx, `
SELECT COUNT(*) FROM INFORMATION_SCHEMA.STATISTICS
WHERE TABLE_SCHEMA = DATABASE() AND TABLE_NAME = ? AND INDEX_NAME = ?
`, table, index).Scan(&count); err != nil {
return false, fmt.Errorf("checking index %s on %s: %w", index, table, err)
}
return count > 0, nil
}
// schemaConstraintExists reports whether table carries a named constraint --
// foreign key or check. Unlike schemaHasPrimaryKey it asks about one specific
// name, which is what an add-if-absent step needs.
func schemaConstraintExists(ctx context.Context, db DBConn, table, constraint string) (bool, error) {
var count int
if err := db.QueryRowContext(ctx, `
SELECT COUNT(*) FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS
WHERE TABLE_SCHEMA = DATABASE() AND TABLE_NAME = ? AND CONSTRAINT_NAME = ?
`, table, constraint).Scan(&count); err != nil {
return false, fmt.Errorf("checking constraint %s on %s: %w", constraint, table, err)
}
return count > 0, nil
}
// schemaShowCreateTable returns a table's CREATE statement. It is the only
// place Dolt exposes generated-column shape: INFORMATION_SCHEMA.COLUMNS returns
// EXTRA and GENERATION_EXPRESSION empty for a generated column, and IS_GENERATED
// does not exist there at all.
func schemaShowCreateTable(ctx context.Context, db DBConn, table string) (string, error) {
var name, ddl string
// table is a package constant, never caller input; SHOW CREATE TABLE takes
// no placeholders.
if err := db.QueryRowContext(ctx, "SHOW CREATE TABLE `"+table+"`").Scan(&name, &ddl); err != nil {
return "", fmt.Errorf("reading SHOW CREATE TABLE %s: %w", table, err)
}
return ddl, nil
}
View on GitHub (pinned to 71377f2769)
Solutions
- Inspect the wrapped cause and restore connectivity/server.
- Re-run the repair; constraint add-if-absent logic is idempotent.
- Verify the DB user can SELECT from INFORMATION_SCHEMA.TABLE_CONSTRAINTS.
- Check for ctx deadline issues on very large databases and retry with a longer timeout.
Defensive patterns
Strategy: retry
Validate before calling
var n int err := db.QueryRowContext(ctx, `SELECT COUNT(*) FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME=? AND CONSTRAINT_NAME=?`, table, constraint).Scan(&n)
Type guard
func isSchemaProbeErr(err error) bool {
return strings.Contains(err.Error(), "checking constraint ")
} Try / catch
if err := ensureWispDepFinalKeysAndConstraints(ctx, db); err != nil {
if isRetryableDB(err) { return ensureWispDepFinalKeysAndConstraints(ctx, db) }
return err
} Prevention
- Grant the DB user SELECT on INFORMATION_SCHEMA.TABLE_CONSTRAINTS
- Retry idempotent constraint reconciliation steps
- Avoid context cancellation mid-repair
- Keep the Dolt server up during the full repair
When it happens
Trigger: The SELECT COUNT(*) FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS query errors during constraint reconciliation in the wisp_dependencies repair — server unreachable, context cancelled, or driver failure.
Common situations: Connection interruption during the multi-step wisp_dependencies reshape; insufficient privileges to read TABLE_CONSTRAINTS; Dolt restart mid-repair.
Related errors
- migration 0053: %d dependencies row(s) have no depends_on_is
- checking wisp_dependencies.%s: %w
- checking wisp_dependencies.depends_on_id: %w
- checking index %s on %s: %w
- failed to migrate credential keys: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/0bb41194a1ab2ba8.
Report an issue: GitHub.