@nationalarchives/frontend 0.1.24-prerelease → 0.1.25-prerelease

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (97) hide show
  1. package/README.md +22 -0
  2. package/govuk-prototype-kit.config.json +4 -12
  3. package/nationalarchives/all.css +2 -2
  4. package/nationalarchives/all.css.map +1 -1
  5. package/nationalarchives/all.js +1 -1
  6. package/nationalarchives/all.js.map +1 -1
  7. package/nationalarchives/components/breadcrumbs/breadcrumbs.css +1 -1
  8. package/nationalarchives/components/breadcrumbs/breadcrumbs.css.map +1 -1
  9. package/nationalarchives/components/breadcrumbs/breadcrumbs.stories.js +1 -1
  10. package/nationalarchives/components/button/button.css +1 -1
  11. package/nationalarchives/components/button/button.css.map +1 -1
  12. package/nationalarchives/components/button/button.scss +8 -8
  13. package/nationalarchives/components/button/template.njk +2 -2
  14. package/nationalarchives/components/card/card.css +1 -1
  15. package/nationalarchives/components/card/card.css.map +1 -1
  16. package/nationalarchives/components/card/card.scss +6 -2
  17. package/nationalarchives/components/card/card.stories.js +6 -78
  18. package/nationalarchives/components/card/fixtures.json +17 -17
  19. package/nationalarchives/components/card/macro-options.json +41 -17
  20. package/nationalarchives/components/card/template.njk +46 -45
  21. package/nationalarchives/components/cookie-banner/cookie-banner.css +1 -1
  22. package/nationalarchives/components/cookie-banner/cookie-banner.css.map +1 -1
  23. package/nationalarchives/components/cookie-banner/cookie-banner.js +1 -1
  24. package/nationalarchives/components/cookie-banner/cookie-banner.js.map +1 -1
  25. package/nationalarchives/components/cookie-banner/cookie-banner.mjs +17 -16
  26. package/nationalarchives/components/cookie-banner/cookie-banner.stories.js +92 -42
  27. package/nationalarchives/components/cookie-banner/fixtures.json +35 -8
  28. package/nationalarchives/components/cookie-banner/macro-options.json +7 -1
  29. package/nationalarchives/components/cookie-banner/template.njk +1 -1
  30. package/nationalarchives/components/featured-records/featured-records.css +1 -1
  31. package/nationalarchives/components/featured-records/featured-records.css.map +1 -1
  32. package/nationalarchives/components/filters/filters.css +1 -1
  33. package/nationalarchives/components/filters/filters.css.map +1 -1
  34. package/nationalarchives/components/filters/filters.scss +6 -6
  35. package/nationalarchives/components/filters/template.njk +1 -1
  36. package/nationalarchives/components/footer/footer.css +1 -1
  37. package/nationalarchives/components/footer/footer.css.map +1 -1
  38. package/nationalarchives/components/footer/footer.stories.js +1 -1
  39. package/nationalarchives/components/footer/template.njk +3 -3
  40. package/nationalarchives/components/gallery/gallery.css +1 -1
  41. package/nationalarchives/components/gallery/gallery.css.map +1 -1
  42. package/nationalarchives/components/gallery/gallery.stories.js +2 -2
  43. package/nationalarchives/components/grid/grid.css +1 -1
  44. package/nationalarchives/components/grid/grid.css.map +1 -1
  45. package/nationalarchives/components/grid/grid.scss +12 -0
  46. package/nationalarchives/components/grid/grid.stories.js +12 -0
  47. package/nationalarchives/components/header/header.css +1 -1
  48. package/nationalarchives/components/header/header.css.map +1 -1
  49. package/nationalarchives/components/header/header.scss +13 -19
  50. package/nationalarchives/components/header/template.njk +2 -2
  51. package/nationalarchives/components/hero/hero.css +1 -1
  52. package/nationalarchives/components/hero/hero.css.map +1 -1
  53. package/nationalarchives/components/hero/hero.scss +2 -2
  54. package/nationalarchives/components/hero/hero.stories.js +6 -0
  55. package/nationalarchives/components/index-grid/index-grid.css +1 -1
  56. package/nationalarchives/components/index-grid/index-grid.css.map +1 -1
  57. package/nationalarchives/components/index-grid/index-grid.stories.js +3 -1
  58. package/nationalarchives/components/message/message.css +1 -1
  59. package/nationalarchives/components/message/message.css.map +1 -1
  60. package/nationalarchives/components/pagination/macro-options.json +6 -0
  61. package/nationalarchives/components/pagination/pagination.css +1 -1
  62. package/nationalarchives/components/pagination/pagination.css.map +1 -1
  63. package/nationalarchives/components/pagination/pagination.scss +4 -0
  64. package/nationalarchives/components/pagination/pagination.stories.js +63 -2
  65. package/nationalarchives/components/pagination/template.njk +9 -2
  66. package/nationalarchives/components/phase-banner/phase-banner.css +1 -1
  67. package/nationalarchives/components/phase-banner/phase-banner.css.map +1 -1
  68. package/nationalarchives/components/picture/picture.css +1 -1
  69. package/nationalarchives/components/picture/picture.css.map +1 -1
  70. package/nationalarchives/components/sensitive-image/sensitive-image.css +1 -1
  71. package/nationalarchives/components/sensitive-image/sensitive-image.css.map +1 -1
  72. package/nationalarchives/components/sensitive-image/sensitive-image.stories.js +3 -0
  73. package/nationalarchives/components/skip-link/skip-link.css +1 -1
  74. package/nationalarchives/components/skip-link/skip-link.css.map +1 -1
  75. package/nationalarchives/components/skip-link/skip-link.stories.js +4 -1
  76. package/nationalarchives/components/tabs/tabs.css +1 -1
  77. package/nationalarchives/components/tabs/tabs.css.map +1 -1
  78. package/nationalarchives/components/tabs/tabs.stories.js +6 -3
  79. package/nationalarchives/lib/cookies.mjs +165 -62
  80. package/nationalarchives/prototype-kit.css +2 -2
  81. package/nationalarchives/prototype-kit.css.map +1 -1
  82. package/nationalarchives/prototype-kit.scss +3 -3
  83. package/nationalarchives/stories/utilities/colour-schemes/colour-schemes.stories.js +153 -65
  84. package/nationalarchives/stories/utilities/overrides/overrides.stories.js +1 -0
  85. package/nationalarchives/stories/utilities/tables/tables.mdx +8 -0
  86. package/nationalarchives/stories/utilities/tables/tables.stories.js +45 -0
  87. package/nationalarchives/stories/utilities/typography/heading-groups.stories.js +59 -19
  88. package/nationalarchives/templates/layouts/_prototype-kit.njk +2 -0
  89. package/nationalarchives/tests/cookies.test.js +427 -0
  90. package/nationalarchives/tests/uuid.test.js +17 -0
  91. package/nationalarchives/tools/_colour.scss +2 -0
  92. package/nationalarchives/utilities/_index.scss +1 -0
  93. package/nationalarchives/utilities/_lists.scss +5 -0
  94. package/nationalarchives/utilities/_tables.scss +86 -0
  95. package/nationalarchives/utilities/_typography.scss +5 -20
  96. package/nationalarchives/variables/_colour.scss +1 -0
  97. package/package.json +6 -6
