mirror of https://github.com/status-im/consul.git
Ingress gateway header manip plumbing
This commit is contained in:
parent
d776a2d236
commit
f439dfc04f
|
@ -54,6 +54,7 @@ func (s *handlerIngressGateway) initialize(ctx context.Context) (ConfigSnapshot,
|
|||
snap.IngressGateway.WatchedUpstreamEndpoints = make(map[string]map[string]structs.CheckServiceNodes)
|
||||
snap.IngressGateway.WatchedGateways = make(map[string]map[string]context.CancelFunc)
|
||||
snap.IngressGateway.WatchedGatewayEndpoints = make(map[string]map[string]structs.CheckServiceNodes)
|
||||
snap.IngressGateway.Listeners = make(map[IngressListenerKey]structs.IngressListener)
|
||||
return snap, nil
|
||||
}
|
||||
|
||||
|
@ -82,6 +83,13 @@ func (s *handlerIngressGateway) handleUpdate(ctx context.Context, u cache.Update
|
|||
snap.IngressGateway.TLSEnabled = gatewayConf.TLS.Enabled
|
||||
snap.IngressGateway.TLSSet = true
|
||||
|
||||
// Load each listener's config from the config entry so we don't have to
|
||||
// pass listener config through "upstreams" types as that grows.
|
||||
for _, l := range gatewayConf.Listeners {
|
||||
key := IngressListenerKey{Protocol: l.Protocol, Port: l.Port}
|
||||
snap.IngressGateway.Listeners[key] = l
|
||||
}
|
||||
|
||||
if err := s.watchIngressLeafCert(ctx, snap); err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
|
@ -321,6 +321,10 @@ type configSnapshotIngressGateway struct {
|
|||
// to. This is constructed from the ingress-gateway config entry, and uses
|
||||
// the GatewayServices RPC to retrieve them.
|
||||
Upstreams map[IngressListenerKey]structs.Upstreams
|
||||
|
||||
// Listeners is the original listener config from the ingress-gateway config
|
||||
// entry to save us trying to pass fields through Upstreams
|
||||
Listeners map[IngressListenerKey]structs.IngressListener
|
||||
}
|
||||
|
||||
func (c *configSnapshotIngressGateway) IsEmpty() bool {
|
||||
|
|
|
@ -1681,6 +1681,15 @@ func testConfigSnapshotIngressGateway(
|
|||
},
|
||||
},
|
||||
},
|
||||
Listeners: map[IngressListenerKey]structs.IngressListener{
|
||||
{protocol, 9191}: {
|
||||
Port: 9191,
|
||||
Protocol: protocol,
|
||||
Services: []structs.IngressService{
|
||||
{Name: "db"},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
return snap
|
||||
|
|
|
@ -168,6 +168,7 @@ func (e *IngressGatewayConfigEntry) Validate() error {
|
|||
}
|
||||
|
||||
declaredHosts := make(map[string]bool)
|
||||
serviceNames := make(map[ServiceID]struct{})
|
||||
for i, s := range listener.Services {
|
||||
if err := validateInnerEnterpriseMeta(&s.EnterpriseMeta, &e.EnterpriseMeta); err != nil {
|
||||
return fmt.Errorf("Services[%d].%v", i, err)
|
||||
|
@ -197,6 +198,11 @@ func (e *IngressGatewayConfigEntry) Validate() error {
|
|||
if s.NamespaceOrDefault() == WildcardSpecifier {
|
||||
return fmt.Errorf("Wildcard namespace is not supported for ingress services (listener on port %d)", listener.Port)
|
||||
}
|
||||
sid := NewServiceID(s.Name, &s.EnterpriseMeta)
|
||||
if _, ok := serviceNames[sid]; ok {
|
||||
return fmt.Errorf("Service %s cannot be added multiple times (listener on port %d)", sid, listener.Port)
|
||||
}
|
||||
serviceNames[sid] = struct{}{}
|
||||
|
||||
for _, h := range s.Hosts {
|
||||
if declaredHosts[h] {
|
||||
|
|
|
@ -523,6 +523,27 @@ func TestIngressGatewayConfigEntry(t *testing.T) {
|
|||
},
|
||||
validateErr: "response headers only valid for http",
|
||||
},
|
||||
"duplicate services not allowed": {
|
||||
entry: &IngressGatewayConfigEntry{
|
||||
Kind: "ingress-gateway",
|
||||
Name: "ingress-web",
|
||||
Listeners: []IngressListener{
|
||||
{
|
||||
Port: 1111,
|
||||
Protocol: "http",
|
||||
Services: []IngressService{
|
||||
{
|
||||
Name: "web",
|
||||
},
|
||||
{
|
||||
Name: "web",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
validateErr: "Service web cannot be added multiple times (listener on port 1111)",
|
||||
},
|
||||
}
|
||||
|
||||
testConfigEntryNormalizeAndValidate(t, cases)
|
||||
|
|
|
@ -375,9 +375,11 @@ type Upstream struct {
|
|||
// MeshGateway is the configuration for mesh gateway usage of this upstream
|
||||
MeshGateway MeshGatewayConfig `json:",omitempty" alias:"mesh_gateway"`
|
||||
|
||||
// IngressHosts are a list of hosts that should route to this upstream from
|
||||
// an ingress gateway. This cannot and should not be set by a user, it is
|
||||
// used internally to store the association of hosts to an upstream service.
|
||||
// IngressHosts are a list of hosts that should route to this upstream from an
|
||||
// ingress gateway. This cannot and should not be set by a user, it is used
|
||||
// internally to store the association of hosts to an upstream service.
|
||||
// TODO(banks): we shouldn't need this any more now we pass through full
|
||||
// listener config in the ingress snapshot.
|
||||
IngressHosts []string `json:"-" bexpr:"-"`
|
||||
|
||||
// CentrallyConfigured indicates whether the upstream was defined in a proxy
|
||||
|
|
|
@ -7,6 +7,7 @@ import (
|
|||
"strings"
|
||||
"time"
|
||||
|
||||
envoy_core_v3 "github.com/envoyproxy/go-control-plane/envoy/config/core/v3"
|
||||
envoy_route_v3 "github.com/envoyproxy/go-control-plane/envoy/config/route/v3"
|
||||
envoy_matcher_v3 "github.com/envoyproxy/go-control-plane/envoy/type/matcher/v3"
|
||||
|
||||
|
@ -29,7 +30,11 @@ func (s *ResourceGenerator) routesFromSnapshot(cfgSnap *proxycfg.ConfigSnapshot)
|
|||
case structs.ServiceKindConnectProxy:
|
||||
return s.routesForConnectProxy(cfgSnap.ConnectProxy.DiscoveryChain)
|
||||
case structs.ServiceKindIngressGateway:
|
||||
return s.routesForIngressGateway(cfgSnap.IngressGateway.Upstreams, cfgSnap.IngressGateway.DiscoveryChain)
|
||||
return s.routesForIngressGateway(
|
||||
cfgSnap.IngressGateway.Listeners,
|
||||
cfgSnap.IngressGateway.Upstreams,
|
||||
cfgSnap.IngressGateway.DiscoveryChain,
|
||||
)
|
||||
case structs.ServiceKindTerminatingGateway:
|
||||
return s.routesFromSnapshotTerminatingGateway(cfgSnap)
|
||||
case structs.ServiceKindMeshGateway:
|
||||
|
@ -160,6 +165,7 @@ func makeNamedDefaultRouteWithLB(clusterName string, lb *structs.LoadBalancer, a
|
|||
// routesForIngressGateway returns the xDS API representation of the
|
||||
// "routes" in the snapshot.
|
||||
func (s *ResourceGenerator) routesForIngressGateway(
|
||||
listeners map[proxycfg.IngressListenerKey]structs.IngressListener,
|
||||
upstreams map[proxycfg.IngressListenerKey]structs.Upstreams,
|
||||
chains map[string]*structs.CompiledDiscoveryChain,
|
||||
) ([]proto.Message, error) {
|
||||
|
@ -190,6 +196,42 @@ func (s *ResourceGenerator) routesForIngressGateway(
|
|||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// See if we need to configure any special settings on this route config
|
||||
if lCfg, ok := listeners[listenerKey]; ok {
|
||||
if is := findIngressServiceMatchingUpstream(lCfg, u); is != nil {
|
||||
// Set up any header manipulation we need
|
||||
if is.RequestHeaders != nil {
|
||||
virtualHost.RequestHeadersToAdd = append(
|
||||
virtualHost.RequestHeadersToAdd,
|
||||
makeHeadersValueOptions(is.RequestHeaders.Add, true)...,
|
||||
)
|
||||
virtualHost.RequestHeadersToAdd = append(
|
||||
virtualHost.RequestHeadersToAdd,
|
||||
makeHeadersValueOptions(is.RequestHeaders.Set, false)...,
|
||||
)
|
||||
virtualHost.RequestHeadersToRemove = append(
|
||||
virtualHost.RequestHeadersToRemove,
|
||||
is.RequestHeaders.Remove...,
|
||||
)
|
||||
}
|
||||
if is.ResponseHeaders != nil {
|
||||
virtualHost.ResponseHeadersToAdd = append(
|
||||
virtualHost.ResponseHeadersToAdd,
|
||||
makeHeadersValueOptions(is.ResponseHeaders.Add, true)...,
|
||||
)
|
||||
virtualHost.ResponseHeadersToAdd = append(
|
||||
virtualHost.ResponseHeadersToAdd,
|
||||
makeHeadersValueOptions(is.ResponseHeaders.Set, false)...,
|
||||
)
|
||||
virtualHost.ResponseHeadersToRemove = append(
|
||||
virtualHost.ResponseHeadersToRemove,
|
||||
is.ResponseHeaders.Remove...,
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
upstreamRoute.VirtualHosts = append(upstreamRoute.VirtualHosts, virtualHost)
|
||||
}
|
||||
|
||||
|
@ -199,6 +241,36 @@ func (s *ResourceGenerator) routesForIngressGateway(
|
|||
return result, nil
|
||||
}
|
||||
|
||||
func makeHeadersValueOptions(vals map[string]string, add bool) []*envoy_core_v3.HeaderValueOption {
|
||||
opts := make([]*envoy_core_v3.HeaderValueOption, 0, len(vals))
|
||||
for k, v := range vals {
|
||||
o := &envoy_core_v3.HeaderValueOption{
|
||||
Header: &envoy_core_v3.HeaderValue{
|
||||
Key: k,
|
||||
Value: v,
|
||||
},
|
||||
Append: makeBoolValue(add),
|
||||
}
|
||||
opts = append(opts, o)
|
||||
}
|
||||
return opts
|
||||
}
|
||||
|
||||
func findIngressServiceMatchingUpstream(l structs.IngressListener, u structs.Upstream) *structs.IngressService {
|
||||
// Hunt through for the matching service. We validate now that there is
|
||||
// only one IngressService for each unique name although originally that
|
||||
// wasn't checked as it didn't matter. Assume there is only one now
|
||||
// though!
|
||||
wantSID := u.DestinationID()
|
||||
for _, s := range l.Services {
|
||||
sid := structs.NewServiceID(s.Name, &s.EnterpriseMeta)
|
||||
if wantSID.Matches(sid) {
|
||||
return &s
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func generateUpstreamIngressDomains(listenerKey proxycfg.IngressListenerKey, u structs.Upstream) []string {
|
||||
var domains []string
|
||||
domainsSet := make(map[string]bool)
|
||||
|
|
|
@ -189,6 +189,33 @@ func TestRoutesFromSnapshot(t *testing.T) {
|
|||
}
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "ingress-with-chain-and-router-header-manip",
|
||||
create: proxycfg.TestConfigSnapshotIngressWithRouter,
|
||||
setup: func(snap *proxycfg.ConfigSnapshot) {
|
||||
k := proxycfg.IngressListenerKey{Port: 9191, Protocol: "http"}
|
||||
l := snap.IngressGateway.Listeners[k]
|
||||
l.Services[0].RequestHeaders = &structs.HTTPHeaderModifiers{
|
||||
Add: map[string]string{
|
||||
"foo": "bar",
|
||||
},
|
||||
Set: map[string]string{
|
||||
"bar": "baz",
|
||||
},
|
||||
Remove: []string{"qux"},
|
||||
}
|
||||
l.Services[0].ResponseHeaders = &structs.HTTPHeaderModifiers{
|
||||
Add: map[string]string{
|
||||
"foo": "bar",
|
||||
},
|
||||
Set: map[string]string{
|
||||
"bar": "baz",
|
||||
},
|
||||
Remove: []string{"qux"},
|
||||
}
|
||||
snap.IngressGateway.Listeners[k] = l
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "terminating-gateway-lb-config",
|
||||
create: proxycfg.TestConfigSnapshotTerminatingGateway,
|
||||
|
|
401
agent/xds/testdata/routes/ingress-with-chain-and-router-header-manip.envoy-1-18-x.golden
vendored
Normal file
401
agent/xds/testdata/routes/ingress-with-chain-and-router-header-manip.envoy-1-18-x.golden
vendored
Normal file
|
@ -0,0 +1,401 @@
|
|||
{
|
||||
"versionInfo": "00000001",
|
||||
"resources": [
|
||||
{
|
||||
"@type": "type.googleapis.com/envoy.config.route.v3.RouteConfiguration",
|
||||
"name": "9191",
|
||||
"virtualHosts": [
|
||||
{
|
||||
"name": "db",
|
||||
"domains": [
|
||||
"db.ingress.*",
|
||||
"db.ingress.*:9191"
|
||||
],
|
||||
"routes": [
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/prefix"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prefix.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"path": "/exact"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "exact.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"safeRegex": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "/regex"
|
||||
}
|
||||
},
|
||||
"route": {
|
||||
"cluster": "regex.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"presentMatch": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-present.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"presentMatch": true,
|
||||
"invertMatch": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-not-present.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"exactMatch": "exact"
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-exact.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"prefixMatch": "prefix"
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-prefix.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"suffixMatch": "suffix"
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-suffix.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"safeRegexMatch": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "regex"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-regex.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": ":method",
|
||||
"safeRegexMatch": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "GET|PUT"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "just-methods.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"exactMatch": "exact"
|
||||
},
|
||||
{
|
||||
"name": ":method",
|
||||
"safeRegexMatch": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "GET|PUT"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-exact-with-method.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"queryParameters": [
|
||||
{
|
||||
"name": "secretparam1",
|
||||
"stringMatch": {
|
||||
"exact": "exact"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prm-exact.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"queryParameters": [
|
||||
{
|
||||
"name": "secretparam2",
|
||||
"stringMatch": {
|
||||
"safeRegex": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "regex"
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prm-regex.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"queryParameters": [
|
||||
{
|
||||
"name": "secretparam3",
|
||||
"presentMatch": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prm-present.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "nil-match.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "empty-match-1.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "empty-match-2.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/prefix"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prefix-rewrite-1.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"prefixRewrite": "/"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/prefix"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prefix-rewrite-2.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"prefixRewrite": "/nested/newlocation"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/timeout"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "req-timeout.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"timeout": "33s"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/retry-connect"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "retry-connect.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"retryPolicy": {
|
||||
"retryOn": "connect-failure",
|
||||
"numRetries": 15
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/retry-codes"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "retry-codes.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"retryPolicy": {
|
||||
"retryOn": "retriable-status-codes",
|
||||
"numRetries": 15,
|
||||
"retriableStatusCodes": [
|
||||
401,
|
||||
409,
|
||||
451
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/retry-both"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "retry-both.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"retryPolicy": {
|
||||
"retryOn": "connect-failure,retriable-status-codes",
|
||||
"retriableStatusCodes": [
|
||||
401,
|
||||
409,
|
||||
451
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/split-3-ways"
|
||||
},
|
||||
"route": {
|
||||
"weightedClusters": {
|
||||
"clusters": [
|
||||
{
|
||||
"name": "big-side.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"weight": 9550
|
||||
},
|
||||
{
|
||||
"name": "goldilocks-side.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"weight": 400
|
||||
},
|
||||
{
|
||||
"name": "lil-bit-side.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"weight": 50
|
||||
}
|
||||
],
|
||||
"totalWeight": 10000
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "db.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
}
|
||||
],
|
||||
"requestHeadersToAdd": [
|
||||
{
|
||||
"header": {
|
||||
"key": "foo",
|
||||
"value": "bar"
|
||||
},
|
||||
"append": true
|
||||
},
|
||||
{
|
||||
"header": {
|
||||
"key": "bar",
|
||||
"value": "baz"
|
||||
},
|
||||
"append": false
|
||||
}
|
||||
],
|
||||
"requestHeadersToRemove": [
|
||||
"qux"
|
||||
],
|
||||
"responseHeadersToAdd": [
|
||||
{
|
||||
"header": {
|
||||
"key": "foo",
|
||||
"value": "bar"
|
||||
},
|
||||
"append": true
|
||||
},
|
||||
{
|
||||
"header": {
|
||||
"key": "bar",
|
||||
"value": "baz"
|
||||
},
|
||||
"append": false
|
||||
}
|
||||
],
|
||||
"responseHeadersToRemove": [
|
||||
"qux"
|
||||
]
|
||||
}
|
||||
],
|
||||
"validateClusters": true
|
||||
}
|
||||
],
|
||||
"typeUrl": "type.googleapis.com/envoy.config.route.v3.RouteConfiguration",
|
||||
"nonce": "00000001"
|
||||
}
|
401
agent/xds/testdata/routes/ingress-with-chain-and-router-header-manip.v2compat.envoy-1-16-x.golden
vendored
Normal file
401
agent/xds/testdata/routes/ingress-with-chain-and-router-header-manip.v2compat.envoy-1-16-x.golden
vendored
Normal file
|
@ -0,0 +1,401 @@
|
|||
{
|
||||
"versionInfo": "00000001",
|
||||
"resources": [
|
||||
{
|
||||
"@type": "type.googleapis.com/envoy.api.v2.RouteConfiguration",
|
||||
"name": "9191",
|
||||
"virtualHosts": [
|
||||
{
|
||||
"name": "db",
|
||||
"domains": [
|
||||
"db.ingress.*",
|
||||
"db.ingress.*:9191"
|
||||
],
|
||||
"routes": [
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/prefix"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prefix.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"path": "/exact"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "exact.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"safeRegex": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "/regex"
|
||||
}
|
||||
},
|
||||
"route": {
|
||||
"cluster": "regex.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"presentMatch": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-present.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"presentMatch": true,
|
||||
"invertMatch": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-not-present.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"exactMatch": "exact"
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-exact.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"prefixMatch": "prefix"
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-prefix.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"suffixMatch": "suffix"
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-suffix.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"safeRegexMatch": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "regex"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-regex.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": ":method",
|
||||
"safeRegexMatch": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "GET|PUT"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "just-methods.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"headers": [
|
||||
{
|
||||
"name": "x-debug",
|
||||
"exactMatch": "exact"
|
||||
},
|
||||
{
|
||||
"name": ":method",
|
||||
"safeRegexMatch": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "GET|PUT"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "hdr-exact-with-method.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"queryParameters": [
|
||||
{
|
||||
"name": "secretparam1",
|
||||
"stringMatch": {
|
||||
"exact": "exact"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prm-exact.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"queryParameters": [
|
||||
{
|
||||
"name": "secretparam2",
|
||||
"stringMatch": {
|
||||
"safeRegex": {
|
||||
"googleRe2": {
|
||||
|
||||
},
|
||||
"regex": "regex"
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prm-regex.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/",
|
||||
"queryParameters": [
|
||||
{
|
||||
"name": "secretparam3",
|
||||
"presentMatch": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prm-present.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "nil-match.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "empty-match-1.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "empty-match-2.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/prefix"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prefix-rewrite-1.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"prefixRewrite": "/"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/prefix"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "prefix-rewrite-2.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"prefixRewrite": "/nested/newlocation"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/timeout"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "req-timeout.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"timeout": "33s"
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/retry-connect"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "retry-connect.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"retryPolicy": {
|
||||
"retryOn": "connect-failure",
|
||||
"numRetries": 15
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/retry-codes"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "retry-codes.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"retryPolicy": {
|
||||
"retryOn": "retriable-status-codes",
|
||||
"numRetries": 15,
|
||||
"retriableStatusCodes": [
|
||||
401,
|
||||
409,
|
||||
451
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/retry-both"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "retry-both.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"retryPolicy": {
|
||||
"retryOn": "connect-failure,retriable-status-codes",
|
||||
"retriableStatusCodes": [
|
||||
401,
|
||||
409,
|
||||
451
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/split-3-ways"
|
||||
},
|
||||
"route": {
|
||||
"weightedClusters": {
|
||||
"clusters": [
|
||||
{
|
||||
"name": "big-side.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"weight": 9550
|
||||
},
|
||||
{
|
||||
"name": "goldilocks-side.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"weight": 400
|
||||
},
|
||||
{
|
||||
"name": "lil-bit-side.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul",
|
||||
"weight": 50
|
||||
}
|
||||
],
|
||||
"totalWeight": 10000
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"match": {
|
||||
"prefix": "/"
|
||||
},
|
||||
"route": {
|
||||
"cluster": "db.default.dc1.internal.11111111-2222-3333-4444-555555555555.consul"
|
||||
}
|
||||
}
|
||||
],
|
||||
"requestHeadersToAdd": [
|
||||
{
|
||||
"header": {
|
||||
"key": "foo",
|
||||
"value": "bar"
|
||||
},
|
||||
"append": true
|
||||
},
|
||||
{
|
||||
"header": {
|
||||
"key": "bar",
|
||||
"value": "baz"
|
||||
},
|
||||
"append": false
|
||||
}
|
||||
],
|
||||
"requestHeadersToRemove": [
|
||||
"qux"
|
||||
],
|
||||
"responseHeadersToAdd": [
|
||||
{
|
||||
"header": {
|
||||
"key": "foo",
|
||||
"value": "bar"
|
||||
},
|
||||
"append": true
|
||||
},
|
||||
{
|
||||
"header": {
|
||||
"key": "bar",
|
||||
"value": "baz"
|
||||
},
|
||||
"append": false
|
||||
}
|
||||
],
|
||||
"responseHeadersToRemove": [
|
||||
"qux"
|
||||
]
|
||||
}
|
||||
],
|
||||
"validateClusters": true
|
||||
}
|
||||
],
|
||||
"typeUrl": "type.googleapis.com/envoy.api.v2.RouteConfiguration",
|
||||
"nonce": "00000001"
|
||||
}
|
Loading…
Reference in New Issue