@skillswaveca/nova-shared-libraries 1.12.2

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 (782) hide show
  1. package/.eslintignore +1 -0
  2. package/.eslintrc.yaml +28 -0
  3. package/.github/dependabot.yml +18 -0
  4. package/.github/workflows/pull-request.yml +25 -0
  5. package/.github/workflows/release.yml +72 -0
  6. package/README.md +69 -0
  7. package/docs/accelerator-7PKwHj6p.js +7 -0
  8. package/docs/accelerator-CTGFUnJj.js +7 -0
  9. package/docs/access-special-BRCQ6BOA.js +7 -0
  10. package/docs/accessibility-check-DDEnCM3T.js +7 -0
  11. package/docs/add-CC95oWZj.js +7 -0
  12. package/docs/add-Dok7V7iV.js +7 -0
  13. package/docs/add-file-CDcwFmxE.js +9 -0
  14. package/docs/add-file-DSIehH-a.js +8 -0
  15. package/docs/add-message-C2J88NtD.js +8 -0
  16. package/docs/add-message-C74U_c_a.js +8 -0
  17. package/docs/add-to-lor-Cx3ALzs6.js +10 -0
  18. package/docs/add-to-lor-mWdPFUuq.js +10 -0
  19. package/docs/add-user-7oZmllZp.js +8 -0
  20. package/docs/add-user-Ct61dWhf.js +8 -0
  21. package/docs/ai-CXRsBcvO.js +7 -0
  22. package/docs/ai-D1Iq7PBt.js +9 -0
  23. package/docs/ai-DvFNdjTJ.js +7 -0
  24. package/docs/alarmbell-BptBR2Jr.js +7 -0
  25. package/docs/alarmbell-CB5dhFiR.js +7 -0
  26. package/docs/alert-DlHwdVP6.js +7 -0
  27. package/docs/alert-V7mrtHbK.js +9 -0
  28. package/docs/alert-p0Ge30rc.js +8 -0
  29. package/docs/align-center--wiBdBfZ.js +7 -0
  30. package/docs/align-full-BfwFgwgv.js +7 -0
  31. package/docs/align-left-DaZbAxVg.js +7 -0
  32. package/docs/align-right-DJm8Hnyk.js +7 -0
  33. package/docs/angry-CLkqqzeH.js +7 -0
  34. package/docs/arrow-collapse-CKVijIdk.js +7 -0
  35. package/docs/arrow-collapse-DgaM5Q7K.js +7 -0
  36. package/docs/arrow-collapse-small-BfTzkoWL.js +7 -0
  37. package/docs/arrow-expand-Bk1J3lIZ.js +7 -0
  38. package/docs/arrow-expand-small-B7KVZXkf.js +7 -0
  39. package/docs/arrow-thin-down-ClfvHk99.js +7 -0
  40. package/docs/arrow-thin-left-D0lmhbm9.js +7 -0
  41. package/docs/arrow-thin-right-CZH1S-Ev.js +7 -0
  42. package/docs/arrow-thin-up-kbf0Hayy.js +7 -0
  43. package/docs/arrow-toggle-down-CWSCkUi8.js +7 -0
  44. package/docs/arrow-toggle-up-sUgzJAuI.js +7 -0
  45. package/docs/assignments-BpNN8uRi.js +9 -0
  46. package/docs/assignments-BwrFNhJf.js +14 -0
  47. package/docs/assignments-DJuzE5TS.js +8 -0
  48. package/docs/attach-CxYJqjr7.js +8 -0
  49. package/docs/attach-DoURgNqH.js +7 -0
  50. package/docs/attendance-Bh8NDNxG.js +7 -0
  51. package/docs/attendance-CKrWYCoi.js +8 -0
  52. package/docs/awards-08R3caDo.js +7 -0
  53. package/docs/awards-CGFZ1AmF.js +7 -0
  54. package/docs/binder-DqjAKrO6.js +7 -0
  55. package/docs/binder-sPoCLPbv.js +9 -0
  56. package/docs/blocked-BqqEqoxS.js +7 -0
  57. package/docs/blocked-CdL2qnqB.js +7 -0
  58. package/docs/blog-EWWLpv3J.js +11 -0
  59. package/docs/blog-mImHk1UE.js +11 -0
  60. package/docs/bold-DvEMGUJQ.js +7 -0
  61. package/docs/book-management-BycZ58Mx.js +8 -0
  62. package/docs/book-management-C5EVLmWE.js +7 -0
  63. package/docs/bookmark-ZSLGVyMZ.js +8 -0
  64. package/docs/bookmark-filled-By-e1Vik.js +7 -0
  65. package/docs/bookmark-filled-C5_hpJmC.js +7 -0
  66. package/docs/bookmark-hollow-BERVrtPe.js +7 -0
  67. package/docs/bookmark-hollow-DmYIKVj-.js +7 -0
  68. package/docs/broken-link-0mE-24kB.js +7 -0
  69. package/docs/broken-link-B0FAWC4d.js +7 -0
  70. package/docs/browser-Bkf2Pqxa.js +11 -0
  71. package/docs/browser-DDKpAnFL.js +7 -0
  72. package/docs/bullet-WEelL-Oz.js +7 -0
  73. package/docs/bullseye-BGaOsg34.js +9 -0
  74. package/docs/bullseye-BI26Yr2r.js +11 -0
  75. package/docs/bullseye-D8leZHHy.js +10 -0
  76. package/docs/calculate-7BO4aJsc.js +7 -0
  77. package/docs/calculate-C1k19iEm.js +17 -0
  78. package/docs/calendar-10jvL2iw.js +7 -0
  79. package/docs/calendar-CAOKFxG8.js +7 -0
  80. package/docs/calendar-N5k43N09.js +7 -0
  81. package/docs/capture-BXEbu8tr.js +7 -0
  82. package/docs/change-file-3zLEwSjU.js +10 -0
  83. package/docs/change-file-CVDVitRF.js +10 -0
  84. package/docs/chat-BLpVloRi.js +7 -0
  85. package/docs/chat-CJvurd17.js +7 -0
  86. package/docs/chat-DkYoPSJD.js +7 -0
  87. package/docs/check-6yKqAXn0.js +7 -0
  88. package/docs/check-BDGGpjpw.js +7 -0
  89. package/docs/check-box-COb-iQnp.js +8 -0
  90. package/docs/check-box-unchecked-CihNEcBY.js +7 -0
  91. package/docs/check-circle-BHCbtC9e.js +8 -0
  92. package/docs/check-circle-CcqlS16f.js +7 -0
  93. package/docs/check-circle-D-88S9HE.js +8 -0
  94. package/docs/check-manual-D118hJse.js +10 -0
  95. package/docs/check-user-CzXE-sqy.js +9 -0
  96. package/docs/checklist-D3dcWqlj.js +12 -0
  97. package/docs/checklist-VRzqF3Cn.js +7 -0
  98. package/docs/chevron-down-CmgQXzCG.js +7 -0
  99. package/docs/chevron-down-NDFaTQA4.js +7 -0
  100. package/docs/chevron-down-eOc83-I6.js +7 -0
  101. package/docs/chevron-down-medium-ZHL8V0yD.js +7 -0
  102. package/docs/chevron-down-small-Cxu3u8oN.js +7 -0
  103. package/docs/chevron-left-CTXSr5gY.js +7 -0
  104. package/docs/chevron-left-DGHEARqj.js +7 -0
  105. package/docs/chevron-left-Dv2XEN1W.js +7 -0
  106. package/docs/chevron-left-circle-DC2ldsYl.js +8 -0
  107. package/docs/chevron-right-DyJ0vK9x.js +7 -0
  108. package/docs/chevron-right-X9aw5FQZ.js +7 -0
  109. package/docs/chevron-right-circle-CfufyneZ.js +8 -0
  110. package/docs/chevron-right-dtXLd_t_.js +7 -0
  111. package/docs/chevron-up-BLvFJkrs.js +7 -0
  112. package/docs/chevron-up-CBgDUU-S.js +7 -0
  113. package/docs/chevron-up-Cz4arn0k.js +7 -0
  114. package/docs/class-MfNPJCE3.js +7 -0
  115. package/docs/classes-BrimJoaQ.js +7 -0
  116. package/docs/classes-DNZeYwP9.js +7 -0
  117. package/docs/classlist-CT7aR3Qp.js +9 -0
  118. package/docs/classlist-lNAGMMK9.js +7 -0
  119. package/docs/close-DZhoaKqc.js +7 -0
  120. package/docs/close-circle-BUNfgKRi.js +8 -0
  121. package/docs/close-default-dnnWtHBx.js +7 -0
  122. package/docs/close-large-bMM1w3Qq.js +7 -0
  123. package/docs/close-large-thick-CIk4u_x5.js +7 -0
  124. package/docs/close-small-BM6jWA00.js +7 -0
  125. package/docs/close-thick-CSMgayuW.js +7 -0
  126. package/docs/comment-filled-BIwNhQOh.js +7 -0
  127. package/docs/comment-hollow-BuEIRoVu.js +7 -0
  128. package/docs/contacts-0c5Ejeie.js +8 -0
  129. package/docs/contacts-0p7GRork.js +9 -0
  130. package/docs/content-BkmZJI2k.js +10 -0
  131. package/docs/copy-ByxRV0Fv.js +9 -0
  132. package/docs/copy-C0jJBW8t.js +8 -0
  133. package/docs/copy-CrrPol58.js +9 -0
  134. package/docs/course-B7-GuqH0.js +9 -0
  135. package/docs/course-progress-complete-D-88S9HE.js +8 -0
  136. package/docs/course-progress-in-progress-CMNxGcwl.js +7 -0
  137. package/docs/course-progress-not-started-CZkienJ8.js +7 -0
  138. package/docs/course-tile-sort-DBH3sD6Y.js +7 -0
  139. package/docs/course-tile-sort-LVnGtfEg.js +7 -0
  140. package/docs/coursebuilder-CksHR_dY.js +7 -0
  141. package/docs/coursebuilder-mK3UOKAz.js +7 -0
  142. package/docs/cut-BSxIDiPd.js +7 -0
  143. package/docs/delete-XUr3hb61.js +8 -0
  144. package/docs/delete-n_0tMiML.js +7 -0
  145. package/docs/direction-ltr-DOOIOEMV.js +7 -0
  146. package/docs/direction-rtl-Zq209crM.js +7 -0
  147. package/docs/disable-CfhAdhZ4.js +8 -0
  148. package/docs/discussions-BV-rVYTJ.js +8 -0
  149. package/docs/discussions-DcjKXpsJ.js +8 -0
  150. package/docs/discussions-FfXuJJ0A.js +8 -0
  151. package/docs/divider-DYcReEjI.js +12 -0
  152. package/docs/divider-big-CNFI3Pvd.js +11 -0
  153. package/docs/divider-solid-BwFmdIq7.js +7 -0
  154. package/docs/dot-GOmm6Bys.js +7 -0
  155. package/docs/dot-THJbh2QW.js +7 -0
  156. package/docs/download-B8F8Cdcb.js +8 -0
  157. package/docs/download-D0w9z3Z3.js +8 -0
  158. package/docs/download-SHKxw6bp.js +8 -0
  159. package/docs/draft-mP5du8rd.js +9 -0
  160. package/docs/draft-vZl_0H-L.js +8 -0
  161. package/docs/dragger-aZ6zsEfR.js +7 -0
  162. package/docs/drivers/assets/anchor.js +350 -0
  163. package/docs/drivers/assets/bass-addons.css +12 -0
  164. package/docs/drivers/assets/bass.css +544 -0
  165. package/docs/drivers/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  166. package/docs/drivers/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  167. package/docs/drivers/assets/fonts/LICENSE.txt +93 -0
  168. package/docs/drivers/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  169. package/docs/drivers/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  170. package/docs/drivers/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  171. package/docs/drivers/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  172. package/docs/drivers/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  173. package/docs/drivers/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  174. package/docs/drivers/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  175. package/docs/drivers/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  176. package/docs/drivers/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  177. package/docs/drivers/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  178. package/docs/drivers/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  179. package/docs/drivers/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  180. package/docs/drivers/assets/fonts/source-code-pro.css +23 -0
  181. package/docs/drivers/assets/github.css +123 -0
  182. package/docs/drivers/assets/site.js +168 -0
  183. package/docs/drivers/assets/split.css +15 -0
  184. package/docs/drivers/assets/split.js +782 -0
  185. package/docs/drivers/assets/style.css +147 -0
  186. package/docs/drivers/index.html +6180 -0
  187. package/docs/edit-XTluWOyY.js +7 -0
  188. package/docs/edit-bulk-CbUTb41B.js +7 -0
  189. package/docs/edit-not-editable-BtNDjkNt.js +9 -0
  190. package/docs/edit-rtSBrFnZ.js +7 -0
  191. package/docs/email-B77IV5dc.js +8 -0
  192. package/docs/email-DShyqmyr.js +7 -0
  193. package/docs/email-Dr_fUQo7.js +7 -0
  194. package/docs/email-open-CNPI-nbt.js +9 -0
  195. package/docs/email-open-sMmv4goK.js +8 -0
  196. package/docs/email-read-D4PMZMhZ.js +8 -0
  197. package/docs/enable-BXJKKu9V.js +8 -0
  198. package/docs/enrollment-D_f33z-t.js +7 -0
  199. package/docs/eportfolio-CmIoQSs-.js +7 -0
  200. package/docs/eportfolio-DiR128Ch.js +8 -0
  201. package/docs/equation-graphical-DEK4DR0o.js +7 -0
  202. package/docs/equation-graphical-chemistry-deGj_Wo1.js +7 -0
  203. package/docs/equation-latex-OwF3WKZs.js +7 -0
  204. package/docs/equation-mathml-BVFy7F04.js +8 -0
  205. package/docs/evaluate-all-D8Ed6wUQ.js +15 -0
  206. package/docs/evaluate-all-DRA08hvM.js +13 -0
  207. package/docs/event-log-BBnLruqh.js +7 -0
  208. package/docs/exemption-add-CuNjn-gE.js +8 -0
  209. package/docs/exemption-remove-C6gurfls.js +10 -0
  210. package/docs/export-B00I40zU.js +8 -0
  211. package/docs/export-C_qczGjD.js +8 -0
  212. package/docs/external-CGUtobc0.js +6 -0
  213. package/docs/external-D14KafxI.js +9 -0
  214. package/docs/external-XLH4ZIpG.js +9 -0
  215. package/docs/feed-CpSir1Op.js +7 -0
  216. package/docs/feed-Dp9gnfxV.js +12 -0
  217. package/docs/feedback-CYkdDNHj.js +7 -0
  218. package/docs/feedback-zuS0X61K.js +7 -0
  219. package/docs/file-archive-BqyAeRx6.js +14 -0
  220. package/docs/file-archive-aUsV28fR.js +14 -0
  221. package/docs/file-audio-C0gLVZ1J.js +7 -0
  222. package/docs/file-audio-DlPChJJD.js +7 -0
  223. package/docs/file-audio-Ez8GKNqD.js +8 -0
  224. package/docs/file-document-OV_yiZc9.js +7 -0
  225. package/docs/file-document-PtERBBjG.js +9 -0
  226. package/docs/file-document-RAyDjBV0.js +9 -0
  227. package/docs/file-image-2kUlJRfa.js +7 -0
  228. package/docs/file-image-DEvp4loc.js +8 -0
  229. package/docs/file-presentation-DnSQf6dJ.js +10 -0
  230. package/docs/file-presentation-Dvm4dJkX.js +11 -0
  231. package/docs/file-presentation-DynwRY3d.js +7 -0
  232. package/docs/file-video-Baynsug6.js +8 -0
  233. package/docs/file-video-DubiL6Pa.js +7 -0
  234. package/docs/file-video-Dz0Xv-nt.js +8 -0
  235. package/docs/filter-BXmy_W6Z.js +7 -0
  236. package/docs/filter-CjP2TU9o.js +11 -0
  237. package/docs/flag-fill-Bon2nRGs.js +7 -0
  238. package/docs/flag-filled-B0f2EsXm.js +7 -0
  239. package/docs/flag-hollow-CaU1iNOl.js +7 -0
  240. package/docs/flag-hollow-DfEoHVNP.js +7 -0
  241. package/docs/folder-D4EQiKEf.js +7 -0
  242. package/docs/folder-DjGOP9kC.js +7 -0
  243. package/docs/folder-up-level-CmUITqEa.js +8 -0
  244. package/docs/forms-BzBisiyk.js +8 -0
  245. package/docs/forms-QmRSltZO.js +7 -0
  246. package/docs/forward-B7OsyI-4.js +8 -0
  247. package/docs/fullscreen-DW5UhnuF.js +8 -0
  248. package/docs/fullscreen-Dos-vYUL.js +7 -0
  249. package/docs/game-BPXtsa4R.js +12 -0
  250. package/docs/game-CAeZpf2P.js +12 -0
  251. package/docs/game-CJBm4W_4.js +6 -0
  252. package/docs/gear-BXgew4r5.js +8 -0
  253. package/docs/gear-BefUgJUH.js +8 -0
  254. package/docs/gear-Dozogx0s.js +7 -0
  255. package/docs/glossary-BYZOnXFD.js +10 -0
  256. package/docs/glossary-pJwGMnFw.js +7 -0
  257. package/docs/google-drive-BY7aNeo4.js +7 -0
  258. package/docs/google-drive-C2K-Q1Sz.js +7 -0
  259. package/docs/google-drive-UaaDdmWX.js +7 -0
  260. package/docs/grabber-DDfgK4q3.js +7 -0
  261. package/docs/grabber-small--2Gc1-LB.js +7 -0
  262. package/docs/grade-BG_E-8NT.js +8 -0
  263. package/docs/grade-D2MISbK9.js +7 -0
  264. package/docs/grade-NOWaSTNa.js +8 -0
  265. package/docs/grade-remove-Ph1Izm-7.js +8 -0
  266. package/docs/grade-visible-CDb-9-br.js +7 -0
  267. package/docs/group-DtqVtMH3.js +8 -0
  268. package/docs/group-locker-ftiR0a03.js +7 -0
  269. package/docs/happy-LeP0nGOv.js +7 -0
  270. package/docs/help-CkV4Dp7d.js +9 -0
  271. package/docs/help-Dxodc931.js +9 -0
  272. package/docs/help-FOiT3jKO.js +7 -0
  273. package/docs/history-DARTknKW.js +8 -0
  274. package/docs/history-rho7wY5T.js +8 -0
  275. package/docs/home-BE2SQvvs.js +7 -0
  276. package/docs/home-D_tSkasl.js +8 -0
  277. package/docs/home-DbQqnxwO.js +7 -0
  278. package/docs/image-BCnN94lf.js +9 -0
  279. package/docs/image-Dmy_y4Fd.js +8 -0
  280. package/docs/import-D_Njyhb9.js +8 -0
  281. package/docs/import-YfiMqwWh.js +8 -0
  282. package/docs/important-2qm6frSZ.js +9 -0
  283. package/docs/indent-decrease-CQm4KxII.js +7 -0
  284. package/docs/indent-increase-BO1QVrc8.js +7 -0
  285. package/docs/index.html +1 -0
  286. package/docs/inline-module-index-0.js +9556 -0
  287. package/docs/insert-attributes-B4iHYS-t.js +8 -0
  288. package/docs/insert-emoticon-BC9tKUjH.js +11 -0
  289. package/docs/insights-portal-Cm3Wea4M.js +10 -0
  290. package/docs/insights-portal-Depbhlwj.js +8 -0
  291. package/docs/italic-AhBNAWI0.js +7 -0
  292. package/docs/link-BgD3fOWi.js +8 -0
  293. package/docs/link-CPDrunkx.js +7 -0
  294. package/docs/link-CmNVOd0t.js +7 -0
  295. package/docs/list-bullet-CyrIsY33.js +11 -0
  296. package/docs/list-ordered-BnmtMuSC.js +7 -0
  297. package/docs/list-view-EI9pvwuC.js +11 -0
  298. package/docs/location-CzWLCAQ8.js +7 -0
  299. package/docs/location-DcnFhfnk.js +10 -0
  300. package/docs/locations-B9k1Fx7T.js +13 -0
  301. package/docs/locations-CSxT0wIK.js +7 -0
  302. package/docs/lock-BWzWh9B7.js +8 -0
  303. package/docs/lock-E8wu8HD6.js +8 -0
  304. package/docs/lock-locked-D5lyHWqQ.js +7 -0
  305. package/docs/lock-unlock-WCjSz1i-.js +7 -0
  306. package/docs/lock-unlocked-CAJCLSet.js +8 -0
  307. package/docs/lock-unlocked-DExBKORh.js +8 -0
  308. package/docs/locker-B10MJtSA.js +7 -0
  309. package/docs/locker-Cqcf7p8D.js +10 -0
  310. package/docs/lol-D_JxRmpk.js +7 -0
  311. package/docs/lor-LgltaGp1.js +7 -0
  312. package/docs/lor-NF8M-dTl.js +7 -0
  313. package/docs/low-priority-CYw20_i6.js +9 -0
  314. package/docs/manage-dates-7pdHHIpP.js +8 -0
  315. package/docs/manage-dates-BvldV3qd.js +10 -0
  316. package/docs/manage-dates-edit-BL7TE5Ca.js +7 -0
  317. package/docs/manage-dates-offset-C36mTMRI.js +8 -0
  318. package/docs/manage-files-CztcMg2T.js +8 -0
  319. package/docs/manage-files-DjhMboB5.js +8 -0
  320. package/docs/manual-run-mkeXX4ZT.js +8 -0
  321. package/docs/media-BIt0cvtO.js +8 -0
  322. package/docs/media-BP3ScDqX.js +7 -0
  323. package/docs/meh-VZVAbZG3.js +7 -0
  324. package/docs/menu-Bax-k1Yb.js +9 -0
  325. package/docs/menu-hamburger-C2vj4eRY.js +7 -0
  326. package/docs/menu-hamburger-DjawJZYW.js +7 -0
  327. package/docs/menu-hamburger-JIneUuO7.js +7 -0
  328. package/docs/merge-9psevQT-.js +11 -0
  329. package/docs/message-new-C2a9sicZ.js +8 -0
  330. package/docs/messages-BfrTLnON.js +12 -0
  331. package/docs/messages-BlNvFjBH.js +7 -0
  332. package/docs/mic-B_QU0QmO.js +8 -0
  333. package/docs/mic-Dq5WbNIP.js +8 -0
  334. package/docs/mobile-DqC65aN6.js +6 -0
  335. package/docs/more-CfLcaduh.js +7 -0
  336. package/docs/move-down-D9PWLWhn.js +7 -0
  337. package/docs/move-down-DNE-3gT2.js +8 -0
  338. package/docs/move-to-Bt5a4Jcj.js +8 -0
  339. package/docs/move-to-CmhSXqJ1.js +8 -0
  340. package/docs/move-up-BaS-oCU5.js +7 -0
  341. package/docs/move-up-ByeMSeVd.js +8 -0
  342. package/docs/my-computer-DTsn7C9t.js +8 -0
  343. package/docs/navigate-BUpXfdU3.js +8 -0
  344. package/docs/navigate-D1BhWZtz.js +11 -0
  345. package/docs/new-line-8f0I71Mh.js +7 -0
  346. package/docs/new-window-B5Ln_cc3.js +8 -0
  347. package/docs/news-C1mrMSqE.js +7 -0
  348. package/docs/news-DlE9A-vs.js +9 -0
  349. package/docs/news-NiNcL5vl.js +8 -0
  350. package/docs/no-entry-C3dnCBCI.js +8 -0
  351. package/docs/notification-bell-D_RdfZKS.js +9 -0
  352. package/docs/nova-middleware/assets/anchor.js +350 -0
  353. package/docs/nova-middleware/assets/bass-addons.css +12 -0
  354. package/docs/nova-middleware/assets/bass.css +544 -0
  355. package/docs/nova-middleware/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  356. package/docs/nova-middleware/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  357. package/docs/nova-middleware/assets/fonts/LICENSE.txt +93 -0
  358. package/docs/nova-middleware/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  359. package/docs/nova-middleware/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  360. package/docs/nova-middleware/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  361. package/docs/nova-middleware/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  362. package/docs/nova-middleware/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  363. package/docs/nova-middleware/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  364. package/docs/nova-middleware/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  365. package/docs/nova-middleware/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  366. package/docs/nova-middleware/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  367. package/docs/nova-middleware/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  368. package/docs/nova-middleware/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  369. package/docs/nova-middleware/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  370. package/docs/nova-middleware/assets/fonts/source-code-pro.css +23 -0
  371. package/docs/nova-middleware/assets/github.css +123 -0
  372. package/docs/nova-middleware/assets/site.js +168 -0
  373. package/docs/nova-middleware/assets/split.css +15 -0
  374. package/docs/nova-middleware/assets/split.js +782 -0
  375. package/docs/nova-middleware/assets/style.css +147 -0
  376. package/docs/nova-middleware/index.html +406 -0
  377. package/docs/nova-model/assets/anchor.js +350 -0
  378. package/docs/nova-model/assets/bass-addons.css +12 -0
  379. package/docs/nova-model/assets/bass.css +544 -0
  380. package/docs/nova-model/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  381. package/docs/nova-model/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  382. package/docs/nova-model/assets/fonts/LICENSE.txt +93 -0
  383. package/docs/nova-model/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  384. package/docs/nova-model/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  385. package/docs/nova-model/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  386. package/docs/nova-model/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  387. package/docs/nova-model/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  388. package/docs/nova-model/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  389. package/docs/nova-model/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  390. package/docs/nova-model/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  391. package/docs/nova-model/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  392. package/docs/nova-model/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  393. package/docs/nova-model/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  394. package/docs/nova-model/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  395. package/docs/nova-model/assets/fonts/source-code-pro.css +23 -0
  396. package/docs/nova-model/assets/github.css +123 -0
  397. package/docs/nova-model/assets/site.js +168 -0
  398. package/docs/nova-model/assets/split.css +15 -0
  399. package/docs/nova-model/assets/split.js +782 -0
  400. package/docs/nova-model/assets/style.css +147 -0
  401. package/docs/nova-model/index.html +3244 -0
  402. package/docs/nova-utils/assets/anchor.js +350 -0
  403. package/docs/nova-utils/assets/bass-addons.css +12 -0
  404. package/docs/nova-utils/assets/bass.css +544 -0
  405. package/docs/nova-utils/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  406. package/docs/nova-utils/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  407. package/docs/nova-utils/assets/fonts/LICENSE.txt +93 -0
  408. package/docs/nova-utils/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  409. package/docs/nova-utils/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  410. package/docs/nova-utils/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  411. package/docs/nova-utils/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  412. package/docs/nova-utils/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  413. package/docs/nova-utils/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  414. package/docs/nova-utils/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  415. package/docs/nova-utils/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  416. package/docs/nova-utils/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  417. package/docs/nova-utils/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  418. package/docs/nova-utils/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  419. package/docs/nova-utils/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  420. package/docs/nova-utils/assets/fonts/source-code-pro.css +23 -0
  421. package/docs/nova-utils/assets/github.css +123 -0
  422. package/docs/nova-utils/assets/site.js +168 -0
  423. package/docs/nova-utils/assets/split.css +15 -0
  424. package/docs/nova-utils/assets/split.js +782 -0
  425. package/docs/nova-utils/assets/style.css +147 -0
  426. package/docs/nova-utils/index.html +986 -0
  427. package/docs/one-drive-B17qEGg3.js +10 -0
  428. package/docs/one-drive-DJkLjiFC.js +6 -0
  429. package/docs/online-C94s_rb_.js +10 -0
  430. package/docs/online-D-ZCoHHm.js +9 -0
  431. package/docs/online-rooms-1mVK1aGi.js +7 -0
  432. package/docs/online-rooms-CDdAm2UO.js +9 -0
  433. package/docs/outcomes-BBf-Ha_8.js +7 -0
  434. package/docs/outcomes-C0izuLnk.js +7 -0
  435. package/docs/password-DLPNSwzE.js +7 -0
  436. package/docs/password-Dh7gVC6R.js +7 -0
  437. package/docs/paste-B-PIibRN.js +7 -0
  438. package/docs/pause-ClttiH9R.js +9 -0
  439. package/docs/pause-CytomPFa.js +7 -0
  440. package/docs/pause-borderless-BI_BVCJy.js +8 -0
  441. package/docs/pic-C5FMoERH.js +7 -0
  442. package/docs/pic-CfSFIefC.js +8 -0
  443. package/docs/pic-Dmy_y4Fd.js +8 -0
  444. package/docs/pin-filled-CXkRNZ5O.js +7 -0
  445. package/docs/pin-filled-w3eah_ZK.js +7 -0
  446. package/docs/pin-hollow-DEWfTASy.js +7 -0
  447. package/docs/pin-hollow-DVbwzH1M.js +7 -0
  448. package/docs/play-DMAGMc2B.js +8 -0
  449. package/docs/play-DbZdG7Gq.js +7 -0
  450. package/docs/play-borderless-DqQ17-YW.js +7 -0
  451. package/docs/plus-default-DHk06f01.js +7 -0
  452. package/docs/plus-large-DfxPCCrT.js +7 -0
  453. package/docs/plus-large-thick-gmHCMimx.js +7 -0
  454. package/docs/preview-BgaRQpP1.js +9 -0
  455. package/docs/preview-DiNoAoRq.js +9 -0
  456. package/docs/preview-DucwBKG_.js +8 -0
  457. package/docs/print-YZ-X09iP.js +7 -0
  458. package/docs/print-p1KbTvQ3.js +8 -0
  459. package/docs/profile-default-CR9VzwIc.js +7 -0
  460. package/docs/profile-default-CrRCaKe0.js +7 -0
  461. package/docs/profile-default-DjZMHiLd.js +7 -0
  462. package/docs/profile-pic-B1r87rnD.js +8 -0
  463. package/docs/profile-pic-FXAOU2-x.js +7 -0
  464. package/docs/profile-pic-WGNyfyzw.js +7 -0
  465. package/docs/project-BmdrPymq.js +9 -0
  466. package/docs/publish-all-C91CIIOg.js +9 -0
  467. package/docs/publish-all-CgPj17Qp.js +9 -0
  468. package/docs/publish-to-lor-BzzkuSPc.js +8 -0
  469. package/docs/publish-to-lor-NqvGf8fs.js +10 -0
  470. package/docs/quicklink-C5CDhyK0.js +6 -0
  471. package/docs/quicklink-DpoklXCh.js +7 -0
  472. package/docs/quiz-submissions-BAMFpmlt.js +12 -0
  473. package/docs/quizzing-B5p4bkL1.js +7 -0
  474. package/docs/quizzing-Bn5KKwty.js +17 -0
  475. package/docs/quizzing-ZT1VsQDi.js +10 -0
  476. package/docs/read-DhyDmmkk.js +7 -0
  477. package/docs/read-DzsAK1Gp.js +7 -0
  478. package/docs/read-unread-BaKkzPgA.js +7 -0
  479. package/docs/read-unread-ayEnU2WS.js +7 -0
  480. package/docs/reading-V8BekXyi.js +9 -0
  481. package/docs/reading-Z7La5_yK.js +7 -0
  482. package/docs/redo-DqrjRBg2.js +7 -0
  483. package/docs/reflection-Bx089gqz.js +10 -0
  484. package/docs/reflection-CWFEnLpT.js +10 -0
  485. package/docs/refresh-CLDK3svm.js +7 -0
  486. package/docs/refresh-DAtZSM_N.js +7 -0
  487. package/docs/release-conditions-BXxl9Dlf.js +7 -0
  488. package/docs/release-conditions-OLqc9pTg.js +7 -0
  489. package/docs/remove-user-B26LnqCu.js +10 -0
  490. package/docs/remove-user-DNXiNHBs.js +10 -0
  491. package/docs/reorder-BIFjdLxG.js +7 -0
  492. package/docs/reorder-Y4_r1Ayt.js +7 -0
  493. package/docs/repeat-JHaa8nfm.js +7 -0
  494. package/docs/replied-D2ix7Rk6.js +8 -0
  495. package/docs/reply-BqzsKC85.js +7 -0
  496. package/docs/reply-CKQu6lmN.js +8 -0
  497. package/docs/reply-all-g5VAmAX4.js +8 -0
  498. package/docs/reporting-ChEapxxJ.js +9 -0
  499. package/docs/reporting-D3LvXPru.js +7 -0
  500. package/docs/reports-Beth_W4X.js +12 -0
  501. package/docs/resize-left-GFaUaulC.js +7 -0
  502. package/docs/resize-right-DT6LaX2w.js +7 -0
  503. package/docs/reverse-order-aSt4RUV4.js +7 -0
  504. package/docs/role-switch-DLSQpVpI.js +7 -0
  505. package/docs/rss-4WhjKoVd.js +7 -0
  506. package/docs/rss-Bkw2Vu26.js +9 -0
  507. package/docs/rubric-C7Bvkdy8.js +7 -0
  508. package/docs/rubric-DCEXGTtW.js +7 -0
  509. package/docs/rubric-graded-DRJ7bKvJ.js +13 -0
  510. package/docs/rubric-graded-UxgPY7mA.js +8 -0
  511. package/docs/rubrics-CbER8LnL.js +7 -0
  512. package/docs/sad-BoDjvLIi.js +7 -0
  513. package/docs/save-C6Wm6dlX.js +7 -0
  514. package/docs/save-jMj_12iN.js +8 -0
  515. package/docs/scorm-BEMJkg_y.js +6 -0
  516. package/docs/scorm-DSQ_wzsf.js +7 -0
  517. package/docs/scorm-DwyYD2cQ.js +7 -0
  518. package/docs/search-Ba4VfUac.js +8 -0
  519. package/docs/search-CcFHrjV6.js +7 -0
  520. package/docs/search-Cg93dHlN.js +7 -0
  521. package/docs/seating-CenUmq00.js +7 -0
  522. package/docs/seating-Diwp3OZ0.js +7 -0
  523. package/docs/self-assessment-DtdsDcKC.js +7 -0
  524. package/docs/self-assessment-YnMgOzTH.js +10 -0
  525. package/docs/send-WLvWpVV4.js +7 -0
  526. package/docs/send-kamyQxgU.js +7 -0
  527. package/docs/share-DGresL3N.js +7 -0
  528. package/docs/share-MaE8kOCt.js +8 -0
  529. package/docs/share-hollow-CfuLT6Gb.js +7 -0
  530. package/docs/share-parent-filled-CvoEBnpc.js +10 -0
  531. package/docs/share-parent-hollow-DyLlXxk9.js +10 -0
  532. package/docs/shout-B8aYlnCU.js +7 -0
  533. package/docs/smallscreen-CAmSoX_a.js +7 -0
  534. package/docs/smallscreen-CJyGrrRY.js +7 -0
  535. package/docs/sort-type-Ccq_znjS.js +10 -0
  536. package/docs/source-editor-Bp_3QBP_.js +7 -0
  537. package/docs/spellcheck-Besf5dkX.js +8 -0
  538. package/docs/spellcheck-DOYSjTvo.js +8 -0
  539. package/docs/stop-DWabYiNA.js +8 -0
  540. package/docs/stop-borderless-CxP7Xjd-.js +7 -0
  541. package/docs/strikethrough-DBZqp7V2.js +7 -0
  542. package/docs/style-BbyPYYVo.js +7 -0
  543. package/docs/style-CDgs5AnH.js +7 -0
  544. package/docs/subscribe-filled-BQyc3NsS.js +7 -0
  545. package/docs/subscribe-filled-DnVzUac6.js +7 -0
  546. package/docs/subscribe-hollow-45odrrmr.js +7 -0
  547. package/docs/subscribe-hollow-C6hluycF.js +7 -0
  548. package/docs/subscript-BjAIARSd.js +7 -0
  549. package/docs/superscript-Bhxn6gvd.js +7 -0
  550. package/docs/support-DUKjOc66.js +7 -0
  551. package/docs/surveys-BE8aGBrC.js +7 -0
  552. package/docs/surveys-DoAUhIgW.js +11 -0
  553. package/docs/syllabus-CkqNQZI-.js +7 -0
  554. package/docs/syllabus-Dp2bL_st.js +8 -0
  555. package/docs/syllabus-QUazS8jY.js +8 -0
  556. package/docs/symbol-Bc-zvfel.js +7 -0
  557. package/docs/table-cell-merge-BE8joEWx.js +8 -0
  558. package/docs/table-cell-properties-CMFT10BB.js +8 -0
  559. package/docs/table-cell-split-DDUBTvcc.js +7 -0
  560. package/docs/table-column-insert-after-DzN38SQI.js +7 -0
  561. package/docs/table-column-insert-before-DeAvcikX.js +7 -0
  562. package/docs/table-column-remove-DYiXM8Jb.js +8 -0
  563. package/docs/table-delete-40sq_iUx.js +8 -0
  564. package/docs/table-of-contents-CpoMBmA3.js +7 -0
  565. package/docs/table-of-contents-DmVLblsk.js +11 -0
  566. package/docs/table-properties-C1ZRZ4ga.js +8 -0
  567. package/docs/table-row-copy-C0NVkTuO.js +8 -0
  568. package/docs/table-row-cut-D8ApKTxR.js +7 -0
  569. package/docs/table-row-insert-after-ZiQdbITr.js +7 -0
  570. package/docs/table-row-insert-before-DOqBNAv2.js +7 -0
  571. package/docs/table-row-paste-above-svu4TZL-.js +7 -0
  572. package/docs/table-row-paste-below-DnVjYP_H.js +7 -0
  573. package/docs/table-row-properties-DKKmT8xi.js +8 -0
  574. package/docs/table-row-remove-BpX_iTdC.js +8 -0
  575. package/docs/tag-CLCrd3YD.js +9 -0
  576. package/docs/tag-Dvlrl1rN.js +7 -0
  577. package/docs/tag-hollow-C4R57T76.js +8 -0
  578. package/docs/thumbs-down-_y6J-GBx.js +7 -0
  579. package/docs/thumbs-up-DmpTufP-.js +14 -0
  580. package/docs/tile-view-DAEgJlr5.js +12 -0
  581. package/docs/time-j7PVTeX4.js +7 -0
  582. package/docs/time-y--dvj05.js +8 -0
  583. package/docs/tools-ApXN5SG4.js +8 -0
  584. package/docs/tools-CI_7JQXe.js +7 -0
  585. package/docs/topic-last-CBI3iGxL.js +8 -0
  586. package/docs/topic-last-Db8wiEGR.js +8 -0
  587. package/docs/turnitin-HVqx-UXy.js +8 -0
  588. package/docs/unapproved-DWiZCrwv.js +10 -0
  589. package/docs/unapproved-Dhu_8xZD.js +10 -0
  590. package/docs/underline-DxnwXTaI.js +7 -0
  591. package/docs/undo-Di_HG7p_.js +7 -0
  592. package/docs/undo-KeM-So3F.js +7 -0
  593. package/docs/unsaved-Cc_mMbdm.js +10 -0
  594. package/docs/unsaved-DeP04L83.js +8 -0
  595. package/docs/upload-AImNeKVm.js +8 -0
  596. package/docs/upload-BIQxUfMy.js +8 -0
  597. package/docs/upload-nuZBVJjg.js +8 -0
  598. package/docs/user-competencies-8dMwEPL6.js +7 -0
  599. package/docs/user-competencies-Y57bDKtV.js +19 -0
  600. package/docs/user-progress-CUzNTpLo.js +10 -0
  601. package/docs/user-progress-DQUFGV7M.js +10 -0
  602. package/docs/validate-TiDv-LdA.js +16 -0
  603. package/docs/video-assignment-C-Eh-N2b.js +10 -0
  604. package/docs/video-assignment-DJhOt4CY.js +11 -0
  605. package/docs/view-submission-list-D56QhpGG.js +13 -0
  606. package/docs/view-submission-list-KS3OLMnE.js +15 -0
  607. package/docs/viewed-notviewed-CSNppbac.js +7 -0
  608. package/docs/virtual-classroom-Cxhu5Mw0.js +10 -0
  609. package/docs/virtual-classroom-De9_fVB7.js +6 -0
  610. package/docs/visibility-conditional-BbN-53aD.js +9 -0
  611. package/docs/visibility-hide-B2KKT0mx.js +7 -0
  612. package/docs/visibility-hide-Bctc7bkg.js +7 -0
  613. package/docs/visibility-show-BD2PP0kM.js +8 -0
  614. package/docs/visibility-show-BwU9PNHL.js +7 -0
  615. package/docs/volume-CYc0W77d.js +8 -0
  616. package/docs/volume-DrPpJaf1.js +7 -0
  617. package/docs/volume-muted-CK8EQ9dK.js +12 -0
  618. package/docs/volume-muted-D2mJNGq6.js +7 -0
  619. package/docs/widgets-BEcQiVkC.js +12 -0
  620. package/docs/wizard-D-phsxRW.js +11 -0
  621. package/docs/wizard-cZqtBjee.js +11 -0
  622. package/docs/zoom-in-Dpu97xmF.js +7 -0
  623. package/docs/zoom-out-Cu3SsLeV.js +7 -0
  624. package/docs-base/index.html +22 -0
  625. package/docs-base/nova-shared-repository.js +54 -0
  626. package/docs-base/package-info.js +26 -0
  627. package/index.js +21 -0
  628. package/package.json +59 -0
  629. package/packages/drivers/README.md +5 -0
  630. package/packages/drivers/docs/assets/anchor.js +350 -0
  631. package/packages/drivers/docs/assets/bass-addons.css +12 -0
  632. package/packages/drivers/docs/assets/bass.css +544 -0
  633. package/packages/drivers/docs/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  634. package/packages/drivers/docs/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  635. package/packages/drivers/docs/assets/fonts/LICENSE.txt +93 -0
  636. package/packages/drivers/docs/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  637. package/packages/drivers/docs/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  638. package/packages/drivers/docs/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  639. package/packages/drivers/docs/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  640. package/packages/drivers/docs/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  641. package/packages/drivers/docs/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  642. package/packages/drivers/docs/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  643. package/packages/drivers/docs/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  644. package/packages/drivers/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  645. package/packages/drivers/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  646. package/packages/drivers/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  647. package/packages/drivers/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  648. package/packages/drivers/docs/assets/fonts/source-code-pro.css +23 -0
  649. package/packages/drivers/docs/assets/github.css +123 -0
  650. package/packages/drivers/docs/assets/site.js +168 -0
  651. package/packages/drivers/docs/assets/split.css +15 -0
  652. package/packages/drivers/docs/assets/split.js +782 -0
  653. package/packages/drivers/docs/assets/style.css +147 -0
  654. package/packages/drivers/docs/index.html +6180 -0
  655. package/packages/drivers/index.js +10 -0
  656. package/packages/drivers/package.json +31 -0
  657. package/packages/drivers/src/aws/aws-base-driver.js +34 -0
  658. package/packages/drivers/src/aws/dynamodb.js +230 -0
  659. package/packages/drivers/src/aws/secrets-manager.js +52 -0
  660. package/packages/drivers/src/aws/sqs.js +140 -0
  661. package/packages/drivers/src/config.js +13 -0
  662. package/packages/drivers/src/http.js +162 -0
  663. package/packages/drivers/src/kraken-driver.js +28 -0
  664. package/packages/drivers/src/nova-driver.js +32 -0
  665. package/packages/drivers/src/oauth.js +145 -0
  666. package/packages/drivers/src/wave.js +83 -0
  667. package/packages/drivers/test/.eslintrc.yaml +27 -0
  668. package/packages/drivers/test/aws/dynamodb.test.js +119 -0
  669. package/packages/drivers/test/aws/secrets-manager.js +146 -0
  670. package/packages/drivers/test/http.test.js +118 -0
  671. package/packages/drivers/test/oauth.test.js +211 -0
  672. package/packages/drivers/test/wave.test.js +109 -0
  673. package/packages/nova-middleware/README.md +5 -0
  674. package/packages/nova-middleware/docs/assets/anchor.js +350 -0
  675. package/packages/nova-middleware/docs/assets/bass-addons.css +12 -0
  676. package/packages/nova-middleware/docs/assets/bass.css +544 -0
  677. package/packages/nova-middleware/docs/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  678. package/packages/nova-middleware/docs/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  679. package/packages/nova-middleware/docs/assets/fonts/LICENSE.txt +93 -0
  680. package/packages/nova-middleware/docs/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  681. package/packages/nova-middleware/docs/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  682. package/packages/nova-middleware/docs/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  683. package/packages/nova-middleware/docs/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  684. package/packages/nova-middleware/docs/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  685. package/packages/nova-middleware/docs/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  686. package/packages/nova-middleware/docs/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  687. package/packages/nova-middleware/docs/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  688. package/packages/nova-middleware/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  689. package/packages/nova-middleware/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  690. package/packages/nova-middleware/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  691. package/packages/nova-middleware/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  692. package/packages/nova-middleware/docs/assets/fonts/source-code-pro.css +23 -0
  693. package/packages/nova-middleware/docs/assets/github.css +123 -0
  694. package/packages/nova-middleware/docs/assets/site.js +168 -0
  695. package/packages/nova-middleware/docs/assets/split.css +15 -0
  696. package/packages/nova-middleware/docs/assets/split.js +782 -0
  697. package/packages/nova-middleware/docs/assets/style.css +147 -0
  698. package/packages/nova-middleware/docs/index.html +406 -0
  699. package/packages/nova-middleware/index.js +2 -0
  700. package/packages/nova-middleware/package.json +21 -0
  701. package/packages/nova-middleware/src/distributed-logging-middleware.js +36 -0
  702. package/packages/nova-middleware/src/oauth-middleware.js +63 -0
  703. package/packages/nova-middleware/test/.eslintrc.yaml +27 -0
  704. package/packages/nova-middleware/test/oauth-middleware.test.js +14 -0
  705. package/packages/nova-model/README.md +5 -0
  706. package/packages/nova-model/docs/assets/anchor.js +350 -0
  707. package/packages/nova-model/docs/assets/bass-addons.css +12 -0
  708. package/packages/nova-model/docs/assets/bass.css +544 -0
  709. package/packages/nova-model/docs/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  710. package/packages/nova-model/docs/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  711. package/packages/nova-model/docs/assets/fonts/LICENSE.txt +93 -0
  712. package/packages/nova-model/docs/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  713. package/packages/nova-model/docs/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  714. package/packages/nova-model/docs/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  715. package/packages/nova-model/docs/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  716. package/packages/nova-model/docs/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  717. package/packages/nova-model/docs/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  718. package/packages/nova-model/docs/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  719. package/packages/nova-model/docs/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  720. package/packages/nova-model/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  721. package/packages/nova-model/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  722. package/packages/nova-model/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  723. package/packages/nova-model/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  724. package/packages/nova-model/docs/assets/fonts/source-code-pro.css +23 -0
  725. package/packages/nova-model/docs/assets/github.css +123 -0
  726. package/packages/nova-model/docs/assets/site.js +168 -0
  727. package/packages/nova-model/docs/assets/split.css +15 -0
  728. package/packages/nova-model/docs/assets/split.js +782 -0
  729. package/packages/nova-model/docs/assets/style.css +147 -0
  730. package/packages/nova-model/docs/index.html +3244 -0
  731. package/packages/nova-model/index.js +6 -0
  732. package/packages/nova-model/package.json +19 -0
  733. package/packages/nova-model/src/model/api-token.js +27 -0
  734. package/packages/nova-model/src/model/models/nova-user.js +55 -0
  735. package/packages/nova-model/src/model/nova-model.js +184 -0
  736. package/packages/nova-model/src/model/nova-schema.js +154 -0
  737. package/packages/nova-model/src/repo/api-token.js +12 -0
  738. package/packages/nova-model/src/repo/nova-model-repo.js +203 -0
  739. package/packages/nova-model/test/.eslintrc.yaml +27 -0
  740. package/packages/nova-model/test/nova-model.test.js +123 -0
  741. package/packages/nova-utils/README.md +5 -0
  742. package/packages/nova-utils/docs/assets/anchor.js +350 -0
  743. package/packages/nova-utils/docs/assets/bass-addons.css +12 -0
  744. package/packages/nova-utils/docs/assets/bass.css +544 -0
  745. package/packages/nova-utils/docs/assets/fonts/EOT/SourceCodePro-Bold.eot +0 -0
  746. package/packages/nova-utils/docs/assets/fonts/EOT/SourceCodePro-Regular.eot +0 -0
  747. package/packages/nova-utils/docs/assets/fonts/LICENSE.txt +93 -0
  748. package/packages/nova-utils/docs/assets/fonts/OTF/SourceCodePro-Bold.otf +0 -0
  749. package/packages/nova-utils/docs/assets/fonts/OTF/SourceCodePro-Regular.otf +0 -0
  750. package/packages/nova-utils/docs/assets/fonts/TTF/SourceCodePro-Bold.ttf +0 -0
  751. package/packages/nova-utils/docs/assets/fonts/TTF/SourceCodePro-Regular.ttf +0 -0
  752. package/packages/nova-utils/docs/assets/fonts/WOFF/OTF/SourceCodePro-Bold.otf.woff +0 -0
  753. package/packages/nova-utils/docs/assets/fonts/WOFF/OTF/SourceCodePro-Regular.otf.woff +0 -0
  754. package/packages/nova-utils/docs/assets/fonts/WOFF/TTF/SourceCodePro-Bold.ttf.woff +0 -0
  755. package/packages/nova-utils/docs/assets/fonts/WOFF/TTF/SourceCodePro-Regular.ttf.woff +0 -0
  756. package/packages/nova-utils/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Bold.otf.woff2 +0 -0
  757. package/packages/nova-utils/docs/assets/fonts/WOFF2/OTF/SourceCodePro-Regular.otf.woff2 +0 -0
  758. package/packages/nova-utils/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Bold.ttf.woff2 +0 -0
  759. package/packages/nova-utils/docs/assets/fonts/WOFF2/TTF/SourceCodePro-Regular.ttf.woff2 +0 -0
  760. package/packages/nova-utils/docs/assets/fonts/source-code-pro.css +23 -0
  761. package/packages/nova-utils/docs/assets/github.css +123 -0
  762. package/packages/nova-utils/docs/assets/site.js +168 -0
  763. package/packages/nova-utils/docs/assets/split.css +15 -0
  764. package/packages/nova-utils/docs/assets/split.js +782 -0
  765. package/packages/nova-utils/docs/assets/style.css +147 -0
  766. package/packages/nova-utils/docs/index.html +986 -0
  767. package/packages/nova-utils/index.js +3 -0
  768. package/packages/nova-utils/package.json +19 -0
  769. package/packages/nova-utils/src/config.js +228 -0
  770. package/packages/nova-utils/src/logger.js +26 -0
  771. package/packages/nova-utils/src/tenant-utils.js +27 -0
  772. package/packages/nova-utils/test/config.test.js +250 -0
  773. package/packages/nova-utils/test/tenant-utiils.test.js +50 -0
  774. package/pnpm-workspace.yaml +2 -0
  775. package/rollup.config.js +13 -0
  776. package/scripts/.eslintrc.yaml +25 -0
  777. package/scripts/aggregate-docs.js +81 -0
  778. package/scripts/bump-version.js +26 -0
  779. package/scripts/create-index.js +30 -0
  780. package/scripts/create-library-template/README.md +5 -0
  781. package/scripts/create-library-template/package.json +19 -0
  782. package/scripts/create-library.js +62 -0
