mosn

Форк
0
/
retry_test.go 
455 строк · 10.7 Кб
1
//go:build MOSNTest
2
// +build MOSNTest
3

4
package retry
5

6
import (
7
	"fmt"
8
	"regexp"
9
	"testing"
10

11
	"mosn.io/api"
12
	"mosn.io/mosn/pkg/protocol"
13
	. "mosn.io/mosn/test/framework"
14
	"mosn.io/mosn/test/lib"
15
	"mosn.io/mosn/test/lib/extends"
16
	"mosn.io/mosn/test/lib/http"
17
)
18

19
func TestSimpleRetry(t *testing.T) {
20
	Scenario(t, "protocol http1 with retry", func() {
21
		_, servers := lib.InitMosn(CreateRetryConfig(protocol.HTTP1, protocol.HTTP1), lib.CreateConfig(`{
22
			"protocol":"Http1",
23
			"config": {
24
				"address": "127.0.0.1:8080",
25
				"response_configs": {
26
					"/": {
27
						"common_builder": {
28
							"status_code": 500
29
						}
30
					}
31
				}
32
			}
33
		}`), lib.CreateConfig(`{
34
			"protocol":"Http1",
35
			"config": {
36
				"address": "127.0.0.1:8081",
37
				"response_configs": {
38
					"/": {
39
						"common_builder": {
40
							"status_code": 200
41
						}
42
					}
43
				}
44
			}
45
		}`))
46

47
		Case("mesh to mesh, one of the upstream server response status code is 500", func() {
48
			client := lib.CreateClient("Http1", &http.HttpClientConfig{
49
				TargetAddr: "127.0.0.1:2045",
50
				Verify: &http.VerifyConfig{
51
					ExpectedStatusCode: 200,
52
				},
53
			})
54
			// at least run twice
55
			for i := 0; i < 2; i++ {
56
				Verify(client.SyncCall(), Equal, true)
57
			}
58
			// veirfy, the second server should have 2 requests
59
			goodsrv := servers[1]
60
			Verify(goodsrv.Stats().Requests(), Equal, 2)
61
		})
62

63
		Case("mesh to upstream, one of the upstream server response status code is 500", func() {
64
			client := lib.CreateClient("Http1", &http.HttpClientConfig{
65
				TargetAddr: "127.0.0.1:2046",
66
				Verify: &http.VerifyConfig{
67
					ExpectedStatusCode: 200,
68
				},
69
			})
70
			// at least run twice
71
			for i := 0; i < 2; i++ {
72
				Verify(client.SyncCall(), Equal, true)
73
			}
74
			goodsrv := servers[1]
75
			Verify(goodsrv.Stats().Requests(), Equal, 4)
76
		})
77

78
		Case("mesh to mesh, one of the upstream server is closed", func() {
79
			// close the bad server
80
			badsrv := servers[0]
81
			badsrv.Stop()
82
			//
83
			client := lib.CreateClient("Http1", &http.HttpClientConfig{
84
				TargetAddr: "127.0.0.1:2045",
85
				Verify: &http.VerifyConfig{
86
					ExpectedStatusCode: 200,
87
				},
88
			})
89
			// at least run twice
90
			for i := 0; i < 2; i++ {
91
				Verify(client.SyncCall(), Equal, true)
92
			}
93
			goodsrv := servers[1]
94
			Verify(goodsrv.Stats().Requests(), Equal, 6)
95
		})
96

97
		Case("mesh to upstream, one of the upstream server is closed", func() {
98
			client := lib.CreateClient("Http1", &http.HttpClientConfig{
99
				TargetAddr: "127.0.0.1:2046",
100
				Verify: &http.VerifyConfig{
101
					ExpectedStatusCode: 200,
102
				},
103
			})
104
			// at least run twice
105
			for i := 0; i < 2; i++ {
106
				Verify(client.SyncCall(), Equal, true)
107
			}
108
			goodsrv := servers[1]
109
			Verify(goodsrv.Stats().Requests(), Equal, 8)
110
		})
111
	})
112

113
	Scenario(t, "protocol http2 with retry", func() {
114
		_, servers := lib.InitMosn(CreateRetryConfig(protocol.HTTP2, protocol.HTTP2), lib.CreateConfig(`{
115
			"protocol":"Http2",
116
			"config": {
117
				"address": "127.0.0.1:8080",
118
				"response_configs": {
119
					"/": {
120
						"common_builder": {
121
							"status_code": 500
122
						}
123
					}
124
				}
125
			}
126
		}`), lib.CreateConfig(`{
127
			"protocol":"Http2",
128
			"config": {
129
				"address": "127.0.0.1:8081",
130
				"response_configs": {
131
					"/": {
132
						"common_builder": {
133
							"status_code": 200
134
						}
135
					}
136
				}
137
			}
138
		}`))
139

140
		Case("mesh to mesh, one of the upstream server response status code is 500", func() {
141
			client := lib.CreateClient("Http2", &http.HttpClientConfig{
142
				TargetAddr: "127.0.0.1:2045",
143
				Verify: &http.VerifyConfig{
144
					ExpectedStatusCode: 200,
145
				},
146
			})
147
			// at least run twice
148
			for i := 0; i < 2; i++ {
149
				Verify(client.SyncCall(), Equal, true)
150
			}
151
			// veirfy, the second server should have 2 requests
152
			goodsrv := servers[1]
153
			Verify(goodsrv.Stats().Requests(), Equal, 2)
154
		})
155

156
		Case("mesh to upstream, one of the upstream server response status code is 500", func() {
157
			client := lib.CreateClient("Http2", &http.HttpClientConfig{
158
				TargetAddr: "127.0.0.1:2046",
159
				Verify: &http.VerifyConfig{
160
					ExpectedStatusCode: 200,
161
				},
162
			})
163
			// at least run twice
164
			for i := 0; i < 2; i++ {
165
				Verify(client.SyncCall(), Equal, true)
166
			}
167
			goodsrv := servers[1]
168
			Verify(goodsrv.Stats().Requests(), Equal, 4)
169
		})
170

171
		Case("mesh to mesh, one of the upstream server is closed", func() {
172
			// close the bad server
173
			badsrv := servers[0]
174
			badsrv.Stop()
175
			//
176
			client := lib.CreateClient("Http2", &http.HttpClientConfig{
177
				TargetAddr: "127.0.0.1:2045",
178
				Verify: &http.VerifyConfig{
179
					ExpectedStatusCode: 200,
180
				},
181
			})
182
			// at least run twice
183
			for i := 0; i < 2; i++ {
184
				Verify(client.SyncCall(), Equal, true)
185
			}
186
			goodsrv := servers[1]
187
			Verify(goodsrv.Stats().Requests(), Equal, 6)
188
		})
189

190
		Case("mesh to upstream, one of the upstream server is closed", func() {
191
			client := lib.CreateClient("Http2", &http.HttpClientConfig{
192
				TargetAddr: "127.0.0.1:2046",
193
				Verify: &http.VerifyConfig{
194
					ExpectedStatusCode: 200,
195
				},
196
			})
197
			// at least run twice
198
			for i := 0; i < 2; i++ {
199
				Verify(client.SyncCall(), Equal, true)
200
			}
201
			goodsrv := servers[1]
202
			Verify(goodsrv.Stats().Requests(), Equal, 8)
203
		})
204

205
	})
206
}
207

