vitessio/vitess · error

ErrImplementationNotRegistered

ErrImplementationNotRegistered

Error message

%w %s

What it means

Discovery.New looks up the requested discovery implementation (e.g. "consul", "etcd", "vitesstopology") in a package-level registry populated by init() functions. If the impl string is not registered, the constructor fails with ErrImplementationNotRegistered wrapped together with the impl name. This guards against building a cluster whose discovery backend does not exist or was never linked in.

Source

Thrown at go/vt/vtadmin/cluster/discovery/discovery.go:121

	_, ok := registry[name]
	if ok {
		panic("[discovery] factory already registered for " + name)
	}

	registry[name] = factory
}

// New returns a Discovery implementation using the registered factory for the
// implementation. Usage of the args slice is dependent on the implementation's
// factory.
func New(impl string, cluster *vtadminpb.Cluster, args []string) (Discovery, error) {
	registryMu.Lock()
	factory, ok := registry[impl]
	registryMu.Unlock()

	if !ok {
		return nil, fmt.Errorf("%w %s", ErrImplementationNotRegistered, impl)
	}

	return factory(cluster, pflag.NewFlagSet("discovery:"+impl, pflag.ContinueOnError), args)
}

func init() {
	Register("consul", NewConsul)
	Register("staticfile", NewStaticFile)
	Register("dynamic", NewDynamic)
}

View on GitHub (pinned to 01a25a7d17)

Solutions

  1. Correct the impl string to a registered implementation name (check registry keys / available impl packages).
  2. Add a blank import of the implementation package in your binary so its init() registers the factory (e.g. _ "vitess.io/vitess/go/vt/vtadmin/cluster/discovery/implconsul").
  3. Compare your flag/env value against the impl names registered in the discovery package before calling New.

Example fix

// before
import "vitess.io/vitess/go/vt/vtadmin/cluster/discovery"
d, err := discovery.New("consul", cluster, args) // impl package never imported
// after
import (
    _ "vitess.io/vitess/go/vt/vtadmin/cluster/discovery/implconsul"
    "vitess.io/vitess/go/vt/vtadmin/cluster/discovery"
)
d, err := discovery.New("consul", cluster, args)
Defensive patterns

Strategy: validation

Validate before calling

// ensure the impl package is linked and the name is registered before New
switch impl {
case "consul", "etcd2":
    // known registered implementations
default:
    return fmt.Errorf("unsupported discovery impl %q", impl)
}

Try / catch

d, err := discovery.New(impl, cluster, args)
if err != nil {
    if errors.Is(err, discovery.ErrImplementationNotRegistered) {
        log.Fatalf("discovery impl %q not registered; check imports/config", impl)
    }
    return err
}

Prevention

When it happens

Trigger: Calling discovery.New("myimpl", cluster, args) with an impl name that no registered factory provides; can also occur when the package containing the implementation's init() is not imported into the binary, so its factory never registers.

Common situations: Typo in the discovery impl flag (e.g. "consul" misspelled), building a custom binary that forgot to import the implementation package (blank import _ "...discovery/implconsul"), or renaming an implementation without updating deployment configs.

Related errors


AI-assisted analysis of vitessio/vitess@01a25a7d17 (2026-09-01). Data as JSON: /api/errors/45261926df0af94e. Report an issue: GitHub.