|
1 | | -// vfmt off |
2 | | -fn test_stub() { |
3 | | - $if !new_veb ? { |
4 | | - return |
5 | | - } |
6 | | -} |
| 1 | +import net |
| 2 | +import net.http |
| 3 | +import time |
| 4 | +import veb |
7 | 5 |
|
8 | | -$if new_veb ? { |
9 | | - import net |
10 | | - import net.http |
11 | | - import time |
12 | | - import veb |
| 6 | +const graceful_shutdown_host = '127.0.0.1' |
13 | 7 |
|
14 | | - const graceful_shutdown_host = '127.0.0.1' |
15 | | - |
16 | | - struct GracefulShutdownContext { |
17 | | - veb.Context |
18 | | - } |
| 8 | +struct GracefulShutdownContext { |
| 9 | + veb.Context |
| 10 | +} |
19 | 11 |
|
20 | | - struct GracefulShutdownApp { |
21 | | - mut: |
22 | | - server &veb.Server = unsafe { nil } |
23 | | - slow_started chan bool = chan bool{cap: 1} |
24 | | - } |
| 12 | +struct GracefulShutdownApp { |
| 13 | +mut: |
| 14 | + server &veb.Server = unsafe { nil } |
| 15 | + slow_started chan bool = chan bool{cap: 1} |
| 16 | +} |
25 | 17 |
|
26 | | - pub fn (mut app GracefulShutdownApp) init_server(server &veb.Server) { |
27 | | - app.server = server |
28 | | - } |
| 18 | +pub fn (mut app GracefulShutdownApp) init_server(server &veb.Server) { |
| 19 | + app.server = server |
| 20 | +} |
29 | 21 |
|
30 | | - pub fn (mut app GracefulShutdownApp) index(mut ctx GracefulShutdownContext) veb.Result { |
31 | | - return ctx.text('ready') |
32 | | - } |
| 22 | +pub fn (mut app GracefulShutdownApp) index(mut ctx GracefulShutdownContext) veb.Result { |
| 23 | + return ctx.text('ready') |
| 24 | +} |
33 | 25 |
|
34 | | - @['/slow'] |
35 | | - pub fn (mut app GracefulShutdownApp) slow(mut ctx GracefulShutdownContext) veb.Result { |
36 | | - app.slow_started <- true |
37 | | - time.sleep(300 * time.millisecond) |
38 | | - return ctx.text('slow done') |
39 | | - } |
| 26 | +@['/slow'] |
| 27 | +pub fn (mut app GracefulShutdownApp) slow(mut ctx GracefulShutdownContext) veb.Result { |
| 28 | + app.slow_started <- true |
| 29 | + time.sleep(300 * time.millisecond) |
| 30 | + return ctx.text('slow done') |
| 31 | +} |
40 | 32 |
|
41 | | - pub fn (mut app GracefulShutdownApp) shutdown(mut ctx GracefulShutdownContext) veb.Result { |
42 | | - spawn app.shutdown_now() |
43 | | - return ctx.text('shutting down') |
44 | | - } |
| 33 | +pub fn (mut app GracefulShutdownApp) shutdown(mut ctx GracefulShutdownContext) veb.Result { |
| 34 | + spawn app.shutdown_now() |
| 35 | + return ctx.text('shutting down') |
| 36 | +} |
45 | 37 |
|
46 | | - fn (app &GracefulShutdownApp) shutdown_now() { |
47 | | - mut server := app.server |
48 | | - if server == unsafe { nil } { |
49 | | - panic('veb server was not initialized') |
50 | | - } |
51 | | - server.shutdown() or { panic(err) } |
| 38 | +fn (app &GracefulShutdownApp) shutdown_now() { |
| 39 | + mut server := app.server |
| 40 | + if server == unsafe { nil } { |
| 41 | + panic('veb server was not initialized') |
52 | 42 | } |
| 43 | + server.shutdown() or { panic(err) } |
| 44 | +} |
53 | 45 |
|
54 | | - fn run_graceful_shutdown_app(mut app GracefulShutdownApp, port int) { |
55 | | - veb.run_at[GracefulShutdownApp, GracefulShutdownContext](mut app, |
56 | | - host: graceful_shutdown_host |
57 | | - port: port |
58 | | - family: .ip |
59 | | - show_startup_message: false |
60 | | - ) or { panic(err) } |
61 | | - } |
| 46 | +fn run_graceful_shutdown_app(mut app GracefulShutdownApp, port int) { |
| 47 | + veb.run_at[GracefulShutdownApp, GracefulShutdownContext](mut app, |
| 48 | + host: graceful_shutdown_host |
| 49 | + port: port |
| 50 | + family: .ip |
| 51 | + show_startup_message: false |
| 52 | + ) or { panic(err) } |
| 53 | +} |
62 | 54 |
|
63 | | - fn send_slow_request(port int, responses chan http.Response) { |
64 | | - response := http.get('http://${graceful_shutdown_host}:${port}/slow') or { panic(err) } |
65 | | - responses <- response |
66 | | - } |
| 55 | +fn send_slow_request(port int, responses chan http.Response) { |
| 56 | + response := http.get('http://${graceful_shutdown_host}:${port}/slow') or { panic(err) } |
| 57 | + responses <- response |
| 58 | +} |
67 | 59 |
|
68 | | - fn wait_for_server(port int) ! { |
69 | | - url := 'http://${graceful_shutdown_host}:${port}/' |
70 | | - for _ in 0 .. 100 { |
71 | | - response := http.get(url) or { |
72 | | - time.sleep(20 * time.millisecond) |
73 | | - continue |
74 | | - } |
75 | | - if response.status() == .ok && response.body == 'ready' { |
76 | | - return |
77 | | - } |
| 60 | +fn wait_for_server(port int) ! { |
| 61 | + url := 'http://${graceful_shutdown_host}:${port}/' |
| 62 | + for _ in 0 .. 100 { |
| 63 | + response := http.get(url) or { |
78 | 64 | time.sleep(20 * time.millisecond) |
| 65 | + continue |
79 | 66 | } |
80 | | - return error('server did not start listening in time') |
| 67 | + if response.status() == .ok && response.body == 'ready' { |
| 68 | + return |
| 69 | + } |
| 70 | + time.sleep(20 * time.millisecond) |
81 | 71 | } |
| 72 | + return error('server did not start listening in time') |
| 73 | +} |
82 | 74 |
|
83 | | - fn test_veb_graceful_shutdown_waits_for_in_flight_requests() { |
84 | | - mut listener := net.listen_tcp(.ip, '${graceful_shutdown_host}:0') or { panic(err) } |
85 | | - port := listener.addr()!.port()! |
86 | | - listener.close() or {} |
| 75 | +fn test_veb_graceful_shutdown_waits_for_in_flight_requests() { |
| 76 | + mut listener := net.listen_tcp(.ip, '${graceful_shutdown_host}:0') or { panic(err) } |
| 77 | + port := listener.addr()!.port()! |
| 78 | + listener.close() or {} |
87 | 79 |
|
88 | | - mut app := &GracefulShutdownApp{} |
89 | | - server_thread := spawn run_graceful_shutdown_app(mut app, int(port)) |
| 80 | + mut app := &GracefulShutdownApp{} |
| 81 | + server_thread := spawn run_graceful_shutdown_app(mut app, int(port)) |
90 | 82 |
|
91 | | - wait_for_server(int(port)) or { |
92 | | - assert false, err.msg() |
93 | | - return |
94 | | - } |
| 83 | + wait_for_server(int(port)) or { |
| 84 | + assert false, err.msg() |
| 85 | + return |
| 86 | + } |
95 | 87 |
|
96 | | - slow_responses := chan http.Response{cap: 1} |
97 | | - spawn send_slow_request(int(port), slow_responses) |
98 | | - _ := <-app.slow_started or { |
99 | | - assert false, 'slow request did not start' |
100 | | - return |
101 | | - } |
| 88 | + slow_responses := chan http.Response{cap: 1} |
| 89 | + spawn send_slow_request(int(port), slow_responses) |
| 90 | + _ := <-app.slow_started or { |
| 91 | + assert false, 'slow request did not start' |
| 92 | + return |
| 93 | + } |
102 | 94 |
|
103 | | - shutdown_response := http.get('http://${graceful_shutdown_host}:${port}/shutdown') or { |
104 | | - assert false, err.msg() |
105 | | - return |
106 | | - } |
107 | | - assert shutdown_response.status() == .ok |
108 | | - assert shutdown_response.body == 'shutting down' |
| 95 | + shutdown_response := http.get('http://${graceful_shutdown_host}:${port}/shutdown') or { |
| 96 | + assert false, err.msg() |
| 97 | + return |
| 98 | + } |
| 99 | + assert shutdown_response.status() == .ok |
| 100 | + assert shutdown_response.body == 'shutting down' |
109 | 101 |
|
110 | | - slow_response := <-slow_responses or { |
111 | | - assert false, err.msg() |
112 | | - return |
113 | | - } |
114 | | - assert slow_response.status() == .ok |
115 | | - assert slow_response.body == 'slow done' |
| 102 | + slow_response := <-slow_responses or { |
| 103 | + assert false, err.msg() |
| 104 | + return |
| 105 | + } |
| 106 | + assert slow_response.status() == .ok |
| 107 | + assert slow_response.body == 'slow done' |
116 | 108 |
|
117 | | - server_thread.wait() |
| 109 | + server_thread.wait() |
118 | 110 |
|
119 | | - http.get('http://${graceful_shutdown_host}:${port}/') or { |
120 | | - assert true |
121 | | - return |
122 | | - } |
123 | | - assert false, 'server still accepts new requests after shutdown' |
| 111 | + http.get('http://${graceful_shutdown_host}:${port}/') or { |
| 112 | + assert true |
| 113 | + return |
124 | 114 | } |
| 115 | + assert false, 'server still accepts new requests after shutdown' |
125 | 116 | } |
0 commit comments