dobo 2.0.0 → 2.2.0

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 (197) hide show
  1. package/.github/FUNDING.yml +13 -0
  2. package/.github/workflows/repo-lockdown.yml +24 -0
  3. package/.jsdoc.conf.json +45 -0
  4. package/LICENSE +1 -1
  5. package/README.md +38 -19
  6. package/docs/Dobo.html +26 -0
  7. package/docs/data/search.json +1 -0
  8. package/docs/fonts/Inconsolata-Regular.ttf +0 -0
  9. package/docs/fonts/OpenSans-Regular.ttf +0 -0
  10. package/docs/fonts/WorkSans-Bold.ttf +0 -0
  11. package/docs/global.html +7 -0
  12. package/docs/index.html +3 -0
  13. package/docs/index.js.html +578 -0
  14. package/docs/lib_collect-connections.js.html +39 -0
  15. package/docs/lib_collect-drivers.js.html +52 -0
  16. package/docs/lib_collect-features.js.html +36 -0
  17. package/docs/lib_collect-schemas.js.html +94 -0
  18. package/docs/lib_index.js.html +6 -0
  19. package/docs/method_model_create.js.html +35 -0
  20. package/docs/method_model_drop.js.html +34 -0
  21. package/docs/method_model_exists.js.html +40 -0
  22. package/docs/method_record_count.js.html +69 -0
  23. package/docs/method_record_create.js.html +114 -0
  24. package/docs/method_record_find-all.js.html +44 -0
  25. package/docs/method_record_find-one.js.html +73 -0
  26. package/docs/method_record_find.js.html +118 -0
  27. package/docs/method_record_get.js.html +92 -0
  28. package/docs/method_record_remove.js.html +75 -0
  29. package/docs/method_record_update.js.html +107 -0
  30. package/docs/method_record_upsert.js.html +54 -0
  31. package/docs/method_sanitize_body.js.html +88 -0
  32. package/docs/method_sanitize_date.js.html +30 -0
  33. package/docs/method_sanitize_id.js.html +20 -0
  34. package/docs/method_validate.js.html +249 -0
  35. package/docs/module-Lib.html +3 -0
  36. package/docs/scripts/core.js +725 -0
  37. package/docs/scripts/core.min.js +23 -0
  38. package/docs/scripts/resize.js +90 -0
  39. package/docs/scripts/search.js +265 -0
  40. package/docs/scripts/search.min.js +6 -0
  41. package/docs/scripts/third-party/Apache-License-2.0.txt +202 -0
  42. package/docs/scripts/third-party/fuse.js +9 -0
  43. package/docs/scripts/third-party/hljs-line-num-original.js +366 -0
  44. package/docs/scripts/third-party/hljs-line-num.js +1 -0
  45. package/docs/scripts/third-party/hljs-original.js +5164 -0
  46. package/docs/scripts/third-party/hljs.js +1 -0
  47. package/docs/scripts/third-party/popper.js +5 -0
  48. package/docs/scripts/third-party/tippy.js +1 -0
  49. package/docs/scripts/third-party/tocbot.js +671 -0
  50. package/docs/scripts/third-party/tocbot.min.js +1 -0
  51. package/docs/static/bitcoin.jpeg +0 -0
  52. package/docs/static/home.md +25 -0
  53. package/docs/static/logo-ecosystem.png +0 -0
  54. package/docs/static/logo.png +0 -0
  55. package/docs/styles/clean-jsdoc-theme-base.css +1159 -0
  56. package/docs/styles/clean-jsdoc-theme-dark.css +412 -0
  57. package/docs/styles/clean-jsdoc-theme-light.css +482 -0
  58. package/docs/styles/clean-jsdoc-theme-scrollbar.css +30 -0
  59. package/docs/styles/clean-jsdoc-theme-without-scrollbar.min.css +1 -0
  60. package/docs/styles/clean-jsdoc-theme.min.css +1 -0
  61. package/extend/bajo/intl/en-US.json +69 -30
  62. package/extend/bajo/intl/id.json +58 -29
  63. package/extend/bajoCli/applet/clear-record.js +22 -0
  64. package/extend/bajoCli/applet/connection.js +5 -5
  65. package/extend/bajoCli/applet/count-record.js +27 -0
  66. package/extend/bajoCli/applet/create-aggregate.js +33 -0
  67. package/extend/bajoCli/applet/create-histogram.js +33 -0
  68. package/extend/bajoCli/applet/create-record.js +39 -0
  69. package/extend/bajoCli/applet/find-record.js +27 -0
  70. package/extend/bajoCli/applet/get-record.js +27 -0
  71. package/extend/bajoCli/applet/lib/post-process.js +25 -26
  72. package/extend/bajoCli/applet/model.js +22 -0
  73. package/extend/bajoCli/applet/rebuild-model.js +91 -0
  74. package/extend/bajoCli/applet/remove-record.js +27 -0
  75. package/extend/bajoCli/applet/update-record.js +44 -0
  76. package/extend/bajoCli/applet.js +0 -0
  77. package/extend/dobo/driver/memory.js +170 -0
  78. package/extend/dobo/feature/created-at.js +10 -8
  79. package/extend/dobo/feature/dt.js +0 -0
  80. package/extend/dobo/feature/immutable.js +30 -0
  81. package/extend/dobo/feature/int-id.js +0 -0
  82. package/extend/dobo/feature/removed-at.js +35 -57
  83. package/extend/dobo/feature/updated-at.js +14 -12
  84. package/extend/waibuMpa/route/attachment/@model/@id/@field/@file.js +5 -9
  85. package/extend/waibuStatic/virtual.json +0 -0
  86. package/index.js +420 -337
  87. package/lib/collect-connections.js +60 -21
  88. package/lib/collect-drivers.js +29 -35
  89. package/lib/collect-features.js +40 -0
  90. package/lib/collect-models.js +319 -0
  91. package/lib/factory/action.js +161 -0
  92. package/lib/factory/connection.js +62 -0
  93. package/lib/factory/driver.js +358 -0
  94. package/lib/factory/feature.js +33 -0
  95. package/lib/factory/model/_util.js +402 -0
  96. package/lib/factory/model/build.js +15 -0
  97. package/lib/factory/model/clear-record.js +17 -0
  98. package/lib/factory/model/count-record.js +17 -0
  99. package/lib/factory/model/create-aggregate.js +17 -0
  100. package/lib/factory/model/create-attachment.js +29 -0
  101. package/lib/factory/model/create-histogram.js +17 -0
  102. package/lib/factory/model/create-record.js +35 -0
  103. package/lib/factory/model/drop.js +15 -0
  104. package/lib/factory/model/exists.js +21 -0
  105. package/lib/factory/model/find-all-record.js +71 -0
  106. package/lib/factory/model/find-attachment.js +29 -0
  107. package/lib/factory/model/find-one-record.js +19 -0
  108. package/lib/factory/model/find-record.js +103 -0
  109. package/lib/factory/model/get-attachment.js +15 -0
  110. package/lib/factory/model/get-record.js +79 -0
  111. package/lib/factory/model/list-attachment.js +37 -0
  112. package/lib/{add-fixtures.js → factory/model/load-fixtures.js} +69 -67
  113. package/lib/factory/model/remove-attachment.js +15 -0
  114. package/lib/factory/model/remove-record.js +59 -0
  115. package/lib/factory/model/sanitize-body.js +62 -0
  116. package/lib/factory/model/sanitize-id.js +7 -0
  117. package/lib/factory/model/sanitize-record.js +26 -0
  118. package/lib/factory/model/update-attachment.js +9 -0
  119. package/lib/factory/model/update-record.js +81 -0
  120. package/lib/factory/model/upsert-record.js +95 -0
  121. package/lib/factory/model/validate.js +232 -0
  122. package/lib/factory/model.js +150 -0
  123. package/lib/index.js +3 -0
  124. package/package.json +45 -36
  125. package/wiki/APPLETS.md +57 -0
  126. package/wiki/CHANGES.md +46 -0
  127. package/wiki/CONFIG.md +25 -0
  128. package/wiki/CONTRIBUTING.md +5 -0
  129. package/wiki/DEV-GUIDE.md +1 -0
  130. package/wiki/ECOSYSTEM.md +20 -0
  131. package/wiki/GETTING-STARTED.md +166 -0
  132. package/{docs/query-language.md → wiki/QUERY-LANGUAGE.md} +0 -0
  133. package/wiki/USER-GUIDE.md +1 -0
  134. package/extend/bajoCli/applet/model-clear.js +0 -11
  135. package/extend/bajoCli/applet/model-rebuild.js +0 -101
  136. package/extend/bajoCli/applet/record-create.js +0 -41
  137. package/extend/bajoCli/applet/record-find.js +0 -27
  138. package/extend/bajoCli/applet/record-get.js +0 -24
  139. package/extend/bajoCli/applet/record-remove.js +0 -24
  140. package/extend/bajoCli/applet/record-update.js +0 -47
  141. package/extend/bajoCli/applet/schema.js +0 -22
  142. package/extend/bajoCli/applet/stat-count.js +0 -24
  143. package/lib/build-bulk-action.js +0 -12
  144. package/lib/check-unique.js +0 -39
  145. package/lib/collect-feature.js +0 -25
  146. package/lib/collect-schemas.js +0 -83
  147. package/lib/exec-feature-hook.js +0 -13
  148. package/lib/exec-validation.js +0 -21
  149. package/lib/generic-prop-sanitizer.js +0 -31
  150. package/lib/handle-attachment-upload.js +0 -16
  151. package/lib/mem-db/conn-sanitizer.js +0 -8
  152. package/lib/mem-db/instantiate.js +0 -41
  153. package/lib/mem-db/method/model/clear.js +0 -6
  154. package/lib/mem-db/method/model/create.js +0 -5
  155. package/lib/mem-db/method/model/drop.js +0 -5
  156. package/lib/mem-db/method/model/exists.js +0 -5
  157. package/lib/mem-db/method/record/create.js +0 -12
  158. package/lib/mem-db/method/record/find.js +0 -20
  159. package/lib/mem-db/method/record/get.js +0 -9
  160. package/lib/mem-db/method/record/remove.js +0 -13
  161. package/lib/mem-db/method/record/update.js +0 -15
  162. package/lib/mem-db/method/stat/count.js +0 -11
  163. package/lib/mem-db/start.js +0 -25
  164. package/lib/merge-attachment-info.js +0 -16
  165. package/lib/multi-rel-rows.js +0 -42
  166. package/lib/resolve-method.js +0 -16
  167. package/lib/sanitize-schema.js +0 -197
  168. package/lib/single-rel-rows.js +0 -38
  169. package/method/attachment/copy-uploaded.js +0 -34
  170. package/method/attachment/create.js +0 -29
  171. package/method/attachment/find.js +0 -27
  172. package/method/attachment/get-path.js +0 -12
  173. package/method/attachment/get.js +0 -12
  174. package/method/attachment/pre-check.js +0 -9
  175. package/method/attachment/remove.js +0 -11
  176. package/method/attachment/update.js +0 -7
  177. package/method/bulk/create.js +0 -46
  178. package/method/model/clear.js +0 -22
  179. package/method/model/create.js +0 -19
  180. package/method/model/drop.js +0 -19
  181. package/method/model/exists.js +0 -24
  182. package/method/record/clear.js +0 -24
  183. package/method/record/count.js +0 -44
  184. package/method/record/create.js +0 -71
  185. package/method/record/find-all.js +0 -25
  186. package/method/record/find-one.js +0 -56
  187. package/method/record/find.js +0 -52
  188. package/method/record/get.js +0 -47
  189. package/method/record/remove.js +0 -41
  190. package/method/record/update.js +0 -63
  191. package/method/record/upsert.js +0 -35
  192. package/method/sanitize/body.js +0 -70
  193. package/method/sanitize/date.js +0 -14
  194. package/method/sanitize/id.js +0 -7
  195. package/method/stat/aggregate.js +0 -23
  196. package/method/stat/histogram.js +0 -26
  197. package/method/validate.js +0 -157
