grpc/grpc-go · error
extproc: error parsing config %v: unknown type %T, want *any
Error message
extproc: error parsing config %v: unknown type %T, want *anypb.Any
What it means
Raised by the ext_proc builder's ParseFilterConfig (ext_proc.go:112) when the message handed in is not an *anypb.Any. Like error 364 for the base (not override) config: the builder contract (httpfilter.go:60) expects filter configs wrapped in *anypb.Any, so a non-Any indicates the xDS decoder supplied the wrong concrete proto type for an ExternalProcessor config.
Source
Thrown at internal/xds/httpfilter/extproc/ext_proc.go:112
// NONE or GRPC. Also ensures that if response body mode is GRPC then response
// trailer mode must be SEND.
func validateBodyProcessingMode(mode *v3procfilterpb.ProcessingMode) error {
if m := mode.GetRequestBodyMode(); m != v3procfilterpb.ProcessingMode_NONE && m != v3procfilterpb.ProcessingMode_GRPC {
return fmt.Errorf("extproc: invalid request body mode %v: want %q or %q", m, "NONE", "GRPC")
}
if m := mode.GetResponseBodyMode(); m != v3procfilterpb.ProcessingMode_NONE && m != v3procfilterpb.ProcessingMode_GRPC {
return fmt.Errorf("extproc: invalid response body mode %v: want %q or %q", m, "NONE", "GRPC")
}
if mode.GetResponseBodyMode() == v3procfilterpb.ProcessingMode_GRPC && mode.GetResponseTrailerMode() != v3procfilterpb.ProcessingMode_SEND {
return fmt.Errorf("extproc: invalid response trailer mode %v: must be %q when response body mode is %q", mode.GetResponseTrailerMode(), "SEND", "GRPC")
}
return nil
}
func (builder) ParseFilterConfig(cfg proto.Message) (httpfilter.FilterConfig, error) {
m, ok := cfg.(*anypb.Any)
if !ok {
return nil, fmt.Errorf("extproc: error parsing config %v: unknown type %T, want *anypb.Any", cfg, cfg)
}
msg := new(v3procfilterpb.ExternalProcessor)
if err := m.UnmarshalTo(msg); err != nil {
return nil, fmt.Errorf("extproc: failed to unmarshal config %v: %v", cfg, err)
}
if msg.GetProcessingMode() == nil {
return nil, fmt.Errorf("extproc: missing processing_mode in config %v", cfg)
}
if err := validateBodyProcessingMode(msg.GetProcessingMode()); err != nil {
return nil, err
}
if msg.GetGrpcService() == nil {
return nil, fmt.Errorf("extproc: empty grpc_service provided in config %v", cfg)
}
server, err := iextproc.ParseGRPCServiceConfig(msg.GetGrpcService())
if err != nil {
return nil, fmt.Errorf("extproc: failed to parse grpc_service %v", err)View on GitHub (pinned to 03255a9237)
Solutions
- If invoking ParseFilterConfig directly, wrap the message with anypb.New first.
- In production, treat this as a resolver/builder version mismatch and update gRPC-Go so both sides agree on the *anypb.Any contract.
- Ensure the HTTP filter typed_config uses the ExternalProcessor type URL so the resolver keeps it wrapped.
Example fix
// before (direct call): passing the raw ExternalProcessor proto
// fc, err := b.ParseFilterConfig(extProc)
//
// after: wrap in *anypb.Any
anyCfg, err := anypb.New(extProc)
if err != nil { return err }
fc, err := b.ParseFilterConfig(anyCfg) Defensive patterns
Strategy: type-guard
Validate before calling
// Guarantee the config is *anypb.Any before parsing (ext_proc.go:110-112).
func ensureAny(m proto.Message) (*anypb.Any, error) {
if a, ok := m.(*anypb.Any); ok {
return a, nil
}
return anypb.New(m)
} Type guard
func isAnyConfig(m proto.Message) (*anypb.Any, bool) {
a, ok := m.(*anypb.Any)
return a, ok
} Prevention
- Always pass *anypb.Any into ParseFilterConfig, never the bare ExternalProcessor proto.
- Keep resolver and filter builder on the same gRPC-Go version.
- In tests/tools, wrap configs with anypb.New.
When it happens
Trigger: The xDS resolver calls builder.ParseFilterConfig(cfg) where the type assertion cfg.(*anypb.Any) at ext_proc.go:110 fails — an internal resolver/builder contract violation rather than a direct end-user config mistake.
Common situations: A resolver change that passes a raw typed struct instead of the wrapping Any; a test calling ParseFilterConfig with the bare ExternalProcessor proto; resolver/filter version skew.
Related errors
- extauthz: error parsing override config %v: unknown type %T,
- extproc: invalid request body mode %v: want %q or %q
- extproc: invalid response body mode %v: want %q or %q
- extproc: invalid response trailer mode %v: must be %q when r
- extproc: failed to unmarshal config %v: %v
AI-assisted analysis of grpc/grpc-go@03255a9237 (2026-08-07).
Data as JSON: /api/errors/aa37933597a2d32e.
Report an issue: GitHub.