]> git.r.bdr.sh - rbdr/forum/blob - src/stores/forums.test.js
732964fe530b6d1ae948c9fc381f4f3f0cdb2abb
[rbdr/forum] / src / stores / forums.test.js
1 import { GraphQLInteraction, Pact, Matchers } from '@pact-foundation/pact';
2 import { resolve } from 'path';
3
4 import { resolveAfter } from '$/utils/resolve_after';
5
6 const { eachLike, like } = Matchers;
7
8 jest.mock('$/config/config.js');
9
10 import { getForum, getForums } from './forums';
11
12 const internals = {
13 provider: null
14 };
15
16 describe('Forums store pact', () => {
17
18 beforeAll(async () => {
19
20 internals.provider = new Pact({
21 port: 1234,
22 dir: resolve(process.cwd(), 'pacts'),
23 consumer: 'ForumClient',
24 provider: 'ForumServer',
25 pactfileWriteMode: 'update'
26 });
27
28 await internals.provider.setup();
29 });
30
31 afterEach(() => internals.provider.verify());
32 afterAll(() => internals.provider.finalize());
33
34 describe('When there\'s data', () => {
35
36 describe('GetForums', () => {
37
38 beforeAll(async () => {
39
40 const forumQuery = new GraphQLInteraction()
41 .given('there\'s data')
42 .uponReceiving('a request to list the forums')
43 .withRequest({
44 path: '/graphql',
45 method: 'POST'
46 })
47 .withOperation('GetForums')
48 .withQuery(
49 `query GetForums {
50 forums {
51 id
52 glyph
53 label
54 position
55 __typename
56 }
57 }`
58 )
59 .withVariables({})
60 .willRespondWith({
61 status: 200,
62 headers: {
63 'Content-Type': 'application/json; charset=utf-8'
64 },
65 body: {
66 data: {
67 forums: eachLike({
68 id: like('butter'),
69 glyph: like('⌘'),
70 label: like('test_forums.butter'),
71 position: like(1)
72 })
73 }
74 }
75 });
76 return await internals.provider.addInteraction(forumQuery);
77 });
78
79 test('it returns the forums', async () => {
80
81 const forums = getForums();
82 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
83 let response = null;
84 forums.subscribe((forumsValue) => {
85
86 response = forumsValue;
87 counter();
88 });
89 expect(response.data).toBeInstanceOf(Array);
90 expect(response.data.length).toBe(0);
91 expect(response.loading).toBe(true);
92 expect(response.error).toBe(undefined);
93 await resolveAfterTwo;
94 expect(response.data).toEqual(expect.arrayContaining([{
95 id: 'butter',
96 glyph: '⌘',
97 label: 'test_forums.butter',
98 position: 1
99 }]));
100 expect(response.loading).toBe(false);
101 expect(response.error).toBe(undefined);
102 });
103 });
104
105 describe('GetForum', () => {
106
107 beforeAll(async () => {
108
109 const forumQuery = new GraphQLInteraction()
110 .given('there\'s data')
111 .uponReceiving('a request to get a single forum')
112 .withRequest({
113 path: '/graphql',
114 method: 'POST'
115 })
116 .withOperation('GetForum')
117 .withQuery(
118 `query GetForum($id: ID!) {
119 forum(id: $id) {
120 id
121 glyph
122 label
123 position
124 topics {
125 id
126 title
127 updated_at
128 ttl
129 __typename
130 }
131 __typename
132 }
133 }`
134 )
135 .withVariables({
136 id: 'freezer'
137 })
138 .willRespondWith({
139 status: 200,
140 headers: {
141 'Content-Type': 'application/json; charset=utf-8'
142 },
143 body: {
144 data: {
145 forum: like({
146 id: 'freezer',
147 glyph: like('✭'),
148 label: like('test_forums.freezer'),
149 position: like(3),
150 topics: eachLike({
151 id: like('629de02c-151a-4db7-bb86-43b2add8a15a'),
152 title: like('Very pacty topic'),
153 updated_at: like(1619954611616),
154 ttl: like(3601)
155 })
156 })
157 }
158 }
159 });
160 return await internals.provider.addInteraction(forumQuery);
161 });
162
163 test('it returns the forum', async () => {
164
165 const forum = getForum('freezer');
166 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
167 let response = null;
168 forum.subscribe((forumsValue) => {
169
170 response = forumsValue;
171 counter();
172 });
173 expect(response.data).toBe(null);
174 expect(response.loading).toBe(true);
175 expect(response.error).toBe(undefined);
176 await resolveAfterTwo;
177 expect(response.data.id).toBe('freezer');
178 expect(response.data.glyph).toBe('✭');
179 expect(response.data.label).toBe('test_forums.freezer');
180 expect(response.data.position).toBe(3);
181 expect(response.data.topics).toEqual(expect.arrayContaining([{
182 id: '629de02c-151a-4db7-bb86-43b2add8a15a',
183 title: 'Very pacty topic',
184 updated_at: 1619954611616,
185 ttl: 3601
186 }]));
187 expect(response.loading).toBe(false);
188 expect(response.error).toBe(undefined);
189 });
190 });
191 });
192
193 describe('When there\'s no data', () => {
194
195 describe('GetForums', () => {
196
197 beforeAll(async () => {
198
199 const forumQuery = new GraphQLInteraction()
200 .given('there\'s no data')
201 .uponReceiving('a request to list the forums')
202 .withRequest({
203 path: '/graphql',
204 method: 'POST'
205 })
206 .withOperation('GetForums')
207 .withQuery(
208 `query GetForums {
209 forums {
210 id
211 glyph
212 label
213 position
214 __typename
215 }
216 }`
217 )
218 .withVariables({})
219 .willRespondWith({
220 status: 200,
221 headers: {
222 'Content-Type': 'application/json; charset=utf-8'
223 },
224 body: {
225 data: {
226 forums: []
227 }
228 }
229 });
230 return await internals.provider.addInteraction(forumQuery);
231 });
232
233 test('it returns the forums', async () => {
234
235 const forums = getForums();
236 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
237 let response = null;
238 forums.subscribe((forumsValue) => {
239
240 response = forumsValue;
241 counter();
242 });
243 expect(response.data).toBeInstanceOf(Array);
244 expect(response.data.length).toBe(0);
245 expect(response.loading).toBe(true);
246 expect(response.error).toBe(undefined);
247 await resolveAfterTwo;
248 expect(response.data).toBeInstanceOf(Array);
249 expect(response.data.length).toBe(0);
250 expect(response.loading).toBe(false);
251 expect(response.error).toBe(undefined);
252 });
253 });
254
255 describe('GetForum', () => {
256
257 beforeAll(async () => {
258
259 const forumQuery = new GraphQLInteraction()
260 .given('there\'s no data')
261 .uponReceiving('a request to get a single forum')
262 .withRequest({
263 path: '/graphql',
264 method: 'POST'
265 })
266 .withOperation('GetForum')
267 .withQuery(
268 `query GetForum($id: ID!) {
269 forum(id: $id) {
270 id
271 glyph
272 label
273 position
274 topics {
275 id
276 title
277 updated_at
278 ttl
279 __typename
280 }
281 __typename
282 }
283 }`
284 )
285 .withVariables({
286 id: 'freezer'
287 })
288 .willRespondWith({
289 status: 200,
290 headers: {
291 'Content-Type': 'application/json; charset=utf-8'
292 },
293 body: {
294 data: {
295 forum: null
296 }
297 }
298 });
299 return await internals.provider.addInteraction(forumQuery);
300 });
301
302 test('it returns the forum', async () => {
303
304 const forum = getForum('freezer');
305 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
306 let response = null;
307 forum.subscribe((forumsValue) => {
308
309 response = forumsValue;
310 counter();
311 });
312 expect(response.data).toBe(null);
313 expect(response.loading).toBe(true);
314 expect(response.error).toBe(undefined);
315 await resolveAfterTwo;
316 expect(response.data).toBe(null);
317 expect(response.loading).toBe(false);
318 expect(response.error).toBe(undefined);
319 });
320 });
321 });
322
323 describe('When there\'s a server error', () => {
324
325 describe('GetForums', () => {
326
327 beforeAll(async () => {
328
329 const forumQuery = new GraphQLInteraction()
330 .given('there\'s a server error')
331 .uponReceiving('a request to list the forums')
332 .withRequest({
333 path: '/graphql',
334 method: 'POST'
335 })
336 .withOperation('GetForums')
337 .withQuery(
338 `query GetForums {
339 forums {
340 id
341 glyph
342 label
343 position
344 __typename
345 }
346 }`
347 )
348 .withVariables({})
349 .willRespondWith({
350 status: 500
351 });
352 return await internals.provider.addInteraction(forumQuery);
353 });
354
355 test('it returns the error', async () => {
356
357 const forums = getForums();
358 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
359 let response = null;
360 forums.subscribe((forumsValue) => {
361
362 response = forumsValue;
363 counter();
364 });
365 expect(response.data).toBeInstanceOf(Array);
366 expect(response.data.length).toBe(0);
367 expect(response.loading).toBe(true);
368 expect(response.error).toBe(undefined);
369 await resolveAfterTwo;
370 expect(response.data).toBeInstanceOf(Array);
371 expect(response.data.length).toBe(0);
372 expect(response.loading).toBe(false);
373 expect(response.error).toBeInstanceOf(Error);
374 });
375 });
376
377 describe('GetForum', () => {
378
379 beforeAll(async () => {
380
381 const forumQuery = new GraphQLInteraction()
382 .given('there\'s a server error')
383 .uponReceiving('a request to get a single forum')
384 .withRequest({
385 path: '/graphql',
386 method: 'POST'
387 })
388 .withOperation('GetForum')
389 .withQuery(
390 `query GetForum($id: ID!) {
391 forum(id: $id) {
392 id
393 glyph
394 label
395 position
396 topics {
397 id
398 title
399 updated_at
400 ttl
401 __typename
402 }
403 __typename
404 }
405 }`
406 )
407 .withVariables({
408 id: 'freezer'
409 })
410 .willRespondWith({
411 status: 500
412 });
413 return await internals.provider.addInteraction(forumQuery);
414 });
415
416 test('it returns the error', async () => {
417
418 const forum = getForum('freezer');
419 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
420 let response = null;
421 forum.subscribe((forumsValue) => {
422
423 response = forumsValue;
424 counter();
425 });
426 expect(response.data).toBe(null);
427 expect(response.loading).toBe(true);
428 expect(response.error).toBe(undefined);
429 await resolveAfterTwo;
430 expect(response.data).toBe(null);
431 expect(response.loading).toBe(false);
432 expect(response.error).toBeInstanceOf(Error);
433 });
434 });
435 });
436
437 describe('When there\'s an error in the response', () => {
438
439 describe('GetForums', () => {
440
441 beforeAll(async () => {
442
443 const forumQuery = new GraphQLInteraction()
444 .given('there\'s an error in the response')
445 .uponReceiving('a request to list the forums')
446 .withRequest({
447 path: '/graphql',
448 method: 'POST'
449 })
450 .withOperation('GetForums')
451 .withQuery(
452 `query GetForums {
453 forums {
454 id
455 glyph
456 label
457 position
458 __typename
459 }
460 }`
461 )
462 .withVariables({})
463 .willRespondWith({
464 status: 200,
465 headers: {
466 'Content-Type': 'application/json; charset=utf-8'
467 },
468 body: {
469 errors: eachLike({
470 message: like('An error occurred when fetching forums')
471 })
472 }
473 });
474 return await internals.provider.addInteraction(forumQuery);
475 });
476
477 test('it returns the error', async () => {
478
479 const forums = getForums();
480 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
481 let response = null;
482 forums.subscribe((forumsValue) => {
483
484 response = forumsValue;
485 counter();
486 });
487 expect(response.data).toBeInstanceOf(Array);
488 expect(response.data.length).toBe(0);
489 expect(response.loading).toBe(true);
490 expect(response.error).toBe(undefined);
491 await resolveAfterTwo;
492 expect(response.data).toBeInstanceOf(Array);
493 expect(response.data.length).toBe(0);
494 expect(response.loading).toBe(false);
495 expect(response.error.graphQLErrors).toEqual(expect.arrayContaining([{
496 message: 'An error occurred when fetching forums'
497 }]));
498 });
499 });
500
501 describe('GetForum', () => {
502
503 beforeAll(async () => {
504
505 const forumQuery = new GraphQLInteraction()
506 .given('there\'s an error in the response')
507 .uponReceiving('a request to get a single forum')
508 .withRequest({
509 path: '/graphql',
510 method: 'POST'
511 })
512 .withOperation('GetForum')
513 .withQuery(
514 `query GetForum($id: ID!) {
515 forum(id: $id) {
516 id
517 glyph
518 label
519 position
520 topics {
521 id
522 title
523 updated_at
524 ttl
525 __typename
526 }
527 __typename
528 }
529 }`
530 )
531 .withVariables({
532 id: 'freezer'
533 })
534 .willRespondWith({
535 status: 200,
536 headers: {
537 'Content-Type': 'application/json; charset=utf-8'
538 },
539 body: {
540 errors: eachLike({
541 message: like('An error occurred when fetching the forum')
542 })
543 }
544 });
545 return await internals.provider.addInteraction(forumQuery);
546 });
547
548 test('it returns the error', async () => {
549
550 const forum = getForum('freezer');
551 const { counter, promise: resolveAfterTwo } = resolveAfter(2);
552 let response = null;
553 forum.subscribe((forumsValue) => {
554
555 response = forumsValue;
556 counter();
557 });
558 expect(response.data).toBe(null);
559 expect(response.loading).toBe(true);
560 expect(response.error).toBe(undefined);
561 await resolveAfterTwo;
562 expect(response.data).toBe(null);
563 expect(response.loading).toBe(false);
564 expect(response.error.graphQLErrors).toEqual(expect.arrayContaining([{
565 message: 'An error occurred when fetching the forum'
566 }]));
567 });
568 });
569 });
570 });