@@ -0,0 +1,725 @@
1
+ /* global document */
2
+ const accordionLocalStorageKey = 'accordion-id'
3
+ const themeLocalStorageKey = 'theme'
4
+ const fontSizeLocalStorageKey = 'font-size'
5
+ const html = document.querySelector('html')
6
+
7
+ const MAX_FONT_SIZE = 30
8
+ const MIN_FONT_SIZE = 10
9
+
10
+ // eslint-disable-next-line no-undef
11
+ const localStorage = window.localStorage
12
+
13
+ function getTheme () {
14
+ let theme = localStorage.getItem(themeLocalStorageKey)
15
+
16
+ if (theme) return theme
17
+
18
+ theme = document.body.getAttribute('data-theme')
19
+
20
+ switch (theme) {
21
+ case 'dark':
22
+ case 'light':
23
+ return theme
24
+ case 'fallback-dark':
25
+ if (
26
+ // eslint-disable-next-line no-undef
27
+ window.matchMedia('(prefers-color-scheme)').matches &&
28
+ // eslint-disable-next-line no-undef
29
+ window.matchMedia('(prefers-color-scheme: light)').matches
30
+ ) {
31
+ return 'light'
32
+ }
33
+
34
+ return 'dark'
35
+
36
+ case 'fallback-light':
37
+ if (
38
+ // eslint-disable-next-line no-undef
39
+ window.matchMedia('(prefers-color-scheme)').matches &&
40
+ // eslint-disable-next-line no-undef
41
+ window.matchMedia('(prefers-color-scheme: dark)').matches
42
+ ) {
43
+ return 'dark'
44
+ }
45
+
46
+ return 'light'
47
+
48
+ default:
49
+ return 'dark'
50
+ }
51
+ }
52
+
53
+ function localUpdateTheme (theme) {
54
+ const body = document.body
55
+ const svgUse = document.querySelectorAll('.theme-svg-use')
56
+ const iconID = theme === 'dark' ? '#light-theme-icon' : '#dark-theme-icon'
57
+
58
+ body.setAttribute('data-theme', theme)
59
+ body.classList.remove('dark', 'light')
60
+ body.classList.add(theme)
61
+
62
+ svgUse.forEach(function (svg) {
63
+ svg.setAttribute('xlink:href', iconID)
64
+ })
65
+ }
66
+
67
+ function updateTheme (theme) {
68
+ localUpdateTheme(theme)
69
+ localStorage.setItem(themeLocalStorageKey, theme)
70
+ }
71
+
72
+ function toggleTheme () {
73
+ const body = document.body
74
+ const theme = body.getAttribute('data-theme')
75
+
76
+ const newTheme = theme === 'dark' ? 'light' : 'dark'
77
+
78
+ updateTheme(newTheme)
79
+ }
80
+
81
+ (function () {
82
+ const theme = getTheme()
83
+
84
+ updateTheme(theme)
85
+ })()
86
+
87
+ /**
88
+ * Function to set accordion id to localStorage.
89
+ * @param {string} id Accordion id
90
+ */
91
+ function setAccordionIdToLocalStorage (id) {
92
+ /**
93
+ * @type {object}
94
+ */
95
+ const ids = JSON.parse(localStorage.getItem(accordionLocalStorageKey))
96
+
97
+ ids[id] = id
98
+ localStorage.setItem(accordionLocalStorageKey, JSON.stringify(ids))
99
+ }
100
+
101
+ /**
102
+ * Function to remove accordion id from localStorage.
103
+ * @param {string} id Accordion id
104
+ */
105
+ function removeAccordionIdFromLocalStorage (id) {
106
+ /**
107
+ * @type {object}
108
+ */
109
+ const ids = JSON.parse(localStorage.getItem(accordionLocalStorageKey))
110
+
111
+ delete ids[id]
112
+ localStorage.setItem(accordionLocalStorageKey, JSON.stringify(ids))
113
+ }
114
+
115
+ /**
116
+ * Function to get all accordion ids from localStorage.
117
+ *
118
+ * @returns {object}
119
+ */
120
+ function getAccordionIdsFromLocalStorage () {
121
+ /**
122
+ * @type {object}
123
+ */
124
+ const ids = JSON.parse(localStorage.getItem(accordionLocalStorageKey))
125
+
126
+ return ids || {}
127
+ }
128
+
129
+ function toggleAccordion (element) {
130
+ const currentNode = element
131
+ const isCollapsed = currentNode.getAttribute('data-isopen') === 'false'
132
+
133
+ if (isCollapsed) {
134
+ currentNode.setAttribute('data-isopen', 'true')
135
+ setAccordionIdToLocalStorage(currentNode.id)
136
+ } else {
137
+ currentNode.setAttribute('data-isopen', 'false')
138
+ removeAccordionIdFromLocalStorage(currentNode.id)
139
+ }
140
+ }
141
+
142
+ function initAccordion () {
143
+ if (
144
+ localStorage.getItem(accordionLocalStorageKey) === undefined ||
145
+ localStorage.getItem(accordionLocalStorageKey) === null
146
+ ) {
147
+ localStorage.setItem(accordionLocalStorageKey, '{}')
148
+ }
149
+ const allAccordion = document.querySelectorAll('.sidebar-section-title')
150
+ const ids = getAccordionIdsFromLocalStorage()
151
+
152
+ allAccordion.forEach(function (item) {
153
+ item.addEventListener('click', function () {
154
+ toggleAccordion(item)
155
+ })
156
+ if (item.id in ids) {
157
+ toggleAccordion(item)
158
+ }
159
+ })
160
+ }
161
+
162
+ function isSourcePage () {
163
+ return Boolean(document.querySelector('#source-page'))
164
+ }
165
+
166
+ function bringElementIntoView (element, updateHistory = true) {
167
+ // If element is null then we are not going further
168
+ if (!element) {
169
+ return
170
+ }
171
+
172
+ /**
173
+ * tocbotInstance is defined in layout.tmpl
174
+ * It is defined when we are initializing tocbot.
175
+ *
176
+ */
177
+ // eslint-disable-next-line no-undef
178
+ if (tocbotInstance) {
179
+ setTimeout(
180
+ // eslint-disable-next-line no-undef
181
+ () => tocbotInstance.updateTocListActiveElement(element),
182
+ 60
183
+ )
184
+ }
185
+ const navbar = document.querySelector('.navbar-container')
186
+ const body = document.querySelector('.main-content')
187
+ const elementTop = element.getBoundingClientRect().top
188
+
189
+ let offset = 16
190
+
191
+ if (navbar) {
192
+ offset += navbar.scrollHeight
193
+ }
194
+
195
+ if (body) {
196
+ body.scrollBy(0, elementTop - offset)
197
+ }
198
+
199
+ if (updateHistory) {
200
+ // eslint-disable-next-line no-undef
201
+ history.pushState(null, null, '#' + element.id)
202
+ }
203
+ }
204
+
205
+ // eslint-disable-next-line no-unused-vars
206
+ function bringLinkToView (event) {
207
+ event.preventDefault()
208
+ event.stopPropagation()
209
+ const id = event.currentTarget.getAttribute('href')
210
+
211
+ if (!id) {
212
+ return
213
+ }
214
+
215
+ const element = document.getElementById(id.slice(1))
216
+
217
+ if (element) {
218
+ bringElementIntoView(element)
219
+ }
220
+ }
221
+
222
+ function bringIdToViewOnMount () {
223
+ if (isSourcePage()) {
224
+ return
225
+ }
226
+
227
+ // eslint-disable-next-line no-undef
228
+ let id = window.location.hash
229
+
230
+ if (id === '') {
231
+ return
232
+ }
233
+
234
+ let element = document.getElementById(id.slice(1))
235
+
236
+ if (!element) {
237
+ id = decodeURI(id)
238
+ element = document.getElementById(id.slice(1))
239
+ }
240
+
241
+ if (element) {
242
+ bringElementIntoView(element, false)
243
+ }
244
+ }
245
+
246
+ function createAnchorElement (id) {
247
+ const anchor = document.createElement('a')
248
+
249
+ anchor.textContent = '#'
250
+ anchor.href = '#' + id
251
+ anchor.classList.add('link-anchor')
252
+ anchor.onclick = bringLinkToView
253
+
254
+ return anchor
255
+ }
256
+
257
+ function addAnchor () {
258
+ const main = document.querySelector('.main-content').querySelector('section')
259
+
260
+ const h1 = main.querySelectorAll('h1')
261
+ const h2 = main.querySelectorAll('h2')
262
+ const h3 = main.querySelectorAll('h3')
263
+ const h4 = main.querySelectorAll('h4')
264
+
265
+ const targets = [h1, h2, h3, h4]
266
+
267
+ targets.forEach(function (target) {
268
+ target.forEach(function (heading) {
269
+ const anchor = createAnchorElement(heading.id)
270
+
271
+ heading.classList.add('has-anchor')
272
+ heading.append(anchor)
273
+ })
274
+ })
275
+ }
276
+
277
+ /**
278
+ *
279
+ * @param {string} value
280
+ */
281
+ function copy (value) {
282
+ const el = document.createElement('textarea')
283
+
284
+ el.value = value
285
+ document.body.appendChild(el)
286
+ el.select()
287
+ document.execCommand('copy')
288
+ document.body.removeChild(el)
289
+ }
290
+
291
+ function showTooltip (id) {
292
+ const tooltip = document.getElementById(id)
293
+
294
+ tooltip.classList.add('show-tooltip')
295
+ setTimeout(function () {
296
+ tooltip.classList.remove('show-tooltip')
297
+ }, 3000)
298
+ }
299
+
300
+ /* eslint-disable-next-line */
301
+ function copyFunction(id) {
302
+ // selecting the pre element
303
+ const code = document.getElementById(id)
304
+
305
+ // selecting the ol.linenums
306
+ let element = code.querySelector('.linenums')
307
+
308
+ if (!element) {
309
+ // selecting the code block
310
+ element = code.querySelector('code')
311
+ }
312
+
313
+ // copy
314
+ copy(element.innerText.trim().replace(/(^\t)/gm, ''))
315
+
316
+ // show tooltip
317
+ showTooltip('tooltip-' + id)
318
+ }
319
+
320
+ function hideTocOnSourcePage () {
321
+ if (isSourcePage()) {
322
+ document.querySelector('.toc-container').style.display = 'none'
323
+ }
324
+ }
325
+
326
+ function getPreTopBar (id, lang = '') {
327
+ // tooltip
328
+ const tooltip = '<div class="tooltip" id="tooltip-' + id + '">Copied!</div>'
329
+
330
+ // template of copy to clipboard icon container
331
+ const copyToClipboard =
332
+ '<button aria-label="copy code" class="icon-button copy-code" onclick="copyFunction(\'' +
333
+ id +
334
+ '\')"><svg class="sm-icon" alt="click to copy"><use xlink:href="#copy-icon"></use></svg>' +
335
+ tooltip +
336
+ '</button>'
337
+
338
+ const langNameDiv =
339
+ '<div class="code-lang-name-container"><div class="code-lang-name">' +
340
+ lang.toLocaleUpperCase() +
341
+ '</div></div>'
342
+
343
+ const topBar =
344
+ '<div class="pre-top-bar-container">' +
345
+ langNameDiv +
346
+ copyToClipboard +
347
+ '</div>'
348
+
349
+ return topBar
350
+ }
351
+
352
+ function getPreDiv () {
353
+ const divElement = document.createElement('div')
354
+
355
+ divElement.classList.add('pre-div')
356
+
357
+ return divElement
358
+ }
359
+
360
+ function processAllPre () {
361
+ const targets = document.querySelectorAll('pre')
362
+ const footer = document.querySelector('#PeOAagUepe')
363
+ const navbar = document.querySelector('#VuAckcnZhf')
364
+
365
+ let navbarHeight = 0
366
+ let footerHeight = 0
367
+
368
+ if (footer) {
369
+ footerHeight = footer.getBoundingClientRect().height
370
+ }
371
+
372
+ if (navbar) {
373
+ navbarHeight = navbar.getBoundingClientRect().height
374
+ }
375
+
376
+ // eslint-disable-next-line no-undef
377
+ const preMaxHeight = window.innerHeight - navbarHeight - footerHeight - 250
378
+
379
+ targets.forEach(function (pre, idx) {
380
+ const parent = pre.parentNode
381
+
382
+ if (parent && parent.getAttribute('data-skip-pre-process') === 'true') {
383
+ return
384
+ }
385
+
386
+ const div = getPreDiv()
387
+ const id = 'ScDloZOMdL' + idx
388
+
389
+ const lang = pre.getAttribute('data-lang') || 'code'
390
+ const topBar = getPreTopBar(id, lang)
391
+
392
+ div.innerHTML = topBar
393
+
394
+ pre.style.maxHeight = preMaxHeight + 'px'
395
+ pre.id = id
396
+ pre.classList.add('prettyprint')
397
+ pre.parentNode.insertBefore(div, pre)
398
+ div.appendChild(pre)
399
+ })
400
+ }
401
+
402
+ function highlightAndBringLineIntoView () {
403
+ // eslint-disable-next-line no-undef
404
+ const lineNumber = window.location.hash.replace('#line', '')
405
+
406
+ try {
407
+ const selector = '[data-line-number="' + lineNumber + '"'
408
+
409
+ const element = document.querySelector(selector)
410
+
411
+ element.scrollIntoView()
412
+ element.parentNode.classList.add('selected')
413
+ } catch (error) {
414
+ console.error(error)
415
+ }
416
+ }
417
+
418
+ function getFontSize () {
419
+ let currentFontSize = 16
420
+
421
+ try {
422
+ currentFontSize = Number.parseInt(
423
+ html.style.fontSize.split('px')[0],
424
+ 10
425
+ )
426
+ } catch (error) {
427
+ console.log(error)
428
+ }
429
+
430
+ return currentFontSize
431
+ }
432
+
433
+ function localUpdateFontSize (fontSize) {
434
+ html.style.fontSize = fontSize + 'px'
435
+
436
+ const fontSizeText = document.querySelector(
437
+ '#b77a68a492f343baabea06fad81f651e'
438
+ )
439
+
440
+ if (fontSizeText) {
441
+ fontSizeText.innerHTML = fontSize
442
+ }
443
+ }
444
+
445
+ function updateFontSize (fontSize) {
446
+ localUpdateFontSize(fontSize)
447
+ localStorage.setItem(fontSizeLocalStorageKey, fontSize)
448
+ }
449
+
450
+ (function () {
451
+ const fontSize = getFontSize()
452
+ const fontSizeInLocalStorage = localStorage.getItem(fontSizeLocalStorageKey)
453
+
454
+ if (fontSizeInLocalStorage) {
455
+ const n = Number.parseInt(fontSizeInLocalStorage, 10)
456
+
457
+ if (n === fontSize) {
458
+ return
459
+ }
460
+ updateFontSize(n)
461
+ } else {
462
+ updateFontSize(fontSize)
463
+ }
464
+ })()
465
+
466
+ // eslint-disable-next-line no-unused-vars
467
+ function incrementFont (event) {
468
+ const n = getFontSize()
469
+
470
+ if (n < MAX_FONT_SIZE) {
471
+ updateFontSize(n + 1)
472
+ }
473
+ }
474
+
475
+ // eslint-disable-next-line no-unused-vars
476
+ function decrementFont (event) {
477
+ const n = getFontSize()
478
+
479
+ if (n > MIN_FONT_SIZE) {
480
+ updateFontSize(n - 1)
481
+ }
482
+ }
483
+
484
+ function fontSizeTooltip () {
485
+ const fontSize = getFontSize()
486
+
487
+ return `
488
+ <div class="font-size-tooltip">
489
+ <button aria-label="decrease-font-size" class="icon-button ${
490
+ fontSize >= MAX_FONT_SIZE ? 'disabled' : ''
491
+ }" onclick="decrementFont(event)">
492
+ <svg>
493
+ <use xlink:href="#minus-icon"></use>
494
+ </svg>
495
+ </button>
496
+ <div class="font-size-text" id="b77a68a492f343baabea06fad81f651e">
497
+ ${fontSize}
498
+ </div>
499
+ <button aria-label="increase-font-size" class="icon-button ${
500
+ fontSize <= MIN_FONT_SIZE ? 'disabled' : ''
501
+ }" onclick="incrementFont(event)">
502
+ <svg>
503
+ <use xlink:href="#add-icon"></use>
504
+ </svg>
505
+ </button>
506
+ <button class="icon-button" onclick="updateFontSize(16)">
507
+ <svg>
508
+ <use xlink:href="#reset-icon"></use>
509
+ </svg>
510
+ </button>
511
+ </div>
512
+
513
+ `
514
+ }
515
+
516
+ function initTooltip () {
517
+ // add tooltip to navbar item
518
+ // eslint-disable-next-line no-undef
519
+ tippy('.theme-toggle', {
520
+ content: 'Toggle Theme',
521
+ delay: 500
522
+ })
523
+
524
+ // eslint-disable-next-line no-undef
525
+ tippy('.search-button', {
526
+ content: 'Search',
527
+ delay: 500
528
+ })
529
+
530
+ // eslint-disable-next-line no-undef
531
+ tippy('.font-size', {
532
+ content: 'Change font size',
533
+ delay: 500
534
+ })
535
+
536
+ // eslint-disable-next-line no-undef
537
+ tippy('.codepen-button', {
538
+ content: 'Open code in CodePen',
539
+ placement: 'left'
540
+ })
541
+
542
+ // eslint-disable-next-line no-undef
543
+ tippy('.copy-code', {
544
+ content: 'Copy this code',
545
+ placement: 'left'
546
+ })
547
+
548
+ // eslint-disable-next-line no-undef
549
+ tippy('.font-size', {
550
+ content: fontSizeTooltip(),
551
+ trigger: 'click',
552
+ interactive: true,
553
+ allowHTML: true,
554
+ placement: 'left'
555
+ })
556
+ }
557
+
558
+ function fixTable () {
559
+ const tables = document.querySelectorAll('table')
560
+
561
+ for (const table of tables) {
562
+ if (table.classList.contains('hljs-ln')) {
563
+ // don't want to wrap code blocks.
564
+ return
565
+ }
566
+
567
+ const div = document.createElement('div')
568
+
569
+ div.classList.add('table-div')
570
+ table.parentNode.insertBefore(div, table)
571
+ div.appendChild(table)
572
+ }
573
+ }
574
+
575
+ function hideMobileMenu () {
576
+ const mobileMenuContainer = document.querySelector('#mobile-sidebar')
577
+ const target = document.querySelector('#mobile-menu')
578
+ const svgUse = target.querySelector('use')
579
+
580
+ if (mobileMenuContainer) {
581
+ mobileMenuContainer.classList.remove('show')
582
+ }
583
+ if (target) {
584
+ target.setAttribute('data-isopen', 'false')
585
+ }
586
+ if (svgUse) {
587
+ svgUse.setAttribute('xlink:href', '#menu-icon')
588
+ }
589
+ }
590
+
591
+ function showMobileMenu () {
592
+ const mobileMenuContainer = document.querySelector('#mobile-sidebar')
593
+ const target = document.querySelector('#mobile-menu')
594
+ const svgUse = target.querySelector('use')
595
+
596
+ if (mobileMenuContainer) {
597
+ mobileMenuContainer.classList.add('show')
598
+ }
599
+ if (target) {
600
+ target.setAttribute('data-isopen', 'true')
601
+ }
602
+ if (svgUse) {
603
+ svgUse.setAttribute('xlink:href', '#close-icon')
604
+ }
605
+ }
606
+
607
+ function onMobileMenuClick () {
608
+ const target = document.querySelector('#mobile-menu')
609
+ const isOpen = target.getAttribute('data-isopen') === 'true'
610
+
611
+ if (isOpen) {
612
+ hideMobileMenu()
613
+ } else {
614
+ showMobileMenu()
615
+ }
616
+ }
617
+
618
+ function initMobileMenu () {
619
+ const menu = document.querySelector('#mobile-menu')
620
+
621
+ if (menu) {
622
+ menu.addEventListener('click', onMobileMenuClick)
623
+ }
624
+ }
625
+
626
+ function addHrefToSidebarTitle () {
627
+ const titles = document.querySelectorAll('.sidebar-title-anchor')
628
+
629
+ titles.forEach(function (title) {
630
+ // eslint-disable-next-line no-undef
631
+ title.setAttribute('href', baseURL)
632
+ })
633
+ }
634
+
635
+ function highlightActiveLinkInSidebar () {
636
+ const list = document.location.href.split('/')
637
+ const targetURL = decodeURI(list[list.length - 1])
638
+ let element = document.querySelector(`.sidebar a[href*='${targetURL}']`)
639
+
640
+ if (!element) {
641
+ try {
642
+ element = document.querySelector(
643
+ `.sidebar a[href*='${targetURL.split('#')[0]}']`
644
+ )
645
+ } catch (e) {
646
+ console.error(e)
647
+
648
+ return
649
+ }
650
+ }
651
+
652
+ if (!element) return
653
+
654
+ element.parentElement.classList.add('active')
655
+ element.scrollIntoView()
656
+ }
657
+
658
+ function onDomContentLoaded () {
659
+ const themeButton = document.querySelectorAll('.theme-toggle')
660
+
661
+ initMobileMenu()
662
+
663
+ if (themeButton) {
664
+ themeButton.forEach(function (button) {
665
+ button.addEventListener('click', toggleTheme)
666
+ })
667
+ }
668
+
669
+ // Highlighting code
670
+
671
+ // eslint-disable-next-line no-undef
672
+ hljs.addPlugin({
673
+ 'after:highlightElement': function (obj) {
674
+ // Replace 'code' with result.language when
675
+ // we are able to cross-check the correctness of
676
+ // result.
677
+ obj.el.parentNode.setAttribute('data-lang', 'code')
678
+ }
679
+ })
680
+ // eslint-disable-next-line no-undef
681
+ hljs.highlightAll()
682
+ // eslint-disable-next-line no-undef
683
+ hljs.initLineNumbersOnLoad({
684
+ singleLine: true
685
+ })
686
+
687
+ // Highlight complete
688
+
689
+ initAccordion()
690
+ addAnchor()
691
+ processAllPre()
692
+ hideTocOnSourcePage()
693
+ setTimeout(function () {
694
+ bringIdToViewOnMount()
695
+ if (isSourcePage()) {
696
+ highlightAndBringLineIntoView()
697
+ }
698
+ }, 1000)
699
+ initTooltip()
700
+ fixTable()
701
+ addHrefToSidebarTitle()
702
+ highlightActiveLinkInSidebar()
703
+ }
704
+
705
+ // eslint-disable-next-line no-undef
706
+ window.addEventListener('DOMContentLoaded', onDomContentLoaded)
707
+
708
+ // eslint-disable-next-line no-undef
709
+ window.addEventListener('hashchange', (event) => {
710
+ const url = new URL(event.newURL)
711
+
712
+ if (url.hash !== '') {
713
+ bringIdToViewOnMount(url.hash)
714
+ }
715
+ })
716
+
717
+ // eslint-disable-next-line no-undef
718
+ window.addEventListener('storage', (event) => {
719
+ if (event.newValue === 'undefined') return
720
+
721
+ initTooltip()
722
+
723
+ if (event.key === themeLocalStorageKey) localUpdateTheme(event.newValue)
724
+ if (event.key === fontSizeLocalStorageKey) { localUpdateFontSize(event.newValue) }
725
+ })