@@ -0,0 +1,427 @@
1
+ import {
2
+ jest,
3
+ describe,
4
+ expect,
5
+ test,
6
+ beforeEach,
7
+ afterEach,
8
+ } from "@jest/globals";
9
+ import { TextEncoder, TextDecoder, store, options } from "util";
10
+ import Cookies from "../lib/cookies.mjs";
11
+
12
+ global.TextEncoder = TextEncoder;
13
+ global.TextDecoder = TextDecoder;
14
+ global.store = store;
15
+ global.options = options;
16
+
17
+ const addCookiesToDocument = (document) => {
18
+ let _cookies = {};
19
+ document.__defineGetter__("cookie", () => {
20
+ return Object.keys(_cookies)
21
+ .map((key) => `${key}=${_cookies[key]}`)
22
+ .join("; ");
23
+ });
24
+ document.__defineSetter__("cookie", (s) => {
25
+ const keyValue = s.trim().split("=");
26
+ const key = keyValue[0].trim();
27
+ const values = keyValue[1].trim().split(";");
28
+ const value = values[0];
29
+ _cookies[key] = value;
30
+ return `${key}=${value}`;
31
+ });
32
+ document.clearAllCookies = () => {
33
+ _cookies = {};
34
+ };
35
+ };
36
+
37
+ addCookiesToDocument(document);
38
+
39
+ describe("No existing cookies", () => {
40
+ afterEach(() => {
41
+ document.clearAllCookies();
42
+ });
43
+
44
+ test("Initialisation", async () => {
45
+ expect(document.cookie).toEqual("");
46
+
47
+ const cookies = new Cookies();
48
+ expect(cookies).toHaveProperty("all");
49
+ expect(cookies).toBeInstanceOf(Cookies);
50
+
51
+ expect(document.cookie).not.toEqual("");
52
+ });
53
+
54
+ test("Getting/setting", async () => {
55
+ const cookies = new Cookies();
56
+ expect(cookies).toHaveProperty("get");
57
+ expect(cookies).toHaveProperty("set");
58
+ expect(cookies).toHaveProperty("exists");
59
+ expect(cookies).toHaveProperty("hasValue");
60
+
61
+ expect(Object.keys(cookies.all)).toHaveLength(1);
62
+
63
+ const testKey = "foo";
64
+ const testValue = "bar";
65
+
66
+ expect(cookies.all).not.toHaveProperty(testKey);
67
+ expect(cookies.exists(testKey)).toEqual(false);
68
+
69
+ cookies.set(testKey, testValue);
70
+
71
+ expect(Object.keys(cookies.all)).toHaveLength(2);
72
+
73
+ expect(cookies.all).toHaveProperty(testKey);
74
+ expect(cookies.all[testKey]).toEqual(testValue);
75
+ expect(cookies.exists(testKey)).toEqual(true);
76
+ expect(cookies.get(testKey)).toEqual(testValue);
77
+ expect(cookies.hasValue(testKey, testValue)).toEqual(true);
78
+ expect(cookies.hasValue(testKey, "different")).toEqual(false);
79
+ });
80
+
81
+ test("Deletion", async () => {
82
+ const cookies = new Cookies();
83
+ expect(cookies).toHaveProperty("delete");
84
+
85
+ const testKey = "foo";
86
+ const testValue = "bar";
87
+
88
+ cookies.set(testKey, testValue);
89
+
90
+ expect(cookies.all).toHaveProperty(testKey);
91
+ expect(cookies.all[testKey]).toEqual(testValue);
92
+ expect(cookies.exists(testKey)).toEqual(true);
93
+ expect(cookies.get(testKey)).toEqual(testValue);
94
+
95
+ cookies.delete(testKey);
96
+
97
+ // expect(cookies.all).not.toHaveProperty(testKey);
98
+ // expect(cookies.exists(testKey)).toEqual(false);
99
+ expect(cookies.get(testKey)).toEqual("");
100
+ });
101
+
102
+ test("Deletion of all", async () => {
103
+ const cookies = new Cookies();
104
+
105
+ const testKeys = ["foo", "bar"];
106
+ const testValue = "testValue";
107
+
108
+ testKeys.forEach((testKey) => cookies.set(testKey, testValue));
109
+
110
+ testKeys.forEach((testKey) => {
111
+ expect(cookies.get(testKey)).toEqual(testValue);
112
+ });
113
+
114
+ cookies.deleteAll();
115
+
116
+ testKeys.forEach((testKey) => {
117
+ expect(cookies.get(testKey)).toEqual("");
118
+ });
119
+ });
120
+
121
+ test("Initial policies", async () => {
122
+ const cookies = new Cookies();
123
+ expect(cookies).toHaveProperty("policies");
124
+
125
+ expect(cookies.policies).toHaveProperty("essential");
126
+ expect(cookies.policies.essential).toEqual(true);
127
+ expect(JSON.parse(cookies.get("cookies_policy"))).toHaveProperty(
128
+ "essential",
129
+ );
130
+ expect(cookies.policies).toHaveProperty("settings");
131
+ expect(cookies.policies.settings).toEqual(false);
132
+ expect(JSON.parse(cookies.get("cookies_policy"))).toHaveProperty(
133
+ "settings",
134
+ );
135
+ expect(cookies.policies).toHaveProperty("usage");
136
+ expect(cookies.policies.usage).toEqual(false);
137
+ expect(JSON.parse(cookies.get("cookies_policy"))).toHaveProperty("usage");
138
+ });
139
+
140
+ test("Accept policy", async () => {
141
+ const cookies = new Cookies();
142
+ expect(cookies).toHaveProperty("isPolicyAccepted");
143
+
144
+ expect(cookies.policies).toHaveProperty("essential");
145
+ expect(cookies.policies.essential).toEqual(true);
146
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
147
+ expect(cookies.policies).toHaveProperty("settings");
148
+ expect(cookies.policies.settings).toEqual(false);
149
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
150
+ expect(cookies.policies).toHaveProperty("usage");
151
+ expect(cookies.policies.usage).toEqual(false);
152
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
153
+
154
+ cookies.acceptPolicy("settings");
155
+ expect(cookies.policies.essential).toEqual(true);
156
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
157
+ expect(cookies.policies.settings).toEqual(true);
158
+ expect(cookies.isPolicyAccepted("settings")).toEqual(true);
159
+ expect(cookies.policies.usage).toEqual(false);
160
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
161
+
162
+ cookies.acceptPolicy("usage");
163
+ expect(cookies.policies.essential).toEqual(true);
164
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
165
+ expect(cookies.policies.settings).toEqual(true);
166
+ expect(cookies.isPolicyAccepted("settings")).toEqual(true);
167
+ expect(cookies.policies.usage).toEqual(true);
168
+ expect(cookies.isPolicyAccepted("usage")).toEqual(true);
169
+ });
170
+
171
+ test("Accept all policies", async () => {
172
+ const cookies = new Cookies();
173
+ expect(cookies).toHaveProperty("acceptAllPolicies");
174
+
175
+ expect(cookies.policies).toHaveProperty("essential");
176
+ expect(cookies.policies.essential).toEqual(true);
177
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
178
+ expect(cookies.policies).toHaveProperty("settings");
179
+ expect(cookies.policies.settings).toEqual(false);
180
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
181
+ expect(cookies.policies).toHaveProperty("usage");
182
+ expect(cookies.policies.usage).toEqual(false);
183
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
184
+
185
+ cookies.acceptAllPolicies();
186
+ expect(cookies.policies.essential).toEqual(true);
187
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
188
+ expect(cookies.policies.settings).toEqual(true);
189
+ expect(cookies.isPolicyAccepted("settings")).toEqual(true);
190
+ expect(cookies.policies.usage).toEqual(true);
191
+ expect(cookies.isPolicyAccepted("usage")).toEqual(true);
192
+ });
193
+
194
+ test("Reject policy", async () => {
195
+ const cookies = new Cookies();
196
+
197
+ cookies.acceptPolicy("settings");
198
+ cookies.acceptPolicy("usage");
199
+ expect(cookies.policies.essential).toEqual(true);
200
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
201
+ expect(cookies.policies.settings).toEqual(true);
202
+ expect(cookies.isPolicyAccepted("settings")).toEqual(true);
203
+ expect(cookies.policies.usage).toEqual(true);
204
+ expect(cookies.isPolicyAccepted("usage")).toEqual(true);
205
+
206
+ cookies.rejectPolicy("settings");
207
+ expect(cookies.policies.essential).toEqual(true);
208
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
209
+ expect(cookies.policies.settings).toEqual(false);
210
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
211
+ expect(cookies.policies.usage).toEqual(true);
212
+ expect(cookies.isPolicyAccepted("usage")).toEqual(true);
213
+
214
+ cookies.rejectPolicy("usage");
215
+ expect(cookies.policies.essential).toEqual(true);
216
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
217
+ expect(cookies.policies.settings).toEqual(false);
218
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
219
+ expect(cookies.policies.usage).toEqual(false);
220
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
221
+ });
222
+
223
+ test("Reject all policies", async () => {
224
+ const cookies = new Cookies();
225
+ expect(cookies).toHaveProperty("rejectAllPolicies");
226
+
227
+ cookies.acceptAllPolicies();
228
+ expect(cookies.policies.essential).toEqual(true);
229
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
230
+ expect(cookies.policies.settings).toEqual(true);
231
+ expect(cookies.isPolicyAccepted("settings")).toEqual(true);
232
+ expect(cookies.policies.usage).toEqual(true);
233
+ expect(cookies.isPolicyAccepted("usage")).toEqual(true);
234
+
235
+ cookies.rejectAllPolicies();
236
+ expect(cookies.policies.essential).toEqual(true);
237
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
238
+ expect(cookies.policies.settings).toEqual(false);
239
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
240
+ expect(cookies.policies.usage).toEqual(false);
241
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
242
+ });
243
+
244
+ test("Protected essential policy", async () => {
245
+ const cookies = new Cookies();
246
+
247
+ expect(cookies.policies).toHaveProperty("essential");
248
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
249
+
250
+ cookies.acceptPolicy("essential");
251
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
252
+
253
+ cookies.rejectPolicy("essential");
254
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
255
+
256
+ cookies.rejectAllPolicies();
257
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
258
+ });
259
+
260
+ test("Basic events", async () => {
261
+ const cookies = new Cookies();
262
+ expect(cookies).toHaveProperty("on");
263
+
264
+ const mockCallback = jest.fn();
265
+ cookies.on("setCookie", mockCallback);
266
+ const testKey = "foo";
267
+ const testValue = "bar";
268
+
269
+ cookies.set(testKey, testValue);
270
+
271
+ expect(mockCallback.mock.calls).toHaveLength(1);
272
+ expect(mockCallback.mock.calls[0][0]).toStrictEqual({
273
+ key: testKey,
274
+ value: testValue,
275
+ domain: "",
276
+ path: "/",
277
+ sameSite: "Lax",
278
+ secure: true,
279
+ maxAge: 31536000,
280
+ cookie: `${testKey}=${testValue}; samesite=Lax; path=/; max-age=31536000; secure`,
281
+ });
282
+
283
+ cookies.set(testKey, testValue);
284
+
285
+ expect(mockCallback.mock.calls).toHaveLength(2);
286
+ expect(mockCallback.mock.calls[1][0]).toStrictEqual({
287
+ key: testKey,
288
+ value: testValue,
289
+ domain: "",
290
+ path: "/",
291
+ sameSite: "Lax",
292
+ secure: true,
293
+ maxAge: 31536000,
294
+ cookie: `${testKey}=${testValue}; samesite=Lax; path=/; max-age=31536000; secure`,
295
+ });
296
+ });
297
+
298
+ test("All events", async () => {
299
+ const cookies = new Cookies();
300
+
301
+ const mockSetCookieCallback = jest.fn();
302
+ cookies.on("setCookie", mockSetCookieCallback);
303
+ const mockDeleteCookieCallback = jest.fn();
304
+ cookies.on("deleteCookie", mockDeleteCookieCallback);
305
+ const mockDeleteAllCookiesCallback = jest.fn();
306
+ cookies.on("deleteAllCookies", mockDeleteAllCookiesCallback);
307
+ const mockAcceptPolicyCallback = jest.fn();
308
+ cookies.on("acceptPolicy", mockAcceptPolicyCallback);
309
+ const mockRejectPolicyCallback = jest.fn();
310
+ cookies.on("rejectPolicy", mockRejectPolicyCallback);
311
+ const mockAcceptAllPoliciesCallback = jest.fn();
312
+ cookies.on("acceptAllPolicies", mockAcceptAllPoliciesCallback);
313
+ const mockRejectAllPoliciesCallback = jest.fn();
314
+ cookies.on("rejectAllPolicies", mockRejectAllPoliciesCallback);
315
+ const mockChangePolicyCallback = jest.fn();
316
+ cookies.on("changePolicy", mockChangePolicyCallback);
317
+
318
+ const testKey = "foo";
319
+ const testValue = "bar";
320
+ cookies.set(testKey, testValue);
321
+ cookies.delete(testKey);
322
+ cookies.acceptPolicy("settings");
323
+ cookies.rejectPolicy("settings");
324
+ cookies.setPolicy("settings", true);
325
+ cookies.acceptAllPolicies();
326
+ cookies.rejectAllPolicies();
327
+ cookies.deleteAll();
328
+
329
+ expect(mockSetCookieCallback.mock.calls).toHaveLength(9);
330
+ expect(mockDeleteCookieCallback.mock.calls).toHaveLength(3);
331
+ expect(mockDeleteAllCookiesCallback.mock.calls).toHaveLength(1);
332
+ expect(mockAcceptPolicyCallback.mock.calls).toHaveLength(1);
333
+ expect(mockRejectPolicyCallback.mock.calls).toHaveLength(1);
334
+ expect(mockAcceptAllPoliciesCallback.mock.calls).toHaveLength(1);
335
+ expect(mockRejectAllPoliciesCallback.mock.calls).toHaveLength(1);
336
+ expect(mockChangePolicyCallback.mock.calls).toHaveLength(7);
337
+ });
338
+
339
+ test("Shared events", async () => {
340
+ const mockCallback = jest.fn();
341
+
342
+ const cookies1 = new Cookies();
343
+
344
+ const cookies2 = new Cookies();
345
+ cookies2.on("setCookie", mockCallback);
346
+
347
+ const testKey = "foo";
348
+ const testValue = "bar";
349
+
350
+ cookies1.set(testKey, testValue);
351
+ expect(mockCallback.mock.calls).toHaveLength(1);
352
+
353
+ cookies1.set(testKey, testValue);
354
+ expect(mockCallback.mock.calls).toHaveLength(2);
355
+
356
+ cookies2.set(testKey, testValue);
357
+ expect(mockCallback.mock.calls).toHaveLength(3);
358
+ });
359
+ });
360
+
361
+ describe("Existing cookies", () => {
362
+ beforeEach(() => {
363
+ document.clearAllCookies();
364
+ document.cookie =
365
+ "cookies_policy=%7B%22usage%22%3Afalse%2C%22settings%22%3Atrue%2C%22essential%22%3Atrue%7D";
366
+ });
367
+
368
+ test("Initialisation", async () => {
369
+ const cookies = new Cookies();
370
+
371
+ expect(cookies.all).toHaveProperty("cookies_policy");
372
+ expect(cookies.policies).toHaveProperty("essential");
373
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
374
+ expect(cookies.policies).toHaveProperty("settings");
375
+ expect(cookies.isPolicyAccepted("settings")).toEqual(true);
376
+ expect(cookies.policies).toHaveProperty("usage");
377
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
378
+ });
379
+
380
+ test("Update policies", async () => {
381
+ const cookies = new Cookies();
382
+ cookies.acceptPolicy("usage");
383
+ cookies.rejectPolicy("settings");
384
+
385
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
386
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
387
+ expect(cookies.isPolicyAccepted("usage")).toEqual(true);
388
+ });
389
+ });
390
+
391
+ describe("Existing empty cookie policies", () => {
392
+ beforeEach(() => {
393
+ document.clearAllCookies();
394
+ document.cookie = "cookies_policy=%7B%7D";
395
+ });
396
+
397
+ test("Initialisation", async () => {
398
+ const cookies = new Cookies();
399
+
400
+ expect(cookies.all).toHaveProperty("cookies_policy");
401
+ expect(cookies.policies).toHaveProperty("essential");
402
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
403
+ expect(cookies.policies).toHaveProperty("settings");
404
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
405
+ expect(cookies.policies).toHaveProperty("usage");
406
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
407
+ });
408
+ });
409
+
410
+ describe("Existing malformed cookie policies", () => {
411
+ beforeEach(() => {
412
+ document.clearAllCookies();
413
+ document.cookie = "cookies_policy=foobar";
414
+ });
415
+
416
+ test("Initialisation", async () => {
417
+ const cookies = new Cookies();
418
+
419
+ expect(cookies.all).toHaveProperty("cookies_policy");
420
+ expect(cookies.policies).toHaveProperty("essential");
421
+ expect(cookies.isPolicyAccepted("essential")).toEqual(true);
422
+ expect(cookies.policies).toHaveProperty("settings");
423
+ expect(cookies.isPolicyAccepted("settings")).toEqual(false);
424
+ expect(cookies.policies).toHaveProperty("usage");
425
+ expect(cookies.isPolicyAccepted("usage")).toEqual(false);
426
+ });
427
+ });
@@ -0,0 +1,17 @@
1
+ import { describe, expect, test } from "@jest/globals";
2
+ import { TextEncoder, TextDecoder, store, options } from "util";
3
+ import uuidv4 from "../lib/uuid.mjs";
4
+
5
+ global.TextEncoder = TextEncoder;
6
+ global.TextDecoder = TextDecoder;
7
+ global.store = store;
8
+ global.options = options;
9
+
10
+ describe("UUID", () => {
11
+ test("Initialisation", async () => {
12
+ const uuid1 = uuidv4();
13
+ const uuid2 = uuidv4();
14
+
15
+ expect(uuid1).not.toEqual(uuid2);
16
+ });
17
+ });
@@ -269,6 +269,7 @@
269
269
 