208
func TestRetryWithHttpConvert(t *testing.T) {
209
	Scenario(t, "protocol http1 trans to http2 with retry", func() {
210
		_, servers := lib.InitMosn(CreateRetryConfig(protocol.HTTP1, protocol.HTTP2), lib.CreateConfig(`{
211
			"protocol":"Http1",
212
			"config": {
213
				"address": "127.0.0.1:8080",
214
				"response_configs": {
215
					"/": {
216
						"common_builder": {
217
							"status_code": 500
218
						}
219
					}
220
				}
221
			}
222
		}`), lib.CreateConfig(`{
223
			"protocol":"Http1",
224
			"config": {
225
				"address": "127.0.0.1:8081",
226
				"response_configs": {
227
					"/": {
228
						"common_builder": {
229
							"status_code": 200
230
						}
231
					}
232
				}
233
			}
234
		}`))
235

236
		Case("mesh to mesh, one of the upstream server response status code is 500", func() {
237
			client := lib.CreateClient("Http1", &http.HttpClientConfig{
238
				TargetAddr: "127.0.0.1:2045",
239
				Verify: &http.VerifyConfig{
240
					ExpectedStatusCode: 200,
241
				},
242
			})
243
			// at least run twice
244
			for i := 0; i < 2; i++ {
245
				Verify(client.SyncCall(), Equal, true)
246
			}
247
			// veirfy, the second server should have 2 requests
248
			goodsrv := servers[1]
249
			Verify(goodsrv.Stats().Requests(), Equal, 2)
250
		})
251

252
		Case("mesh to mesh, one of the upstream server is closed", func() {
253
			// close the bad server
254
			badsrv := servers[0]
255
			badsrv.Stop()
256
			//
257
			client := lib.CreateClient("Http1", &http.HttpClientConfig{
258
				TargetAddr: "127.0.0.1:2045",
259
				Verify: &http.VerifyConfig{
260
					ExpectedStatusCode: 200,
261
				},
262
			})
263
			// at least run twice
264
			for i := 0; i < 2; i++ {
265
				Verify(client.SyncCall(), Equal, true)
266
			}
267
			goodsrv := servers[1]
268
			Verify(goodsrv.Stats().Requests(), Equal, 4)
269
		})
270

271
	})
272

273
	Scenario(t, "protocol http2 trans to http1 with retry", func() {
274
		_, servers := lib.InitMosn(CreateRetryConfig(protocol.HTTP2, protocol.HTTP1), lib.CreateConfig(`{
275
			"protocol":"Http2",
276
			"config": {
277
				"address": "127.0.0.1:8080",
278
				"response_configs": {
279
					"/": {
280
						"common_builder": {
281
							"status_code": 500
282
						}
283
					}
284
				}
285
			}
286
		}`), lib.CreateConfig(`{
287
			"protocol":"Http2",
288
			"config": {
289
				"address": "127.0.0.1:8081",
290
				"response_configs": {
291
					"/": {
292
						"common_builder": {
293
							"status_code": 200
294
						}
295
					}
296
				}
297
			}
298
		}`))
299

300
		Case("mesh to mesh, one of the upstream server response status code is 500", func() {
301
			client := lib.CreateClient("Http2", &http.HttpClientConfig{
302
				TargetAddr: "127.0.0.1:2045",
303
				Verify: &http.VerifyConfig{
304
					ExpectedStatusCode: 200,
305
				},
306
			})
307
			// at least run twice
308
			for i := 0; i < 2; i++ {
309
				Verify(client.SyncCall(), Equal, true)
310
			}
311
			// veirfy, the second server should have 2 requests
312
			goodsrv := servers[1]
313
			Verify(goodsrv.Stats().Requests(), Equal, 2)
314
		})
315

316
		Case("mesh to mesh, one of the upstream server is closed", func() {
317
			// close the bad server
318
			badsrv := servers[0]
319
			badsrv.Stop()
320
			//
321
			client := lib.CreateClient("Http2", &http.HttpClientConfig{
322
				TargetAddr: "127.0.0.1:2045",
323
				Verify: &http.VerifyConfig{
324
					ExpectedStatusCode: 200,
325
				},
326
			})
327
			// at least run twice
328
			for i := 0; i < 2; i++ {
329
				Verify(client.SyncCall(), Equal, true)
330
			}
331
			goodsrv := servers[1]
332
			Verify(goodsrv.Stats().Requests(), Equal, 4)
333
		})
334

335
	})
336
}
337

