Software /
code /
prosody
Annotate
spec/util_async_spec.lua @ 8607:62bb06cf8a43
util.async: Add tests to specifically cover error handling
author | Matthew Wild <mwild1@gmail.com> |
---|---|
date | Fri, 16 Mar 2018 17:50:16 +0000 |
parent | 8605:3a1efc0532cb |
child | 8608:a2e6caf5848d |
rev | line source |
---|---|
8605 | 1 local async = require "util.async"; |
2 | |
3 describe("util.async", function() | |
4 local debug = false; | |
5 local print = print; | |
6 if debug then | |
7 require "util.logger".add_simple_sink(print); | |
8 else | |
9 print = function () end | |
10 end | |
11 local function new(func, name) | |
12 local log = {}; | |
13 return async.runner(func, setmetatable({}, { | |
14 __index = function (_, event) | |
15 return function (runner, err) | |
16 print(name, "event", event, err) | |
17 print "--" | |
18 table.insert(log, { event = event, err = err }); | |
19 end; | |
20 end; | |
21 })), log; | |
22 end | |
23 describe("#runner", function() | |
24 it("should work", function() | |
25 local r, l = new(function (item) assert(type(item) == "number") end); | |
26 r:run(1); | |
27 r:run(2); | |
28 end); | |
8607
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
29 |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
30 it("should be ready after creation", function () |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
31 local r = async.runner(function (item) end); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
32 assert.equal(r.state, "ready"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
33 end); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
34 |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
35 describe("#errors", function () |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
36 local last_processed_item, last_error; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
37 local r; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
38 r = async.runner(function (item) |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
39 if item == "error" then |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
40 error({ e = "test error" }); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
41 end |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
42 last_processed_item = item; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
43 end, { |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
44 error = function (runner, err) |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
45 assert.equal(r, runner); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
46 last_error = err; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
47 end; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
48 }); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
49 |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
50 randomize(false); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
51 |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
52 it("should notify", function () |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
53 local last_processed_item, last_error; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
54 local r; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
55 r = async.runner(function (item) |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
56 if item == "error" then |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
57 error({ e = "test error" }); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
58 end |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
59 last_processed_item = item; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
60 end, { |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
61 error = function (runner, err) |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
62 assert.equal(r, runner); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
63 last_error = err; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
64 end; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
65 }); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
66 |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
67 r:run("hello"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
68 assert.equal(r.state, "ready"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
69 assert.equal(last_processed_item, "hello"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
70 |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
71 assert.equal(last_error, nil); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
72 r:run("error"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
73 assert.is_table(last_error); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
74 assert.equal(last_error.e, "test error"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
75 last_error = nil; |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
76 assert.equal(r.state, "ready"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
77 assert.equal(last_processed_item, "hello"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
78 end); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
79 it("should not be fatal to the runner", function () |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
80 r:run("world"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
81 assert.equal(r.state, "ready"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
82 assert.equal(last_processed_item, "world"); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
83 end); |
62bb06cf8a43
util.async: Add tests to specifically cover error handling
Matthew Wild <mwild1@gmail.com>
parents:
8605
diff
changeset
|
84 end); |
8605 | 85 end); |
86 describe("#waiter", function() | |
87 it("should work", function () | |
88 local wait, done; | |
89 | |
90 local r, l = new(function (item) | |
91 assert(type(item) == "number") | |
92 if item == 3 then | |
93 wait, done = async.waiter(); | |
94 wait(); | |
95 end | |
96 end); | |
97 | |
98 r:run(1); | |
99 assert(r.state == "ready"); | |
100 r:run(2); | |
101 assert(r.state == "ready"); | |
102 r:run(3); | |
103 assert(r.state == "waiting"); | |
104 done(); | |
105 assert(r.state == "ready"); | |
106 --for k, v in ipairs(l) do print(k,v) end | |
107 end); | |
108 | |
109 it("should work", function () | |
110 -------------------- | |
111 local wait, done; | |
112 local last_item = 0; | |
113 local r, l = new(function (item) | |
114 assert(type(item) == "number") | |
115 assert(item == last_item + 1); | |
116 last_item = item; | |
117 if item == 3 then | |
118 wait, done = async.waiter(); | |
119 wait(); | |
120 end | |
121 end); | |
122 | |
123 r:run(1); | |
124 assert(r.state == "ready"); | |
125 r:run(2); | |
126 assert(r.state == "ready"); | |
127 r:run(3); | |
128 assert(r.state == "waiting"); | |
129 r:run(4); | |
130 assert(r.state == "waiting"); | |
131 done(); | |
132 assert(r.state == "ready"); | |
133 --for k, v in ipairs(l) do print(k,v) end | |
134 end); | |
135 it("should work", function () | |
136 -------------------- | |
137 local wait, done; | |
138 local last_item = 0; | |
139 local r, l = new(function (item) | |
140 assert(type(item) == "number") | |
141 assert((item == last_item + 1) or item == 3); | |
142 last_item = item; | |
143 if item == 3 then | |
144 wait, done = async.waiter(); | |
145 wait(); | |
146 end | |
147 end); | |
148 | |
149 r:run(1); | |
150 assert(r.state == "ready"); | |
151 r:run(2); | |
152 assert(r.state == "ready"); | |
153 | |
154 local dones = {}; | |
155 r:run(3); | |
156 assert(r.state == "waiting"); | |
157 r:run(3); | |
158 assert(r.state == "waiting"); | |
159 r:run(3); | |
160 assert(r.state == "waiting"); | |
161 r:run(4); | |
162 assert(r.state == "waiting"); | |
163 | |
164 for i = 1, 3 do | |
165 done(); | |
166 if i < 3 then | |
167 assert(r.state == "waiting"); | |
168 end | |
169 end | |
170 | |
171 assert(r.state == "ready"); | |
172 --for k, v in ipairs(l) do print(k,v) end | |
173 end); | |
174 it("should work", function () | |
175 -------------------- | |
176 local wait, done; | |
177 local last_item = 0; | |
178 local r, l = new(function (item) | |
179 assert(type(item) == "number") | |
180 assert((item == last_item + 1) or item == 3); | |
181 last_item = item; | |
182 if item == 3 then | |
183 wait, done = async.waiter(); | |
184 wait(); | |
185 end | |
186 end); | |
187 | |
188 r:run(1); | |
189 assert(r.state == "ready"); | |
190 r:run(2); | |
191 assert(r.state == "ready"); | |
192 | |
193 local dones = {}; | |
194 r:run(3); | |
195 assert(r.state == "waiting"); | |
196 r:run(3); | |
197 assert(r.state == "waiting"); | |
198 | |
199 for i = 1, 2 do | |
200 done(); | |
201 if i < 2 then | |
202 assert(r.state == "waiting"); | |
203 end | |
204 end | |
205 | |
206 assert(r.state == "ready"); | |
207 r:run(4); | |
208 assert(r.state == "ready"); | |
209 | |
210 assert(r.state == "ready"); | |
211 --for k, v in ipairs(l) do print(k,v) end | |
212 end); | |
213 it("should work with multiple runners in parallel", function () | |
214 -- Now with multiple runners | |
215 -------------------- | |
216 local wait1, done1; | |
217 local last_item1 = 0; | |
218 local r1, l1 = new(function (item) | |
219 assert(type(item) == "number") | |
220 assert((item == last_item1 + 1) or item == 3); | |
221 last_item1 = item; | |
222 if item == 3 then | |
223 wait1, done1 = async.waiter(); | |
224 wait1(); | |
225 end | |
226 end, "r1"); | |
227 | |
228 local wait2, done2; | |
229 local last_item2 = 0; | |
230 local r2, l2 = new(function (item) | |
231 assert(type(item) == "number") | |
232 assert((item == last_item2 + 1) or item == 3); | |
233 last_item2 = item; | |
234 if item == 3 then | |
235 wait2, done2 = async.waiter(); | |
236 wait2(); | |
237 end | |
238 end, "r2"); | |
239 | |
240 r1:run(1); | |
241 assert(r1.state == "ready"); | |
242 r1:run(2); | |
243 assert(r1.state == "ready"); | |
244 | |
245 local dones = {}; | |
246 r1:run(3); | |
247 assert(r1.state == "waiting"); | |
248 r1:run(3); | |
249 assert(r1.state == "waiting"); | |
250 | |
251 r2:run(1); | |
252 assert(r1.state == "waiting"); | |
253 assert(r2.state == "ready"); | |
254 | |
255 r2:run(2); | |
256 assert(r1.state == "waiting"); | |
257 assert(r2.state == "ready"); | |
258 | |
259 r2:run(3); | |
260 assert(r1.state == "waiting"); | |
261 assert(r2.state == "waiting"); | |
262 done2(); | |
263 | |
264 r2:run(3); | |
265 assert(r1.state == "waiting"); | |
266 assert(r2.state == "waiting"); | |
267 done2(); | |
268 | |
269 r2:run(4); | |
270 assert(r1.state == "waiting"); | |
271 assert(r2.state == "ready"); | |
272 | |
273 for i = 1, 2 do | |
274 done1(); | |
275 if i < 2 then | |
276 assert(r1.state == "waiting"); | |
277 end | |
278 end | |
279 | |
280 assert(r1.state == "ready"); | |
281 r1:run(4); | |
282 assert(r1.state == "ready"); | |
283 | |
284 assert(r1.state == "ready"); | |
285 --for k, v in ipairs(l1) do print(k,v) end | |
286 end); | |
287 it("should work work with multiple runners in parallel", function () | |
288 -------------------- | |
289 local wait1, done1; | |
290 local last_item1 = 0; | |
291 local r1, l1 = new(function (item) | |
292 print("r1 processing ", item); | |
293 assert(type(item) == "number") | |
294 assert((item == last_item1 + 1) or item == 3); | |
295 last_item1 = item; | |
296 if item == 3 then | |
297 wait1, done1 = async.waiter(); | |
298 wait1(); | |
299 end | |
300 end, "r1"); | |
301 | |
302 local wait2, done2; | |
303 local last_item2 = 0; | |
304 local r2, l2 = new(function (item) | |
305 print("r2 processing ", item); | |
306 assert.is_number(item); | |
307 assert((item == last_item2 + 1) or item == 3); | |
308 last_item2 = item; | |
309 if item == 3 then | |
310 wait2, done2 = async.waiter(); | |
311 wait2(); | |
312 end | |
313 end, "r2"); | |
314 | |
315 r1:run(1); | |
316 assert.equal(r1.state, "ready"); | |
317 r1:run(2); | |
318 assert.equal(r1.state, "ready"); | |
319 | |
320 r1:run(5); | |
321 assert.equal(r1.state, "ready"); | |
322 | |
323 local dones = {}; | |
324 r1:run(3); | |
325 assert.equal(r1.state, "waiting"); | |
326 r1:run(5); -- Will error, when we get to it | |
327 assert.equal(r1.state, "waiting"); | |
328 done1(); | |
329 assert.equal(r1.state, "ready"); | |
330 r1:run(3); | |
331 assert.equal(r1.state, "waiting"); | |
332 | |
333 r2:run(1); | |
334 assert.equal(r1.state, "waiting"); | |
335 assert.equal(r2.state, "ready"); | |
336 | |
337 r2:run(2); | |
338 assert.equal(r1.state, "waiting"); | |
339 assert.equal(r2.state, "ready"); | |
340 | |
341 r2:run(3); | |
342 assert.equal(r1.state, "waiting"); | |
343 assert.equal(r2.state, "waiting"); | |
344 | |
345 done2(); | |
346 assert.equal(r1.state, "waiting"); | |
347 assert.equal(r2.state, "ready"); | |
348 | |
349 r2:run(3); | |
350 assert.equal(r1.state, "waiting"); | |
351 assert.equal(r2.state, "waiting"); | |
352 | |
353 done2(); | |
354 assert.equal(r1.state, "waiting"); | |
355 assert.equal(r2.state, "ready"); | |
356 | |
357 r2:run(4); | |
358 assert.equal(r1.state, "waiting"); | |
359 assert.equal(r2.state, "ready"); | |
360 | |
361 done1(); | |
362 | |
363 assert.equal(r1.state, "ready"); | |
364 r1:run(4); | |
365 assert.equal(r1.state, "ready"); | |
366 | |
367 assert.equal(r1.state, "ready"); | |
368 --for k, v in ipairs(l1) do print(k,v) end | |
369 end); | |
370 end); | |
371 end); |