github.com/lmb/consul@v1.4.1/connect/proxy/config_test.go (about) 1 package proxy 2 3 import ( 4 "log" 5 "os" 6 "testing" 7 "time" 8 9 "github.com/stretchr/testify/assert" 10 11 "github.com/hashicorp/consul/agent" 12 "github.com/hashicorp/consul/api" 13 "github.com/hashicorp/consul/connect" 14 "github.com/stretchr/testify/require" 15 ) 16 17 func TestUpstreamResolverFuncFromClient(t *testing.T) { 18 t.Parallel() 19 20 tests := []struct { 21 name string 22 cfg UpstreamConfig 23 want *connect.ConsulResolver 24 }{ 25 { 26 name: "service", 27 cfg: UpstreamConfig{ 28 DestinationNamespace: "foo", 29 DestinationName: "web", 30 Datacenter: "ny1", 31 DestinationType: "service", 32 }, 33 want: &connect.ConsulResolver{ 34 Namespace: "foo", 35 Name: "web", 36 Datacenter: "ny1", 37 Type: connect.ConsulResolverTypeService, 38 }, 39 }, 40 { 41 name: "prepared_query", 42 cfg: UpstreamConfig{ 43 DestinationNamespace: "foo", 44 DestinationName: "web", 45 Datacenter: "ny1", 46 DestinationType: "prepared_query", 47 }, 48 want: &connect.ConsulResolver{ 49 Namespace: "foo", 50 Name: "web", 51 Datacenter: "ny1", 52 Type: connect.ConsulResolverTypePreparedQuery, 53 }, 54 }, 55 { 56 name: "unknown behaves like service", 57 cfg: UpstreamConfig{ 58 DestinationNamespace: "foo", 59 DestinationName: "web", 60 Datacenter: "ny1", 61 DestinationType: "junk", 62 }, 63 want: &connect.ConsulResolver{ 64 Namespace: "foo", 65 Name: "web", 66 Datacenter: "ny1", 67 Type: connect.ConsulResolverTypeService, 68 }, 69 }, 70 } 71 for _, tt := range tests { 72 t.Run(tt.name, func(t *testing.T) { 73 // Client doesn't really matter as long as it's passed through. 74 gotFn := UpstreamResolverFuncFromClient(nil) 75 got, err := gotFn(tt.cfg) 76 require.NoError(t, err) 77 require.Equal(t, tt.want, got) 78 }) 79 } 80 } 81 82 func TestAgentConfigWatcherManagedProxy(t *testing.T) { 83 t.Parallel() 84 85 a := agent.NewTestAgent("agent_smith", ` 86 connect { 87 enabled = true 88 proxy { 89 allow_managed_api_registration = true 90 } 91 } 92 `) 93 defer a.Shutdown() 94 95 client := a.Client() 96 agent := client.Agent() 97 98 // Register a local agent service with a managed proxy 99 reg := &api.AgentServiceRegistration{ 100 Name: "web", 101 Port: 8080, 102 Connect: &api.AgentServiceConnect{ 103 Proxy: &api.AgentServiceConnectProxy{ 104 Config: map[string]interface{}{ 105 "bind_address": "10.10.10.10", 106 "bind_port": 1010, 107 "local_service_address": "127.0.0.1:5000", 108 "handshake_timeout_ms": 999, 109 }, 110 Upstreams: []api.Upstream{ 111 { 112 DestinationName: "db", 113 LocalBindPort: 9191, 114 }, 115 }, 116 }, 117 }, 118 } 119 err := agent.ServiceRegister(reg) 120 require.NoError(t, err) 121 122 w, err := NewAgentConfigWatcher(client, "web-proxy", 123 log.New(os.Stderr, "", log.LstdFlags)) 124 require.NoError(t, err) 125 126 cfg := testGetConfigValTimeout(t, w, 500*time.Millisecond) 127 128 expectCfg := &Config{ 129 ProxiedServiceName: "web", 130 ProxiedServiceNamespace: "default", 131 PublicListener: PublicListenerConfig{ 132 BindAddress: "10.10.10.10", 133 BindPort: 1010, 134 LocalServiceAddress: "127.0.0.1:5000", 135 HandshakeTimeoutMs: 999, 136 LocalConnectTimeoutMs: 1000, // from applyDefaults 137 }, 138 Upstreams: []UpstreamConfig{ 139 { 140 DestinationName: "db", 141 DestinationNamespace: "default", 142 DestinationType: "service", 143 LocalBindPort: 9191, 144 LocalBindAddress: "127.0.0.1", 145 }, 146 }, 147 } 148 149 assert.Equal(t, expectCfg, cfg) 150 151 // Now keep watching and update the config. 152 go func() { 153 // Wait for watcher to be watching 154 time.Sleep(20 * time.Millisecond) 155 reg.Connect.Proxy.Upstreams = append(reg.Connect.Proxy.Upstreams, 156 api.Upstream{ 157 DestinationName: "cache", 158 LocalBindPort: 9292, 159 LocalBindAddress: "127.10.10.10", 160 }) 161 reg.Connect.Proxy.Config["local_connect_timeout_ms"] = 444 162 err := agent.ServiceRegister(reg) 163 require.NoError(t, err) 164 }() 165 166 cfg = testGetConfigValTimeout(t, w, 2*time.Second) 167 168 expectCfg.Upstreams = append(expectCfg.Upstreams, UpstreamConfig{ 169 DestinationName: "cache", 170 DestinationNamespace: "default", 171 DestinationType: "service", 172 LocalBindPort: 9292, 173 LocalBindAddress: "127.10.10.10", 174 }) 175 expectCfg.PublicListener.LocalConnectTimeoutMs = 444 176 177 assert.Equal(t, expectCfg, cfg) 178 } 179 180 func TestAgentConfigWatcherSidecarProxy(t *testing.T) { 181 t.Parallel() 182 183 a := agent.NewTestAgent("agent_smith", ``) 184 defer a.Shutdown() 185 186 client := a.Client() 187 agent := client.Agent() 188 189 // Register a local agent service with a managed proxy 190 reg := &api.AgentServiceRegistration{ 191 Name: "web", 192 Port: 8080, 193 Connect: &api.AgentServiceConnect{ 194 SidecarService: &api.AgentServiceRegistration{ 195 Proxy: &api.AgentServiceConnectProxyConfig{ 196 Config: map[string]interface{}{ 197 "handshake_timeout_ms": 999, 198 }, 199 Upstreams: []api.Upstream{ 200 { 201 DestinationName: "db", 202 LocalBindPort: 9191, 203 }, 204 }, 205 }, 206 }, 207 }, 208 } 209 err := agent.ServiceRegister(reg) 210 require.NoError(t, err) 211 212 w, err := NewAgentConfigWatcher(client, "web-sidecar-proxy", 213 log.New(os.Stderr, "", log.LstdFlags)) 214 require.NoError(t, err) 215 216 cfg := testGetConfigValTimeout(t, w, 500*time.Millisecond) 217 218 expectCfg := &Config{ 219 ProxiedServiceName: "web", 220 ProxiedServiceNamespace: "default", 221 PublicListener: PublicListenerConfig{ 222 BindAddress: "0.0.0.0", 223 BindPort: 21000, 224 LocalServiceAddress: "127.0.0.1:8080", 225 HandshakeTimeoutMs: 999, 226 LocalConnectTimeoutMs: 1000, // from applyDefaults 227 }, 228 Upstreams: []UpstreamConfig{ 229 { 230 DestinationName: "db", 231 DestinationNamespace: "default", 232 DestinationType: "service", 233 LocalBindPort: 9191, 234 LocalBindAddress: "127.0.0.1", 235 }, 236 }, 237 } 238 239 require.Equal(t, expectCfg, cfg) 240 241 // Now keep watching and update the config. 242 go func() { 243 // Wait for watcher to be watching 244 time.Sleep(20 * time.Millisecond) 245 reg.Connect.SidecarService.Proxy.Upstreams = append(reg.Connect.SidecarService.Proxy.Upstreams, 246 api.Upstream{ 247 DestinationName: "cache", 248 LocalBindPort: 9292, 249 LocalBindAddress: "127.10.10.10", 250 }) 251 reg.Connect.SidecarService.Proxy.Config["local_connect_timeout_ms"] = 444 252 err := agent.ServiceRegister(reg) 253 require.NoError(t, err) 254 }() 255 256 cfg = testGetConfigValTimeout(t, w, 2*time.Second) 257 258 expectCfg.Upstreams = append(expectCfg.Upstreams, UpstreamConfig{ 259 DestinationName: "cache", 260 DestinationNamespace: "default", 261 DestinationType: "service", 262 LocalBindPort: 9292, 263 LocalBindAddress: "127.10.10.10", 264 }) 265 expectCfg.PublicListener.LocalConnectTimeoutMs = 444 266 267 assert.Equal(t, expectCfg, cfg) 268 } 269 270 func testGetConfigValTimeout(t *testing.T, w ConfigWatcher, 271 timeout time.Duration) *Config { 272 t.Helper() 273 select { 274 case cfg := <-w.Watch(): 275 return cfg 276 case <-time.After(timeout): 277 t.Fatalf("timeout after %s waiting for config update", timeout) 278 return nil 279 } 280 }