istio.io/istio@v0.0.0-20240520182934-d79c90f27776/pkg/envoy/agent_test.go (about) 1 // Copyright Istio Authors 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package envoy 16 17 import ( 18 "context" 19 "net" 20 "testing" 21 22 "istio.io/istio/pilot/cmd/pilot-agent/status/testserver" 23 ) 24 25 var invalidStats = "" 26 27 var downstreamCxPostiveAcStats = "http.admin.downstream_cx_active: 2 \n" + 28 "http.agent.downstream_cx_active: 0 \n" + 29 "http.inbound_0.0.0.0_8080.downstream_cx_active: 0 \n" + 30 "listener.0.0.0.0_15001.downstream_cx_active: 0 \n" + 31 "listener.0.0.0.0_15006.downstream_cx_active: 0 \n" + 32 "listener.0.0.0.0_15021.downstream_cx_active: 0 \n" + 33 "listener.0.0.0.0_8443.downstream_cx_active: 6 \n" + 34 "listener.0.0.0.0_9093.downstream_cx_active: 8 \n" + 35 "listener.10.112.32.70_9043.downstream_cx_active: 1 \n" + 36 "listener.10.112.33.230_2181.downstream_cx_active: 0 \n" + 37 "listener.10.112.40.186_2181.downstream_cx_active: 1 \n" + 38 "listener.10.112.43.239_9043.downstream_cx_active: 2 \n" + 39 "listener.10.112.49.68_9043.downstream_cx_active: 1 \n" + 40 "listener.admin.downstream_cx_active: 2 \n" + 41 "listener.admin.main_thread.downstream_cx_active: 2" 42 43 var downstreamCxZeroAcStats = "http.admin.downstream_cx_active: 2 \n" + 44 "http.agent.downstream_cx_active: 0 \n" + 45 "http.inbound_0.0.0.0_8080.downstream_cx_active: 0 \n" + 46 "listener.0.0.0.0_15001.downstream_cx_active: 0 \n" + 47 "listener.0.0.0.0_15006.downstream_cx_active: 0 \n" + 48 "listener.0.0.0.0_15021.downstream_cx_active: 1 \n" + 49 "listener.0.0.0.0_8443.downstream_cx_active: 0 \n" + 50 "listener.0.0.0.0_9093.downstream_cx_active: 0 \n" + 51 "listener.10.112.32.70_9043.downstream_cx_active: 0 \n" + 52 "listener.10.112.33.230_2181.downstream_cx_active: 0 \n" + 53 "listener.10.112.40.186_2181.downstream_cx_active: 0 \n" + 54 "listener.10.112.43.239_9043.downstream_cx_active: 0 \n" + 55 "listener.10.112.49.68_9043.downstream_cx_active: 0\n" + 56 "listener.admin.downstream_cx_active: 2 \n" + 57 "listener.admin.main_thread.downstream_cx_active: 2" 58 59 // TestProxy sample struct for proxy 60 type TestProxy struct { 61 run func(<-chan error) error 62 cleanup func() 63 blockChannel chan any 64 } 65 66 func (tp TestProxy) Run(stop <-chan error) error { 67 if tp.run == nil { 68 return nil 69 } 70 return tp.run(stop) 71 } 72 73 func (tp TestProxy) Drain(bool) error { 74 tp.blockChannel <- "unblock" 75 return nil 76 } 77 78 func (tp TestProxy) Cleanup() { 79 if tp.cleanup != nil { 80 tp.cleanup() 81 } 82 } 83 84 func (tp TestProxy) UpdateConfig(_ []byte) error { 85 return nil 86 } 87 88 // TestStartExit starts a proxy and ensures the agent exits once the proxy exits 89 func TestStartExit(t *testing.T) { 90 ctx := context.Background() 91 done := make(chan struct{}) 92 a := NewAgent(TestProxy{}, 0, 0, "", 0, 0, 0, true) 93 go func() { 94 a.Run(ctx) 95 done <- struct{}{} 96 }() 97 <-done 98 } 99 100 // TestStartTwiceStop applies three configs and validates that cleanups are called in order 101 func TestStartStop(t *testing.T) { 102 ctx, cancel := context.WithCancel(context.Background()) 103 start := func(_ <-chan error) error { 104 return nil 105 } 106 cleanup := func() { 107 cancel() 108 } 109 a := NewAgent(TestProxy{run: start, cleanup: cleanup}, 0, 0, "", 0, 0, 0, true) 110 go func() { a.Run(ctx) }() 111 <-ctx.Done() 112 } 113 114 func TestActiveConnections(t *testing.T) { 115 cases := []struct { 116 name string 117 stats string 118 expected int 119 }{ 120 { 121 "invalid stats", 122 invalidStats, 123 -1, 124 }, 125 { 126 "valid active connections", 127 downstreamCxPostiveAcStats, 128 19, 129 }, 130 { 131 "zero active connections", 132 downstreamCxZeroAcStats, 133 0, 134 }, 135 } 136 137 for _, tt := range cases { 138 t.Run(tt.name, func(t *testing.T) { 139 server := testserver.CreateAndStartServer(tt.stats) 140 defer server.Close() 141 142 agent := NewAgent(TestProxy{}, 0, 0, "localhost", server.Listener.Addr().(*net.TCPAddr).Port, 15021, 15009, true) 143 if ac, _ := agent.activeProxyConnections(); ac != tt.expected { 144 t.Errorf("unexpected active proxy connections. expected: %d got: %d", tt.expected, ac) 145 } 146 }) 147 } 148 }