270
270
  %tint {
271
271
  @include colour-background("background-tint");
272
+ @include colour-font("font-base");
272
273
  }
273
274
 
274
275
  @mixin tint {
@@ -307,6 +308,7 @@
307
308
  )};
308
309
 
309
310
  @include colour-background("background");
311
+ @include colour-font("font-base");
310
312
  }
311
313
 
312
314
  @mixin accent-light {
@@ -5,4 +5,5 @@
5
5
  @use "global";
6
6
  @use "lists";
7
7
  @use "overrides";
8
+ @use "tables";
8
9
  @use "typography";
@@ -22,6 +22,11 @@
22
22
 
23
23
  list-style: none;
24
24
  }
25
+
26
+ .tna-ul,
27
+ .tna-ol {
28
+ margin-top: 0;
29
+ }
25
30
  }
26
31
 
27
32
  .tna-dl {
@@ -0,0 +1,86 @@
1
+ @use "sass:math";
2
+ @use "sass:selector";
3
+ @use "../tools/colour";
4
+ @use "../tools/media";
5
+ @use "../tools/spacing";
6
+ @use "../tools/typography";
7
+ @use "../variables/assets";
8
+ @use "../variables/grid";
9
+
10
+ .tna-table {
11
+ width: 100%;
12
+ @include spacing.space-above;
13
+
14
+ border-collapse: collapse;
15
+
16
+ text-align: left;
17
+
18
+ &:first-child {
19
+ margin-top: 0;
20
+ }
21
+
22
+ &__caption {
23
+ text-align: left;
24
+
25
+ @include typography.main-font-weight-bold;
26
+ }
27
+
28
+ &__head {
29
+ }
30
+
31
+ &__header {
32
+ }
33
+
34
+ &__body {
35
+ }
36
+
37
+ &__row {
38
+ }
39
+
40
+ &__cell {
41
+ }
42
+
43
+ &__header,
44
+ &__cell {
45
+ padding: 0.25rem 1rem;
46
+
47
+ @include colour.colour-border("keyline", 1px, solid, bottom);
48
+
49
+ &:first-child {
50
+ padding-left: 0;
51
+ }
52
+
53
+ &:last-child {
54
+ padding-right: 0;
55
+ }
56
+ }
57
+
58
+ &__head &__header {
59
+ @include colour.colour-border("keyline-dark", 0.25rem, solid, bottom);
60
+ }
61
+
62
+ p {
63
+ + p {
64
+ margin-top: 0.25rem;
65
+ }
66
+ }
67
+ }
68
+
69
+ .tna-table-wrapper {
70
+ width: 100%;
71
+ @include spacing.space-above;
72
+ padding-left: grid.$gutter-width;
73
+ padding-right: grid.$gutter-width;
74
+
75
+ position: relative;
76
+ left: -#{grid.$gutter-width};
77
+
78
+ overflow: auto;
79
+
80
+ @include media.on-tiny {
81
+ padding-left: grid.$gutter-width-tiny;
82
+ padding-right: grid.$gutter-width-tiny;
83
+
84
+ left: -#{grid.$gutter-width-tiny};
85
+ }
86
+ }
@@ -67,15 +67,9 @@
67
67
  }
