@@ -10,6 +10,7 @@ import (
1010 "testing"
1111
1212 cluster "github.com/envoyproxy/go-control-plane/envoy/config/cluster/v3"
13+ endpoint "github.com/envoyproxy/go-control-plane/envoy/config/endpoint/v3"
1314 listener "github.com/envoyproxy/go-control-plane/envoy/config/listener/v3"
1415 route "github.com/envoyproxy/go-control-plane/envoy/config/route/v3"
1516 tls "github.com/envoyproxy/go-control-plane/envoy/extensions/transport_sockets/tls/v3"
@@ -29,6 +30,7 @@ import (
2930type mockXDSHookClient struct {
3031 postRouteModifyHook func (r * route.Route , hostnames []string , resources []* unstructured.Unstructured ) (* route.Route , error )
3132 postVirtualHostModifyHook func (vh * route.VirtualHost ) (* route.VirtualHost , error )
33+ postEndpointsModifyHook func (loadAssignment * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error )
3234 postHTTPListenerModifyHook func (l * listener.Listener , resources []* unstructured.Unstructured ) (* listener.Listener , error )
3335 postClusterModifyHook func (c * cluster.Cluster , resources []* unstructured.Unstructured ) (* cluster.Cluster , error )
3436 postTranslateModifyHook func (clusters []* cluster.Cluster , secrets []* tls.Secret , listeners []* listener.Listener , routes []* route.RouteConfiguration , policies []* ir.UnstructuredRef ) ([]* cluster.Cluster , []* tls.Secret , []* listener.Listener , []* route.RouteConfiguration , error )
@@ -50,6 +52,13 @@ func (m *mockXDSHookClient) PostVirtualHostModifyHook(vh *route.VirtualHost) (*r
5052 return vh , nil
5153}
5254
55+ func (m * mockXDSHookClient ) PostEndpointsModifyHook (loadAssignment * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
56+ if m .postEndpointsModifyHook != nil {
57+ return m .postEndpointsModifyHook (loadAssignment )
58+ }
59+ return loadAssignment , nil
60+ }
61+
5362func (m * mockXDSHookClient ) PostHTTPListenerModifyHook (l * listener.Listener , resources []* unstructured.Unstructured ) (* listener.Listener , error ) {
5463 if m .postHTTPListenerModifyHook != nil {
5564 return m .postHTTPListenerModifyHook (l , resources )
@@ -302,6 +311,81 @@ func TestCompositeHookClient_PostVirtualHostModifyHook(t *testing.T) {
302311 })
303312}
304313
314+ func TestCompositeHookClient_PostEndpointsModifyHook (t * testing.T ) {
315+ t .Run ("chains two clients" , func (t * testing.T ) {
316+ client1 := & mockXDSHookClient {
317+ postEndpointsModifyHook : func (la * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
318+ la .ClusterName += "-ext1"
319+ return la , nil
320+ },
321+ }
322+ client2 := & mockXDSHookClient {
323+ postEndpointsModifyHook : func (la * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
324+ la .ClusterName += "-ext2"
325+ return la , nil
326+ },
327+ }
328+
329+ composite := & compositeXDSHookClient {
330+ entries : []hookClientEntry {
331+ {name : "ext1" , client : client1 },
332+ {name : "ext2" , client : client2 },
333+ },
334+ }
335+
336+ input := & endpoint.ClusterLoadAssignment {ClusterName : "test" }
337+ result , err := composite .PostEndpointsModifyHook (input )
338+ require .NoError (t , err )
339+ require .Equal (t , "test-ext1-ext2" , result .ClusterName )
340+ })
341+
342+ t .Run ("failOpen skips erroring extension" , func (t * testing.T ) {
343+ composite := & compositeXDSHookClient {
344+ entries : []hookClientEntry {
345+ {name : "ext1" , client : & mockXDSHookClient {
346+ postEndpointsModifyHook : func (_ * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
347+ return nil , fmt .Errorf ("extension error" )
348+ },
349+ }, failOpen : true },
350+ {name : "ext2" , client : & mockXDSHookClient {
351+ postEndpointsModifyHook : func (la * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
352+ la .ClusterName += "-ext2"
353+ return la , nil
354+ },
355+ }},
356+ },
357+ }
358+
359+ result , err := composite .PostEndpointsModifyHook (& endpoint.ClusterLoadAssignment {ClusterName : "test" })
360+ require .NoError (t , err )
361+ require .Equal (t , "test-ext2" , result .ClusterName )
362+ })
363+
364+ t .Run ("failClosed stops chain" , func (t * testing.T ) {
365+ client2Called := false
366+ composite := & compositeXDSHookClient {
367+ entries : []hookClientEntry {
368+ {name : "ext1" , client : & mockXDSHookClient {
369+ postEndpointsModifyHook : func (_ * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
370+ return nil , fmt .Errorf ("extension error" )
371+ },
372+ }, failOpen : false },
373+ {name : "ext2" , client : & mockXDSHookClient {
374+ postEndpointsModifyHook : func (la * endpoint.ClusterLoadAssignment ) (* endpoint.ClusterLoadAssignment , error ) {
375+ client2Called = true
376+ la .ClusterName += "-ext2"
377+ return la , nil
378+ },
379+ }},
380+ },
381+ }
382+
383+ _ , err := composite .PostEndpointsModifyHook (& endpoint.ClusterLoadAssignment {ClusterName : "test" })
384+ require .Equal (t , fmt .Errorf (`extension "ext1": %w` , fmt .Errorf ("extension error" )), err )
385+ require .False (t , client2Called )
386+ })
387+ }
388+
305389func TestCompositeHookClient_PostHTTPListenerModifyHook (t * testing.T ) {
306390 t .Run ("chains two clients" , func (t * testing.T ) {
307391 client1 := & mockXDSHookClient {
0 commit comments