gastownhall/beads · error
resolving %s: %w
Error message
resolving %s: %w
What it means
Wraps any non-ErrNotFound error from workapi.GetIssueOrWisp while resolving the target issue for a proxied heartbeat. It distinguishes 'the lookup itself failed' from 'the issue does not exist'. The %w keeps the underlying storage/use-case cause.
Source
Thrown at cmd/bd/heartbeat_proxied_server.go:40
// bd-lrgn1): the transaction commits via uow.RunTxEphemeral's SQL-only form,
// so a heartbeat mints exactly ZERO Dolt commits per invocation — the same
// commit discipline as the classic DoltStore.HeartbeatIssue, and deliberately
// nothing here sets commandDidWrite or creates a Dolt commit. The exit code
// is the worker contract (workers call this every ~90s and only check rc):
// 0 = lease refreshed; nonzero = the lease is gone (wrong owner, not
// in_progress, closed, reclaimed) and the worker should stop.
func runHeartbeatProxiedServer(ctx context.Context, id string) error {
if uowProvider == nil {
return HandleErrorRespectJSON("proxied-server UOW provider not initialized")
}
res, err := uow.RunTxEphemeral(ctx, uowProvider, func(ctx context.Context, uw uow.UnitOfWork) (heartbeatProxiedOutcome, error) {
issue, _, rerr := workapi.GetIssueOrWisp(ctx, workapi.NewUOWDetailSource(uw), id)
if errors.Is(rerr, storage.ErrNotFound) {
return heartbeatProxiedOutcome{}, fmt.Errorf("issue %s not found", id)
}
if rerr != nil {
return heartbeatProxiedOutcome{}, fmt.Errorf("resolving %s: %w", id, rerr)
}
// Wisps resolve here too and are refused below: the repo verb
// classifies them ErrNotClaimable ("is ephemeral"), same as classic.
if herr := uw.IssueUseCase().Heartbeat(ctx, issue.ID, actor); herr != nil {
return heartbeatProxiedOutcome{}, fmt.Errorf("heartbeat %s: %w", issue.ID, herr)
}
return heartbeatProxiedOutcome{id: issue.ID, title: issue.Title}, nil
})
if err != nil {
return HandleErrorRespectJSON("%v", err)
}
SetLastTouchedID(res.id)
return renderHeartbeatSuccess(res.id, res.title)
}
View on GitHub (pinned to 71377f2769)
Solutions
- Read the wrapped cause (%v) to identify the storage-level failure.
- Verify storage connectivity and DB health (bd doctor).
- Retry the heartbeat; if persistent, check for corrupt records for that ID.
Defensive patterns
Strategy: retry
Validate before calling
// check DB health first bd doctor --json | jq -e '.storage.ok == true'
Try / catch
if err != nil && !errors.Is(err, storage.ErrNotFound) {
// transient storage failure: retry with backoff
} Prevention
- Ensure the Dolt driver is healthy before issuing heartbeat commands.
- Avoid concurrent processes holding long write transactions.
- Watch for corrupt records; validate the DB if errors persist for one ID.
When it happens
Trigger: GetIssueOrWisp returns an error that is not storage.ErrNotFound (e.g. storage failure, ambiguous ID resolution error, driver fault) inside the heartbeat RunTxEphemeral transaction.
Common situations: Database lock or I/O error, driver misconfiguration in proxied mode, corrupted issue record failing unmarshalling, or transient failure during ID-prefix resolution.
Related errors
- heartbeat %s: %w
- failed to check parent issue: %w
- graph create: %w
- failed to search issues: %w
- failed to load dependencies: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/01e1d508c38c343b.
Report an issue: GitHub.