@@ -0,0 +1,28 @@
1
+ import { OAuthDriver } from './oauth.js';
2
+
3
+ /**
4
+ * KrakenDriver
5
+ */
6
+ export class KrakenDriver extends OAuthDriver {
7
+ constructor(configuration) {
8
+ super('kraken', configuration);
9
+ }
10
+
11
+ /**
12
+ * Upsert a user
13
+ * @param user
14
+ * @returns {Promise<Object>}
15
+ */
16
+ upsertUser(user) {
17
+ return this.put('/api/v2/users', user);
18
+ }
19
+
20
+ /**
21
+ * Upsert users
22
+ * @param users
23
+ * @returns {Promise<Object>}
24
+ */
25
+ upsertUsers(users) {
26
+ return this.put('/api/v2/users/bulk', { users });
27
+ }
28
+ }
@@ -0,0 +1,32 @@
1
+ import { DEFAULT_CONFIG } from './config.js';
2
+
3
+ /**
4
+ * NovaDriver class to provide a common interface for all drivers.
5
+
6
+ */
7
+ export class NovaDriver {
8
+
9
+ /**
10
+ * NovaDriver constructor.
11
+ * @param {Object} configOverrides - Configuration overrides for the Nova driver.
12
+ */
13
+ constructor(configOverrides = {}) {
14
+ this.config = { ...DEFAULT_CONFIG, ...configOverrides };
15
+ this.log = this.config.logger;
16
+ this.enabled = this.config.enabled;
17
+ this.novaRequestId = null;
18
+ }
19
+
20
+ /**
21
+ * Provides a way to override the context of the driver. Specifically useful for logging
22
+ * and sending requests making use of the `distributedLoggingMiddleware` and it's reliance
23
+ * on the http header `x-nova-request-id`
24
+ *
25
+ * @param novaRequestId - The unique id of the request to send to external services
26
+ * @param log - The provided logger to use
27
+ */
28
+ useContext({ novaRequestId, log }) {
29
+ this.novaRequestId = novaRequestId;
30
+ this.log = log || this.log;
31
+ }
32
+ }
@@ -0,0 +1,145 @@
1
+ import { ClientCredentials } from 'simple-oauth2';
2
+
3
+ import { HttpDriver } from './http.js';
4
+ import { ApiToken } from '../../nova-model/src/model/api-token.js';
5
+ import { apiTokenRepo } from '../../nova-model/src/repo/api-token.js';
6
+
7
+ import { secretsManager } from './aws/secrets-manager.js';
8
+
9
+ const TOKEN_EXPIRATION_WINDOW_SECONDS = 60;
10
+
11
+ /**
12
+ * OAuthClient class extends HttpDriver.
13
+ * This class is responsible for handling OAuth client operations.
14
+ *
15
+ * @extends HttpDriver
16
+ */
17
+ export class OAuthDriver extends HttpDriver {
18
+
19
+ /**
20
+ * Creates a new instance of the OAuthClient.
21
+ *
22
+ * *NOTE* The clientConfig object is passed directly to the simple-oauth2 library. The simle-oauth2 library doc can be found here:
23
+ * https://github.com/lelylan/simple-oauth2/blob/master/API.md
24
+ *
25
+ * @constructor
26
+ * @param {string} apiIdentifier - The API identifier.
27
+ * @param configuration
28
+ * @param {string} configuration.baseUrl - The base URL for making HTTP requests.
29
+ * @param {Object} configuration.tokenConfig - The token configuration
30
+ * @param {Object} configuration.oauth - The client configuration.
31
+ * @param {Object} configuration.oauth.client - The client details.
32
+ * @param {string} configuration.oauth.client.id - The client ID.
33
+ * @param {string} configuration.oauth.client.secret - The name of a secret stored in AWS Secret Manager.
34
+ * @param {string} [configuration.oauth.client.secretKeyId] - An optional id to retrieve a specific value from an AWS secret object.
35
+ * @param {Object} configuration.oauth.auth - The authentication details.
36
+ * @param {string} configuration.oauth.auth.tokenHost - The host for the token.
37
+ * @param {string} configuration.oauth.auth.tokenPath - The path for the token.
38
+ */
39
+ constructor(apiIdentifier, configuration = {}) {
40
+ const { baseUrl, oauth, tokenConfig } = configuration;
41
+ super(baseUrl, configuration);
42
+ this.log.info({ apiIdentifier, configuration }, 'OAuthClient - creating new instance');
43
+ this.clientConfig = oauth;
44
+ this.apiIdentifier = apiIdentifier;
45
+ this.accessToken = null;
46
+ this.clientCredentialsInstance = null;
47
+ this.tokenConfig = tokenConfig;
48
+ this.secretKey = oauth.client.secret;
49
+ this.secretKeyId = oauth.client.secretKeyId;
50
+ }
51
+
52
+ /**
53
+ * Retrieves the headers for the OAuth client, ensuring the access token is valid.
54
+ * @returns {Promise<Object>} The headers for the OAuth client.
55
+ */
56
+ async getHeaders() {
57
+ await this.ensureAccessToken();
58
+ this.log.trace(this.accessToken, 'OAuthClient - getHeaders, got token');
59
+ const { token } = this.accessToken;
60
+ return {
61
+ 'Content-Type': 'application/json',
62
+ Authorization: `${token.token_type} ${token.access_token}`,
63
+ };
64
+ }
65
+
66
+ /**
67
+ * Ensures the access token is valid, retrieving a stored token or a new token as necessary.
68
+ * @returns {Promise<Object>} The valid access token.
69
+ */
70
+ async ensureAccessToken() {
71
+ if (this.accessToken && !this.accessToken.expired(TOKEN_EXPIRATION_WINDOW_SECONDS)) {
72
+ return this.accessToken;
73
+ }
74
+
75
+ const storedToken = await this.getStoredToken();
76
+ if (storedToken && !storedToken.expired(TOKEN_EXPIRATION_WINDOW_SECONDS)) {
77
+ this.accessToken = storedToken;
78
+ return storedToken;
79
+ }
80
+
81
+ const newToken = await this.getNewToken();
82
+ await this.storeToken(newToken);
83
+ this.accessToken = newToken;
84
+ return newToken;
85
+ }
86
+
87
+ /**
88
+ * Retrieves a new token for the OAuth client.
89
+ * @returns {Promise<Object>} The new token.
90
+ */
91
+ async getNewToken() {
92
+ const client = await this.getClientInstance();
93
+ try {
94
+ this.log.info({ apiIdentifier: this.apiIdentifier, tokenConfig: this.tokenConfig }, 'OAuthClient - getting new token');
95
+ return await client.getToken(this.tokenConfig, { json: true });
96
+ } catch (error) {
97
+ this.log.error({ apiIdentifier: this.apiIdentifier, error: error.message }, 'OAuthClient - error getting new token');
98
+ throw error;
99
+ }
100
+ }
101
+
102
+ /**
103
+ * Retrieves a stored token for the OAuth client.
104
+ * @returns {Promise<Object>} The stored token.
105
+ */
106
+ async getStoredToken() {
107
+ const client = await this.getClientInstance();
108
+ try {
109
+ const storedTokenData = await apiTokenRepo.get({ apiIdentifier: this.apiIdentifier });
110
+ const tokenJson = JSON.parse(storedTokenData.token);
111
+ return client.createToken(tokenJson);
112
+ } catch (error) {
113
+ this.log.warn({ apiIdentifier: this.apiIdentifier, error: error.message }, 'OAuthClient - could not retrieve existing token');
114
+ return undefined;
115
+ }
116
+ }
117
+
118
+ /**
119
+ * Stores a token for the OAuth client.
120
+ * @param {Object} token - The token to store.
121
+ * @returns {Promise<void>}
122
+ */
123
+ async storeToken(token) {
124
+ const tokenData = new ApiToken({
125
+ apiIdentifier: this.apiIdentifier,
126
+ token: JSON.stringify(token),
127
+ ttl: token.token.expires_in,
128
+ });
129
+ await apiTokenRepo.save(tokenData);
130
+ }
131
+
132
+ /**
133
+ * Retrieves an instance of the ClientCredentials class for the OAuth client.
134
+ * @returns {Promise<ClientCredentials>} The ClientCredentials instance.
135
+ */
136
+ async getClientInstance() {
137
+ if (this.clientCredentialsInstance) {
138
+ return this.clientCredentialsInstance;
139
+ }
140
+ if (this.secretKey) this.clientConfig.client.secret = await secretsManager.getSecret(this.secretKey, this.secretKeyId);
141
+ delete this.clientConfig.client.secretKeyId;
142
+ this.clientCredentialsInstance = new ClientCredentials(this.clientConfig);
143
+ return this.clientCredentialsInstance;
144
+ }
145
+ }
@@ -0,0 +1,83 @@
1
+ import { usersBelongToSameTenant } from '../../nova-utils/index.js';
2
+ import { OAuthDriver } from './oauth.js';
3
+
4
+ /**
5
+ * WaveDriver class to simplify making HTTP requests to a Wave API.
6
+ * Inherits from HttpDriver for basic HTTP request functionalities.
7
+ */
8
+ export class WaveDriver extends OAuthDriver {
9
+
10
+ /**
11
+ * Constructs a new WaveDriver instance.
12
+ *
13
+ * @param {Object} configuration - The configuration object for the WaveDriver.
14
+ * @example
15
+ * ```
16
+ * new WaveDriver({
17
+ * wave: {
18
+ * baseUrl: 'https://wave.example.com',
19
+ * enabled: true
20
+ * ...
21
+ * },
22
+ * });
23
+ * ```
24
+ **/
25
+ constructor(configuration) {
26
+ super('wave', configuration);
27
+ }
28
+
29
+ /**
30
+ * Upserts users in the Wave platform. If a user already exists, they will be updated.
31
+ * Refuses to upsert if users belong to multiple tenants.
32
+ *
33
+ * @param {Array<Object>} users - An array of user objects to be upserted.
34
+ * @returns {Promise<Object|undefined>} A promise that resolves to an empty object if successful, or is rejected if an error occurs.
35
+ * If the Wave driver is disabled or users belong to multiple tenants, the promise resolves to `undefined`.
36
+ */
37
+ async upsertUsers(users) {
38
+
39
+ // We expect only 1 tenant id for all the users
40
+ if (!usersBelongToSameTenant(users)) {
41
+ this.log.error('Refusing to upsert users in wave for multiple tenants');
42
+ return;
43
+ }
44
+
45
+ const url = '/api/v2/users/bulk';
46
+
47
+ this.log.debug({ 'users': users, 'url': url }, 'Upserting users in Wave');
48
+ const response = await this.post(url, { users }, {});
49
+
50
+ const { success, body, error } = response;
51
+
52
+ if (response.success) {
53
+ this.log.info({ 'response': { success, body } }, 'Users upserted in wave');
54
+ } else {
55
+ this.log.error({ 'response': { success, error } }, 'Failed to upsert users in wave');
56
+ throw new Error(`Failed to upsert users in Wave: ${error}`);
57
+ }
58
+ }
59
+
60
+ /**
61
+ * Gets a tenant object from the Wave platform
62
+ *
63
+ * @param tenantId the guid of the tenant
64
+ * @returns {Promise<*>} the tenant object
65
+ */
66
+ async getTenant(tenantId) {
67
+ const url = `/api/v2/tenants/${tenantId}`;
68
+
69
+ this.log.debug({ tenantId, url }, 'Getting tenant from Wave');
70
+ const response = await this.get(url, {});
71
+
72
+ const { success, body, error } = response;
73
+
74
+ if (response.success) {
75
+ this.log.info({ 'response': { success, body } }, 'Tenant retrieved from wave');
76
+ return body;
77
+ } else {
78
+ this.log.error({ 'response': { success, error } }, 'Failed to retrieve tenant from wave');
79
+ throw new Error(`Failed to retrieve tenant from Wave: ${error}`);
80
+ }
81
+
82
+ }
83
+ }
@@ -0,0 +1,27 @@
1
+ extends:
2
+ - brightspace/testing-config
3
+
4
+ rules:
5
+ indent:
6
+ - error
7
+ - 2
8
+ - SwitchCase: 1
9
+ no-console:
10
+ - off
11
+ sort-imports:
12
+ - error
13
+ - ignoreCase: true
14
+ ignoreDeclarationSort: false
15
+ ignoreMemberSort: false
16
+ memberSyntaxSortOrder:
17
+ - none
18
+ - all
19
+ - multiple
20
+ - single
21
+ allowSeparatedGroups: true
22
+ import/no-extraneous-dependencies:
23
+ - error
24
+ - devDependencies:
25
+ - "**/test/**/*.js"
26
+ - "**/*.spec.js"
27
+ - "**/*.test.js"
@@ -0,0 +1,119 @@
1
+ import { expect } from 'chai';
2
+
3
+ // eslint-disable-next-line import/no-extraneous-dependencies
4
+ import sinon from 'sinon';
5
+
6
+ import { DynamoDBDocumentClient } from '@aws-sdk/lib-dynamodb';
7
+ import { DynamoDbDriver } from '../../src/aws/dynamodb.js';
8
+
9
+ describe('DynamoDb', () => {
10
+ let dynamoDbInstance;
11
+ let sandbox;
12
+ let mockClient;
13
+
14
+ beforeEach(() => {
15
+ sandbox = sinon.createSandbox();
16
+ mockClient = {
17
+ send: sandbox.stub().resolves({}),
18
+ };
19
+ sandbox.stub(DynamoDBDocumentClient, 'from').returns(mockClient);
20
+ dynamoDbInstance = new DynamoDbDriver({});
21
+ });
22
+
23
+ afterEach(() => {
24
+ sandbox.restore();
25
+ });
26
+
27
+ describe('put', () => {
28
+ it('should call the put method of the DynamoDB client', async() => {
29
+ const params = { TableName: 'testTable', Item: { id: '1', value: 'test' } };
30
+
31
+ await dynamoDbInstance.put(params);
32
+
33
+ expect(mockClient.send.calledOnce).to.be.true;
34
+ // Ensure the PutCommand was instantiated with the correct parameters
35
+ const [putCommand] = mockClient.send.firstCall.args;
36
+ expect(putCommand.input).to.deep.equal(params);
37
+ });
38
+ });
39
+
40
+ describe('get', () => {
41
+ it('should call the get method of the DynamoDB client', async() => {
42
+ const params = { TableName: 'testTable', Key: { id: '1' } };
43
+
44
+ await dynamoDbInstance.get(params);
45
+
46
+ expect(mockClient.send.calledOnce).to.be.true;
47
+ const [getCommand] = mockClient.send.firstCall.args;
48
+ expect(getCommand.input).to.deep.equal(params);
49
+ });
50
+ });
51
+
52
+ describe('batchGet', () => {
53
+ it('should process batch get requests', async() => {
54
+ const params = {
55
+ RequestItems: {
56
+ 'testTable': {
57
+ Keys: [{ id: '1' }, { id: '2' }],
58
+ },
59
+ },
60
+ };
61
+ mockClient.send.resolves({
62
+ Responses: { 'testTable': [{ id: '1', value: 'item1' }, { id: '2', value: 'item2' }] },
63
+ UnprocessedKeys: {},
64
+ });
65
+
66
+ const result = await dynamoDbInstance.batchGet(params);
67
+
68
+ expect(result).to.have.property('Responses').that.is.an('object');
69
+ expect(result.Responses['testTable']).to.have.lengthOf(2);
70
+ });
71
+ });
72
+
73
+ describe('delete', () => {
74
+ it('should call the delete method of the DynamoDB client', async() => {
75
+ const params = { TableName: 'testTable', Key: { id: '1' } };
76
+
77
+ await dynamoDbInstance.delete(params);
78
+
79
+ expect(mockClient.send.calledOnce).to.be.true;
80
+ const [deleteCommand] = mockClient.send.firstCall.args;
81
+ expect(deleteCommand.input).to.deep.equal(params);
82
+ });
83
+ });
84
+
85
+ describe('query', () => {
86
+ it('should call the query method of the DynamoDB client', async() => {
87
+ const params = { TableName: 'testTable', KeyConditionExpression: 'id = :id', ExpressionAttributeValues: { ':id': '1' } };
88
+
89
+ await dynamoDbInstance.query(params);
90
+
91
+ expect(mockClient.send.calledOnce).to.be.true;
92
+ const [queryCommand] = mockClient.send.firstCall.args;
93
+ expect(queryCommand.input).to.deep.equal(params);
94
+ });
95
+ });
96
+
97
+ describe('getAllResultsRecursive', () => {
98
+ it('should recursively fetch all items', async() => {
99
+ const params = { TableName: 'testTable', KeyConditionExpression: 'id = :id', ExpressionAttributeValues: { ':id': '1' } };
100
+ const itemsPage1 = Array(10).fill(null).map((_, index) => ({ id: `1-${index}` }));
101
+ const itemsPage2 = Array(5).fill(null).map((_, index) => ({ id: `2-${index}` }));
102
+
103
+ // Setup stub to simulate paginated response
104
+ mockClient.send.onFirstCall().resolves({
105
+ Items: itemsPage1,
106
+ LastEvaluatedKey: { id: '1-9' },
107
+ }).onSecondCall().resolves({
108
+ Items: itemsPage2,
109
+ LastEvaluatedKey: null, // Indicate no more pages
110
+ });
111
+
112
+ const results = await dynamoDbInstance.getAllResultsRecursive(params, [], undefined, 0, 0);
113
+
114
+ expect(results.length).to.equal(15);
115
+ expect(results).to.deep.include.members(itemsPage1);
116
+ expect(results).to.deep.include.members(itemsPage2);
117
+ });
118
+ });
119
+ });
@@ -0,0 +1,146 @@
1
+ // Import the necessary libraries
2
+ import { expect } from 'chai';
3
+ import sinon from 'sinon';
4
+ import { GetSecretValueCommand, SecretsManagerClient } from '@aws-sdk/client-secrets-manager';
5
+
6
+ import { SecretsManager } from '../../src/aws/secrets-manager.js';
7
+
8
+ describe('SecretsManager', () => {
9
+ let secretsManager;
10
+ let stubSend;
11
+
12
+ beforeEach(() => {
13
+ // Initialize the SecretsManager instance
14
+ secretsManager = new SecretsManager();
15
+
16
+ // Stub the send method of SecretsManagerClient
17
+ stubSend = sinon.stub(SecretsManagerClient.prototype, 'send');
18
+ });
19
+
20
+ afterEach(() => {
21
+ // Restore the stubbed send method to its original state
22
+ sinon.restore();
23
+ });
24
+
25
+ it('should fetch and return the correct secret value', async() => {
26
+ const secretName = 'testSecret';
27
+ const secretValue = 'secretValue';
28
+ const secretString = JSON.stringify({ [secretValue]: 'TestValue' });
29
+
30
+ stubSend.resolves({
31
+ SecretString: secretString,
32
+ });
33
+
34
+ const result = await secretsManager.getSecret(secretName);
35
+ expect(result).to.equal('TestValue');
36
+ });
37
+
38
+ it('should throw an error if secretName is not provided', async() => {
39
+ try {
40
+ await secretsManager.getSecret();
41
+ } catch (error) {
42
+ expect(error.message).to.equal('Missing secret name to fetch secret');
43
+ }
44
+ });
45
+
46
+ it('should handle and rethrow AWS SDK errors', async() => {
47
+ const secretName = 'invalidSecret';
48
+ stubSend.rejects(new Error('The requested secret does not exist'));
49
+
50
+ try {
51
+ await secretsManager.getSecret(secretName);
52
+ } catch (error) {
53
+ expect(error.message).to.include('SecretsManager: The requested secret does not exist');
54
+ }
55
+ });
56
+
57
+ it('should return the entire secret object if keyId is "allKeys"', async() => {
58
+ const secretName = 'complexSecret';
59
+ const secretObject = { key1: 'value1', key2: 'value2', key3: 'value3' };
60
+ const secretString = JSON.stringify(secretObject);
61
+
62
+ stubSend.resolves({
63
+ SecretString: secretString,
64
+ });
65
+
66
+ const result = await secretsManager.getSecret(secretName, 'allKeys');
67
+ expect(result).to.deep.equal(secretObject);
68
+ });
69
+
70
+ it('should return a specific key-value pair from the secret', async() => {
71
+ const secretName = 'specificKeySecret';
72
+ const secretObject = { specificKey: 'specificValue', otherKey: 'otherValue' };
73
+ const secretString = JSON.stringify(secretObject);
74
+
75
+ stubSend.resolves({
76
+ SecretString: secretString,
77
+ });
78
+
79
+ const result = await secretsManager.getSecret(secretName, 'specificKey');
80
+ expect(result).to.equal('specificValue');
81
+ });
82
+
83
+ it('should return the prod specific value if in production environment', async() => {
84
+ // Simulate production environment
85
+ secretsManager.isProdEnvironment = true;
86
+ const secretName = 'envSpecificSecret';
87
+ const secretObject = { dev: 'devValue', prod: 'prodValue' };
88
+ const secretString = JSON.stringify(secretObject);
89
+
90
+ stubSend.resolves({
91
+ SecretString: secretString,
92
+ });
93
+
94
+ const result = await secretsManager.getSecret(secretName);
95
+ expect(result).to.equal('prodValue');
96
+ });
97
+
98
+ it('should return the dev specific value if not in production environment', async() => {
99
+ // Ensure non-production environment
100
+ secretsManager.isProdEnvironment = false;
101
+ const secretName = 'envSpecificSecret';
102
+ const secretObject = { dev: 'devValue', unused: 'unusedValue' };
103
+ const secretString = JSON.stringify(secretObject);
104
+
105
+ stubSend.resolves({
106
+ SecretString: secretString,
107
+ });
108
+
109
+ const result = await secretsManager.getSecret(secretName);
110
+ expect(result).to.equal('devValue');
111
+ });
112
+
113
+ it('should throw an error if the specified keyId does not exist in the secret', async() => {
114
+ const secretName = 'missingKeySecret';
115
+ const secretObject = { existingKey: 'existingValue' };
116
+ const secretString = JSON.stringify(secretObject);
117
+
118
+ stubSend.resolves({
119
+ SecretString: secretString,
120
+ });
121
+
122
+ try {
123
+ await secretsManager.getSecret(secretName, 'nonExistingKey');
124
+ } catch (error) {
125
+ expect(error.message).to.equal('SecretsManager: nonExistingKey does not exist');
126
+ }
127
+ });
128
+
129
+ it('should log the error before rethrowing', async() => {
130
+ const secretName = 'erroredSecret';
131
+ const errorMessage = 'Simulated failure';
132
+ stubSend.rejects(new Error(errorMessage));
133
+
134
+ const logSpy = sinon.spy(console, 'log');
135
+
136
+ try {
137
+ await secretsManager.getSecret(secretName);
138
+ } catch (error) {
139
+ // The error should be logged before being rethrown
140
+ sinon.assert.calledWith(logSpy, sinon.match.instanceOf(Error));
141
+ expect(error.message).to.include(`SecretsManager: ${errorMessage}`);
142
+ } finally {
143
+ logSpy.restore();
144
+ }
145
+ });
146
+ });