338
var trimStreamFilters = regexp.MustCompile(`"stream_filters":\[.*\]`)
339

340
func CreateRetryConfig(original api.ProtocolName, trans api.ProtocolName) string {
341
	if original == trans {
342
		newTmpl := trimStreamFilters.ReplaceAllString(ConfigWithRetryTmpl, `"stream_filters":[]`)
343
		return fmt.Sprintf(newTmpl, original, original)
344
	}
345
	filterin, filtermid := extends.GetTransFilter(original, trans)
346
	return fmt.Sprintf(ConfigWithRetryTmpl, original, filterin, trans, filtermid)
347
}
348

349
const ConfigWithRetryTmpl = `{
350
	"servers":[
351
		{
352
			"default_log_path":"stdout",
353
			"default_log_level": "ERROR",
354
			"routers": [
355
				{
356
					"router_config_name":"router_to_upstream",
357
					"virtual_hosts":[{
358
						"name":"server_hosts",
359
						"domains": ["*"],
360
						"routers": [
361
							{
362
								"match":{"prefix":"/"},
363
								"route":{
364
									"cluster_name":"upstream",
365
									"retry_policy": {
366
										"retry_on": true,
367
										"retry_timeout": "5s",
368
										"num_retries": 3
369
									}
370
								}
371
							}
372
						]
373
					}]
374
				},
375
				{
376
					"router_config_name":"router_to_mesh",
377
					"virtual_hosts":[{
378
						"name":"server_hosts2",
379
						"domains": ["*"],
380
						"routers": [
381
							{
382
								"match":{"prefix":"/"},
383
								"route":{
384
									"cluster_name":"mesh",
385
									"retry_policy": {
386
										"retry_on": true,
387
										"retry_timeout": "5s",
388
										"num_retries": 3
389
									}
390
								}
391
							}
392
						]
393
					}]
394
				}
395
			],
396
			"listeners":[
397
				{
398
					"address":"127.0.0.1:2045",
399
					"bind_port": true,
400
					"filter_chains": [{
401
						"filters": [
402
							{
403
								"type": "proxy",
404
								"config": {
405
									"downstream_protocol": "%s",
406
									"upstream_protocol": "Auto",
407
									"router_config_name":"router_to_mesh"
408
								}
409
							}
410
						]
411
					}],
412
					"stream_filters":[{"type": "transcoder","config": {"type": "%s"}}]
413
				},
414
				{
415
					"address":"127.0.0.1:2046",
416
					"bind_port": true,
417
					"filter_chains": [{
418
						"filters": [
419
							{
420
								"type": "proxy",
421
								"config": {
422
									"downstream_protocol": "%s",
423
									"upstream_protocol": "Auto",
424
									"router_config_name":"router_to_upstream"
425
								}
426
							}
427
						]
428
					}],
429
					"stream_filters":[{"type": "transcoder","config": {"type": "%s"}}]
430
				}
431
			]
432
		}
433
	],
434
	"cluster_manager":{
435
		"clusters":[
436
			{
437
				"name": "mesh",
438
				"type": "SIMPLE",
439
				"lb_type": "LB_ROUNDROBIN",
440
				"hosts":[
441
					{"address":"127.0.0.1:2046"}
442
				]
443
			},
444
			{
445
				"name": "upstream",
446
				"type": "SIMPLE",
447
				"lb_type": "LB_ROUNDROBIN",
448
				"hosts":[
449
					{"address":"127.0.0.1:8080"},
450
					{"address":"127.0.0.1:8081"}
451
				]
452
			}
453
		]
454
	}
455
}`
456

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.