grpc/grpc-go · error
rls_csp: error marshaling load balancing config
Error message
rls_csp: error marshaling load balancing config %v: %v
What it means
The internally constructed lbConfigJSON struct could not be serialized via encoding/json.Marshal (rls.go:81-83). The struct contains a json.RawMessage field (RouteLookupConfig bytes from protojson), so a marshal failure means those bytes are not valid JSON.
Solutions
- This is likely a google.golang.org/protobuf library bug — report it with the RouteLookupConfig proto that triggered it
- Check for outdated or mismatched google.golang.org/protobuf versions in go.mod
- Inspect the lbCfgJSON.RouteLookupConfig bytes for anomalies
Defensive patterns
Strategy: validation
Validate before calling
// Validate that protojson output is valid JSON before re-marshaling.
if !json.Valid(rlcJSON) {
return fmt.Errorf("protojson produced invalid JSON for RouteLookupConfig")
} Prevention
- Keep google.golang.org/protobuf dependency up to date
- Report reproducible marshal failures to the protobuf team with the triggering proto
- Pin protobuf library versions in go.mod to avoid unexpected behavior changes
When it happens
Trigger: json.Marshal(lbCfgJSON) fails because the RouteLookupConfig json.RawMessage produced by the preceding protojson.Marshal contains bytes that encoding/json rejects as invalid JSON.
Common situations: Extremely rare — protojson.Marshal succeeded but produced output that encoding/json considers invalid; indicates a bug in the protobuf library or corrupted proto state. Effectively an internal/library error rather than a configuration issue.
Related errors
- rls_csp: error marshaling route lookup config
- rls_csp: error parsing config
- rls_csp: error parsing config
- rls_csp: nil configuration message provided
- rls_csp: validation error from rls lb policy parsing
AI-assisted analysis of grpc/grpc-go@0c51461d27 (2026-08-11).
Data as JSON: /api/errors/eeae4e1a1dca9459.
Report an issue: GitHub.
Appendix: source
Thrown at internal/xds/clusterspecifier/rls/rls.go:83
return nil, fmt.Errorf("rls_csp: error parsing config %v: %v", cfg, err)
}
rlcJSON, err := protojson.Marshal(rlcs.GetRouteLookupConfig())
if err != nil {
return nil, fmt.Errorf("rls_csp: error marshaling route lookup config: %v: %v", rlcs.GetRouteLookupConfig(), err)
}
lbCfgJSON := &lbConfigJSON{
RouteLookupConfig: rlcJSON, // "JSON form of RouteLookupClusterSpecifier.config" - RLS in xDS Design Doc
ChildPolicy: []map[string]json.RawMessage{
{
"cds_experimental": json.RawMessage(`{"isDynamic":true}`),
},
},
ChildPolicyConfigTargetFieldName: "cluster",
}
rawJSON, err := json.Marshal(lbCfgJSON)
if err != nil {
return nil, fmt.Errorf("rls_csp: error marshaling load balancing config %v: %v", lbCfgJSON, err)
}
rlsBB := balancer.Get(internal.RLSLoadBalancingPolicyName)
if rlsBB == nil {
return nil, fmt.Errorf("RLS LB policy not registered")
}
if _, err = rlsBB.(balancer.ConfigParser).ParseConfig(rawJSON); err != nil {
return nil, fmt.Errorf("rls_csp: validation error from rls lb policy parsing: %v", err)
}
return clusterspecifier.BalancerConfig{{internal.RLSLoadBalancingPolicyName: lbCfgJSON}}, nil
}
View on GitHub (pinned to 0c51461d27)