Skip to content

Commit 41b839d

Browse files
authored
fix: set SchemeHeaderTransformation.MatchUpstream on AI Gateway listeners (#2194)
**Description** Azure is strict about `scheme` header to be same as the TLS transport on which the request is being made. If the listener is an http listener, envoy forwards a request with `scheme: http` instead of `https`. This leads to requests getting dropped. The simple solution is to use `matchUpstream` which is what is being done in MCP backend listeners but missed in regular AI gateway route listeners. **Related Issues/PRs (if applicable)** Fixes #2095 Signed-off-by: Anurag Aggarwal <kanurag94@gmail.com>
1 parent ef6044f commit 41b839d

2 files changed

Lines changed: 27 additions & 0 deletions

File tree

internal/extensionserver/post_translate_modify.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -676,6 +676,10 @@ func (s *Server) insertRouterLevelAIGatewayExtProc(listener *listenerv3.Listener
676676
if err = insertAIGatewayExtProcFilter(httpConManager, extProcFilter); err != nil {
677677
return fmt.Errorf("failed to insert AI Gateway extproc filter: %w", err)
678678
}
679+
// Match the :scheme pseudo-header to the upstream transport protocol.
680+
httpConManager.SchemeHeaderTransformation = &corev3.SchemeHeaderTransformation{
681+
MatchUpstream: true,
682+
}
679683
hcAny, err := toAny(httpConManager)
680684
if err != nil {
681685
return fmt.Errorf("failed to marshal updated HCM to Any: %w", err)

internal/extensionserver/post_translate_modify_test.go

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -340,6 +340,29 @@ func Test_shouldAIGatewayExtProcBeInserted(t *testing.T) {
340340
}
341341
}
342342

343+
func TestServer_insertRouterLevelAIGatewayExtProc_setsSchemeHeaderTransformation(t *testing.T) {
344+
hcm := &httpconnectionmanagerv3.HttpConnectionManager{
345+
HttpFilters: []*httpconnectionmanagerv3.HttpFilter{{Name: wellknown.Router}},
346+
}
347+
listener := &listenerv3.Listener{
348+
DefaultFilterChain: &listenerv3.FilterChain{
349+
Filters: []*listenerv3.Filter{
350+
{
351+
Name: wellknown.HTTPConnectionManager,
352+
ConfigType: &listenerv3.Filter_TypedConfig{TypedConfig: mustToAny(t, hcm)},
353+
},
354+
},
355+
},
356+
}
357+
s := &Server{log: zap.New()}
358+
require.NoError(t, s.insertRouterLevelAIGatewayExtProc(listener))
359+
360+
updatedHCM, _, err := findHCM(listener.DefaultFilterChain)
361+
require.NoError(t, err)
362+
require.True(t, updatedHCM.GetSchemeHeaderTransformation().GetMatchUpstream(),
363+
"SchemeHeaderTransformation.MatchUpstream must be true so :scheme matches upstream TLS transport")
364+
}
365+
343366
func Test_findListenerRouteConfigs(t *testing.T) {
344367
newHCM := func(name string) *httpconnectionmanagerv3.HttpConnectionManager {
345368
return &httpconnectionmanagerv3.HttpConnectionManager{

0 commit comments

Comments
 (0)