{"record":{"id":"9c32cfb6de79abc6","repo":"gastownhall/beads","slug":"query-neighbors-from-s-w","errorCode":null,"errorMessage":"query neighbors from %s: %w","messagePattern":"query neighbors from (.+?): %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/storage/issueops/delete_role.go","lineNumber":272,"sourceCode":"\tneighborIDs := make(map[string]bool)\n\tfor i := 0; i < len(ids); i += deleteBatchSize {\n\t\tend := i + deleteBatchSize\n\t\tif end > len(ids) {\n\t\t\tend = len(ids)\n\t\t}\n\t\tinClause, args := buildSQLInClause(ids[i:end])\n\t\tdoubled := append(append([]interface{}{}, args...), args...)\n\n\t\tfor _, depTable := range []string{\"dependencies\", \"wisp_dependencies\"} {\n\t\t\trows, err := tx.QueryContext(ctx,\n\t\t\t\tfmt.Sprintf(`SELECT issue_id, %s AS depends_on_id FROM %s WHERE issue_id IN (%s) OR %s`,\n\t\t\t\t\tDepTargetExpr, depTable, inClause, depTargetIn(\"\", inClause)),\n\t\t\t\tdoubled...)\n\t\t\tif err != nil {\n\t\t\t\tif optionalBlockedTable(depTable) && isTableNotExistError(err) {\n\t\t\t\t\tcontinue\n\t\t\t\t}\n\t\t\t\treturn nil, fmt.Errorf(\"query neighbors from %s: %w\", depTable, err)\n\t\t\t}\n\t\t\tfor rows.Next() {\n\t\t\t\tvar source, target string\n\t\t\t\tif err := rows.Scan(&source, &target); err != nil {\n\t\t\t\t\t_ = rows.Close()\n\t\t\t\t\treturn nil, fmt.Errorf(\"scan neighbor: %w\", err)\n\t\t\t\t}\n\t\t\t\tfor _, candidate := range [2]string{source, target} {\n\t\t\t\t\tif candidate == \"\" || deleting[candidate] {\n\t\t\t\t\t\tcontinue\n\t\t\t\t\t}\n\t\t\t\t\tneighborIDs[candidate] = true\n\t\t\t\t}\n\t\t\t}\n\t\t\t_ = rows.Close()\n\t\t\tif err := rows.Err(); err != nil {\n\t\t\t\treturn nil, fmt.Errorf(\"iterate neighbors from %s: %w\", depTable, err)\n\t\t\t}","sourceCodeStart":254,"sourceCodeEnd":290,"githubUrl":"https://github.com/gastownhall/beads/blob/71377f276968b452ee607177637970a4ff888584/internal/storage/issueops/delete_role.go#L254-L290","documentation":"deleteNeighborsInTx queries both dependency planes for surviving rows joined to the deletion set in either direction, so their text can later be rewritten with [deleted:<id>] markers. This error wraps a query failure and names the table. Absent optional tables (wisp_dependencies) are skipped via optionalBlockedTable + isTableNotExistError, so reaching this error means a real failure on a table that exists.","triggerScenarios":"deleteNeighborsInTx (called from DeleteInTx with set.All) runs tx.QueryContext with the doubled-args IN query on 'dependencies' or 'wisp_dependencies' and gets a non-'table not exist' error — connection failure, driver error, or cancelled context.","commonSituations":"Connection lost between deletion-set resolution and the neighborhood read; context timeout on a large cascade set; driver mismatch on the DepTargetExpr expression; missing migration.","solutions":["Read the wrapped driver error and the named table in the message","Check connectivity and retry; the transaction rolls back so the delete is safely re-runnable","Raise the context timeout for large cascade batches","Confirm migrations for both dependency tables are applied","Verify driver version matches what isTableNotExistError/optionalBlockedTable expect"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"// ensure the backend is reachable before a wide delete\nif err := db.PingContext(ctx); err != nil { return err }","typeGuard":null,"tryCatchPattern":"err := store.Delete(ctx, req)\nif err != nil && strings.Contains(err.Error(), \"query neighbors from\") {\n    // driver/query failure on a dependency plane; inspect unwrapped cause, retry\n}","preventionTips":["Keep the delete transaction short; check connection health beforehand","Apply all migrations for both dependency planes","Size context timeouts to the cascade breadth","Verify driver versions after upgrades"],"tags":["database","sql","neighbors","query-error"],"backgroundTag":"db-query-failed","analyzedSha":"71377f276968b452ee607177637970a4ff888584","analyzedAt":"2026-08-30T18:55:39.744Z","schemaVersion":2},"datasetVersion":"2026-08-30T23:17:21.991Z"}