gastownhall/beads · error
gate not found: %s
Error message
gate not found: %s
What it means
Thrown inside the gate AddWaiter transaction when GetIssue reports the gate ID does not exist. The caller asked to attach a waiter to a gate issue, but no issue with that ID is present in storage. This distinguishes a clean not-found from a storage failure (which produces 'reading gate %s' instead).
Source
Thrown at cmd/bd/gate_proxied_server.go:250
defer func() {
if c := metrics.Global(); c != nil {
c.CloseEventAndAdd(evt)
}
}()
gateID := args[0]
waiter := args[1]
if uowProvider == nil {
return HandleError("proxied-server UOW provider not initialized")
}
applied, err := uow.RunTxResult(ctx, uowProvider, func(ctx context.Context, uw uow.UnitOfWork) (gateAddWaiterApply, string, error) {
var out gateAddWaiterApply
issue, err := uw.IssueUseCase().GetIssue(ctx, gateID)
if gateProxiedNotFound(err) {
return out, "", fmt.Errorf("gate not found: %s", gateID)
}
if err != nil {
return out, "", fmt.Errorf("reading gate %s: %w", gateID, err)
}
if issue.IssueType != "gate" {
return out, "", fmt.Errorf("%s is not a gate issue (type=%s)", gateID, issue.IssueType)
}
for _, w := range issue.Waiters {
if w == waiter {
out.already = true
// Empty commit message: a registered waiter is a no-op, and a
// no-op writes no Dolt commit.
return out, "", nil
}
}
newWaiters := append(issue.Waiters, waiter)View on GitHub (pinned to 71377f2769)
Solutions
- Run `bd show <gateID>` to confirm the issue exists in the connected database
- Check for typos in the gate ID; use `bd list --type gate` to list valid gate issues
- If the gate was deleted intentionally, remove or recreate the waiter registration instead of retrying
- Verify the server is pointed at the expected database/remote (`bd doctor`)
Example fix
// before: blind AddWaiter call
err := client.AddWaiter(ctx, gateID, waiter)
// after: confirm the gate exists and is a gate first
issue, err := client.Show(ctx, gateID)
if err != nil || issue == nil {
return fmt.Errorf("gate %s does not exist; run bd list --type gate", gateID)
}
if issue.IssueType != "gate" {
return fmt.Errorf("%s is not a gate issue (type=%s)", gateID, issue.IssueType)
}
err = client.AddWaiter(ctx, gateID, waiter) Defensive patterns
Strategy: validation
Validate before calling
issue, err := bdClient.Show(ctx, gateID)
if err != nil {
return fmt.Errorf("gate %s does not exist in this database; run bd list --type gate", gateID)
} Type guard
func gateExists(ctx context.Context, uc *IssueUseCase, gateID string) bool {
issue, err := uc.GetIssue(ctx, gateID)
return err == nil && issue != nil
} Try / catch
err := client.AddWaiter(ctx, gateID, waiter)
if err != nil && strings.Contains(err.Error(), "gate not found") {
gates, _ := client.List(ctx, ListFilter{IssueType: "gate"})
return fmt.Errorf("gate %s not found; known gates: %v", gateID, gates)
} Prevention
- Copy gate IDs from `bd list --type gate` output, never from memory
- Confirm the server/client point at the same database/remote (`bd doctor`)
- Re-resolve gate IDs after any issue-deletion workflow
- Use tab-completion or bd's ID resolution instead of hand-typing bd-xxx IDs
When it happens
Trigger: Calling the proxied-server gate AddWaiter path with a gateID that was never created, was deleted, or is mistyped; gateProxiedNotFound(err) returns true for the GetIssue result.
Common situations: Typo in the gate issue ID (bd-xxx vs bd-yyy); gate deleted after a workflow run completed; issue created in a different database/remote than the one the server is connected to; stale cached ID from an earlier session.
Related errors
- no store is open for this workspace
- not found
- db: ChildCounterSQLRepository.NextChildID: parentID must not
- db: DependencySQLRepository.Insert: dep must not be nil
- db: DependencySQLRepository.Insert: IssueID must not be empt
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/547dc639577a8ad8.
Report an issue: GitHub.