gastownhall/beads · error
query dependents for batch from %s: %w
Error message
query dependents for batch from %s: %w
What it means
FindAllDependentsInTx queries the dependencies/wisp_dependencies tables in batches to find dependents. A query error on a required table (one that is not an optional/absent table) is wrapped with this message naming the table. Table-not-exist errors are tolerated only for optional tables.
Source
Thrown at internal/storage/issueops/delete.go:435
return nil, fmt.Errorf("cascade traversal discovered over %d issues; aborting to prevent runaway deletion", maxRecursiveResults)
}
batchEnd := deleteBatchSize
if batchEnd > len(toProcess) {
batchEnd = len(toProcess)
}
batch := toProcess[:batchEnd]
toProcess = toProcess[batchEnd:]
inClause, args := buildSQLInClause(batch)
for _, depTable := range []string{"dependencies", "wisp_dependencies"} {
rows, err := tx.QueryContext(ctx,
fmt.Sprintf(`SELECT issue_id FROM %s WHERE %s`, depTable, depTargetIn("", inClause)),
args...)
if err != nil {
if optionalBlockedTable(depTable) && isTableNotExistError(err) {
continue
}
return nil, fmt.Errorf("query dependents for batch from %s: %w", depTable, err)
}
for rows.Next() {
var depID string
if err := rows.Scan(&depID); err != nil {
_ = rows.Close()
return nil, fmt.Errorf("scan dependent: %w", err)
}
if !result[depID] {
result[depID] = true
toProcess = append(toProcess, depID)
}
}
_ = rows.Close()
if err := rows.Err(); err != nil {
return nil, fmt.Errorf("iterate dependents for batch from %s: %w", depTable, err)
}
}View on GitHub (pinned to 71377f2769)
Solutions
- Read the wrapped driver error; if the table is missing, run schema migration (bd doctor/migrate)
- Retry after resolving lock contention or restoring the connection
- Verify wisp_dependencies presence if you use wisp mode and it is treated as required
Example fix
// before
rows, err := tx.QueryContext(ctx, fmt.Sprintf(`SELECT issue_id FROM %s WHERE %s`, depTable, depTargetIn("", inClause)), args...)
// after — ensure schema is current first
// bd doctor; bd migrate (or equivalent) before retrying cascade delete Defensive patterns
Strategy: try-catch
Validate before calling
// verify required dependency tables exist before cascade delete
for _, t := range []string{"dependencies"} {
var n int
db.QueryRow("SELECT COUNT(*) FROM sqlite_master WHERE name=?", t).Scan(&n)
if n == 0 { return fmt.Errorf("missing table %s; migrate first", t) }
} Try / catch
_, err := DeleteIssuesInTx(ctx, tx, ids, WithCascade())
if err != nil && strings.Contains(err.Error(), "query dependents for batch from") {
if strings.Contains(err.Error(), "no such table") { migrate(db); return retry(ctx, ids) }
return err
} Prevention
- Keep schema migrations current with the binary version
- Avoid concurrent writers during cascade deletes
- Check connection stability to remote Dolt before large traversals
When it happens
Trigger: ResolveDeletionSetInTx cascade traversal where SELECT issue_id FROM dependencies (or wisp_dependencies) fails — table does not exist and is not marked optional, SQL error, lock contention, or connection failure.
Common situations: Partially migrated or corrupted database missing a dependencies table; remote Dolt server connection reset mid-traversal; database locked by a concurrent writer.
Understand the failure class
Background: "query failed", "%w: SQL error" — wrapped database query errors in Go libraries explained — this error's family across 3 libraries.
Related errors
- expand cascade: %w
- get dependent records from %s: %w
- count edges in %s: %w
- failed to begin transaction: %w
- failed to recompute is_blocked: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/deb02dbcdadf6088.
Report an issue: GitHub.