gastownhall/beads · error
proxied-server provider %T does not offer the batch-close su
Error message
proxied-server provider %T does not offer the batch-close surface
What it means
A capability-mismatch guard in proxied-server mode: the injected unit-of-work provider does not implement `uow.BatchCloserSource`, so no batch-closer surface can be obtained. This indicates a wiring/version mismatch between the CLI command and the provider that the server assembled.
Source
Thrown at cmd/bd/close_proxied_server.go:217
if in.session == "" {
in.session = os.Getenv("CLAUDE_SESSION_ID")
}
in.jsonOut, _ = cmd.Flags().GetBool("json")
return in
}
// proxiedBatchCloser hands back the guarded close-many surface for the
// proxied-server provider, through the provider's OWN capability accessor —
// the same two-step proxiedIssueReader performs, and for the same reason: the
// accessor is where each layer is added, so a command that reached for the
// constructor would get an unlayered closer.
func proxiedBatchCloser() (issueops.BatchCloser, error) {
if uowProvider == nil {
return nil, errors.New("proxied-server UOW provider not initialized")
}
src, ok := uowProvider.(uow.BatchCloserSource)
if !ok {
return nil, fmt.Errorf("proxied-server provider %T does not offer the batch-close surface", uowProvider)
}
return src.BatchCloser()
}
// closeProxiedRunPreflight resolves every argument and applies the CLI's own
// close policy to it, in one read-only unit of work.
func closeProxiedRunPreflight(ctx context.Context, args, reasons []string, in closeProxiedInput) (closeProxiedPreflight, error) {
pre := closeProxiedPreflight{
errors: make([]string, len(args)),
before: make(map[string]*types.Issue, len(args)),
}
_, err := uow.RunTxRead(ctx, uowProvider, func(ctx context.Context, uw uow.UnitOfWork) (struct{}, error) {
for i, id := range args {
refusal, current := closeProxiedCheckOne(ctx, uw, id, in)
if refusal != "" {
pre.errors[i] = refusal
continue
}View on GitHub (pinned to 71377f2769)
Solutions
- Rebuild the bd binary and the proxied server from the same commit so interfaces match
- Check the provider type reported in the message (%T) against uow.BatchCloserSource and update the provider to implement it
- Pin client and server to the same version in your deployment
- Fall back to non-proxied close (run close locally against the store) if the server cannot be upgraded
Example fix
// before
src, ok := uowProvider.(uow.BatchCloserSource) // ok == false
// after
// implement the surface on the provider:
func (p *MyProvider) BatchCloser() (issueops.BatchCloser, error) { ... } Defensive patterns
Strategy: type-guard
Validate before calling
// ensure client/server parity bd --version # compare with server version before proxied ops
Type guard
// check the surface before relying on proxied batch close
if _, ok := provider.(uow.BatchCloserSource); !ok {
// fall back to local close
} Try / catch
if err := runClose(); strings.Contains(err.Error(), "does not offer the batch-close surface") {
// rebuild/upgrade server, or close locally
} Prevention
- Deploy CLI and proxied server from the same build
- Restart the server after every bd upgrade
- Keep custom providers implementing all uow source interfaces
- Add a smoke test exercising proxied batch close in CI
When it happens
Trigger: Running a batch close through the proxied-server path when the configured uowProvider is a narrower provider type lacking BatchCloser() — typically a stale binary, mixed-version server/client, or custom provider that only implements a subset of sources.
Common situations: Server and `bd` CLI built from different commits; a plugin/custom provider compiled against an older interface that predates the batch-close surface.
Related errors
- proxied-server provider %T does not offer the add-comment su
- proxied-server provider %T does not offer the batch-create s
- proxied-server provider %T does not offer the issue-lifecycl
- proxied-server provider %T does not offer the version-marker
- resolve proxied server root: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/49eb35bfa3ab7671.
Report an issue: GitHub.