68
68
  }
69
69
 
70
- h1,
71
- h2,
72
- h3,
73
- h4,
74
- h5,
75
- h6,
76
- ul,
77
- ol {
78
- margin-top: 0;
70
+ * {
71
+ margin: 0;
72
+ padding: 0;
79
73
  }
80
74
 
81
75
  strong {
@@ -83,15 +77,11 @@ strong {
83
77
  }
84
78
 
85
79
  p {
86
- margin: 2rem 0 0;
80
+ @include spacing.space-above;
87
81
 
88
82
  + p {
89
83
  margin-top: 1rem;
90
84
  }
91
-
92
- &:first-child {
93
- margin-top: 0;
94
- }
95
85
  }
96
86
 
97
87
  a {
@@ -333,17 +323,12 @@ small {
333
323
  %headings-and-heading-groups {
334
324
  @include spacing.space-above;
335
325
  margin-bottom: 0;
336
- padding-top: 1rem;
326
+ padding: 1rem 0 0;
337
327
 
338
328
  &:first-child {
339
329
  padding-top: 0;
340
330
  }
341
331
 
342
- &:last-child {
343
- margin-bottom: 0;
344
- padding-bottom: 0;
345
- }
346
-
347
332
  + p {
348
333
  margin-top: 1rem;
349
334
  }
@@ -108,6 +108,7 @@ $colour-palette-dark: map.merge(
108
108
  "icon-light": brand-colour("white", 0.35),
109
109
  "link": brand-colour("blue"),
110
110
  "link-visited": #a8f,
111
+ "focus-outline": brand-colour("orange"),
111
112
  "keyline": brand-colour("white", 0.25),
112
113
  "keyline-dark": brand-colour("white"),
113
114
  "button-text": brand-colour("black"),
package/package.json CHANGED
@@ -1,13 +1,13 @@
1
1
  {
2
2
  "name": "@nationalarchives/frontend",
3
- "version": "0.1.24-prerelease",
3
+ "version": "0.1.25-prerelease",
4
4
  "description": "The National Archives frontend styles",
5
5
  "scripts": {
6
6
  "start": "storybook dev -p 6006",
7
7
  "build": "storybook build -o storybook --webpack-stats-json",
8
- "test": "node tasks/test-fixtures.js && test-storybook --verbose --stories-json",
9
- "lint": "prettier --check '{src,.storybook,tasks}/**/*.{js,mjs,scss,json,html}' && stylelint 'src/**/*.scss' && eslint 'src/**/*.mjs'",
10
- "lint:fix": "prettier --write '{src,.storybook,tasks}/**/*.{js,mjs,scss,json,html}' && stylelint --fix 'src/**/*.scss' && eslint --fix 'src/**/*.mjs'",
8
+ "test": "node tasks/test-fixtures.js && test-storybook --verbose && jest",
9
+ "lint": "prettier --check '{src,.storybook,tasks,.}/**/*.{js,mjs,scss,json,html}' && stylelint 'src/**/*.scss' && eslint 'src/**/*.{js,mjs}'",
10
+ "lint:fix": "prettier --write '{src,.storybook,tasks,.}/**/*.{js,mjs,scss,json,html}' && stylelint --fix 'src/**/*.scss' && eslint --fix 'src/**/*.{js,mjs}'",
11
11
  "package:sass": "sass --style=compressed --embed-sources src/nationalarchives:package/nationalarchives",
12
12
  "package:scripts": "webpack"
13
13
  },
@@ -55,6 +55,7 @@
55
55
  "@storybook/test-runner": "^0.13.0",
56
56
  "@storybook/testing-library": "^0.2.2",
57
57
  "axe-playwright": "^1.2.3",
58
+ "babel-jest": "^29.7.0",
58
59
  "babel-loader": "^9.0.1",
59
60
  "chromatic": "^7.5.0",
60
61
  "copy-webpack-plugin": "^11.0.0",
@@ -63,8 +64,7 @@
63
64
  "eslint": "^8.52.0",
64
65
  "eslint-plugin-storybook": "^0.6.15",
65
66
  "glob": "^10.3.10",
66
- "jest-image-snapshot": "^6.2.0",
67
- "jsdom": "^22.1.0",
67
+ "jest-environment-jsdom": "^29.7.0",
68
68
  "mdx-mermaid": "^2.0.0",
69
69
  "node-self": "^1.0.2",
70
70
  "nunjucks": "^3.2.3",