@transcend-io/cli 10.23.7 → 10.24.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 (191) hide show
  1. package/README.md +4 -149
  2. package/dist/{app-BV8ug_1A.mjs → app-1gLg-ah3.mjs} +19 -19
  3. package/dist/{app-BV8ug_1A.mjs.map → app-1gLg-ah3.mjs.map} +1 -1
  4. package/dist/{approvePrivacyRequests-BQpI-RdX.mjs → approvePrivacyRequests-qaoxGH11.mjs} +2 -2
  5. package/dist/{approvePrivacyRequests-BQpI-RdX.mjs.map → approvePrivacyRequests-qaoxGH11.mjs.map} +1 -1
  6. package/dist/bin/bash-complete.mjs +1 -1
  7. package/dist/bin/cli.mjs +1 -1
  8. package/dist/bin/deprecated-command.mjs +1 -1
  9. package/dist/{buildExamples-BUaHx4F1.mjs → buildExamples-CDlFYuEg.mjs} +2 -2
  10. package/dist/{buildExamples-BUaHx4F1.mjs.map → buildExamples-CDlFYuEg.mjs.map} +1 -1
  11. package/dist/{buildXdiSyncEndpoint-CI91Blyp.mjs → buildXdiSyncEndpoint-Bmr-hWLk.mjs} +2 -2
  12. package/dist/{buildXdiSyncEndpoint-CI91Blyp.mjs.map → buildXdiSyncEndpoint-Bmr-hWLk.mjs.map} +1 -1
  13. package/dist/{bulkRestartRequests-0VBrEHER.mjs → bulkRestartRequests-n2_EwVEM.mjs} +2 -2
  14. package/dist/{bulkRestartRequests-0VBrEHER.mjs.map → bulkRestartRequests-n2_EwVEM.mjs.map} +1 -1
  15. package/dist/{bulkRetryEnrichers-D7t7iYbi.mjs → bulkRetryEnrichers-DDftLRtp.mjs} +2 -2
  16. package/dist/{bulkRetryEnrichers-D7t7iYbi.mjs.map → bulkRetryEnrichers-DDftLRtp.mjs.map} +1 -1
  17. package/dist/{cancelPrivacyRequests-DvQL3z2K.mjs → cancelPrivacyRequests-CunKdVs6.mjs} +2 -2
  18. package/dist/{cancelPrivacyRequests-DvQL3z2K.mjs.map → cancelPrivacyRequests-CunKdVs6.mjs.map} +1 -1
  19. package/dist/codecs-HQHBtqht.mjs +2 -0
  20. package/dist/codecs-HQHBtqht.mjs.map +1 -0
  21. package/dist/{command-Bq17gJPJ.mjs → command-DO9AWMvB.mjs} +2 -2
  22. package/dist/{command-Bq17gJPJ.mjs.map → command-DO9AWMvB.mjs.map} +1 -1
  23. package/dist/{constants-ykNINvFg.mjs → constants-C9xZJ9YW.mjs} +2 -2
  24. package/dist/{constants-ykNINvFg.mjs.map → constants-C9xZJ9YW.mjs.map} +1 -1
  25. package/dist/{constants-B44yUGaB.mjs → constants-DNF09zFX.mjs} +3 -3
  26. package/dist/{constants-B44yUGaB.mjs.map → constants-DNF09zFX.mjs.map} +1 -1
  27. package/dist/constants-DR-hU9Xj.mjs +2 -0
  28. package/dist/constants-DR-hU9Xj.mjs.map +1 -0
  29. package/dist/{createExtraKeyHandler-DHhGPEWE.mjs → createExtraKeyHandler-DTbSbhrp.mjs} +2 -2
  30. package/dist/{createExtraKeyHandler-DHhGPEWE.mjs.map → createExtraKeyHandler-DTbSbhrp.mjs.map} +1 -1
  31. package/dist/{downloadPrivacyRequestFiles-Dtnhb3v2.mjs → downloadPrivacyRequestFiles-AArYL4OL.mjs} +2 -2
  32. package/dist/{downloadPrivacyRequestFiles-Dtnhb3v2.mjs.map → downloadPrivacyRequestFiles-AArYL4OL.mjs.map} +1 -1
  33. package/dist/enums-UlIe_AeF.mjs +2 -0
  34. package/dist/enums-UlIe_AeF.mjs.map +1 -0
  35. package/dist/{fetchAllRequests-Bya6iwzL.mjs → fetchAllRequests-DP24WqrP.mjs} +2 -2
  36. package/dist/{fetchAllRequests-Bya6iwzL.mjs.map → fetchAllRequests-DP24WqrP.mjs.map} +1 -1
  37. package/dist/{fuzzyMatchColumns-Ds0TqtJ5.mjs → fuzzyMatchColumns-C1STZ_T1.mjs} +2 -2
  38. package/dist/{fuzzyMatchColumns-Ds0TqtJ5.mjs.map → fuzzyMatchColumns-C1STZ_T1.mjs.map} +1 -1
  39. package/dist/{generateCrossAccountApiKeys-CTVfbS9-.mjs → generateCrossAccountApiKeys-DfGJ8Svq.mjs} +2 -2
  40. package/dist/{generateCrossAccountApiKeys-CTVfbS9-.mjs.map → generateCrossAccountApiKeys-DfGJ8Svq.mjs.map} +1 -1
  41. package/dist/{impl-D1X9qygD2.mjs → impl-4heSgrC92.mjs} +2 -2
  42. package/dist/{impl-D1X9qygD2.mjs.map → impl-4heSgrC92.mjs.map} +1 -1
  43. package/dist/{impl-Wyz88FnA2.mjs → impl-4oiDSr3J2.mjs} +2 -2
  44. package/dist/{impl-Wyz88FnA2.mjs.map → impl-4oiDSr3J2.mjs.map} +1 -1
  45. package/dist/{impl-Bug3axux.mjs → impl-8gLOHK9a.mjs} +2 -2
  46. package/dist/{impl-Bug3axux.mjs.map → impl-8gLOHK9a.mjs.map} +1 -1
  47. package/dist/{impl-BPlwQGJw.mjs → impl-B6kpEx0X.mjs} +2 -2
  48. package/dist/{impl-BPlwQGJw.mjs.map → impl-B6kpEx0X.mjs.map} +1 -1
  49. package/dist/{impl-C5RWQxAV.mjs → impl-BF9Ekyjn.mjs} +2 -2
  50. package/dist/{impl-C5RWQxAV.mjs.map → impl-BF9Ekyjn.mjs.map} +1 -1
  51. package/dist/{impl-BfEBQCDY2.mjs → impl-BVh3JHAk2.mjs} +2 -2
  52. package/dist/{impl-BfEBQCDY2.mjs.map → impl-BVh3JHAk2.mjs.map} +1 -1
  53. package/dist/{impl-DJ37yGAw2.mjs → impl-BYtnm2cU2.mjs} +2 -2
  54. package/dist/{impl-DJ37yGAw2.mjs.map → impl-BYtnm2cU2.mjs.map} +1 -1
  55. package/dist/{impl-Ctagwhzp.mjs → impl-BZ-EmLtv.mjs} +2 -2
  56. package/dist/{impl-Ctagwhzp.mjs.map → impl-BZ-EmLtv.mjs.map} +1 -1
  57. package/dist/{impl-BjlpBG3U.mjs → impl-BZ4pxOP_.mjs} +2 -2
  58. package/dist/{impl-BjlpBG3U.mjs.map → impl-BZ4pxOP_.mjs.map} +1 -1
  59. package/dist/{impl-CdZ-nr1b.mjs → impl-Bgg6AZQS.mjs} +4 -4
  60. package/dist/{impl-CdZ-nr1b.mjs.map → impl-Bgg6AZQS.mjs.map} +1 -1
  61. package/dist/{impl-rOo6vhkj.mjs → impl-Bu7iHn-Z.mjs} +2 -2
  62. package/dist/{impl-rOo6vhkj.mjs.map → impl-Bu7iHn-Z.mjs.map} +1 -1
  63. package/dist/{impl-BbIP694E.mjs → impl-BvLjryD7.mjs} +2 -2
  64. package/dist/{impl-BbIP694E.mjs.map → impl-BvLjryD7.mjs.map} +1 -1
  65. package/dist/{impl-BBtHggqa2.mjs → impl-C3-twUUE2.mjs} +2 -2
  66. package/dist/{impl-BBtHggqa2.mjs.map → impl-C3-twUUE2.mjs.map} +1 -1
  67. package/dist/{impl-BXgq2IRf2.mjs → impl-C6eLQ_5o2.mjs} +2 -2
  68. package/dist/{impl-BXgq2IRf2.mjs.map → impl-C6eLQ_5o2.mjs.map} +1 -1
  69. package/dist/{impl-9b_P5Q4s.mjs → impl-C7-Z-9EZ.mjs} +2 -2
  70. package/dist/{impl-9b_P5Q4s.mjs.map → impl-C7-Z-9EZ.mjs.map} +1 -1
  71. package/dist/{impl-CiA-v1ol.mjs → impl-C8azdMaD.mjs} +2 -2
  72. package/dist/{impl-CiA-v1ol.mjs.map → impl-C8azdMaD.mjs.map} +1 -1
  73. package/dist/{impl-D-RKBMCp.mjs → impl-CIJjwRW4.mjs} +2 -2
  74. package/dist/{impl-D-RKBMCp.mjs.map → impl-CIJjwRW4.mjs.map} +1 -1
  75. package/dist/{impl-DqtLjqiN.mjs → impl-Cqruzptc.mjs} +2 -2
  76. package/dist/{impl-DqtLjqiN.mjs.map → impl-Cqruzptc.mjs.map} +1 -1
  77. package/dist/{impl-z5dBnPm5.mjs → impl-CtbuXbCF.mjs} +3 -3
  78. package/dist/{impl-z5dBnPm5.mjs.map → impl-CtbuXbCF.mjs.map} +1 -1
  79. package/dist/{impl-D1c3dsHI.mjs → impl-CymJoQ9l.mjs} +2 -2
  80. package/dist/{impl-D1c3dsHI.mjs.map → impl-CymJoQ9l.mjs.map} +1 -1
  81. package/dist/{impl-BWenu3QG.mjs → impl-D-JYZ74k.mjs} +6 -6
  82. package/dist/{impl-BWenu3QG.mjs.map → impl-D-JYZ74k.mjs.map} +1 -1
  83. package/dist/impl-D53J7hI_.mjs +2 -0
  84. package/dist/{impl-CyhHVprA.mjs.map → impl-D53J7hI_.mjs.map} +1 -1
  85. package/dist/{impl-C69Nh_YS.mjs → impl-D9VysVCe.mjs} +2 -2
  86. package/dist/{impl-C69Nh_YS.mjs.map → impl-D9VysVCe.mjs.map} +1 -1
  87. package/dist/{impl-DMtn2boK.mjs → impl-DUHcGmOB.mjs} +2 -2
  88. package/dist/{impl-DMtn2boK.mjs.map → impl-DUHcGmOB.mjs.map} +1 -1
  89. package/dist/impl-DgkExXp2.mjs +2 -0
  90. package/dist/{impl-DQ-kymSs.mjs.map → impl-DgkExXp2.mjs.map} +1 -1
  91. package/dist/{impl-B5-BwYN92.mjs → impl-DjgE9MBH2.mjs} +2 -2
  92. package/dist/{impl-B5-BwYN92.mjs.map → impl-DjgE9MBH2.mjs.map} +1 -1
  93. package/dist/{impl-veZF32mx2.mjs → impl-Dniv3dkB2.mjs} +2 -2
  94. package/dist/{impl-veZF32mx2.mjs.map → impl-Dniv3dkB2.mjs.map} +1 -1
  95. package/dist/{impl-B0bOfWq32.mjs → impl-DtJCihfL2.mjs} +2 -2
  96. package/dist/{impl-B0bOfWq32.mjs.map → impl-DtJCihfL2.mjs.map} +1 -1
  97. package/dist/{impl-DREUe83K2.mjs → impl-E2edQft02.mjs} +2 -2
  98. package/dist/{impl-DREUe83K2.mjs.map → impl-E2edQft02.mjs.map} +1 -1
  99. package/dist/{impl--vtVpVpr2.mjs → impl-GnoT1LmK2.mjs} +2 -2
  100. package/dist/{impl--vtVpVpr2.mjs.map → impl-GnoT1LmK2.mjs.map} +1 -1
  101. package/dist/{impl-B2LrNhxI2.mjs → impl-HaxoPgWV2.mjs} +2 -2
  102. package/dist/{impl-B2LrNhxI2.mjs.map → impl-HaxoPgWV2.mjs.map} +1 -1
  103. package/dist/{impl-CwQ9tdkG.mjs → impl-N_erRf2y.mjs} +2 -2
  104. package/dist/{impl-CwQ9tdkG.mjs.map → impl-N_erRf2y.mjs.map} +1 -1
  105. package/dist/{impl-DUn7OYtx.mjs → impl-SESkv0Uk.mjs} +2 -2
  106. package/dist/{impl-DUn7OYtx.mjs.map → impl-SESkv0Uk.mjs.map} +1 -1
  107. package/dist/{impl-C5cGjdOA2.mjs → impl-SauDltth2.mjs} +2 -2
  108. package/dist/{impl-C5cGjdOA2.mjs.map → impl-SauDltth2.mjs.map} +1 -1
  109. package/dist/{impl-Be7F4ZrH2.mjs → impl-T66dFrc42.mjs} +2 -2
  110. package/dist/{impl-Be7F4ZrH2.mjs.map → impl-T66dFrc42.mjs.map} +1 -1
  111. package/dist/{impl-Bvk9QYS0.mjs → impl-U_CtHEj5.mjs} +2 -2
  112. package/dist/{impl-Bvk9QYS0.mjs.map → impl-U_CtHEj5.mjs.map} +1 -1
  113. package/dist/{impl-BBx1Kx8M.mjs → impl-Y2Gge5Bd.mjs} +2 -2
  114. package/dist/{impl-BBx1Kx8M.mjs.map → impl-Y2Gge5Bd.mjs.map} +1 -1
  115. package/dist/{impl-BfVQRJEl2.mjs → impl-dcRplDpN2.mjs} +2 -2
  116. package/dist/{impl-BfVQRJEl2.mjs.map → impl-dcRplDpN2.mjs.map} +1 -1
  117. package/dist/{impl-BmoyPAJJ.mjs → impl-gfNcn8cd.mjs} +2 -2
  118. package/dist/{impl-BmoyPAJJ.mjs.map → impl-gfNcn8cd.mjs.map} +1 -1
  119. package/dist/{impl-C7ULQEpk2.mjs → impl-nikMH0CU2.mjs} +2 -2
  120. package/dist/{impl-C7ULQEpk2.mjs.map → impl-nikMH0CU2.mjs.map} +1 -1
  121. package/dist/{impl-Bj7Sb_7k2.mjs → impl-qSB65eS52.mjs} +2 -2
  122. package/dist/{impl-Bj7Sb_7k2.mjs.map → impl-qSB65eS52.mjs.map} +1 -1
  123. package/dist/{impl-BKMx2xOY.mjs → impl-vQQfP_hX.mjs} +2 -2
  124. package/dist/{impl-BKMx2xOY.mjs.map → impl-vQQfP_hX.mjs.map} +1 -1
  125. package/dist/{impl-DtlyH0Ku.mjs → impl-y9YssNt_.mjs} +2 -2
  126. package/dist/{impl-DtlyH0Ku.mjs.map → impl-y9YssNt_.mjs.map} +1 -1
  127. package/dist/index.d.mts +4 -562
  128. package/dist/index.d.mts.map +1 -1
  129. package/dist/index.mjs +4 -4
  130. package/dist/index.mjs.map +1 -1
  131. package/dist/{inquirer-AEchly0b.mjs → inquirer-B0OF_nRe.mjs} +2 -2
  132. package/dist/{inquirer-AEchly0b.mjs.map → inquirer-B0OF_nRe.mjs.map} +1 -1
  133. package/dist/{markRequestDataSiloIdsCompleted-gl4RNpl7.mjs → markRequestDataSiloIdsCompleted-CklEg1h9.mjs} +2 -2
  134. package/dist/{markRequestDataSiloIdsCompleted-gl4RNpl7.mjs.map → markRequestDataSiloIdsCompleted-CklEg1h9.mjs.map} +1 -1
  135. package/dist/{markSilentPrivacyRequests-Bvcdqy0L.mjs → markSilentPrivacyRequests-C_Fc81_k.mjs} +2 -2
  136. package/dist/{markSilentPrivacyRequests-Bvcdqy0L.mjs.map → markSilentPrivacyRequests-C_Fc81_k.mjs.map} +1 -1
  137. package/dist/{notifyPrivacyRequestsAdditionalTime-D8YT0K-a.mjs → notifyPrivacyRequestsAdditionalTime-DEb7lcKx.mjs} +2 -2
  138. package/dist/{notifyPrivacyRequestsAdditionalTime-D8YT0K-a.mjs.map → notifyPrivacyRequestsAdditionalTime-DEb7lcKx.mjs.map} +1 -1
  139. package/dist/parseVariablesFromString-6ZwJyWSu.mjs +3 -0
  140. package/dist/parseVariablesFromString-6ZwJyWSu.mjs.map +1 -0
  141. package/dist/{pullChunkedCustomSiloOutstandingIdentifiers-MuvYnFIK.mjs → pullChunkedCustomSiloOutstandingIdentifiers-DcSSx712.mjs} +2 -2
  142. package/dist/{pullChunkedCustomSiloOutstandingIdentifiers-MuvYnFIK.mjs.map → pullChunkedCustomSiloOutstandingIdentifiers-DcSSx712.mjs.map} +1 -1
  143. package/dist/{pullManualEnrichmentIdentifiersToCsv-HQSnLyVf.mjs → pullManualEnrichmentIdentifiersToCsv-CEtJleqX.mjs} +2 -2
  144. package/dist/{pullManualEnrichmentIdentifiersToCsv-HQSnLyVf.mjs.map → pullManualEnrichmentIdentifiersToCsv-CEtJleqX.mjs.map} +1 -1
  145. package/dist/pullTranscendConfiguration-C21Yq51h.mjs +58 -0
  146. package/dist/pullTranscendConfiguration-C21Yq51h.mjs.map +1 -0
  147. package/dist/{pushCronIdentifiersFromCsv-C4QfGxME.mjs → pushCronIdentifiersFromCsv-dCDnCM6Y.mjs} +2 -2
  148. package/dist/{pushCronIdentifiersFromCsv-C4QfGxME.mjs.map → pushCronIdentifiersFromCsv-dCDnCM6Y.mjs.map} +1 -1
  149. package/dist/{pushManualEnrichmentIdentifiersFromCsv-NqWFouaI.mjs → pushManualEnrichmentIdentifiersFromCsv-D6tsUf6k.mjs} +2 -2
  150. package/dist/{pushManualEnrichmentIdentifiersFromCsv-NqWFouaI.mjs.map → pushManualEnrichmentIdentifiersFromCsv-D6tsUf6k.mjs.map} +1 -1
  151. package/dist/readCsv--FfP8n-H.mjs +2 -0
  152. package/dist/{readCsv-C84Jhrzx.mjs.map → readCsv--FfP8n-H.mjs.map} +1 -1
  153. package/dist/{readTranscendYaml-dI3G3Og9.mjs → readTranscendYaml-CWIS9ki1.mjs} +3 -3
  154. package/dist/{readTranscendYaml-dI3G3Og9.mjs.map → readTranscendYaml-CWIS9ki1.mjs.map} +1 -1
  155. package/dist/{removeUnverifiedRequestIdentifiers-C4G6EUc9.mjs → removeUnverifiedRequestIdentifiers-kGR-7H8G.mjs} +2 -2
  156. package/dist/{removeUnverifiedRequestIdentifiers-C4G6EUc9.mjs.map → removeUnverifiedRequestIdentifiers-kGR-7H8G.mjs.map} +1 -1
  157. package/dist/{retryRequestDataSilos-B4h0Efcq.mjs → retryRequestDataSilos-d8gzmd-2.mjs} +2 -2
  158. package/dist/{retryRequestDataSilos-B4h0Efcq.mjs.map → retryRequestDataSilos-d8gzmd-2.mjs.map} +1 -1
  159. package/dist/{skipPreflightJobs-D9eKsCzH.mjs → skipPreflightJobs-B7C-mjSV.mjs} +2 -2
  160. package/dist/{skipPreflightJobs-D9eKsCzH.mjs.map → skipPreflightJobs-B7C-mjSV.mjs.map} +1 -1
  161. package/dist/{skipRequestDataSilos-4shablHf.mjs → skipRequestDataSilos-B5m8luWz.mjs} +2 -2
  162. package/dist/{skipRequestDataSilos-4shablHf.mjs.map → skipRequestDataSilos-B5m8luWz.mjs.map} +1 -1
  163. package/dist/{streamPrivacyRequestsToCsv-5Lv4Vchx.mjs → streamPrivacyRequestsToCsv-HwUKG1kF.mjs} +2 -2
  164. package/dist/{streamPrivacyRequestsToCsv-5Lv4Vchx.mjs.map → streamPrivacyRequestsToCsv-HwUKG1kF.mjs.map} +1 -1
  165. package/dist/{updateConsentManagerVersionToLatest-CeEs3OJT.mjs → updateConsentManagerVersionToLatest-B9RIn1o-.mjs} +2 -2
  166. package/dist/{updateConsentManagerVersionToLatest-CeEs3OJT.mjs.map → updateConsentManagerVersionToLatest-B9RIn1o-.mjs.map} +1 -1
  167. package/dist/{uploadConsents-Z0N-ULVA.mjs → uploadConsents-Cbn0O4fM.mjs} +2 -2
  168. package/dist/{uploadConsents-Z0N-ULVA.mjs.map → uploadConsents-Cbn0O4fM.mjs.map} +1 -1
  169. package/dist/{uploadCookiesFromCsv-DZSP7M-u.mjs → uploadCookiesFromCsv-r8mTeMe9.mjs} +2 -2
  170. package/dist/{uploadCookiesFromCsv-DZSP7M-u.mjs.map → uploadCookiesFromCsv-r8mTeMe9.mjs.map} +1 -1
  171. package/dist/{uploadDataFlowsFromCsv-vaN5DwL4.mjs → uploadDataFlowsFromCsv-BsBay5Vi.mjs} +2 -2
  172. package/dist/{uploadDataFlowsFromCsv-vaN5DwL4.mjs.map → uploadDataFlowsFromCsv-BsBay5Vi.mjs.map} +1 -1
  173. package/dist/{uploadPrivacyRequestsFromCsv-ByRf-2jO.mjs → uploadPrivacyRequestsFromCsv-B0hRYldF.mjs} +2 -2
  174. package/dist/{uploadPrivacyRequestsFromCsv-ByRf-2jO.mjs.map → uploadPrivacyRequestsFromCsv-B0hRYldF.mjs.map} +1 -1
  175. package/dist/validateTranscendAuth-CbYKgCP5.mjs +2 -0
  176. package/dist/{validateTranscendAuth-DhzCBA3F.mjs.map → validateTranscendAuth-CbYKgCP5.mjs.map} +1 -1
  177. package/package.json +5 -7
  178. package/dist/codecs-Dch3sv5m.mjs +0 -2
  179. package/dist/codecs-Dch3sv5m.mjs.map +0 -1
  180. package/dist/constants-Btn1yJ8a.mjs +0 -2
  181. package/dist/constants-Btn1yJ8a.mjs.map +0 -1
  182. package/dist/enums-BymyVyqr.mjs +0 -2
  183. package/dist/enums-BymyVyqr.mjs.map +0 -1
  184. package/dist/impl-CyhHVprA.mjs +0 -2
  185. package/dist/impl-DQ-kymSs.mjs +0 -2
  186. package/dist/parseVariablesFromString-RM3zV9Av.mjs +0 -3
  187. package/dist/parseVariablesFromString-RM3zV9Av.mjs.map +0 -1
  188. package/dist/pullTranscendConfiguration-C2LAOKG4.mjs +0 -58
  189. package/dist/pullTranscendConfiguration-C2LAOKG4.mjs.map +0 -1
  190. package/dist/readCsv-C84Jhrzx.mjs +0 -2
  191. package/dist/validateTranscendAuth-DhzCBA3F.mjs +0 -2
@@ -1 +1 @@
1
- {"version":3,"file":"downloadPrivacyRequestFiles-Dtnhb3v2.mjs","names":[],"sources":["../src/lib/requests/getFileMetadataForPrivacyRequests.ts","../src/lib/requests/streamPrivacyRequestFiles.ts","../src/lib/requests/downloadPrivacyRequestFiles.ts"],"sourcesContent":["import { TableEncryptionType } from '@transcend-io/privacy-types';\nimport { decodeCodec, valuesOf } from '@transcend-io/type-utils';\nimport { map } from '@transcend-io/utils';\nimport cliProgress from 'cli-progress';\nimport colors from 'colors';\nimport type { Got } from 'got';\nimport * as t from 'io-ts';\n\nimport { logger } from '../../logger.js';\nimport { PrivacyRequest } from '../graphql/index.js';\n\nexport const IntlMessage = t.type({\n /** The message key */\n defaultMessage: t.string,\n /** ID */\n id: t.string,\n});\n\n/** Type */\nexport type IntlMessage = t.TypeOf<typeof IntlMessage>;\n\nexport const RequestFileMetadata = t.type({\n /** The key to pass to download the file contents */\n downloadKey: t.string,\n /** Error message related to file */\n error: t.union([t.null, t.string]),\n /** Mimetype of file */\n mimetype: t.string,\n /** Size of file, stored as string as this can be a BigInt */\n size: t.string,\n /** Name of file based on datapoint names in Transcend */\n fileName: t.string,\n /** The metadata on the datapoint */\n dataPoint: t.type({\n /** ID of datapoint */\n id: t.string,\n /** The title of datapoint */\n title: t.union([IntlMessage, t.null]),\n /** Description of datapoint */\n description: t.union([IntlMessage, t.null]),\n /** Name of datapoint */\n name: t.string,\n /** Slug of datapoint */\n slug: t.string,\n /** Table level encryption information */\n encryption: t.union([valuesOf(TableEncryptionType), t.null]),\n /** The name of the data silo */\n dataSilo: t.type({\n /** ID of the data silo */\n id: t.string,\n /** The title of the data silo */\n title: t.string,\n /** The description of the data silo */\n description: t.string,\n /** The type of the data silo */\n type: t.string,\n /** The outer type of the data silo */\n outerType: t.union([t.string, t.null]),\n }),\n /** The path to the datapoint if a database (e.g. name of schema) */\n path: t.array(t.string),\n }),\n});\n\n/** Type override */\nexport type RequestFileMetadata = t.TypeOf<typeof RequestFileMetadata>;\n\nexport const RequestFileMetadataResponse = t.type({\n /** The list of file metadata */\n nodes: t.array(RequestFileMetadata),\n /** The total number of file metadata */\n totalCount: t.number,\n /** Links to next pages */\n _links: t.partial({\n /** The link to the next page of file metadata */\n next: t.union([t.string, t.null]),\n /** The link to the previous page of file metadata */\n previous: t.union([t.string, t.null]),\n }),\n});\n\n/** Type override */\nexport type RequestFileMetadataResponse = t.TypeOf<typeof RequestFileMetadataResponse>;\n\n/**\n * Given a list of privacy requests, download the file metadata\n * for these requests - this is useful to prepare the files in a\n * data access request for download.\n *\n * @param requests - The list of privacy requests to download files for\n * @param options - Options\n * @returns The number of requests canceled\n */\nexport async function getFileMetadataForPrivacyRequests(\n requests: Pick<PrivacyRequest, 'id' | 'status'>[],\n {\n sombra,\n concurrency = 5,\n limit = 100,\n }: {\n /** Sombra instance */\n sombra: Got;\n /** Number of files to pull at once */\n limit?: number;\n /** Concurrency limit for approving */\n concurrency?: number;\n },\n): Promise<[Pick<PrivacyRequest, 'id' | 'status'>, RequestFileMetadata[]][]> {\n logger.info(colors.magenta(`Pulling file metadata for ${requests.length} requests`));\n\n // Time duration\n const t0 = new Date().getTime();\n // create a new progress bar instance and use shades_classic theme\n const progressBar = new cliProgress.SingleBar({}, cliProgress.Presets.shades_classic);\n\n // Start timer\n let total = 0;\n progressBar.start(requests.length, 0);\n\n // Loop over the requests\n const results = await map(\n requests,\n async (\n requestToDownload,\n ): Promise<[Pick<PrivacyRequest, 'id' | 'status'>, RequestFileMetadata[]]> => {\n const localResults: RequestFileMetadata[] = [];\n\n // Paginate over the file metadata for this request\n let shouldContinue = true;\n let offset = 0;\n while (shouldContinue) {\n let response: RequestFileMetadataResponse;\n try {\n // Grab the file metadata for this request\n\n const rawResponse = await sombra\n .get(`v1/data-subject-request/${requestToDownload.id}/download-keys`, {\n searchParams: {\n limit,\n offset,\n },\n })\n .json();\n response = decodeCodec(RequestFileMetadataResponse, rawResponse);\n localResults.push(...response.nodes);\n\n // Increase offset and break if no more pages\n offset += limit;\n shouldContinue =\n // eslint-disable-next-line no-underscore-dangle\n !!response._links.next && response.nodes.length === limit;\n } catch (err) {\n throw new Error(`Received an error from server: ${err?.response?.body || err?.message}`);\n }\n }\n\n total += 1;\n progressBar.update(total);\n return [requestToDownload, localResults];\n },\n { concurrency },\n );\n\n progressBar.stop();\n const t1 = new Date().getTime();\n const totalTime = t1 - t0;\n\n logger.info(\n colors.green(\n `Successfully downloaded file metadata ${requests.length} requests in \"${\n totalTime / 1000\n }\" seconds!`,\n ),\n );\n\n return results;\n}\n","import { map } from '@transcend-io/utils';\nimport colors from 'colors';\nimport type { Got } from 'got';\n\nimport { logger } from '../../logger.js';\nimport { RequestFileMetadata } from './getFileMetadataForPrivacyRequests.js';\n\n/**\n * This function will take in a set of file metadata for privacy requests\n * call the Transcend API to stream the file metadata for these requests\n * and pass that through a callback function\n *\n * @param fileMetadata - Metadata to download\n * @param options - Options for the request\n */\nexport async function streamPrivacyRequestFiles(\n fileMetadata: RequestFileMetadata[],\n {\n requestId,\n sombra,\n onFileDownloaded,\n concurrency = 20,\n }: {\n /** Request ID for logging */\n requestId: string;\n /** Sombra got instance */\n sombra: Got;\n /** Handler on each file */\n onFileDownloaded: (metadata: RequestFileMetadata, stream: Uint8Array) => void;\n /** Concurrent downloads at once */\n concurrency?: number;\n },\n): Promise<void> {\n // Loop over each file\n await map(\n fileMetadata,\n async (metadata) => {\n try {\n // Construct the stream\n await sombra\n .get('v1/files', {\n searchParams: {\n downloadKey: metadata.downloadKey,\n },\n })\n .buffer()\n .then((fileResponse) => onFileDownloaded(metadata, fileResponse));\n } catch (err) {\n if (err?.response?.body?.includes('fileMetadata#verify')) {\n logger.error(\n colors.red(\n `Failed to pull file for: ${metadata.fileName} (request:${requestId}) - JWT expired. ` +\n 'This likely means that the file is no longer available. ' +\n 'Try restarting the request from scratch in Transcend Admin Dashboard. ' +\n 'Skipping the download of this file.',\n ),\n );\n return;\n }\n throw new Error(`Received an error from server: ${err?.response?.body || err?.message}`);\n }\n },\n {\n concurrency,\n },\n );\n}\n","import { existsSync, mkdirSync, writeFileSync } from 'node:fs';\nimport { dirname, join } from 'node:path';\n\nimport { RequestAction, RequestStatus } from '@transcend-io/privacy-types';\nimport {\n buildTranscendGraphQLClient,\n createSombraGotInstance,\n makeGraphQLRequest,\n} from '@transcend-io/sdk';\nimport { map } from '@transcend-io/utils';\nimport cliProgress from 'cli-progress';\nimport colors from 'colors';\n\nimport { DEFAULT_TRANSCEND_API } from '../../constants.js';\nimport { logger } from '../../logger.js';\nimport { fetchAllRequests, APPROVE_PRIVACY_REQUEST } from '../graphql/index.js';\nimport { getFileMetadataForPrivacyRequests } from './getFileMetadataForPrivacyRequests.js';\nimport { streamPrivacyRequestFiles } from './streamPrivacyRequestFiles.js';\n\n/**\n * Download a set of privacy requests to disk\n *\n * @param options - Options\n * @returns The number of requests canceled\n */\nexport async function downloadPrivacyRequestFiles({\n auth,\n folderPath,\n requestIds,\n createdAtBefore,\n sombraAuth,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n statuses = [RequestStatus.Approving, RequestStatus.Downloadable],\n concurrency = 5,\n transcendUrl = DEFAULT_TRANSCEND_API,\n approveAfterDownload = false,\n}: {\n /** The folder path to download the files to */\n folderPath: string;\n /** Transcend API key authentication */\n auth: string;\n /** Sombra API key authentication */\n sombraAuth?: string;\n /** Concurrency limit for approving */\n concurrency?: number;\n /** The request statuses to cancel */\n statuses?: RequestStatus[];\n /** The set of privacy requests to cancel */\n requestIds?: string[];\n /** Filter for requests created before this date */\n createdAtBefore?: Date;\n /** Filter for requests created after this date */\n createdAtAfter?: Date;\n /** Filter for requests updated before this date */\n updatedAtBefore?: Date;\n /** Filter for requests updated after this date */\n updatedAtAfter?: Date;\n /** API URL for Transcend backend */\n transcendUrl?: string;\n /** When true, approve any requests in Transcend that are in status=APPROVING */\n approveAfterDownload?: boolean;\n}): Promise<number> {\n // Find all requests made before createdAt that are in a removing data state\n const client = buildTranscendGraphQLClient(transcendUrl, auth);\n\n // Create sombra instance to communicate with\n const sombra = await createSombraGotInstance(transcendUrl, auth, {\n logger,\n sombraApiKey: sombraAuth,\n sombraUrl: process.env.SOMBRA_URL,\n });\n\n // Create the folder if it does not exist\n if (!existsSync(folderPath)) {\n mkdirSync(folderPath);\n }\n\n // Pull in the requests\n const allRequests = await fetchAllRequests(client, {\n actions: [RequestAction.Access],\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n statuses,\n requestIds,\n });\n\n // Download the file metadata for each request\n const requestFileMetadata = await getFileMetadataForPrivacyRequests(allRequests, {\n sombra,\n concurrency,\n });\n\n // Start timer for download process\n const t0 = new Date().getTime();\n const progressBar = new cliProgress.SingleBar({}, cliProgress.Presets.shades_classic);\n let total = 0;\n let totalApproved = 0;\n progressBar.start(allRequests.length, 0);\n\n // Download the files for each request\n await map(\n requestFileMetadata,\n async ([request, metadata]) => {\n // Create a new folder to store request files\n const requestFolder = join(folderPath, request.id);\n if (!existsSync(requestFolder)) {\n mkdirSync(requestFolder);\n }\n\n // Stream each file to disk\n await streamPrivacyRequestFiles(metadata, {\n sombra,\n requestId: request.id,\n onFileDownloaded: (fil, stream) => {\n // Ensure a folder exists for the file\n // filename looks like Health/heartbeat.csv\n const filePath = join(requestFolder, fil.fileName);\n const folder = dirname(filePath);\n if (!existsSync(folder)) {\n mkdirSync(folder, { recursive: true });\n }\n\n // Write to disk\n writeFileSync(filePath, stream);\n },\n });\n\n // Approve the request if requested\n if (approveAfterDownload && request.status === RequestStatus.Approving) {\n await makeGraphQLRequest(client, APPROVE_PRIVACY_REQUEST, {\n variables: { input: { requestId: request.id } },\n logger,\n });\n totalApproved += 1;\n }\n\n // Increment the progress bar\n total += 1;\n progressBar.update(total);\n },\n { concurrency },\n );\n\n progressBar.stop();\n const t1 = new Date().getTime();\n const totalTime = t1 - t0;\n\n logger.info(\n colors.green(`Successfully downloaded ${total} requests in \"${totalTime / 1000}\" seconds!`),\n );\n if (totalApproved > 0) {\n logger.info(colors.green(`Approved ${totalApproved} requests in Transcend.`));\n }\n return allRequests.length;\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"downloadPrivacyRequestFiles-AArYL4OL.mjs","names":[],"sources":["../src/lib/requests/getFileMetadataForPrivacyRequests.ts","../src/lib/requests/streamPrivacyRequestFiles.ts","../src/lib/requests/downloadPrivacyRequestFiles.ts"],"sourcesContent":["import { TableEncryptionType } from '@transcend-io/privacy-types';\nimport { decodeCodec, valuesOf } from '@transcend-io/type-utils';\nimport { map } from '@transcend-io/utils';\nimport cliProgress from 'cli-progress';\nimport colors from 'colors';\nimport type { Got } from 'got';\nimport * as t from 'io-ts';\n\nimport { logger } from '../../logger.js';\nimport { PrivacyRequest } from '../graphql/index.js';\n\nexport const IntlMessage = t.type({\n /** The message key */\n defaultMessage: t.string,\n /** ID */\n id: t.string,\n});\n\n/** Type */\nexport type IntlMessage = t.TypeOf<typeof IntlMessage>;\n\nexport const RequestFileMetadata = t.type({\n /** The key to pass to download the file contents */\n downloadKey: t.string,\n /** Error message related to file */\n error: t.union([t.null, t.string]),\n /** Mimetype of file */\n mimetype: t.string,\n /** Size of file, stored as string as this can be a BigInt */\n size: t.string,\n /** Name of file based on datapoint names in Transcend */\n fileName: t.string,\n /** The metadata on the datapoint */\n dataPoint: t.type({\n /** ID of datapoint */\n id: t.string,\n /** The title of datapoint */\n title: t.union([IntlMessage, t.null]),\n /** Description of datapoint */\n description: t.union([IntlMessage, t.null]),\n /** Name of datapoint */\n name: t.string,\n /** Slug of datapoint */\n slug: t.string,\n /** Table level encryption information */\n encryption: t.union([valuesOf(TableEncryptionType), t.null]),\n /** The name of the data silo */\n dataSilo: t.type({\n /** ID of the data silo */\n id: t.string,\n /** The title of the data silo */\n title: t.string,\n /** The description of the data silo */\n description: t.string,\n /** The type of the data silo */\n type: t.string,\n /** The outer type of the data silo */\n outerType: t.union([t.string, t.null]),\n }),\n /** The path to the datapoint if a database (e.g. name of schema) */\n path: t.array(t.string),\n }),\n});\n\n/** Type override */\nexport type RequestFileMetadata = t.TypeOf<typeof RequestFileMetadata>;\n\nexport const RequestFileMetadataResponse = t.type({\n /** The list of file metadata */\n nodes: t.array(RequestFileMetadata),\n /** The total number of file metadata */\n totalCount: t.number,\n /** Links to next pages */\n _links: t.partial({\n /** The link to the next page of file metadata */\n next: t.union([t.string, t.null]),\n /** The link to the previous page of file metadata */\n previous: t.union([t.string, t.null]),\n }),\n});\n\n/** Type override */\nexport type RequestFileMetadataResponse = t.TypeOf<typeof RequestFileMetadataResponse>;\n\n/**\n * Given a list of privacy requests, download the file metadata\n * for these requests - this is useful to prepare the files in a\n * data access request for download.\n *\n * @param requests - The list of privacy requests to download files for\n * @param options - Options\n * @returns The number of requests canceled\n */\nexport async function getFileMetadataForPrivacyRequests(\n requests: Pick<PrivacyRequest, 'id' | 'status'>[],\n {\n sombra,\n concurrency = 5,\n limit = 100,\n }: {\n /** Sombra instance */\n sombra: Got;\n /** Number of files to pull at once */\n limit?: number;\n /** Concurrency limit for approving */\n concurrency?: number;\n },\n): Promise<[Pick<PrivacyRequest, 'id' | 'status'>, RequestFileMetadata[]][]> {\n logger.info(colors.magenta(`Pulling file metadata for ${requests.length} requests`));\n\n // Time duration\n const t0 = new Date().getTime();\n // create a new progress bar instance and use shades_classic theme\n const progressBar = new cliProgress.SingleBar({}, cliProgress.Presets.shades_classic);\n\n // Start timer\n let total = 0;\n progressBar.start(requests.length, 0);\n\n // Loop over the requests\n const results = await map(\n requests,\n async (\n requestToDownload,\n ): Promise<[Pick<PrivacyRequest, 'id' | 'status'>, RequestFileMetadata[]]> => {\n const localResults: RequestFileMetadata[] = [];\n\n // Paginate over the file metadata for this request\n let shouldContinue = true;\n let offset = 0;\n while (shouldContinue) {\n let response: RequestFileMetadataResponse;\n try {\n // Grab the file metadata for this request\n\n const rawResponse = await sombra\n .get(`v1/data-subject-request/${requestToDownload.id}/download-keys`, {\n searchParams: {\n limit,\n offset,\n },\n })\n .json();\n response = decodeCodec(RequestFileMetadataResponse, rawResponse);\n localResults.push(...response.nodes);\n\n // Increase offset and break if no more pages\n offset += limit;\n shouldContinue =\n // eslint-disable-next-line no-underscore-dangle\n !!response._links.next && response.nodes.length === limit;\n } catch (err) {\n throw new Error(`Received an error from server: ${err?.response?.body || err?.message}`);\n }\n }\n\n total += 1;\n progressBar.update(total);\n return [requestToDownload, localResults];\n },\n { concurrency },\n );\n\n progressBar.stop();\n const t1 = new Date().getTime();\n const totalTime = t1 - t0;\n\n logger.info(\n colors.green(\n `Successfully downloaded file metadata ${requests.length} requests in \"${\n totalTime / 1000\n }\" seconds!`,\n ),\n );\n\n return results;\n}\n","import { map } from '@transcend-io/utils';\nimport colors from 'colors';\nimport type { Got } from 'got';\n\nimport { logger } from '../../logger.js';\nimport { RequestFileMetadata } from './getFileMetadataForPrivacyRequests.js';\n\n/**\n * This function will take in a set of file metadata for privacy requests\n * call the Transcend API to stream the file metadata for these requests\n * and pass that through a callback function\n *\n * @param fileMetadata - Metadata to download\n * @param options - Options for the request\n */\nexport async function streamPrivacyRequestFiles(\n fileMetadata: RequestFileMetadata[],\n {\n requestId,\n sombra,\n onFileDownloaded,\n concurrency = 20,\n }: {\n /** Request ID for logging */\n requestId: string;\n /** Sombra got instance */\n sombra: Got;\n /** Handler on each file */\n onFileDownloaded: (metadata: RequestFileMetadata, stream: Uint8Array) => void;\n /** Concurrent downloads at once */\n concurrency?: number;\n },\n): Promise<void> {\n // Loop over each file\n await map(\n fileMetadata,\n async (metadata) => {\n try {\n // Construct the stream\n await sombra\n .get('v1/files', {\n searchParams: {\n downloadKey: metadata.downloadKey,\n },\n })\n .buffer()\n .then((fileResponse) => onFileDownloaded(metadata, fileResponse));\n } catch (err) {\n if (err?.response?.body?.includes('fileMetadata#verify')) {\n logger.error(\n colors.red(\n `Failed to pull file for: ${metadata.fileName} (request:${requestId}) - JWT expired. ` +\n 'This likely means that the file is no longer available. ' +\n 'Try restarting the request from scratch in Transcend Admin Dashboard. ' +\n 'Skipping the download of this file.',\n ),\n );\n return;\n }\n throw new Error(`Received an error from server: ${err?.response?.body || err?.message}`);\n }\n },\n {\n concurrency,\n },\n );\n}\n","import { existsSync, mkdirSync, writeFileSync } from 'node:fs';\nimport { dirname, join } from 'node:path';\n\nimport { RequestAction, RequestStatus } from '@transcend-io/privacy-types';\nimport {\n buildTranscendGraphQLClient,\n createSombraGotInstance,\n makeGraphQLRequest,\n} from '@transcend-io/sdk';\nimport { map } from '@transcend-io/utils';\nimport cliProgress from 'cli-progress';\nimport colors from 'colors';\n\nimport { DEFAULT_TRANSCEND_API } from '../../constants.js';\nimport { logger } from '../../logger.js';\nimport { fetchAllRequests, APPROVE_PRIVACY_REQUEST } from '../graphql/index.js';\nimport { getFileMetadataForPrivacyRequests } from './getFileMetadataForPrivacyRequests.js';\nimport { streamPrivacyRequestFiles } from './streamPrivacyRequestFiles.js';\n\n/**\n * Download a set of privacy requests to disk\n *\n * @param options - Options\n * @returns The number of requests canceled\n */\nexport async function downloadPrivacyRequestFiles({\n auth,\n folderPath,\n requestIds,\n createdAtBefore,\n sombraAuth,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n statuses = [RequestStatus.Approving, RequestStatus.Downloadable],\n concurrency = 5,\n transcendUrl = DEFAULT_TRANSCEND_API,\n approveAfterDownload = false,\n}: {\n /** The folder path to download the files to */\n folderPath: string;\n /** Transcend API key authentication */\n auth: string;\n /** Sombra API key authentication */\n sombraAuth?: string;\n /** Concurrency limit for approving */\n concurrency?: number;\n /** The request statuses to cancel */\n statuses?: RequestStatus[];\n /** The set of privacy requests to cancel */\n requestIds?: string[];\n /** Filter for requests created before this date */\n createdAtBefore?: Date;\n /** Filter for requests created after this date */\n createdAtAfter?: Date;\n /** Filter for requests updated before this date */\n updatedAtBefore?: Date;\n /** Filter for requests updated after this date */\n updatedAtAfter?: Date;\n /** API URL for Transcend backend */\n transcendUrl?: string;\n /** When true, approve any requests in Transcend that are in status=APPROVING */\n approveAfterDownload?: boolean;\n}): Promise<number> {\n // Find all requests made before createdAt that are in a removing data state\n const client = buildTranscendGraphQLClient(transcendUrl, auth);\n\n // Create sombra instance to communicate with\n const sombra = await createSombraGotInstance(transcendUrl, auth, {\n logger,\n sombraApiKey: sombraAuth,\n sombraUrl: process.env.SOMBRA_URL,\n });\n\n // Create the folder if it does not exist\n if (!existsSync(folderPath)) {\n mkdirSync(folderPath);\n }\n\n // Pull in the requests\n const allRequests = await fetchAllRequests(client, {\n actions: [RequestAction.Access],\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n statuses,\n requestIds,\n });\n\n // Download the file metadata for each request\n const requestFileMetadata = await getFileMetadataForPrivacyRequests(allRequests, {\n sombra,\n concurrency,\n });\n\n // Start timer for download process\n const t0 = new Date().getTime();\n const progressBar = new cliProgress.SingleBar({}, cliProgress.Presets.shades_classic);\n let total = 0;\n let totalApproved = 0;\n progressBar.start(allRequests.length, 0);\n\n // Download the files for each request\n await map(\n requestFileMetadata,\n async ([request, metadata]) => {\n // Create a new folder to store request files\n const requestFolder = join(folderPath, request.id);\n if (!existsSync(requestFolder)) {\n mkdirSync(requestFolder);\n }\n\n // Stream each file to disk\n await streamPrivacyRequestFiles(metadata, {\n sombra,\n requestId: request.id,\n onFileDownloaded: (fil, stream) => {\n // Ensure a folder exists for the file\n // filename looks like Health/heartbeat.csv\n const filePath = join(requestFolder, fil.fileName);\n const folder = dirname(filePath);\n if (!existsSync(folder)) {\n mkdirSync(folder, { recursive: true });\n }\n\n // Write to disk\n writeFileSync(filePath, stream);\n },\n });\n\n // Approve the request if requested\n if (approveAfterDownload && request.status === RequestStatus.Approving) {\n await makeGraphQLRequest(client, APPROVE_PRIVACY_REQUEST, {\n variables: { input: { requestId: request.id } },\n logger,\n });\n totalApproved += 1;\n }\n\n // Increment the progress bar\n total += 1;\n progressBar.update(total);\n },\n { concurrency },\n );\n\n progressBar.stop();\n const t1 = new Date().getTime();\n const totalTime = t1 - t0;\n\n logger.info(\n colors.green(`Successfully downloaded ${total} requests in \"${totalTime / 1000}\" seconds!`),\n );\n if (totalApproved > 0) {\n logger.info(colors.green(`Approved ${totalApproved} requests in Transcend.`));\n }\n return allRequests.length;\n}\n"],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ let e=function(e){return e.Json=`json`,e}({}),t=function(e){return e.Assessments=`assessments`,e}({}),n=function(e){return e.OneTrust=`oneTrust`,e.File=`file`,e}({}),r=function(e){return e.ApiKeys=`apiKeys`,e.Attributes=`customFields`,e.Templates=`templates`,e.DataSilos=`dataSilos`,e.Enrichers=`enrichers`,e.DataFlows=`dataFlows`,e.BusinessEntities=`businessEntities`,e.ProcessingActivities=`processingActivities`,e.Actions=`actions`,e.DataSubjects=`dataSubjects`,e.Identifiers=`identifiers`,e.Cookies=`cookies`,e.ConsentManager=`consentManager`,e.Partitions=`partitions`,e.Prompts=`prompts`,e.PromptPartials=`promptPartials`,e.PromptGroups=`promptGroups`,e.Vendors=`vendors`,e.DataCategories=`dataCategories`,e.ProcessingPurposes=`processingPurposes`,e.ActionItems=`actionItems`,e.ActionItemCollections=`actionItemCollections`,e.Teams=`teams`,e.PrivacyCenters=`privacyCenters`,e.Policies=`policies`,e.Messages=`messages`,e.Assessments=`assessments`,e.AssessmentTemplates=`assessmentTemplates`,e.Purposes=`purposes`,e.PreferenceOptions=`preferenceOptions`,e.SystemDiscovery=`systemDiscovery`,e.PreferenceWorkflowConfigs=`preferenceWorkflowConfigs`,e.WorkflowConfigs=`workflowConfigs`,e}({});export{r as i,t as n,n as r,e as t};
2
+ //# sourceMappingURL=enums-UlIe_AeF.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"enums-UlIe_AeF.mjs","names":[],"sources":["../src/enums.ts"],"sourcesContent":["import { makeEnum } from '@transcend-io/type-utils';\n\n/** Accepted file formats for exporting resources from OneTrust */\nexport enum OneTrustFileFormat {\n Json = 'json',\n}\n\n/**\n * Resources that can be pulled in from OneTrust\n */\nexport enum OneTrustPullResource {\n Assessments = 'assessments',\n}\n\n/**\n * Where to read OneTrust resources from\n */\nexport enum OneTrustPullSource {\n OneTrust = 'oneTrust',\n File = 'file',\n}\n\n/**\n * Resources that can be pulled in\n */\nexport enum TranscendPullResource {\n ApiKeys = 'apiKeys',\n Attributes = 'customFields',\n Templates = 'templates',\n DataSilos = 'dataSilos',\n Enrichers = 'enrichers',\n DataFlows = 'dataFlows',\n BusinessEntities = 'businessEntities',\n ProcessingActivities = 'processingActivities',\n Actions = 'actions',\n DataSubjects = 'dataSubjects',\n Identifiers = 'identifiers',\n Cookies = 'cookies',\n ConsentManager = 'consentManager',\n Partitions = 'partitions',\n Prompts = 'prompts',\n PromptPartials = 'promptPartials',\n PromptGroups = 'promptGroups',\n Vendors = 'vendors',\n DataCategories = 'dataCategories',\n ProcessingPurposes = 'processingPurposes',\n ActionItems = 'actionItems',\n ActionItemCollections = 'actionItemCollections',\n Teams = 'teams',\n PrivacyCenters = 'privacyCenters',\n Policies = 'policies',\n Messages = 'messages',\n Assessments = 'assessments',\n AssessmentTemplates = 'assessmentTemplates',\n Purposes = 'purposes',\n PreferenceOptions = 'preferenceOptions',\n SystemDiscovery = 'systemDiscovery',\n PreferenceWorkflowConfigs = 'preferenceWorkflowConfigs',\n WorkflowConfigs = 'workflowConfigs',\n}\n"],"mappings":"AAGA,IAAY,EAAL,SAAA,EAAA,OACL,GAAA,KAAA,aACD,CAKW,EAAL,SAAA,EAAA,OACL,GAAA,YAAA,oBACD,CAKW,EAAL,SAAA,EAAA,OACL,GAAA,SAAA,WACA,EAAA,KAAA,aACD,CAKW,EAAL,SAAA,EAAA,OACL,GAAA,QAAA,UACA,EAAA,WAAA,eACA,EAAA,UAAA,YACA,EAAA,UAAA,YACA,EAAA,UAAA,YACA,EAAA,UAAA,YACA,EAAA,iBAAA,mBACA,EAAA,qBAAA,uBACA,EAAA,QAAA,UACA,EAAA,aAAA,eACA,EAAA,YAAA,cACA,EAAA,QAAA,UACA,EAAA,eAAA,iBACA,EAAA,WAAA,aACA,EAAA,QAAA,UACA,EAAA,eAAA,iBACA,EAAA,aAAA,eACA,EAAA,QAAA,UACA,EAAA,eAAA,iBACA,EAAA,mBAAA,qBACA,EAAA,YAAA,cACA,EAAA,sBAAA,wBACA,EAAA,MAAA,QACA,EAAA,eAAA,iBACA,EAAA,SAAA,WACA,EAAA,SAAA,WACA,EAAA,YAAA,cACA,EAAA,oBAAA,sBACA,EAAA,SAAA,WACA,EAAA,kBAAA,oBACA,EAAA,gBAAA,kBACA,EAAA,0BAAA,4BACA,EAAA,gBAAA,wBACD"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./logger-Ckep4QXn.mjs";import{a as t,i as n}from"./request-BIplTb3L.mjs";import{IsoCountryCode as r,IsoCountrySubdivisionCode as i,RequestAction as a,RequestOrigin as o,RequestStatus as s}from"@transcend-io/privacy-types";import{valuesOf as c}from"@transcend-io/type-utils";import l from"colors";import{LOCALE_KEY as u}from"@transcend-io/internationalization";import*as d from"io-ts";import{makeGraphQLRequest as f}from"@transcend-io/sdk";import p from"cli-progress";const m=d.type({title:d.string,name:d.string,consent:d.boolean,enrichedPreferences:d.array(d.type({topic:d.string,selectValues:d.array(d.type({id:d.string,name:d.string,preferenceOption:d.type({id:d.string,slug:d.string,title:d.type({defaultMessage:d.string})})})),selectValue:d.type({id:d.string,name:d.string}),preferenceTopic:d.type({title:d.type({defaultMessage:d.string}),id:d.string,slug:d.string}),name:d.string,id:d.string,booleanValue:d.boolean}))}),h=d.intersection([d.type({id:d.string,createdAt:d.string,email:d.string,type:c(a),link:d.string,isSilent:d.boolean,origin:c(o),isTest:d.boolean,coreIdentifier:d.string,details:d.string,locale:c(u),status:c(s),subjectType:d.string,country:d.union([d.null,c(r)]),countrySubDivision:d.union([d.null,c(i)]),attributeValues:d.array(d.type({id:d.string,attributeKey:d.type({name:d.string,id:d.string}),name:d.string}))}),d.partial({daysRemaining:d.union([d.null,d.number]),successfullyCompletedAt:d.union([d.null,d.string]),purpose:m})]);async function g(n,r){let{requests:{totalCount:i}}=await f(n,t,{variables:{filterBy:r},logger:e});return i}async function _(r,{actions:i=[],statuses:a=[],origins:o=[],text:s,createdAtBefore:c,createdAtAfter:u,updatedAtBefore:d,updatedAtAfter:m,isTest:h,isSilent:g,isClosed:_,requestIds:v=[],onPage:y}={}){let b=!!y,x={text:s,type:i.length>0?i:void 0,status:a.length>0?a:void 0,origin:o.length>0?o:void 0,isTest:h,isSilent:g,isClosed:_,createdAtBefore:c?c.toISOString():void 0,createdAtAfter:u?u.toISOString():void 0,updatedAtBefore:d?d.toISOString():void 0,updatedAtAfter:m?m.toISOString():void 0},S=new Date().getTime(),C=new p.SingleBar({},p.Presets.shades_classic);if(!b){e.info(l.magenta(`Fetching requests...`));let{requests:{totalCount:n}}=await f(r,t,{variables:{filterBy:x},logger:e});n>100&&(e.info(l.magenta(`Fetching ${n} requests`)),C.start(n,0))}let w=[],T=0,E,D=!1;do{let{requests:{nodes:t,pageInfo:i}}=await f(r,n,{variables:{first:100,after:E,filterBy:x},logger:e});b?await y(t):w.push(...t),T+=t.length,E=i.endCursor??void 0,b||C.update(T),D=i.hasNextPage}while(D);if(!b){C.stop();let t=new Date().getTime()-S;e.info(l.green(`Completed fetching of ${T} request in "${t/1e3}" seconds.`))}if(b)return[];let O=w;return v&&v.length>0&&(O=O.filter(e=>v.includes(e.id)),e.info(l.green(`Filtered down to ${O.length} requests based on ${v.length} provided IDs.`))),O}export{g as i,m as n,_ as r,h as t};
2
- //# sourceMappingURL=fetchAllRequests-Bya6iwzL.mjs.map
1
+ import{t as e}from"./logger-Ckep4QXn.mjs";import{a as t,i as n}from"./request-BIplTb3L.mjs";import{IsoCountryCode as r,IsoCountrySubdivisionCode as i,RequestAction as a,RequestOrigin as o,RequestStatus as s}from"@transcend-io/privacy-types";import c from"colors";import{LOCALE_KEY as l}from"@transcend-io/internationalization";import{valuesOf as u}from"@transcend-io/type-utils";import*as d from"io-ts";import{makeGraphQLRequest as f}from"@transcend-io/sdk";import p from"cli-progress";const m=d.type({title:d.string,name:d.string,consent:d.boolean,enrichedPreferences:d.array(d.type({topic:d.string,selectValues:d.array(d.type({id:d.string,name:d.string,preferenceOption:d.type({id:d.string,slug:d.string,title:d.type({defaultMessage:d.string})})})),selectValue:d.type({id:d.string,name:d.string}),preferenceTopic:d.type({title:d.type({defaultMessage:d.string}),id:d.string,slug:d.string}),name:d.string,id:d.string,booleanValue:d.boolean}))}),h=d.intersection([d.type({id:d.string,createdAt:d.string,email:d.string,type:u(a),link:d.string,isSilent:d.boolean,origin:u(o),isTest:d.boolean,coreIdentifier:d.string,details:d.string,locale:u(l),status:u(s),subjectType:d.string,country:d.union([d.null,u(r)]),countrySubDivision:d.union([d.null,u(i)]),attributeValues:d.array(d.type({id:d.string,attributeKey:d.type({name:d.string,id:d.string}),name:d.string}))}),d.partial({daysRemaining:d.union([d.null,d.number]),successfullyCompletedAt:d.union([d.null,d.string]),purpose:m})]);async function g(n,r){let{requests:{totalCount:i}}=await f(n,t,{variables:{filterBy:r},logger:e});return i}async function _(r,{actions:i=[],statuses:a=[],origins:o=[],text:s,createdAtBefore:l,createdAtAfter:u,updatedAtBefore:d,updatedAtAfter:m,isTest:h,isSilent:g,isClosed:_,requestIds:v=[],onPage:y}={}){let b=!!y,x={text:s,type:i.length>0?i:void 0,status:a.length>0?a:void 0,origin:o.length>0?o:void 0,isTest:h,isSilent:g,isClosed:_,createdAtBefore:l?l.toISOString():void 0,createdAtAfter:u?u.toISOString():void 0,updatedAtBefore:d?d.toISOString():void 0,updatedAtAfter:m?m.toISOString():void 0},S=new Date().getTime(),C=new p.SingleBar({},p.Presets.shades_classic);if(!b){e.info(c.magenta(`Fetching requests...`));let{requests:{totalCount:n}}=await f(r,t,{variables:{filterBy:x},logger:e});n>100&&(e.info(c.magenta(`Fetching ${n} requests`)),C.start(n,0))}let w=[],T=0,E,D=!1;do{let{requests:{nodes:t,pageInfo:i}}=await f(r,n,{variables:{first:100,after:E,filterBy:x},logger:e});b?await y(t):w.push(...t),T+=t.length,E=i.endCursor??void 0,b||C.update(T),D=i.hasNextPage}while(D);if(!b){C.stop();let t=new Date().getTime()-S;e.info(c.green(`Completed fetching of ${T} request in "${t/1e3}" seconds.`))}if(b)return[];let O=w;return v&&v.length>0&&(O=O.filter(e=>v.includes(e.id)),e.info(c.green(`Filtered down to ${O.length} requests based on ${v.length} provided IDs.`))),O}export{g as i,m as n,_ as r,h as t};
2
+ //# sourceMappingURL=fetchAllRequests-DP24WqrP.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"fetchAllRequests-Bya6iwzL.mjs","names":[],"sources":["../src/lib/graphql/fetchAllRequests.ts"],"sourcesContent":["import { LOCALE_KEY } from '@transcend-io/internationalization';\nimport {\n RequestAction,\n RequestOrigin,\n RequestStatus,\n IsoCountryCode,\n IsoCountrySubdivisionCode,\n} from '@transcend-io/privacy-types';\nimport { makeGraphQLRequest } from '@transcend-io/sdk';\nimport { valuesOf } from '@transcend-io/type-utils';\nimport cliProgress from 'cli-progress';\nimport colors from 'colors';\nimport { GraphQLClient } from 'graphql-request';\nimport * as t from 'io-ts';\n\nimport { logger } from '../../logger.js';\nimport { REQUESTS, REQUESTS_COUNT } from './gqls/index.js';\n\nexport const RequestPurposeTrigger = t.type({\n title: t.string,\n name: t.string,\n consent: t.boolean,\n enrichedPreferences: t.array(\n t.type({\n topic: t.string,\n selectValues: t.array(\n t.type({\n id: t.string,\n name: t.string,\n preferenceOption: t.type({\n id: t.string,\n slug: t.string,\n title: t.type({\n defaultMessage: t.string,\n }),\n }),\n }),\n ),\n selectValue: t.type({\n id: t.string,\n name: t.string,\n }),\n preferenceTopic: t.type({\n title: t.type({\n defaultMessage: t.string,\n }),\n id: t.string,\n slug: t.string,\n }),\n name: t.string,\n id: t.string,\n booleanValue: t.boolean,\n }),\n ),\n});\n\n/** Override type */\nexport type RequestPurposeTrigger = t.TypeOf<typeof RequestPurposeTrigger>;\n\nexport const PrivacyRequest = t.intersection([\n t.type({\n /** Request ID */\n id: t.string,\n /** Time request was made */\n createdAt: t.string,\n /** Email of request */\n email: t.string,\n /** The type of request */\n type: valuesOf(RequestAction),\n /** Link to request in Transcend dashboard */\n link: t.string,\n /** Whether request is in silent mode */\n isSilent: t.boolean,\n /** Where request was made */\n origin: valuesOf(RequestOrigin),\n /** Whether request is a test request */\n isTest: t.boolean,\n /** The core identifier of the request */\n coreIdentifier: t.string,\n /** Request details */\n details: t.string,\n /** Locale of request */\n locale: valuesOf(LOCALE_KEY),\n /** Status of request */\n status: valuesOf(RequestStatus),\n /** Type of data subject */\n subjectType: t.string,\n /** Country of request */\n country: t.union([t.null, valuesOf(IsoCountryCode)]),\n /** Subdivision of request */\n countrySubDivision: t.union([t.null, valuesOf(IsoCountrySubdivisionCode)]),\n /** Request attributes */\n attributeValues: t.array(\n t.type({\n id: t.string,\n attributeKey: t.type({ name: t.string, id: t.string }),\n name: t.string,\n }),\n ),\n }),\n t.partial({\n /** Days remaining until expired */\n daysRemaining: t.union([t.null, t.number]),\n /** Time when request was successfully completed */\n successfullyCompletedAt: t.union([t.null, t.string]),\n /** Purpose */\n purpose: RequestPurposeTrigger,\n }),\n]);\n\n/** Type override */\nexport type PrivacyRequest = t.TypeOf<typeof PrivacyRequest>;\n\nconst PAGE_SIZE = 100;\n\n/**\n * Fetch just the total count of requests matching a set of filters.\n * Useful for setting up a progress bar before streaming pages.\n *\n * @param client - GraphQL client\n * @param filterBy - Filter object (already serialized to ISO strings)\n * @returns The total count\n */\nexport async function fetchRequestsTotalCount(\n client: GraphQLClient,\n filterBy: Record<string, unknown>,\n): Promise<number> {\n const {\n requests: { totalCount },\n } = await makeGraphQLRequest<{\n /** Requests */\n requests: {\n /** Total count */\n totalCount: number;\n };\n }>(client, REQUESTS_COUNT, { variables: { filterBy }, logger });\n return totalCount;\n}\n\n/**\n * Fetch all requests matching a set of filters.\n *\n * When `onPage` is provided the function streams pages to the callback\n * and never accumulates nodes in memory — ideal for very large exports.\n * Without `onPage` the function returns all nodes in a single array\n * (existing behaviour, kept for backward compatibility).\n *\n * @param client - GraphQL client\n * @param options - Filter options\n * @returns List of requests (empty when using onPage)\n */\nexport async function fetchAllRequests(\n client: GraphQLClient,\n {\n actions = [],\n statuses = [],\n origins = [],\n text,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n isTest,\n isSilent,\n isClosed,\n requestIds = [],\n onPage,\n }: {\n /** Actions to filter on */\n actions?: RequestAction[];\n /** Origins to filter on */\n origins?: RequestOrigin[];\n /** Statuses to filter on */\n statuses?: RequestStatus[];\n /** Filter for requests created before this date */\n createdAtBefore?: Date;\n /** Filter for requests created after this date */\n createdAtAfter?: Date;\n /** Filter for requests updated before this date */\n updatedAtBefore?: Date;\n /** Filter for requests updated after this date */\n updatedAtAfter?: Date;\n /** Filter for requests with a specific identifier */\n text?: string;\n /** Return test requests */\n isTest?: boolean;\n /** Return silent mode requests */\n isSilent?: boolean;\n /** Filter by whether request is active */\n isClosed?: boolean;\n /**\n * Filter the list of requests for a set of IDs - these are applied\n * at runtime while other filters are applied at the GraphQL level.\n */\n requestIds?: string[];\n /** When provided, called with each page of nodes instead of accumulating in memory */\n onPage?: (nodes: PrivacyRequest[]) => void | Promise<void>;\n } = {},\n): Promise<PrivacyRequest[]> {\n const streaming = !!onPage;\n\n const filterBy = {\n text,\n type: actions.length > 0 ? actions : undefined,\n status: statuses.length > 0 ? statuses : undefined,\n origin: origins.length > 0 ? origins : undefined,\n isTest,\n isSilent,\n isClosed,\n createdAtBefore: createdAtBefore ? createdAtBefore.toISOString() : undefined,\n createdAtAfter: createdAtAfter ? createdAtAfter.toISOString() : undefined,\n updatedAtBefore: updatedAtBefore ? updatedAtBefore.toISOString() : undefined,\n updatedAtAfter: updatedAtAfter ? updatedAtAfter.toISOString() : undefined,\n };\n\n // When streaming, the caller manages progress/logging — skip count query & bar\n const t0 = new Date().getTime();\n const progressBar = new cliProgress.SingleBar({}, cliProgress.Presets.shades_classic);\n\n if (!streaming) {\n logger.info(colors.magenta('Fetching requests...'));\n const {\n requests: { totalCount },\n } = await makeGraphQLRequest<{\n /** Requests */\n requests: {\n /** Total count */\n totalCount: number;\n };\n }>(client, REQUESTS_COUNT, { variables: { filterBy }, logger });\n\n if (totalCount > PAGE_SIZE) {\n logger.info(colors.magenta(`Fetching ${totalCount} requests`));\n progressBar.start(totalCount, 0);\n }\n }\n\n const requests: PrivacyRequest[] = [];\n let fetchedCount = 0;\n\n // Paginate through all results\n let cursor: string | undefined;\n let shouldContinue = false;\n do {\n const {\n requests: { nodes, pageInfo },\n } = await makeGraphQLRequest<{\n /** Requests */\n requests: {\n /** List */\n nodes: PrivacyRequest[];\n /** Pagination info */\n pageInfo: {\n /** Cursor for the last item */\n endCursor: string | null;\n /** Whether more pages exist */\n hasNextPage: boolean;\n };\n };\n }>(client, REQUESTS, {\n variables: { first: PAGE_SIZE, after: cursor, filterBy },\n logger,\n });\n\n if (streaming) {\n await onPage!(nodes);\n } else {\n requests.push(...nodes);\n }\n\n fetchedCount += nodes.length;\n cursor = pageInfo.endCursor ?? undefined;\n if (!streaming) {\n progressBar.update(fetchedCount);\n }\n shouldContinue = pageInfo.hasNextPage;\n } while (shouldContinue);\n\n if (!streaming) {\n progressBar.stop();\n const t1 = new Date().getTime();\n const totalTime = t1 - t0;\n\n logger.info(\n colors.green(\n `Completed fetching of ${fetchedCount} request in \"${totalTime / 1000}\" seconds.`,\n ),\n );\n }\n\n if (streaming) {\n return [];\n }\n\n // Filter down requests by request ID\n let allRequests = requests;\n if (requestIds && requestIds.length > 0) {\n allRequests = allRequests.filter((request) => requestIds.includes(request.id));\n logger.info(\n colors.green(\n `Filtered down to ${allRequests.length} requests based on ${requestIds.length} provided IDs.`,\n ),\n );\n }\n\n return allRequests;\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"fetchAllRequests-DP24WqrP.mjs","names":[],"sources":["../src/lib/graphql/fetchAllRequests.ts"],"sourcesContent":["import { LOCALE_KEY } from '@transcend-io/internationalization';\nimport {\n RequestAction,\n RequestOrigin,\n RequestStatus,\n IsoCountryCode,\n IsoCountrySubdivisionCode,\n} from '@transcend-io/privacy-types';\nimport { makeGraphQLRequest } from '@transcend-io/sdk';\nimport { valuesOf } from '@transcend-io/type-utils';\nimport cliProgress from 'cli-progress';\nimport colors from 'colors';\nimport { GraphQLClient } from 'graphql-request';\nimport * as t from 'io-ts';\n\nimport { logger } from '../../logger.js';\nimport { REQUESTS, REQUESTS_COUNT } from './gqls/index.js';\n\nexport const RequestPurposeTrigger = t.type({\n title: t.string,\n name: t.string,\n consent: t.boolean,\n enrichedPreferences: t.array(\n t.type({\n topic: t.string,\n selectValues: t.array(\n t.type({\n id: t.string,\n name: t.string,\n preferenceOption: t.type({\n id: t.string,\n slug: t.string,\n title: t.type({\n defaultMessage: t.string,\n }),\n }),\n }),\n ),\n selectValue: t.type({\n id: t.string,\n name: t.string,\n }),\n preferenceTopic: t.type({\n title: t.type({\n defaultMessage: t.string,\n }),\n id: t.string,\n slug: t.string,\n }),\n name: t.string,\n id: t.string,\n booleanValue: t.boolean,\n }),\n ),\n});\n\n/** Override type */\nexport type RequestPurposeTrigger = t.TypeOf<typeof RequestPurposeTrigger>;\n\nexport const PrivacyRequest = t.intersection([\n t.type({\n /** Request ID */\n id: t.string,\n /** Time request was made */\n createdAt: t.string,\n /** Email of request */\n email: t.string,\n /** The type of request */\n type: valuesOf(RequestAction),\n /** Link to request in Transcend dashboard */\n link: t.string,\n /** Whether request is in silent mode */\n isSilent: t.boolean,\n /** Where request was made */\n origin: valuesOf(RequestOrigin),\n /** Whether request is a test request */\n isTest: t.boolean,\n /** The core identifier of the request */\n coreIdentifier: t.string,\n /** Request details */\n details: t.string,\n /** Locale of request */\n locale: valuesOf(LOCALE_KEY),\n /** Status of request */\n status: valuesOf(RequestStatus),\n /** Type of data subject */\n subjectType: t.string,\n /** Country of request */\n country: t.union([t.null, valuesOf(IsoCountryCode)]),\n /** Subdivision of request */\n countrySubDivision: t.union([t.null, valuesOf(IsoCountrySubdivisionCode)]),\n /** Request attributes */\n attributeValues: t.array(\n t.type({\n id: t.string,\n attributeKey: t.type({ name: t.string, id: t.string }),\n name: t.string,\n }),\n ),\n }),\n t.partial({\n /** Days remaining until expired */\n daysRemaining: t.union([t.null, t.number]),\n /** Time when request was successfully completed */\n successfullyCompletedAt: t.union([t.null, t.string]),\n /** Purpose */\n purpose: RequestPurposeTrigger,\n }),\n]);\n\n/** Type override */\nexport type PrivacyRequest = t.TypeOf<typeof PrivacyRequest>;\n\nconst PAGE_SIZE = 100;\n\n/**\n * Fetch just the total count of requests matching a set of filters.\n * Useful for setting up a progress bar before streaming pages.\n *\n * @param client - GraphQL client\n * @param filterBy - Filter object (already serialized to ISO strings)\n * @returns The total count\n */\nexport async function fetchRequestsTotalCount(\n client: GraphQLClient,\n filterBy: Record<string, unknown>,\n): Promise<number> {\n const {\n requests: { totalCount },\n } = await makeGraphQLRequest<{\n /** Requests */\n requests: {\n /** Total count */\n totalCount: number;\n };\n }>(client, REQUESTS_COUNT, { variables: { filterBy }, logger });\n return totalCount;\n}\n\n/**\n * Fetch all requests matching a set of filters.\n *\n * When `onPage` is provided the function streams pages to the callback\n * and never accumulates nodes in memory — ideal for very large exports.\n * Without `onPage` the function returns all nodes in a single array\n * (existing behaviour, kept for backward compatibility).\n *\n * @param client - GraphQL client\n * @param options - Filter options\n * @returns List of requests (empty when using onPage)\n */\nexport async function fetchAllRequests(\n client: GraphQLClient,\n {\n actions = [],\n statuses = [],\n origins = [],\n text,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n isTest,\n isSilent,\n isClosed,\n requestIds = [],\n onPage,\n }: {\n /** Actions to filter on */\n actions?: RequestAction[];\n /** Origins to filter on */\n origins?: RequestOrigin[];\n /** Statuses to filter on */\n statuses?: RequestStatus[];\n /** Filter for requests created before this date */\n createdAtBefore?: Date;\n /** Filter for requests created after this date */\n createdAtAfter?: Date;\n /** Filter for requests updated before this date */\n updatedAtBefore?: Date;\n /** Filter for requests updated after this date */\n updatedAtAfter?: Date;\n /** Filter for requests with a specific identifier */\n text?: string;\n /** Return test requests */\n isTest?: boolean;\n /** Return silent mode requests */\n isSilent?: boolean;\n /** Filter by whether request is active */\n isClosed?: boolean;\n /**\n * Filter the list of requests for a set of IDs - these are applied\n * at runtime while other filters are applied at the GraphQL level.\n */\n requestIds?: string[];\n /** When provided, called with each page of nodes instead of accumulating in memory */\n onPage?: (nodes: PrivacyRequest[]) => void | Promise<void>;\n } = {},\n): Promise<PrivacyRequest[]> {\n const streaming = !!onPage;\n\n const filterBy = {\n text,\n type: actions.length > 0 ? actions : undefined,\n status: statuses.length > 0 ? statuses : undefined,\n origin: origins.length > 0 ? origins : undefined,\n isTest,\n isSilent,\n isClosed,\n createdAtBefore: createdAtBefore ? createdAtBefore.toISOString() : undefined,\n createdAtAfter: createdAtAfter ? createdAtAfter.toISOString() : undefined,\n updatedAtBefore: updatedAtBefore ? updatedAtBefore.toISOString() : undefined,\n updatedAtAfter: updatedAtAfter ? updatedAtAfter.toISOString() : undefined,\n };\n\n // When streaming, the caller manages progress/logging — skip count query & bar\n const t0 = new Date().getTime();\n const progressBar = new cliProgress.SingleBar({}, cliProgress.Presets.shades_classic);\n\n if (!streaming) {\n logger.info(colors.magenta('Fetching requests...'));\n const {\n requests: { totalCount },\n } = await makeGraphQLRequest<{\n /** Requests */\n requests: {\n /** Total count */\n totalCount: number;\n };\n }>(client, REQUESTS_COUNT, { variables: { filterBy }, logger });\n\n if (totalCount > PAGE_SIZE) {\n logger.info(colors.magenta(`Fetching ${totalCount} requests`));\n progressBar.start(totalCount, 0);\n }\n }\n\n const requests: PrivacyRequest[] = [];\n let fetchedCount = 0;\n\n // Paginate through all results\n let cursor: string | undefined;\n let shouldContinue = false;\n do {\n const {\n requests: { nodes, pageInfo },\n } = await makeGraphQLRequest<{\n /** Requests */\n requests: {\n /** List */\n nodes: PrivacyRequest[];\n /** Pagination info */\n pageInfo: {\n /** Cursor for the last item */\n endCursor: string | null;\n /** Whether more pages exist */\n hasNextPage: boolean;\n };\n };\n }>(client, REQUESTS, {\n variables: { first: PAGE_SIZE, after: cursor, filterBy },\n logger,\n });\n\n if (streaming) {\n await onPage!(nodes);\n } else {\n requests.push(...nodes);\n }\n\n fetchedCount += nodes.length;\n cursor = pageInfo.endCursor ?? undefined;\n if (!streaming) {\n progressBar.update(fetchedCount);\n }\n shouldContinue = pageInfo.hasNextPage;\n } while (shouldContinue);\n\n if (!streaming) {\n progressBar.stop();\n const t1 = new Date().getTime();\n const totalTime = t1 - t0;\n\n logger.info(\n colors.green(\n `Completed fetching of ${fetchedCount} request in \"${totalTime / 1000}\" seconds.`,\n ),\n );\n }\n\n if (streaming) {\n return [];\n }\n\n // Filter down requests by request ID\n let allRequests = requests;\n if (requestIds && requestIds.length > 0) {\n allRequests = allRequests.filter((request) => requestIds.includes(request.id));\n logger.info(\n colors.green(\n `Filtered down to ${allRequests.length} requests based on ${requestIds.length} provided IDs.`,\n ),\n );\n }\n\n return allRequests;\n}\n"],"mappings":"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"}
@@ -1,2 +1,2 @@
1
- import{l as e,n as t}from"./constants-ykNINvFg.mjs";import n from"fuzzysearch";import r from"inquirer";function i(e,t){return n(e.toLowerCase(),t.toLowerCase())||n(t.toLowerCase(),e.toLowerCase())}function a(n,a,o,s){let c=n.filter(e=>i(a.toLowerCase(),e.toLowerCase()));return[...c,new r.Separator,...o?[]:[e],...s?[t]:[],...n.filter(e=>!c.includes(e))]}export{i as n,a as t};
2
- //# sourceMappingURL=fuzzyMatchColumns-Ds0TqtJ5.mjs.map
1
+ import{l as e,n as t}from"./constants-C9xZJ9YW.mjs";import n from"fuzzysearch";import r from"inquirer";function i(e,t){return n(e.toLowerCase(),t.toLowerCase())||n(t.toLowerCase(),e.toLowerCase())}function a(n,a,o,s){let c=n.filter(e=>i(a.toLowerCase(),e.toLowerCase()));return[...c,new r.Separator,...o?[]:[e],...s?[t]:[],...n.filter(e=>!c.includes(e))]}export{i as n,a as t};
2
+ //# sourceMappingURL=fuzzyMatchColumns-C1STZ_T1.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"fuzzyMatchColumns-Ds0TqtJ5.mjs","names":[],"sources":["../src/lib/requests/fuzzyMatchColumns.ts"],"sourcesContent":["import fuzzysearch from 'fuzzysearch';\nimport inquirer from 'inquirer';\n\nimport { NONE, BULK_APPLY } from './constants.js';\n\n/**\n * Check if word1 and word2 are a fuzzy match of each other.\n * Returns true if word1 is fuzzy match of word2 or vice versa.\n *\n * @param word1 - First word\n * @param word2 - Second word\n * @returns True if words are fuzzy match\n */\nexport function fuzzySearch(word1: string, word2: string): boolean {\n return (\n fuzzysearch(word1.toLowerCase(), word2.toLowerCase()) ||\n fuzzysearch(word2.toLowerCase(), word1.toLowerCase())\n );\n}\n\n/**\n * Fuzzy match column names for a particular field\n *\n * @param allColumnNames - List of all column names\n * @param fuzzyMapName - The name of field being mapped to\n * @param isRequired - When true, don't include \"NONE\" as an option\n * @param canApplyAll - When true, include an option to specify the value in bulk\n * @returns The list of suggestions for inquirer\n */\nexport function fuzzyMatchColumns(\n allColumnNames: string[],\n fuzzyMapName: string,\n isRequired: boolean,\n canApplyAll?: boolean,\n): (string | InstanceType<typeof inquirer.Separator>)[] {\n const matchingColumnNames = allColumnNames.filter((x) =>\n fuzzySearch(fuzzyMapName.toLowerCase(), x.toLowerCase()),\n );\n return [\n ...matchingColumnNames,\n new inquirer.Separator(),\n ...(isRequired ? [] : [NONE]),\n ...(canApplyAll ? [BULK_APPLY] : []),\n ...allColumnNames.filter((x) => !matchingColumnNames.includes(x)),\n ];\n}\n"],"mappings":"uGAaA,SAAgB,EAAY,EAAe,EAAwB,CACjE,OACE,EAAY,EAAM,aAAa,CAAE,EAAM,aAAa,CAAC,EACrD,EAAY,EAAM,aAAa,CAAE,EAAM,aAAa,CAAC,CAazD,SAAgB,EACd,EACA,EACA,EACA,EACsD,CACtD,IAAM,EAAsB,EAAe,OAAQ,GACjD,EAAY,EAAa,aAAa,CAAE,EAAE,aAAa,CAAC,CACzD,CACD,MAAO,CACL,GAAG,EACH,IAAI,EAAS,UACb,GAAI,EAAa,EAAE,CAAG,CAAC,EAAK,CAC5B,GAAI,EAAc,CAAC,EAAW,CAAG,EAAE,CACnC,GAAG,EAAe,OAAQ,GAAM,CAAC,EAAoB,SAAS,EAAE,CAAC,CAClE"}
1
+ {"version":3,"file":"fuzzyMatchColumns-C1STZ_T1.mjs","names":[],"sources":["../src/lib/requests/fuzzyMatchColumns.ts"],"sourcesContent":["import fuzzysearch from 'fuzzysearch';\nimport inquirer from 'inquirer';\n\nimport { NONE, BULK_APPLY } from './constants.js';\n\n/**\n * Check if word1 and word2 are a fuzzy match of each other.\n * Returns true if word1 is fuzzy match of word2 or vice versa.\n *\n * @param word1 - First word\n * @param word2 - Second word\n * @returns True if words are fuzzy match\n */\nexport function fuzzySearch(word1: string, word2: string): boolean {\n return (\n fuzzysearch(word1.toLowerCase(), word2.toLowerCase()) ||\n fuzzysearch(word2.toLowerCase(), word1.toLowerCase())\n );\n}\n\n/**\n * Fuzzy match column names for a particular field\n *\n * @param allColumnNames - List of all column names\n * @param fuzzyMapName - The name of field being mapped to\n * @param isRequired - When true, don't include \"NONE\" as an option\n * @param canApplyAll - When true, include an option to specify the value in bulk\n * @returns The list of suggestions for inquirer\n */\nexport function fuzzyMatchColumns(\n allColumnNames: string[],\n fuzzyMapName: string,\n isRequired: boolean,\n canApplyAll?: boolean,\n): (string | InstanceType<typeof inquirer.Separator>)[] {\n const matchingColumnNames = allColumnNames.filter((x) =>\n fuzzySearch(fuzzyMapName.toLowerCase(), x.toLowerCase()),\n );\n return [\n ...matchingColumnNames,\n new inquirer.Separator(),\n ...(isRequired ? [] : [NONE]),\n ...(canApplyAll ? [BULK_APPLY] : []),\n ...allColumnNames.filter((x) => !matchingColumnNames.includes(x)),\n ];\n}\n"],"mappings":"uGAaA,SAAgB,EAAY,EAAe,EAAwB,CACjE,OACE,EAAY,EAAM,aAAa,CAAE,EAAM,aAAa,CAAC,EACrD,EAAY,EAAM,aAAa,CAAE,EAAM,aAAa,CAAC,CAazD,SAAgB,EACd,EACA,EACA,EACA,EACsD,CACtD,IAAM,EAAsB,EAAe,OAAQ,GACjD,EAAY,EAAa,aAAa,CAAE,EAAE,aAAa,CAAC,CACzD,CACD,MAAO,CACL,GAAG,EACH,IAAI,EAAS,UACb,GAAI,EAAa,EAAE,CAAG,CAAC,EAAK,CAC5B,GAAI,EAAc,CAAC,EAAW,CAAG,EAAE,CACnC,GAAG,EAAe,OAAQ,GAAM,CAAC,EAAoB,SAAS,EAAE,CAAC,CAClE"}
@@ -1,2 +1,2 @@
1
- import{a as e}from"./constants-Btn1yJ8a.mjs";import{t}from"./logger-Ckep4QXn.mjs";import n from"colors";import{assumeRole as r,buildTranscendGraphQLClientGeneric as i,createApiKey as a,deleteApiKey as o,fetchAllApiKeys as s,loginUser as c}from"@transcend-io/sdk";import{mapSeries as l}from"@transcend-io/utils";async function u({email:u,password:d,scopes:f,apiKeyTitle:p,parentOrganizationId:m,deleteExistingApiKey:h=!0,createNewApiKey:g=!0,transcendUrl:_=e}){let v=await i(_,{});t.info(n.magenta(`Logging in using email and password.`));let{roles:y,loginCookie:b}=await c(v,{email:u,password:d,logger:t});t.info(n.green(`Successfully logged in and found ${y.length} role${y.length===1?``:`s`}!`));let x=m?y.filter(e=>e.organization.id===m||e.organization.parentOrganizationId===m):y;v.setHeaders({Cookie:b});let S=[],C=[];return t.info(n.magenta(`Generating API keys with title: ${p}, scopes: ${f.join(`,`)}.`)),await l(x,async e=>{try{await r(v,{roleId:e.id,email:u,logger:t}),t.info(n.magenta(`Checking if API key already exists in organization "${e.organization.name}" with title: "${p}".`));let[i]=await s(v,{logger:t,filterBy:{titles:[p]}});if(i&&h)t.info(n.yellow(`Deleting existing API key in "${e.organization.name}" with title: "${p}".`)),await o(v,{id:i.id,logger:t}),t.info(n.green(`Successfully deleted API key in "${e.organization.name}" with title: "${p}".`));else if(i)throw Error(`API key already exists with title: "${p}"`);if(g){t.info(n.magenta(`Creating API key in "${e.organization.name}" with title: "${p}".`));let{apiKey:r}=await a(v,{input:{title:p,scopes:f},logger:t});S.push({organizationName:e.organization.name,organizationId:e.organization.id,apiKey:r}),t.info(n.green(`Successfully created API key in "${e.organization.name}" with title: "${p}".`))}else S.push({organizationName:e.organization.name,organizationId:e.organization.id,apiKey:``})}catch(r){t.error(n.red(`Failed to create API key in organization "${e.organization.name}"! - ${r.message}`)),C.push({organizationName:e.organization.name,organizationId:e.organization.id,error:r.message})}}),t.info(n.green(`Successfully created ${S.length} API key${S.length===1?``:`s`}`)),C.length>0&&t.error(n.red(`Failed to create ${C.length} API key${C.length===1?``:`s`}!`)),{errors:C,apiKeys:S}}export{u as t};
2
- //# sourceMappingURL=generateCrossAccountApiKeys-CTVfbS9-.mjs.map
1
+ import{a as e}from"./constants-DR-hU9Xj.mjs";import{t}from"./logger-Ckep4QXn.mjs";import n from"colors";import{assumeRole as r,buildTranscendGraphQLClientGeneric as i,createApiKey as a,deleteApiKey as o,fetchAllApiKeys as s,loginUser as c}from"@transcend-io/sdk";import{mapSeries as l}from"@transcend-io/utils";async function u({email:u,password:d,scopes:f,apiKeyTitle:p,parentOrganizationId:m,deleteExistingApiKey:h=!0,createNewApiKey:g=!0,transcendUrl:_=e}){let v=await i(_,{});t.info(n.magenta(`Logging in using email and password.`));let{roles:y,loginCookie:b}=await c(v,{email:u,password:d,logger:t});t.info(n.green(`Successfully logged in and found ${y.length} role${y.length===1?``:`s`}!`));let x=m?y.filter(e=>e.organization.id===m||e.organization.parentOrganizationId===m):y;v.setHeaders({Cookie:b});let S=[],C=[];return t.info(n.magenta(`Generating API keys with title: ${p}, scopes: ${f.join(`,`)}.`)),await l(x,async e=>{try{await r(v,{roleId:e.id,email:u,logger:t}),t.info(n.magenta(`Checking if API key already exists in organization "${e.organization.name}" with title: "${p}".`));let[i]=await s(v,{logger:t,filterBy:{titles:[p]}});if(i&&h)t.info(n.yellow(`Deleting existing API key in "${e.organization.name}" with title: "${p}".`)),await o(v,{id:i.id,logger:t}),t.info(n.green(`Successfully deleted API key in "${e.organization.name}" with title: "${p}".`));else if(i)throw Error(`API key already exists with title: "${p}"`);if(g){t.info(n.magenta(`Creating API key in "${e.organization.name}" with title: "${p}".`));let{apiKey:r}=await a(v,{input:{title:p,scopes:f},logger:t});S.push({organizationName:e.organization.name,organizationId:e.organization.id,apiKey:r}),t.info(n.green(`Successfully created API key in "${e.organization.name}" with title: "${p}".`))}else S.push({organizationName:e.organization.name,organizationId:e.organization.id,apiKey:``})}catch(r){t.error(n.red(`Failed to create API key in organization "${e.organization.name}"! - ${r.message}`)),C.push({organizationName:e.organization.name,organizationId:e.organization.id,error:r.message})}}),t.info(n.green(`Successfully created ${S.length} API key${S.length===1?``:`s`}`)),C.length>0&&t.error(n.red(`Failed to create ${C.length} API key${C.length===1?``:`s`}!`)),{errors:C,apiKeys:S}}export{u as t};
2
+ //# sourceMappingURL=generateCrossAccountApiKeys-DfGJ8Svq.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"generateCrossAccountApiKeys-CTVfbS9-.mjs","names":[],"sources":["../src/lib/api-keys/generateCrossAccountApiKeys.ts"],"sourcesContent":["import { ScopeName } from '@transcend-io/privacy-types';\nimport {\n buildTranscendGraphQLClientGeneric,\n loginUser,\n createApiKey,\n fetchAllApiKeys,\n deleteApiKey,\n assumeRole,\n} from '@transcend-io/sdk';\nimport { mapSeries } from '@transcend-io/utils';\nimport colors from 'colors';\n\nimport { StoredApiKey } from '../../codecs.js';\nimport { DEFAULT_TRANSCEND_API } from '../../constants.js';\nimport { logger } from '../../logger.js';\n\nexport interface ApiKeyGenerateError {\n /** Name of instance */\n organizationName: string;\n /** Error */\n error: string;\n /** Organization ID API key is for */\n organizationId: string;\n}\n\n/**\n * Generate API keys across multiple transcend accounts\n *\n * @param options - Options\n * @returns Number of API keys created\n */\nexport async function generateCrossAccountApiKeys({\n email,\n password,\n scopes,\n apiKeyTitle,\n parentOrganizationId,\n deleteExistingApiKey = true,\n createNewApiKey = true,\n transcendUrl = DEFAULT_TRANSCEND_API,\n}: {\n /** Email address of user generating API keys */\n email: string;\n /** Password of user generating API keys */\n password: string;\n /** Filter for organizations that match this parent organization ID */\n parentOrganizationId?: string;\n /** Title of the API create to create */\n apiKeyTitle: string;\n /** Title of the API create to create */\n scopes: ScopeName[];\n /** API URL for Transcend backend */\n transcendUrl?: string;\n /** When true delete existing API keys with that title, if set to false an API key exists with that title, an error is thrown */\n deleteExistingApiKey?: boolean;\n /** When true, generate new API keys, otherwise only will delete past API keys */\n createNewApiKey?: boolean;\n}): Promise<{\n /** Successfully generated */\n apiKeys: StoredApiKey[];\n /** Error results */\n errors: ApiKeyGenerateError[];\n}> {\n // Create GraphQL client\n const client = await buildTranscendGraphQLClientGeneric(transcendUrl, {});\n\n // Login the user\n logger.info(colors.magenta('Logging in using email and password.'));\n const { roles, loginCookie } = await loginUser(client, { email, password, logger });\n logger.info(\n colors.green(\n `Successfully logged in and found ${roles.length} role${roles.length === 1 ? '' : 's'}!`,\n ),\n );\n\n // Filter down by parentOrganizationId\n const filteredRoles = parentOrganizationId\n ? roles.filter(\n (role) =>\n role.organization.id === parentOrganizationId ||\n role.organization.parentOrganizationId === parentOrganizationId,\n )\n : roles;\n\n // Save cookie to call route subsequent times\n client.setHeaders({\n Cookie: loginCookie,\n });\n\n // Save the resulting API keys\n const results: StoredApiKey[] = [];\n const errors: ApiKeyGenerateError[] = [];\n\n // Generate API keys\n logger.info(\n colors.magenta(`Generating API keys with title: ${apiKeyTitle}, scopes: ${scopes.join(',')}.`),\n );\n\n // Map over each role\n await mapSeries(filteredRoles, async (role) => {\n try {\n // Log into the other instance\n await assumeRole(client, { roleId: role.id, email, logger });\n\n // Grab API keys with that title\n logger.info(\n colors.magenta(\n `Checking if API key already exists in organization \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n\n // Delete existing API key\n const [apiKeyWithTitle] = await fetchAllApiKeys(client, {\n logger,\n filterBy: { titles: [apiKeyTitle] },\n });\n if (apiKeyWithTitle && deleteExistingApiKey) {\n logger.info(\n colors.yellow(\n `Deleting existing API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n await deleteApiKey(client, { id: apiKeyWithTitle.id, logger });\n logger.info(\n colors.green(\n `Successfully deleted API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n } else if (apiKeyWithTitle) {\n // throw error if one exists but not configured to delete\n throw new Error(`API key already exists with title: \"${apiKeyTitle}\"`);\n }\n\n // Create the API key\n if (createNewApiKey) {\n logger.info(\n colors.magenta(\n `Creating API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n const { apiKey } = await createApiKey(client, {\n input: { title: apiKeyTitle, scopes },\n logger,\n });\n results.push({\n organizationName: role.organization.name,\n organizationId: role.organization.id,\n apiKey,\n });\n logger.info(\n colors.green(\n `Successfully created API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n } else {\n // Delete only\n results.push({\n organizationName: role.organization.name,\n organizationId: role.organization.id,\n apiKey: '',\n });\n }\n } catch (err) {\n logger.error(\n colors.red(\n `Failed to create API key in organization \"${role.organization.name}\"! - ${err.message}`,\n ),\n );\n errors.push({\n organizationName: role.organization.name,\n organizationId: role.organization.id,\n error: err.message,\n });\n }\n });\n logger.info(\n colors.green(\n `Successfully created ${results.length} API key${results.length === 1 ? '' : 's'}`,\n ),\n );\n\n if (errors.length > 0) {\n logger.error(\n colors.red(`Failed to create ${errors.length} API key${errors.length === 1 ? '' : 's'}!`),\n );\n }\n\n return { errors, apiKeys: results };\n}\n"],"mappings":"uTA+BA,eAAsB,EAA4B,CAChD,QACA,WACA,SACA,cACA,uBACA,uBAAuB,GACvB,kBAAkB,GAClB,eAAe,GAuBd,CAED,IAAM,EAAS,MAAM,EAAmC,EAAc,EAAE,CAAC,CAGzE,EAAO,KAAK,EAAO,QAAQ,uCAAuC,CAAC,CACnE,GAAM,CAAE,QAAO,eAAgB,MAAM,EAAU,EAAQ,CAAE,QAAO,WAAU,SAAQ,CAAC,CACnF,EAAO,KACL,EAAO,MACL,oCAAoC,EAAM,OAAO,OAAO,EAAM,SAAW,EAAI,GAAK,IAAI,GACvF,CACF,CAGD,IAAM,EAAgB,EAClB,EAAM,OACH,GACC,EAAK,aAAa,KAAO,GACzB,EAAK,aAAa,uBAAyB,EAC9C,CACD,EAGJ,EAAO,WAAW,CAChB,OAAQ,EACT,CAAC,CAGF,IAAM,EAA0B,EAAE,CAC5B,EAAgC,EAAE,CAgGxC,OA7FA,EAAO,KACL,EAAO,QAAQ,mCAAmC,EAAY,YAAY,EAAO,KAAK,IAAI,CAAC,GAAG,CAC/F,CAGD,MAAM,EAAU,EAAe,KAAO,IAAS,CAC7C,GAAI,CAEF,MAAM,EAAW,EAAQ,CAAE,OAAQ,EAAK,GAAI,QAAO,SAAQ,CAAC,CAG5D,EAAO,KACL,EAAO,QACL,uDAAuD,EAAK,aAAa,KAAK,iBAAiB,EAAY,IAC5G,CACF,CAGD,GAAM,CAAC,GAAmB,MAAM,EAAgB,EAAQ,CACtD,SACA,SAAU,CAAE,OAAQ,CAAC,EAAY,CAAE,CACpC,CAAC,CACF,GAAI,GAAmB,EACrB,EAAO,KACL,EAAO,OACL,iCAAiC,EAAK,aAAa,KAAK,iBAAiB,EAAY,IACtF,CACF,CACD,MAAM,EAAa,EAAQ,CAAE,GAAI,EAAgB,GAAI,SAAQ,CAAC,CAC9D,EAAO,KACL,EAAO,MACL,oCAAoC,EAAK,aAAa,KAAK,iBAAiB,EAAY,IACzF,CACF,SACQ,EAET,MAAU,MAAM,uCAAuC,EAAY,GAAG,CAIxE,GAAI,EAAiB,CACnB,EAAO,KACL,EAAO,QACL,wBAAwB,EAAK,aAAa,KAAK,iBAAiB,EAAY,IAC7E,CACF,CACD,GAAM,CAAE,UAAW,MAAM,EAAa,EAAQ,CAC5C,MAAO,CAAE,MAAO,EAAa,SAAQ,CACrC,SACD,CAAC,CACF,EAAQ,KAAK,CACX,iBAAkB,EAAK,aAAa,KACpC,eAAgB,EAAK,aAAa,GAClC,SACD,CAAC,CACF,EAAO,KACL,EAAO,MACL,oCAAoC,EAAK,aAAa,KAAK,iBAAiB,EAAY,IACzF,CACF,MAGD,EAAQ,KAAK,CACX,iBAAkB,EAAK,aAAa,KACpC,eAAgB,EAAK,aAAa,GAClC,OAAQ,GACT,CAAC,OAEG,EAAK,CACZ,EAAO,MACL,EAAO,IACL,6CAA6C,EAAK,aAAa,KAAK,OAAO,EAAI,UAChF,CACF,CACD,EAAO,KAAK,CACV,iBAAkB,EAAK,aAAa,KACpC,eAAgB,EAAK,aAAa,GAClC,MAAO,EAAI,QACZ,CAAC,GAEJ,CACF,EAAO,KACL,EAAO,MACL,wBAAwB,EAAQ,OAAO,UAAU,EAAQ,SAAW,EAAI,GAAK,MAC9E,CACF,CAEG,EAAO,OAAS,GAClB,EAAO,MACL,EAAO,IAAI,oBAAoB,EAAO,OAAO,UAAU,EAAO,SAAW,EAAI,GAAK,IAAI,GAAG,CAC1F,CAGI,CAAE,SAAQ,QAAS,EAAS"}
1
+ {"version":3,"file":"generateCrossAccountApiKeys-DfGJ8Svq.mjs","names":[],"sources":["../src/lib/api-keys/generateCrossAccountApiKeys.ts"],"sourcesContent":["import { ScopeName } from '@transcend-io/privacy-types';\nimport {\n buildTranscendGraphQLClientGeneric,\n loginUser,\n createApiKey,\n fetchAllApiKeys,\n deleteApiKey,\n assumeRole,\n} from '@transcend-io/sdk';\nimport { mapSeries } from '@transcend-io/utils';\nimport colors from 'colors';\n\nimport { StoredApiKey } from '../../codecs.js';\nimport { DEFAULT_TRANSCEND_API } from '../../constants.js';\nimport { logger } from '../../logger.js';\n\nexport interface ApiKeyGenerateError {\n /** Name of instance */\n organizationName: string;\n /** Error */\n error: string;\n /** Organization ID API key is for */\n organizationId: string;\n}\n\n/**\n * Generate API keys across multiple transcend accounts\n *\n * @param options - Options\n * @returns Number of API keys created\n */\nexport async function generateCrossAccountApiKeys({\n email,\n password,\n scopes,\n apiKeyTitle,\n parentOrganizationId,\n deleteExistingApiKey = true,\n createNewApiKey = true,\n transcendUrl = DEFAULT_TRANSCEND_API,\n}: {\n /** Email address of user generating API keys */\n email: string;\n /** Password of user generating API keys */\n password: string;\n /** Filter for organizations that match this parent organization ID */\n parentOrganizationId?: string;\n /** Title of the API create to create */\n apiKeyTitle: string;\n /** Title of the API create to create */\n scopes: ScopeName[];\n /** API URL for Transcend backend */\n transcendUrl?: string;\n /** When true delete existing API keys with that title, if set to false an API key exists with that title, an error is thrown */\n deleteExistingApiKey?: boolean;\n /** When true, generate new API keys, otherwise only will delete past API keys */\n createNewApiKey?: boolean;\n}): Promise<{\n /** Successfully generated */\n apiKeys: StoredApiKey[];\n /** Error results */\n errors: ApiKeyGenerateError[];\n}> {\n // Create GraphQL client\n const client = await buildTranscendGraphQLClientGeneric(transcendUrl, {});\n\n // Login the user\n logger.info(colors.magenta('Logging in using email and password.'));\n const { roles, loginCookie } = await loginUser(client, { email, password, logger });\n logger.info(\n colors.green(\n `Successfully logged in and found ${roles.length} role${roles.length === 1 ? '' : 's'}!`,\n ),\n );\n\n // Filter down by parentOrganizationId\n const filteredRoles = parentOrganizationId\n ? roles.filter(\n (role) =>\n role.organization.id === parentOrganizationId ||\n role.organization.parentOrganizationId === parentOrganizationId,\n )\n : roles;\n\n // Save cookie to call route subsequent times\n client.setHeaders({\n Cookie: loginCookie,\n });\n\n // Save the resulting API keys\n const results: StoredApiKey[] = [];\n const errors: ApiKeyGenerateError[] = [];\n\n // Generate API keys\n logger.info(\n colors.magenta(`Generating API keys with title: ${apiKeyTitle}, scopes: ${scopes.join(',')}.`),\n );\n\n // Map over each role\n await mapSeries(filteredRoles, async (role) => {\n try {\n // Log into the other instance\n await assumeRole(client, { roleId: role.id, email, logger });\n\n // Grab API keys with that title\n logger.info(\n colors.magenta(\n `Checking if API key already exists in organization \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n\n // Delete existing API key\n const [apiKeyWithTitle] = await fetchAllApiKeys(client, {\n logger,\n filterBy: { titles: [apiKeyTitle] },\n });\n if (apiKeyWithTitle && deleteExistingApiKey) {\n logger.info(\n colors.yellow(\n `Deleting existing API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n await deleteApiKey(client, { id: apiKeyWithTitle.id, logger });\n logger.info(\n colors.green(\n `Successfully deleted API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n } else if (apiKeyWithTitle) {\n // throw error if one exists but not configured to delete\n throw new Error(`API key already exists with title: \"${apiKeyTitle}\"`);\n }\n\n // Create the API key\n if (createNewApiKey) {\n logger.info(\n colors.magenta(\n `Creating API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n const { apiKey } = await createApiKey(client, {\n input: { title: apiKeyTitle, scopes },\n logger,\n });\n results.push({\n organizationName: role.organization.name,\n organizationId: role.organization.id,\n apiKey,\n });\n logger.info(\n colors.green(\n `Successfully created API key in \"${role.organization.name}\" with title: \"${apiKeyTitle}\".`,\n ),\n );\n } else {\n // Delete only\n results.push({\n organizationName: role.organization.name,\n organizationId: role.organization.id,\n apiKey: '',\n });\n }\n } catch (err) {\n logger.error(\n colors.red(\n `Failed to create API key in organization \"${role.organization.name}\"! - ${err.message}`,\n ),\n );\n errors.push({\n organizationName: role.organization.name,\n organizationId: role.organization.id,\n error: err.message,\n });\n }\n });\n logger.info(\n colors.green(\n `Successfully created ${results.length} API key${results.length === 1 ? '' : 's'}`,\n ),\n );\n\n if (errors.length > 0) {\n logger.error(\n colors.red(`Failed to create ${errors.length} API key${errors.length === 1 ? '' : 's'}!`),\n );\n }\n\n return { errors, apiKeys: results };\n}\n"],"mappings":"uTA+BA,eAAsB,EAA4B,CAChD,QACA,WACA,SACA,cACA,uBACA,uBAAuB,GACvB,kBAAkB,GAClB,eAAe,GAuBd,CAED,IAAM,EAAS,MAAM,EAAmC,EAAc,EAAE,CAAC,CAGzE,EAAO,KAAK,EAAO,QAAQ,uCAAuC,CAAC,CACnE,GAAM,CAAE,QAAO,eAAgB,MAAM,EAAU,EAAQ,CAAE,QAAO,WAAU,SAAQ,CAAC,CACnF,EAAO,KACL,EAAO,MACL,oCAAoC,EAAM,OAAO,OAAO,EAAM,SAAW,EAAI,GAAK,IAAI,GACvF,CACF,CAGD,IAAM,EAAgB,EAClB,EAAM,OACH,GACC,EAAK,aAAa,KAAO,GACzB,EAAK,aAAa,uBAAyB,EAC9C,CACD,EAGJ,EAAO,WAAW,CAChB,OAAQ,EACT,CAAC,CAGF,IAAM,EAA0B,EAAE,CAC5B,EAAgC,EAAE,CAgGxC,OA7FA,EAAO,KACL,EAAO,QAAQ,mCAAmC,EAAY,YAAY,EAAO,KAAK,IAAI,CAAC,GAAG,CAC/F,CAGD,MAAM,EAAU,EAAe,KAAO,IAAS,CAC7C,GAAI,CAEF,MAAM,EAAW,EAAQ,CAAE,OAAQ,EAAK,GAAI,QAAO,SAAQ,CAAC,CAG5D,EAAO,KACL,EAAO,QACL,uDAAuD,EAAK,aAAa,KAAK,iBAAiB,EAAY,IAC5G,CACF,CAGD,GAAM,CAAC,GAAmB,MAAM,EAAgB,EAAQ,CACtD,SACA,SAAU,CAAE,OAAQ,CAAC,EAAY,CAAE,CACpC,CAAC,CACF,GAAI,GAAmB,EACrB,EAAO,KACL,EAAO,OACL,iCAAiC,EAAK,aAAa,KAAK,iBAAiB,EAAY,IACtF,CACF,CACD,MAAM,EAAa,EAAQ,CAAE,GAAI,EAAgB,GAAI,SAAQ,CAAC,CAC9D,EAAO,KACL,EAAO,MACL,oCAAoC,EAAK,aAAa,KAAK,iBAAiB,EAAY,IACzF,CACF,SACQ,EAET,MAAU,MAAM,uCAAuC,EAAY,GAAG,CAIxE,GAAI,EAAiB,CACnB,EAAO,KACL,EAAO,QACL,wBAAwB,EAAK,aAAa,KAAK,iBAAiB,EAAY,IAC7E,CACF,CACD,GAAM,CAAE,UAAW,MAAM,EAAa,EAAQ,CAC5C,MAAO,CAAE,MAAO,EAAa,SAAQ,CACrC,SACD,CAAC,CACF,EAAQ,KAAK,CACX,iBAAkB,EAAK,aAAa,KACpC,eAAgB,EAAK,aAAa,GAClC,SACD,CAAC,CACF,EAAO,KACL,EAAO,MACL,oCAAoC,EAAK,aAAa,KAAK,iBAAiB,EAAY,IACzF,CACF,MAGD,EAAQ,KAAK,CACX,iBAAkB,EAAK,aAAa,KACpC,eAAgB,EAAK,aAAa,GAClC,OAAQ,GACT,CAAC,OAEG,EAAK,CACZ,EAAO,MACL,EAAO,IACL,6CAA6C,EAAK,aAAa,KAAK,OAAO,EAAI,UAChF,CACF,CACD,EAAO,KAAK,CACV,iBAAkB,EAAK,aAAa,KACpC,eAAgB,EAAK,aAAa,GAClC,MAAO,EAAI,QACZ,CAAC,GAEJ,CACF,EAAO,KACL,EAAO,MACL,wBAAwB,EAAQ,OAAO,UAAU,EAAQ,SAAW,EAAI,GAAK,MAC9E,CACF,CAEG,EAAO,OAAS,GAClB,EAAO,MACL,EAAO,IAAI,oBAAoB,EAAO,OAAO,UAAU,EAAO,SAAW,EAAI,GAAK,IAAI,GAAG,CAC1F,CAGI,CAAE,SAAQ,QAAS,EAAS"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./logger-Ckep4QXn.mjs";import{t}from"./readCsv-C84Jhrzx.mjs";import{t as n}from"./markRequestDataSiloIdsCompleted-gl4RNpl7.mjs";import{t as r}from"./done-input-validation-uqIgnJcw.mjs";import i from"colors";import*as a from"io-ts";const o=a.type({"Request Id":a.string});async function s({auth:a,dataSiloId:s,file:c,transcendUrl:l}){r(this.process.exit),e.info(i.magenta(`Reading "${c}" from disk`)),await n({requestIds:t(c,o).map(e=>e[`Request Id`]),transcendUrl:l,auth:a,dataSiloId:s})}export{s as markRequestDataSilosCompleted};
2
- //# sourceMappingURL=impl-D1X9qygD2.mjs.map
1
+ import{t as e}from"./logger-Ckep4QXn.mjs";import{t}from"./readCsv--FfP8n-H.mjs";import{t as n}from"./markRequestDataSiloIdsCompleted-CklEg1h9.mjs";import{t as r}from"./done-input-validation-uqIgnJcw.mjs";import i from"colors";import*as a from"io-ts";const o=a.type({"Request Id":a.string});async function s({auth:a,dataSiloId:s,file:c,transcendUrl:l}){r(this.process.exit),e.info(i.magenta(`Reading "${c}" from disk`)),await n({requestIds:t(c,o).map(e=>e[`Request Id`]),transcendUrl:l,auth:a,dataSiloId:s})}export{s as markRequestDataSilosCompleted};
2
+ //# sourceMappingURL=impl-4heSgrC92.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-D1X9qygD2.mjs","names":[],"sources":["../src/commands/request/system/mark-request-data-silos-completed/impl.ts"],"sourcesContent":["import colors from 'colors';\nimport * as t from 'io-ts';\n\nimport type { LocalContext } from '../../../../context.js';\nimport { doneInputValidation } from '../../../../lib/cli/done-input-validation.js';\nimport { markRequestDataSiloIdsCompleted } from '../../../../lib/cron/index.js';\nimport { readCsv } from '../../../../lib/requests/index.js';\nimport { logger } from '../../../../logger.js';\n\nconst RequestIdRow = t.type({\n 'Request Id': t.string,\n});\n\nexport interface MarkRequestDataSilosCompletedCommandFlags {\n auth: string;\n dataSiloId: string;\n file: string;\n transcendUrl: string;\n}\n\nexport async function markRequestDataSilosCompleted(\n this: LocalContext,\n { auth, dataSiloId, file, transcendUrl }: MarkRequestDataSilosCompletedCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n logger.info(colors.magenta(`Reading \"${file}\" from disk`));\n const activeResults = readCsv(file, RequestIdRow);\n\n await markRequestDataSiloIdsCompleted({\n requestIds: activeResults.map((request) => request['Request Id']),\n transcendUrl,\n auth,\n dataSiloId,\n });\n}\n"],"mappings":"0PASA,MAAM,EAAe,EAAE,KAAK,CAC1B,aAAc,EAAE,OACjB,CAAC,CASF,eAAsB,EAEpB,CAAE,OAAM,aAAY,OAAM,gBACX,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,EAAO,KAAK,EAAO,QAAQ,YAAY,EAAK,aAAa,CAAC,CAG1D,MAAM,EAAgC,CACpC,WAHoB,EAAQ,EAAM,EAGT,CAAC,IAAK,GAAY,EAAQ,cAAc,CACjE,eACA,OACA,aACD,CAAC"}
1
+ {"version":3,"file":"impl-4heSgrC92.mjs","names":[],"sources":["../src/commands/request/system/mark-request-data-silos-completed/impl.ts"],"sourcesContent":["import colors from 'colors';\nimport * as t from 'io-ts';\n\nimport type { LocalContext } from '../../../../context.js';\nimport { doneInputValidation } from '../../../../lib/cli/done-input-validation.js';\nimport { markRequestDataSiloIdsCompleted } from '../../../../lib/cron/index.js';\nimport { readCsv } from '../../../../lib/requests/index.js';\nimport { logger } from '../../../../logger.js';\n\nconst RequestIdRow = t.type({\n 'Request Id': t.string,\n});\n\nexport interface MarkRequestDataSilosCompletedCommandFlags {\n auth: string;\n dataSiloId: string;\n file: string;\n transcendUrl: string;\n}\n\nexport async function markRequestDataSilosCompleted(\n this: LocalContext,\n { auth, dataSiloId, file, transcendUrl }: MarkRequestDataSilosCompletedCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n logger.info(colors.magenta(`Reading \"${file}\" from disk`));\n const activeResults = readCsv(file, RequestIdRow);\n\n await markRequestDataSiloIdsCompleted({\n requestIds: activeResults.map((request) => request['Request Id']),\n transcendUrl,\n auth,\n dataSiloId,\n });\n}\n"],"mappings":"0PASA,MAAM,EAAe,EAAE,KAAK,CAC1B,aAAc,EAAE,OACjB,CAAC,CASF,eAAsB,EAEpB,CAAE,OAAM,aAAY,OAAM,gBACX,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,EAAO,KAAK,EAAO,QAAQ,YAAY,EAAK,aAAa,CAAC,CAG1D,MAAM,EAAgC,CACpC,WAHoB,EAAQ,EAAM,EAGT,CAAC,IAAK,GAAY,EAAQ,cAAc,CACjE,eACA,OACA,aACD,CAAC"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./approvePrivacyRequests-BQpI-RdX.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,actions:r,origins:i,silentModeBefore:a,createdAtBefore:o,createdAtAfter:s,updatedAtBefore:c,updatedAtAfter:l,transcendUrl:u,concurrency:d}){t(this.process.exit),await e({transcendUrl:u,requestActions:r,auth:n,requestOrigins:i,concurrency:d,silentModeBefore:a,createdAtBefore:o,createdAtAfter:s,updatedAtBefore:c,updatedAtAfter:l})}export{n as approve};
2
- //# sourceMappingURL=impl-Wyz88FnA2.mjs.map
1
+ import{t as e}from"./approvePrivacyRequests-qaoxGH11.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,actions:r,origins:i,silentModeBefore:a,createdAtBefore:o,createdAtAfter:s,updatedAtBefore:c,updatedAtAfter:l,transcendUrl:u,concurrency:d}){t(this.process.exit),await e({transcendUrl:u,requestActions:r,auth:n,requestOrigins:i,concurrency:d,silentModeBefore:a,createdAtBefore:o,createdAtAfter:s,updatedAtBefore:c,updatedAtAfter:l})}export{n as approve};
2
+ //# sourceMappingURL=impl-4oiDSr3J2.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-Wyz88FnA2.mjs","names":[],"sources":["../src/commands/request/approve/impl.ts"],"sourcesContent":["import { RequestAction, RequestOrigin } from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { approvePrivacyRequests } from '../../../lib/requests/index.js';\n\nexport interface ApproveCommandFlags {\n auth: string;\n actions: RequestAction[];\n origins?: RequestOrigin[];\n silentModeBefore?: Date;\n createdAtBefore?: Date;\n createdAtAfter?: Date;\n updatedAtBefore?: Date;\n updatedAtAfter?: Date;\n transcendUrl: string;\n concurrency: number;\n}\n\nexport async function approve(\n this: LocalContext,\n {\n auth,\n actions,\n origins,\n silentModeBefore,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n transcendUrl,\n concurrency,\n }: ApproveCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n await approvePrivacyRequests({\n transcendUrl,\n requestActions: actions,\n auth,\n requestOrigins: origins,\n concurrency,\n silentModeBefore,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n });\n}\n"],"mappings":"8GAmBA,eAAsB,EAEpB,CACE,OACA,UACA,UACA,mBACA,kBACA,iBACA,kBACA,iBACA,eACA,eAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,MAAM,EAAuB,CAC3B,eACA,eAAgB,EAChB,OACA,eAAgB,EAChB,cACA,mBACA,kBACA,iBACA,kBACA,iBACD,CAAC"}
1
+ {"version":3,"file":"impl-4oiDSr3J2.mjs","names":[],"sources":["../src/commands/request/approve/impl.ts"],"sourcesContent":["import { RequestAction, RequestOrigin } from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { approvePrivacyRequests } from '../../../lib/requests/index.js';\n\nexport interface ApproveCommandFlags {\n auth: string;\n actions: RequestAction[];\n origins?: RequestOrigin[];\n silentModeBefore?: Date;\n createdAtBefore?: Date;\n createdAtAfter?: Date;\n updatedAtBefore?: Date;\n updatedAtAfter?: Date;\n transcendUrl: string;\n concurrency: number;\n}\n\nexport async function approve(\n this: LocalContext,\n {\n auth,\n actions,\n origins,\n silentModeBefore,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n transcendUrl,\n concurrency,\n }: ApproveCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n await approvePrivacyRequests({\n transcendUrl,\n requestActions: actions,\n auth,\n requestOrigins: origins,\n concurrency,\n silentModeBefore,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n });\n}\n"],"mappings":"8GAmBA,eAAsB,EAEpB,CACE,OACA,UACA,UACA,mBACA,kBACA,iBACA,kBACA,iBACA,eACA,eAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,MAAM,EAAuB,CAC3B,eACA,eAAgB,EAChB,OACA,eAAgB,EAChB,cACA,mBACA,kBACA,iBACA,kBACA,iBACD,CAAC"}
@@ -1,2 +1,2 @@
1
- import{r as e}from"./constants-Btn1yJ8a.mjs";import{t}from"./logger-Ckep4QXn.mjs";import{r as n}from"./readTranscendYaml-dI3G3Og9.mjs";import{n as r,r as i,t as a}from"./parseVariablesFromString-RM3zV9Av.mjs";import{t as o}from"./validateTranscendAuth-DhzCBA3F.mjs";import{t as s}from"./listFiles-BPx3iDV6.mjs";import{t as c}from"./done-input-validation-uqIgnJcw.mjs";import{existsSync as l,lstatSync as u}from"node:fs";import{join as d}from"node:path";import f from"colors";import{buildTranscendGraphQLClient as p}from"@transcend-io/sdk";import{mapSeries as m}from"@transcend-io/utils";async function h({transcendUrl:e,auth:n,pageSize:r,publishToPrivacyCenter:a,contents:o,deleteExtraAttributeValues:s=!1,classifyService:c=!1}){let l=p(e,n);try{let e=await i(o,l,{pageSize:r,publishToPrivacyCenter:a,classifyService:c,deleteExtraAttributeValues:s,logger:t});return e.success||e.errors.forEach(({resource:e,item:n,message:r})=>{t.error(f.red(`Failed to sync ${e}${n?` "${n}"`:``}: ${r}`))}),e.success}catch(e){return t.error(f.red(`An unexpected error occurred syncing the schema: ${e.message}`)),!1}}async function g({file:i=`./transcend.yml`,transcendUrl:p,auth:g,variables:_,pageSize:v,publishToPrivacyCenter:y,classifyService:b,deleteExtraAttributeValues:x}){c(this.process.exit);let S=await o(g),C=a(_),w;if(w=Array.isArray(S)&&u(i).isDirectory()?s(i).map(e=>d(i,e)):i.split(`,`),w.length<1)throw Error(`No file specified!`);let T=w.map(e=>{l(e)?t.info(f.magenta(`Reading file "${e}"...`)):(t.error(f.red(`The file path does not exist on disk: ${e}. You can specify the filepath using --file=./examples/transcend.yml`)),this.process.exit(1));try{let r=n(e,C);return t.info(f.green(`Successfully read in "${e}"`)),{content:r,name:e.split(`/`).pop().replace(`.yml`,``)}}catch(e){t.error(f.red(`The shape of your yaml file is invalid with the following errors: ${e.message}`)),this.process.exit(1)}});if(typeof S==`string`){let[n,...i]=T.map(({content:e})=>e);await h({transcendUrl:p,auth:S,contents:r(n,...i),publishToPrivacyCenter:y,deleteExtraAttributeValues:x,pageSize:v,classifyService:!!b})||(t.info(f.red(`Sync encountered errors. View output above for more information, or check out ${e}`)),this.process.exit(1))}else{if(T.length!==1&&T.length!==S.length)throw Error(`Expected list of yml files to be equal to the list of API keys.Got ${T.length} YML file${T.length===1?``:`s`} and ${S.length} API key${S.length===1?``:`s`}`);let n=[];await m(S,async(e,r)=>{let i=`[${r+1}/${S.length}][${e.organizationName}] `;t.info(f.magenta(`~~~\n\n${i}Attempting to push configuration...\n\n~~~`));let a=T.length===1?T[0].content:T.find(t=>t.name===e.organizationName)?.content;if(!a){t.error(f.red(`${i}Failed to find transcend.yml file for organization: "${e.organizationName}".`)),n.push(e.organizationName);return}await h({transcendUrl:p,auth:e.apiKey,contents:a,pageSize:v,publishToPrivacyCenter:y,deleteExtraAttributeValues:x,classifyService:b})?t.info(f.green(`${i}Successfully pushed configuration!`)):(t.error(f.red(`${i}Failed to sync configuration.`)),n.push(e.organizationName))}),n.length>0&&(t.info(f.red(`Sync encountered errors for "${n.join(`,`)}". View output above for more information, or check out ${e}`)),this.process.exit(1))}t.info(f.green(`Successfully synced yaml file to Transcend! View at ${e}`))}export{g as push};
2
- //# sourceMappingURL=impl-Bug3axux.mjs.map
1
+ import{r as e}from"./constants-DR-hU9Xj.mjs";import{t}from"./logger-Ckep4QXn.mjs";import{r as n}from"./readTranscendYaml-CWIS9ki1.mjs";import{n as r,r as i,t as a}from"./parseVariablesFromString-6ZwJyWSu.mjs";import{t as o}from"./validateTranscendAuth-CbYKgCP5.mjs";import{t as s}from"./listFiles-BPx3iDV6.mjs";import{t as c}from"./done-input-validation-uqIgnJcw.mjs";import{existsSync as l,lstatSync as u}from"node:fs";import{join as d}from"node:path";import f from"colors";import{buildTranscendGraphQLClient as p}from"@transcend-io/sdk";import{mapSeries as m}from"@transcend-io/utils";async function h({transcendUrl:e,auth:n,pageSize:r,publishToPrivacyCenter:a,contents:o,deleteExtraAttributeValues:s=!1,classifyService:c=!1}){let l=p(e,n);try{let e=await i(o,l,{pageSize:r,publishToPrivacyCenter:a,classifyService:c,deleteExtraAttributeValues:s,logger:t});return e.success||e.errors.forEach(({resource:e,item:n,message:r})=>{t.error(f.red(`Failed to sync ${e}${n?` "${n}"`:``}: ${r}`))}),e.success}catch(e){return t.error(f.red(`An unexpected error occurred syncing the schema: ${e.message}`)),!1}}async function g({file:i=`./transcend.yml`,transcendUrl:p,auth:g,variables:_,pageSize:v,publishToPrivacyCenter:y,classifyService:b,deleteExtraAttributeValues:x}){c(this.process.exit);let S=await o(g),C=a(_),w;if(w=Array.isArray(S)&&u(i).isDirectory()?s(i).map(e=>d(i,e)):i.split(`,`),w.length<1)throw Error(`No file specified!`);let T=w.map(e=>{l(e)?t.info(f.magenta(`Reading file "${e}"...`)):(t.error(f.red(`The file path does not exist on disk: ${e}. You can specify the filepath using --file=./examples/transcend.yml`)),this.process.exit(1));try{let r=n(e,C);return t.info(f.green(`Successfully read in "${e}"`)),{content:r,name:e.split(`/`).pop().replace(`.yml`,``)}}catch(e){t.error(f.red(`The shape of your yaml file is invalid with the following errors: ${e.message}`)),this.process.exit(1)}});if(typeof S==`string`){let[n,...i]=T.map(({content:e})=>e);await h({transcendUrl:p,auth:S,contents:r(n,...i),publishToPrivacyCenter:y,deleteExtraAttributeValues:x,pageSize:v,classifyService:!!b})||(t.info(f.red(`Sync encountered errors. View output above for more information, or check out ${e}`)),this.process.exit(1))}else{if(T.length!==1&&T.length!==S.length)throw Error(`Expected list of yml files to be equal to the list of API keys.Got ${T.length} YML file${T.length===1?``:`s`} and ${S.length} API key${S.length===1?``:`s`}`);let n=[];await m(S,async(e,r)=>{let i=`[${r+1}/${S.length}][${e.organizationName}] `;t.info(f.magenta(`~~~\n\n${i}Attempting to push configuration...\n\n~~~`));let a=T.length===1?T[0].content:T.find(t=>t.name===e.organizationName)?.content;if(!a){t.error(f.red(`${i}Failed to find transcend.yml file for organization: "${e.organizationName}".`)),n.push(e.organizationName);return}await h({transcendUrl:p,auth:e.apiKey,contents:a,pageSize:v,publishToPrivacyCenter:y,deleteExtraAttributeValues:x,classifyService:b})?t.info(f.green(`${i}Successfully pushed configuration!`)):(t.error(f.red(`${i}Failed to sync configuration.`)),n.push(e.organizationName))}),n.length>0&&(t.info(f.red(`Sync encountered errors for "${n.join(`,`)}". View output above for more information, or check out ${e}`)),this.process.exit(1))}t.info(f.green(`Successfully synced yaml file to Transcend! View at ${e}`))}export{g as push};
2
+ //# sourceMappingURL=impl-8gLOHK9a.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-Bug3axux.mjs","names":[],"sources":["../src/commands/inventory/push/impl.ts"],"sourcesContent":["import { existsSync, lstatSync } from 'node:fs';\nimport { join } from 'node:path';\n\nimport { buildTranscendGraphQLClient } from '@transcend-io/sdk';\nimport { mapSeries } from '@transcend-io/utils';\nimport colors from 'colors';\n\nimport { TranscendInput } from '../../../codecs.js';\nimport { ADMIN_DASH_INTEGRATIONS } from '../../../constants.js';\nimport type { LocalContext } from '../../../context.js';\nimport { validateTranscendAuth, listFiles } from '../../../lib/api-keys/index.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { syncConfigurationToTranscend } from '../../../lib/graphql/index.js';\nimport { parseVariablesFromString } from '../../../lib/helpers/parseVariablesFromString.js';\nimport { mergeTranscendInputs } from '../../../lib/mergeTranscendInputs.js';\nimport { readTranscendYaml } from '../../../lib/readTranscendYaml.js';\nimport { logger } from '../../../logger.js';\n\n/**\n * Sync configuration to Transcend\n *\n * @param options - Options\n * @returns True if synced successfully, false if error occurs\n */\nasync function syncConfiguration({\n transcendUrl,\n auth,\n pageSize,\n publishToPrivacyCenter,\n contents,\n deleteExtraAttributeValues = false,\n classifyService = false,\n}: {\n /** Transcend YAML */\n contents: TranscendInput;\n /** Transcend URL */\n transcendUrl: string;\n /** API key */\n auth: string;\n /** Page size */\n pageSize: number;\n /** Skip privacy center publish step */\n publishToPrivacyCenter: boolean;\n /** classify data flow service if missing */\n classifyService?: boolean;\n /** Delete attributes when syncing */\n deleteExtraAttributeValues?: boolean;\n}): Promise<boolean> {\n const client = buildTranscendGraphQLClient(transcendUrl, auth);\n\n // Sync to Transcend\n try {\n const result = await syncConfigurationToTranscend(contents, client, {\n pageSize,\n publishToPrivacyCenter,\n classifyService,\n deleteExtraAttributeValues,\n logger,\n });\n if (!result.success) {\n result.errors.forEach(({ resource, item, message }) => {\n logger.error(\n colors.red(`Failed to sync ${resource}${item ? ` \"${item}\"` : ''}: ${message}`),\n );\n });\n }\n return result.success;\n } catch (err) {\n logger.error(colors.red(`An unexpected error occurred syncing the schema: ${err.message}`));\n return false;\n }\n}\n\nexport interface PushCommandFlags {\n auth: string;\n file: string;\n transcendUrl: string;\n pageSize: number;\n variables: string;\n publishToPrivacyCenter: boolean;\n classifyService: boolean;\n deleteExtraAttributeValues: boolean;\n}\n\nexport async function push(\n this: LocalContext,\n {\n file = './transcend.yml',\n transcendUrl,\n auth,\n variables,\n pageSize,\n publishToPrivacyCenter,\n classifyService,\n deleteExtraAttributeValues,\n }: PushCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n // Parse authentication as API key or path to list of API keys\n const apiKeyOrList = await validateTranscendAuth(auth);\n\n // Parse out the variables\n const vars = parseVariablesFromString(variables);\n\n // check if we are being passed a list of API keys and a list of files\n let fileList: string[];\n if (Array.isArray(apiKeyOrList) && lstatSync(file).isDirectory()) {\n fileList = listFiles(file).map((filePath) => join(file, filePath));\n } else {\n fileList = file.split(',');\n }\n\n // Ensure at least one file is parsed\n if (fileList.length < 1) {\n throw new Error('No file specified!');\n }\n\n // eslint-disable-next-line array-callback-return,consistent-return\n const transcendInputs = fileList.map((filePath) => {\n // Ensure yaml file exists on disk\n if (!existsSync(filePath)) {\n logger.error(\n colors.red(\n `The file path does not exist on disk: ${filePath}. You can specify the filepath using --file=./examples/transcend.yml`,\n ),\n );\n this.process.exit(1);\n } else {\n logger.info(colors.magenta(`Reading file \"${filePath}\"...`));\n }\n\n try {\n // Read in the yaml file and validate it's shape\n const newContents = readTranscendYaml(filePath, vars);\n logger.info(colors.green(`Successfully read in \"${filePath}\"`));\n return {\n content: newContents,\n name: filePath.split('/').pop()!.replace('.yml', ''),\n };\n } catch (err) {\n logger.error(\n colors.red(\n `The shape of your yaml file is invalid with the following errors: ${err.message}`,\n ),\n );\n this.process.exit(1);\n }\n });\n\n // process a single API key\n if (typeof apiKeyOrList === 'string') {\n // if passed multiple inputs, merge them together\n const [base, ...rest] = transcendInputs.map(({ content }) => content);\n const contents = mergeTranscendInputs(base, ...rest);\n\n // sync the configuration\n const success = await syncConfiguration({\n transcendUrl,\n auth: apiKeyOrList,\n contents,\n publishToPrivacyCenter,\n deleteExtraAttributeValues,\n pageSize,\n classifyService: !!classifyService,\n });\n\n // exist with error code\n if (!success) {\n logger.info(\n colors.red(\n `Sync encountered errors. View output above for more information, or check out ${ADMIN_DASH_INTEGRATIONS}`,\n ),\n );\n\n this.process.exit(1);\n }\n } else {\n // if passed multiple inputs, expect them to be one per instance\n if (transcendInputs.length !== 1 && transcendInputs.length !== apiKeyOrList.length) {\n throw new Error(\n 'Expected list of yml files to be equal to the list of API keys.' +\n `Got ${transcendInputs.length} YML file${\n transcendInputs.length === 1 ? '' : 's'\n } and ${apiKeyOrList.length} API key${apiKeyOrList.length === 1 ? '' : 's'}`,\n );\n }\n\n const encounteredErrors: string[] = [];\n await mapSeries(apiKeyOrList, async (apiKey, ind) => {\n const prefix = `[${ind + 1}/${apiKeyOrList.length}][${apiKey.organizationName}] `;\n logger.info(colors.magenta(`~~~\\n\\n${prefix}Attempting to push configuration...\\n\\n~~~`));\n\n // use the merged contents if 1 yml passed, else use the contents that map to that organization\n const useContents =\n transcendInputs.length === 1\n ? transcendInputs[0].content\n : transcendInputs.find((input) => input.name === apiKey.organizationName)?.content;\n\n // Throw error if cannot find a yml file matching that organization name\n if (!useContents) {\n logger.error(\n colors.red(\n `${prefix}Failed to find transcend.yml file for organization: \"${apiKey.organizationName}\".`,\n ),\n );\n encounteredErrors.push(apiKey.organizationName);\n return;\n }\n\n const success = await syncConfiguration({\n transcendUrl,\n auth: apiKey.apiKey,\n contents: useContents,\n pageSize,\n publishToPrivacyCenter,\n deleteExtraAttributeValues,\n classifyService,\n });\n\n if (success) {\n logger.info(colors.green(`${prefix}Successfully pushed configuration!`));\n } else {\n logger.error(colors.red(`${prefix}Failed to sync configuration.`));\n encounteredErrors.push(apiKey.organizationName);\n }\n });\n\n if (encounteredErrors.length > 0) {\n logger.info(\n colors.red(\n `Sync encountered errors for \"${encounteredErrors.join(\n ',',\n )}\". View output above for more information, or check out ${ADMIN_DASH_INTEGRATIONS}`,\n ),\n );\n\n this.process.exit(1);\n }\n }\n\n // Indicate success\n logger.info(\n colors.green(`Successfully synced yaml file to Transcend! View at ${ADMIN_DASH_INTEGRATIONS}`),\n );\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"impl-8gLOHK9a.mjs","names":[],"sources":["../src/commands/inventory/push/impl.ts"],"sourcesContent":["import { existsSync, lstatSync } from 'node:fs';\nimport { join } from 'node:path';\n\nimport { buildTranscendGraphQLClient } from '@transcend-io/sdk';\nimport { mapSeries } from '@transcend-io/utils';\nimport colors from 'colors';\n\nimport { TranscendInput } from '../../../codecs.js';\nimport { ADMIN_DASH_INTEGRATIONS } from '../../../constants.js';\nimport type { LocalContext } from '../../../context.js';\nimport { validateTranscendAuth, listFiles } from '../../../lib/api-keys/index.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { syncConfigurationToTranscend } from '../../../lib/graphql/index.js';\nimport { parseVariablesFromString } from '../../../lib/helpers/parseVariablesFromString.js';\nimport { mergeTranscendInputs } from '../../../lib/mergeTranscendInputs.js';\nimport { readTranscendYaml } from '../../../lib/readTranscendYaml.js';\nimport { logger } from '../../../logger.js';\n\n/**\n * Sync configuration to Transcend\n *\n * @param options - Options\n * @returns True if synced successfully, false if error occurs\n */\nasync function syncConfiguration({\n transcendUrl,\n auth,\n pageSize,\n publishToPrivacyCenter,\n contents,\n deleteExtraAttributeValues = false,\n classifyService = false,\n}: {\n /** Transcend YAML */\n contents: TranscendInput;\n /** Transcend URL */\n transcendUrl: string;\n /** API key */\n auth: string;\n /** Page size */\n pageSize: number;\n /** Skip privacy center publish step */\n publishToPrivacyCenter: boolean;\n /** classify data flow service if missing */\n classifyService?: boolean;\n /** Delete attributes when syncing */\n deleteExtraAttributeValues?: boolean;\n}): Promise<boolean> {\n const client = buildTranscendGraphQLClient(transcendUrl, auth);\n\n // Sync to Transcend\n try {\n const result = await syncConfigurationToTranscend(contents, client, {\n pageSize,\n publishToPrivacyCenter,\n classifyService,\n deleteExtraAttributeValues,\n logger,\n });\n if (!result.success) {\n result.errors.forEach(({ resource, item, message }) => {\n logger.error(\n colors.red(`Failed to sync ${resource}${item ? ` \"${item}\"` : ''}: ${message}`),\n );\n });\n }\n return result.success;\n } catch (err) {\n logger.error(colors.red(`An unexpected error occurred syncing the schema: ${err.message}`));\n return false;\n }\n}\n\nexport interface PushCommandFlags {\n auth: string;\n file: string;\n transcendUrl: string;\n pageSize: number;\n variables: string;\n publishToPrivacyCenter: boolean;\n classifyService: boolean;\n deleteExtraAttributeValues: boolean;\n}\n\nexport async function push(\n this: LocalContext,\n {\n file = './transcend.yml',\n transcendUrl,\n auth,\n variables,\n pageSize,\n publishToPrivacyCenter,\n classifyService,\n deleteExtraAttributeValues,\n }: PushCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n // Parse authentication as API key or path to list of API keys\n const apiKeyOrList = await validateTranscendAuth(auth);\n\n // Parse out the variables\n const vars = parseVariablesFromString(variables);\n\n // check if we are being passed a list of API keys and a list of files\n let fileList: string[];\n if (Array.isArray(apiKeyOrList) && lstatSync(file).isDirectory()) {\n fileList = listFiles(file).map((filePath) => join(file, filePath));\n } else {\n fileList = file.split(',');\n }\n\n // Ensure at least one file is parsed\n if (fileList.length < 1) {\n throw new Error('No file specified!');\n }\n\n // eslint-disable-next-line array-callback-return,consistent-return\n const transcendInputs = fileList.map((filePath) => {\n // Ensure yaml file exists on disk\n if (!existsSync(filePath)) {\n logger.error(\n colors.red(\n `The file path does not exist on disk: ${filePath}. You can specify the filepath using --file=./examples/transcend.yml`,\n ),\n );\n this.process.exit(1);\n } else {\n logger.info(colors.magenta(`Reading file \"${filePath}\"...`));\n }\n\n try {\n // Read in the yaml file and validate it's shape\n const newContents = readTranscendYaml(filePath, vars);\n logger.info(colors.green(`Successfully read in \"${filePath}\"`));\n return {\n content: newContents,\n name: filePath.split('/').pop()!.replace('.yml', ''),\n };\n } catch (err) {\n logger.error(\n colors.red(\n `The shape of your yaml file is invalid with the following errors: ${err.message}`,\n ),\n );\n this.process.exit(1);\n }\n });\n\n // process a single API key\n if (typeof apiKeyOrList === 'string') {\n // if passed multiple inputs, merge them together\n const [base, ...rest] = transcendInputs.map(({ content }) => content);\n const contents = mergeTranscendInputs(base, ...rest);\n\n // sync the configuration\n const success = await syncConfiguration({\n transcendUrl,\n auth: apiKeyOrList,\n contents,\n publishToPrivacyCenter,\n deleteExtraAttributeValues,\n pageSize,\n classifyService: !!classifyService,\n });\n\n // exist with error code\n if (!success) {\n logger.info(\n colors.red(\n `Sync encountered errors. View output above for more information, or check out ${ADMIN_DASH_INTEGRATIONS}`,\n ),\n );\n\n this.process.exit(1);\n }\n } else {\n // if passed multiple inputs, expect them to be one per instance\n if (transcendInputs.length !== 1 && transcendInputs.length !== apiKeyOrList.length) {\n throw new Error(\n 'Expected list of yml files to be equal to the list of API keys.' +\n `Got ${transcendInputs.length} YML file${\n transcendInputs.length === 1 ? '' : 's'\n } and ${apiKeyOrList.length} API key${apiKeyOrList.length === 1 ? '' : 's'}`,\n );\n }\n\n const encounteredErrors: string[] = [];\n await mapSeries(apiKeyOrList, async (apiKey, ind) => {\n const prefix = `[${ind + 1}/${apiKeyOrList.length}][${apiKey.organizationName}] `;\n logger.info(colors.magenta(`~~~\\n\\n${prefix}Attempting to push configuration...\\n\\n~~~`));\n\n // use the merged contents if 1 yml passed, else use the contents that map to that organization\n const useContents =\n transcendInputs.length === 1\n ? transcendInputs[0].content\n : transcendInputs.find((input) => input.name === apiKey.organizationName)?.content;\n\n // Throw error if cannot find a yml file matching that organization name\n if (!useContents) {\n logger.error(\n colors.red(\n `${prefix}Failed to find transcend.yml file for organization: \"${apiKey.organizationName}\".`,\n ),\n );\n encounteredErrors.push(apiKey.organizationName);\n return;\n }\n\n const success = await syncConfiguration({\n transcendUrl,\n auth: apiKey.apiKey,\n contents: useContents,\n pageSize,\n publishToPrivacyCenter,\n deleteExtraAttributeValues,\n classifyService,\n });\n\n if (success) {\n logger.info(colors.green(`${prefix}Successfully pushed configuration!`));\n } else {\n logger.error(colors.red(`${prefix}Failed to sync configuration.`));\n encounteredErrors.push(apiKey.organizationName);\n }\n });\n\n if (encounteredErrors.length > 0) {\n logger.info(\n colors.red(\n `Sync encountered errors for \"${encounteredErrors.join(\n ',',\n )}\". View output above for more information, or check out ${ADMIN_DASH_INTEGRATIONS}`,\n ),\n );\n\n this.process.exit(1);\n }\n }\n\n // Indicate success\n logger.info(\n colors.green(`Successfully synced yaml file to Transcend! View at ${ADMIN_DASH_INTEGRATIONS}`),\n );\n}\n"],"mappings":"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"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./uploadCookiesFromCsv-DZSP7M-u.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,trackerStatus:r,file:i,transcendUrl:a}){t(this.process.exit),await e({auth:n,trackerStatus:r,file:i,transcendUrl:a})}export{n as uploadCookiesFromCsv};
2
- //# sourceMappingURL=impl-BPlwQGJw.mjs.map
1
+ import{t as e}from"./uploadCookiesFromCsv-r8mTeMe9.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,trackerStatus:r,file:i,transcendUrl:a}){t(this.process.exit),await e({auth:n,trackerStatus:r,file:i,transcendUrl:a})}export{n as uploadCookiesFromCsv};
2
+ //# sourceMappingURL=impl-B6kpEx0X.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-BPlwQGJw.mjs","names":["uploadCookiesFromCsvHelper"],"sources":["../src/commands/consent/upload-cookies-from-csv/impl.ts"],"sourcesContent":["import { ConsentTrackerStatus } from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { uploadCookiesFromCsv as uploadCookiesFromCsvHelper } from '../../../lib/consent-manager/index.js';\n\nexport interface UploadCookiesFromCsvCommandFlags {\n auth: string;\n trackerStatus: ConsentTrackerStatus;\n file: string;\n transcendUrl: string;\n}\n\nexport async function uploadCookiesFromCsv(\n this: LocalContext,\n { auth, trackerStatus, file, transcendUrl }: UploadCookiesFromCsvCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n // Upload cookies\n await uploadCookiesFromCsvHelper({\n auth,\n trackerStatus,\n file,\n transcendUrl,\n });\n}\n"],"mappings":"4GAaA,eAAsB,EAEpB,CAAE,OAAM,gBAAe,OAAM,gBACd,CACf,EAAoB,KAAK,QAAQ,KAAK,CAGtC,MAAMA,EAA2B,CAC/B,OACA,gBACA,OACA,eACD,CAAC"}
1
+ {"version":3,"file":"impl-B6kpEx0X.mjs","names":["uploadCookiesFromCsvHelper"],"sources":["../src/commands/consent/upload-cookies-from-csv/impl.ts"],"sourcesContent":["import { ConsentTrackerStatus } from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { uploadCookiesFromCsv as uploadCookiesFromCsvHelper } from '../../../lib/consent-manager/index.js';\n\nexport interface UploadCookiesFromCsvCommandFlags {\n auth: string;\n trackerStatus: ConsentTrackerStatus;\n file: string;\n transcendUrl: string;\n}\n\nexport async function uploadCookiesFromCsv(\n this: LocalContext,\n { auth, trackerStatus, file, transcendUrl }: UploadCookiesFromCsvCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n // Upload cookies\n await uploadCookiesFromCsvHelper({\n auth,\n trackerStatus,\n file,\n transcendUrl,\n });\n}\n"],"mappings":"4GAaA,eAAsB,EAEpB,CAAE,OAAM,gBAAe,OAAM,gBACd,CACf,EAAoB,KAAK,QAAQ,KAAK,CAGtC,MAAMA,EAA2B,CAC/B,OACA,gBACA,OACA,eACD,CAAC"}
@@ -1,3 +1,3 @@
1
- import{n as e,r as t,t as n}from"./runOpa-D511z37u.mjs";import{t as r}from"./logger-Ckep4QXn.mjs";import{n as i}from"./inquirer-AEchly0b.mjs";import{t as a}from"./done-input-validation-uqIgnJcw.mjs";import o from"node:path";import s from"colors";async function c({dir:c}){a(this.process.exit),t();let l=o.resolve(c);r.info(s.green(`Linting policy bundle in ${l}...`));let u=await e([`check`,`--strict`,l]);u!==0&&this.process.exit(u);let{stdout:d}=await n([`fmt`,`--list`,l]),f=d.trim().split(`
1
+ import{n as e,r as t,t as n}from"./runOpa-D511z37u.mjs";import{t as r}from"./logger-Ckep4QXn.mjs";import{n as i}from"./inquirer-B0OF_nRe.mjs";import{t as a}from"./done-input-validation-uqIgnJcw.mjs";import o from"node:path";import s from"colors";async function c({dir:c}){a(this.process.exit),t();let l=o.resolve(c);r.info(s.green(`Linting policy bundle in ${l}...`));let u=await e([`check`,`--strict`,l]);u!==0&&this.process.exit(u);let{stdout:d}=await n([`fmt`,`--list`,l]),f=d.trim().split(`
2
2
  `).filter(e=>e.length>0);if(f.length>0){r.error(s.red(`Policy files are not formatted:`)),f.forEach(e=>{r.error(s.red(` - ${e}`))}),r.error(``),await e([`fmt`,`--diff`,l]),this.process.stdin.isTTY||(r.error(s.red(`Cannot format policy files in a non-interactive environment.`)),this.process.exit(1)),await i({message:`Format the unformatted policy files listed above?`})||this.process.exit(1);let t=await e([`fmt`,`-w`,l]);t!==0&&this.process.exit(t),r.info(s.green(`Policy files formatted.`)),r.info(s.green(`Policy lint passed.`));return}r.info(s.green(`Policy lint passed.`))}export{c as lint};
3
- //# sourceMappingURL=impl-C5RWQxAV.mjs.map
3
+ //# sourceMappingURL=impl-BF9Ekyjn.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-C5RWQxAV.mjs","names":[],"sources":["../src/commands/policy/lint/impl.ts"],"sourcesContent":["import path from 'node:path';\n\nimport colors from 'colors';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { inquirerConfirmBoolean } from '../../../lib/helpers/inquirer.js';\nimport { logger } from '../../../logger.js';\nimport { assertOpaInstalled, runOpa, runOPACapture } from '../helpers/index.js';\n\n/** CLI flags for `transcend policy lint`. */\nexport interface LintCommandFlags {\n /** Directory containing Rego policy files */\n dir: string;\n}\n\n/**\n * Local Rego lint via `opa check` and optional interactive formatting via `opa fmt`.\n *\n * @param this - CLI context\n * @param flags - Command flags\n */\nexport async function lint(this: LocalContext, { dir }: LintCommandFlags): Promise<void> {\n doneInputValidation(this.process.exit);\n\n assertOpaInstalled();\n const resolvedDir = path.resolve(dir);\n\n logger.info(colors.green(`Linting policy bundle in ${resolvedDir}...`));\n\n const checkCode = await runOpa(['check', '--strict', resolvedDir]);\n if (checkCode !== 0) {\n this.process.exit(checkCode);\n }\n\n const { stdout } = await runOPACapture(['fmt', '--list', resolvedDir]);\n const unformattedFiles = stdout\n .trim()\n .split('\\n')\n .filter((file) => file.length > 0);\n\n if (unformattedFiles.length > 0) {\n logger.error(colors.red('Policy files are not formatted:'));\n unformattedFiles.forEach((file) => {\n logger.error(colors.red(` - ${file}`));\n });\n logger.error('');\n await runOpa(['fmt', '--diff', resolvedDir]);\n\n if (!this.process.stdin.isTTY) {\n logger.error(colors.red('Cannot format policy files in a non-interactive environment.'));\n this.process.exit(1);\n }\n\n const shouldFormat = await inquirerConfirmBoolean({\n message: 'Format the unformatted policy files listed above?',\n });\n if (!shouldFormat) {\n this.process.exit(1);\n }\n\n const fmtWriteCode = await runOpa(['fmt', '-w', resolvedDir]);\n if (fmtWriteCode !== 0) {\n this.process.exit(fmtWriteCode);\n }\n\n logger.info(colors.green('Policy files formatted.'));\n logger.info(colors.green('Policy lint passed.'));\n return;\n }\n\n logger.info(colors.green('Policy lint passed.'));\n}\n"],"mappings":"sPAsBA,eAAsB,EAAyB,CAAE,OAAwC,CACvF,EAAoB,KAAK,QAAQ,KAAK,CAEtC,GAAoB,CACpB,IAAM,EAAc,EAAK,QAAQ,EAAI,CAErC,EAAO,KAAK,EAAO,MAAM,4BAA4B,EAAY,KAAK,CAAC,CAEvE,IAAM,EAAY,MAAM,EAAO,CAAC,QAAS,WAAY,EAAY,CAAC,CAC9D,IAAc,GAChB,KAAK,QAAQ,KAAK,EAAU,CAG9B,GAAM,CAAE,UAAW,MAAM,EAAc,CAAC,MAAO,SAAU,EAAY,CAAC,CAChE,EAAmB,EACtB,MAAM,CACN,MAAM;EAAK,CACX,OAAQ,GAAS,EAAK,OAAS,EAAE,CAEpC,GAAI,EAAiB,OAAS,EAAG,CAC/B,EAAO,MAAM,EAAO,IAAI,kCAAkC,CAAC,CAC3D,EAAiB,QAAS,GAAS,CACjC,EAAO,MAAM,EAAO,IAAI,OAAO,IAAO,CAAC,EACvC,CACF,EAAO,MAAM,GAAG,CAChB,MAAM,EAAO,CAAC,MAAO,SAAU,EAAY,CAAC,CAEvC,KAAK,QAAQ,MAAM,QACtB,EAAO,MAAM,EAAO,IAAI,+DAA+D,CAAC,CACxF,KAAK,QAAQ,KAAK,EAAE,EAMjB,MAHsB,EAAuB,CAChD,QAAS,oDACV,CAAC,EAEA,KAAK,QAAQ,KAAK,EAAE,CAGtB,IAAM,EAAe,MAAM,EAAO,CAAC,MAAO,KAAM,EAAY,CAAC,CACzD,IAAiB,GACnB,KAAK,QAAQ,KAAK,EAAa,CAGjC,EAAO,KAAK,EAAO,MAAM,0BAA0B,CAAC,CACpD,EAAO,KAAK,EAAO,MAAM,sBAAsB,CAAC,CAChD,OAGF,EAAO,KAAK,EAAO,MAAM,sBAAsB,CAAC"}
1
+ {"version":3,"file":"impl-BF9Ekyjn.mjs","names":[],"sources":["../src/commands/policy/lint/impl.ts"],"sourcesContent":["import path from 'node:path';\n\nimport colors from 'colors';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { inquirerConfirmBoolean } from '../../../lib/helpers/inquirer.js';\nimport { logger } from '../../../logger.js';\nimport { assertOpaInstalled, runOpa, runOPACapture } from '../helpers/index.js';\n\n/** CLI flags for `transcend policy lint`. */\nexport interface LintCommandFlags {\n /** Directory containing Rego policy files */\n dir: string;\n}\n\n/**\n * Local Rego lint via `opa check` and optional interactive formatting via `opa fmt`.\n *\n * @param this - CLI context\n * @param flags - Command flags\n */\nexport async function lint(this: LocalContext, { dir }: LintCommandFlags): Promise<void> {\n doneInputValidation(this.process.exit);\n\n assertOpaInstalled();\n const resolvedDir = path.resolve(dir);\n\n logger.info(colors.green(`Linting policy bundle in ${resolvedDir}...`));\n\n const checkCode = await runOpa(['check', '--strict', resolvedDir]);\n if (checkCode !== 0) {\n this.process.exit(checkCode);\n }\n\n const { stdout } = await runOPACapture(['fmt', '--list', resolvedDir]);\n const unformattedFiles = stdout\n .trim()\n .split('\\n')\n .filter((file) => file.length > 0);\n\n if (unformattedFiles.length > 0) {\n logger.error(colors.red('Policy files are not formatted:'));\n unformattedFiles.forEach((file) => {\n logger.error(colors.red(` - ${file}`));\n });\n logger.error('');\n await runOpa(['fmt', '--diff', resolvedDir]);\n\n if (!this.process.stdin.isTTY) {\n logger.error(colors.red('Cannot format policy files in a non-interactive environment.'));\n this.process.exit(1);\n }\n\n const shouldFormat = await inquirerConfirmBoolean({\n message: 'Format the unformatted policy files listed above?',\n });\n if (!shouldFormat) {\n this.process.exit(1);\n }\n\n const fmtWriteCode = await runOpa(['fmt', '-w', resolvedDir]);\n if (fmtWriteCode !== 0) {\n this.process.exit(fmtWriteCode);\n }\n\n logger.info(colors.green('Policy files formatted.'));\n logger.info(colors.green('Policy lint passed.'));\n return;\n }\n\n logger.info(colors.green('Policy lint passed.'));\n}\n"],"mappings":"sPAsBA,eAAsB,EAAyB,CAAE,OAAwC,CACvF,EAAoB,KAAK,QAAQ,KAAK,CAEtC,GAAoB,CACpB,IAAM,EAAc,EAAK,QAAQ,EAAI,CAErC,EAAO,KAAK,EAAO,MAAM,4BAA4B,EAAY,KAAK,CAAC,CAEvE,IAAM,EAAY,MAAM,EAAO,CAAC,QAAS,WAAY,EAAY,CAAC,CAC9D,IAAc,GAChB,KAAK,QAAQ,KAAK,EAAU,CAG9B,GAAM,CAAE,UAAW,MAAM,EAAc,CAAC,MAAO,SAAU,EAAY,CAAC,CAChE,EAAmB,EACtB,MAAM,CACN,MAAM;EAAK,CACX,OAAQ,GAAS,EAAK,OAAS,EAAE,CAEpC,GAAI,EAAiB,OAAS,EAAG,CAC/B,EAAO,MAAM,EAAO,IAAI,kCAAkC,CAAC,CAC3D,EAAiB,QAAS,GAAS,CACjC,EAAO,MAAM,EAAO,IAAI,OAAO,IAAO,CAAC,EACvC,CACF,EAAO,MAAM,GAAG,CAChB,MAAM,EAAO,CAAC,MAAO,SAAU,EAAY,CAAC,CAEvC,KAAK,QAAQ,MAAM,QACtB,EAAO,MAAM,EAAO,IAAI,+DAA+D,CAAC,CACxF,KAAK,QAAQ,KAAK,EAAE,EAMjB,MAHsB,EAAuB,CAChD,QAAS,oDACV,CAAC,EAEA,KAAK,QAAQ,KAAK,EAAE,CAGtB,IAAM,EAAe,MAAM,EAAO,CAAC,MAAO,KAAM,EAAY,CAAC,CACzD,IAAiB,GACnB,KAAK,QAAQ,KAAK,EAAa,CAGjC,EAAO,KAAK,EAAO,MAAM,0BAA0B,CAAC,CACpD,EAAO,KAAK,EAAO,MAAM,sBAAsB,CAAC,CAChD,OAGF,EAAO,KAAK,EAAO,MAAM,sBAAsB,CAAC"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./logger-Ckep4QXn.mjs";import{t}from"./pullChunkedCustomSiloOutstandingIdentifiers-MuvYnFIK.mjs";import{i as n,s as r}from"./writeCsv-BMVkiMHM.mjs";import{t as i}from"./done-input-validation-uqIgnJcw.mjs";import{chunk as a,uniq as o}from"lodash-es";import s from"colors";import{buildTranscendGraphQLClient as c,fetchRequestFilesForRequest as l}from"@transcend-io/sdk";import{map as u}from"@transcend-io/utils";async function d({file:d,fileTarget:f,transcendUrl:p,auth:m,sombraAuth:h,cronDataSiloId:g,targetDataSiloId:_,actions:v,skipRequestCount:y,pageLimit:b,chunkSize:x}){y&&e.info(s.yellow(`Skipping request count as requested. This may help speed up the call.`)),(Number.isNaN(x)||x<=0||x%b!==0)&&(e.error(s.red(`Invalid chunk size: "${x}". Must be a positive integer that is a multiple of ${b}.`)),this.process.exit(1)),i(this.process.exit);let S=c(p,m),{baseName:C,extension:w}=n(d),{baseName:T,extension:E}=n(f),D=0,O=0,k=0;await t({dataSiloId:g,auth:m,sombraAuth:h,actions:v,apiPageSize:b,savePageSize:x,onSave:async t=>{D+=t.length;let n=await u(a(o(t.map(e=>e.requestId)),b),async t=>(e.info(s.magenta(`Fetching target identifiers for ${t.length} requests`)),(await l(S,{logger:e,pageSize:b*2,filterBy:{requestIds:t,dataSiloIds:[_]}})).map(({fileName:e,remoteId:t})=>{if(!t)throw Error(`Failed to find remoteId for ${e}`);return{RecordId:t,Object:e.replace(`.json`,``).split(`/`).pop()?.replace(` Information`,``),Comment:`Customer data deletion request submitted via transcend.io`}})),{concurrency:1});O+=n.flat().length;let i=o(t.map(e=>Object.keys(e)).flat()),c=`${C}-${k}${w}`,p=`${T}-${k}${E}`;await r(c,t,i),e.info(s.green(`Successfully wrote ${t.length} identifiers to file "${d}"`));let m=n.flat();await r(p,m,o(m.map(e=>Object.keys(e)).flat())),e.info(s.green(`Successfully wrote ${m.length} identifiers to file "${f}"`)),e.info(s.blue(`Processed chunk of ${a.length} identifiers, found ${m.length} target identifiers`)),k+=1},transcendUrl:p,skipRequestCount:y}),e.info(s.green(`Successfully wrote ${D} identifiers to file "${d}"`)),e.info(s.green(`Successfully wrote ${O} identifiers to file "${f}"`))}export{d as pullProfiles};
2
- //# sourceMappingURL=impl-BfEBQCDY2.mjs.map
1
+ import{t as e}from"./logger-Ckep4QXn.mjs";import{t}from"./pullChunkedCustomSiloOutstandingIdentifiers-DcSSx712.mjs";import{i as n,s as r}from"./writeCsv-BMVkiMHM.mjs";import{t as i}from"./done-input-validation-uqIgnJcw.mjs";import{chunk as a,uniq as o}from"lodash-es";import s from"colors";import{buildTranscendGraphQLClient as c,fetchRequestFilesForRequest as l}from"@transcend-io/sdk";import{map as u}from"@transcend-io/utils";async function d({file:d,fileTarget:f,transcendUrl:p,auth:m,sombraAuth:h,cronDataSiloId:g,targetDataSiloId:_,actions:v,skipRequestCount:y,pageLimit:b,chunkSize:x}){y&&e.info(s.yellow(`Skipping request count as requested. This may help speed up the call.`)),(Number.isNaN(x)||x<=0||x%b!==0)&&(e.error(s.red(`Invalid chunk size: "${x}". Must be a positive integer that is a multiple of ${b}.`)),this.process.exit(1)),i(this.process.exit);let S=c(p,m),{baseName:C,extension:w}=n(d),{baseName:T,extension:E}=n(f),D=0,O=0,k=0;await t({dataSiloId:g,auth:m,sombraAuth:h,actions:v,apiPageSize:b,savePageSize:x,onSave:async t=>{D+=t.length;let n=await u(a(o(t.map(e=>e.requestId)),b),async t=>(e.info(s.magenta(`Fetching target identifiers for ${t.length} requests`)),(await l(S,{logger:e,pageSize:b*2,filterBy:{requestIds:t,dataSiloIds:[_]}})).map(({fileName:e,remoteId:t})=>{if(!t)throw Error(`Failed to find remoteId for ${e}`);return{RecordId:t,Object:e.replace(`.json`,``).split(`/`).pop()?.replace(` Information`,``),Comment:`Customer data deletion request submitted via transcend.io`}})),{concurrency:1});O+=n.flat().length;let i=o(t.map(e=>Object.keys(e)).flat()),c=`${C}-${k}${w}`,p=`${T}-${k}${E}`;await r(c,t,i),e.info(s.green(`Successfully wrote ${t.length} identifiers to file "${d}"`));let m=n.flat();await r(p,m,o(m.map(e=>Object.keys(e)).flat())),e.info(s.green(`Successfully wrote ${m.length} identifiers to file "${f}"`)),e.info(s.blue(`Processed chunk of ${a.length} identifiers, found ${m.length} target identifiers`)),k+=1},transcendUrl:p,skipRequestCount:y}),e.info(s.green(`Successfully wrote ${D} identifiers to file "${d}"`)),e.info(s.green(`Successfully wrote ${O} identifiers to file "${f}"`))}export{d as pullProfiles};
2
+ //# sourceMappingURL=impl-BVh3JHAk2.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-BfEBQCDY2.mjs","names":[],"sources":["../src/commands/request/cron/pull-profiles/impl.ts"],"sourcesContent":["import type { RequestAction } from '@transcend-io/privacy-types';\nimport { buildTranscendGraphQLClient, fetchRequestFilesForRequest } from '@transcend-io/sdk';\nimport { map } from '@transcend-io/utils';\nimport colors from 'colors';\nimport { uniq, chunk } from 'lodash-es';\n\nimport type { LocalContext } from '../../../../context.js';\nimport { doneInputValidation } from '../../../../lib/cli/done-input-validation.js';\nimport {\n pullChunkedCustomSiloOutstandingIdentifiers,\n type CsvFormattedIdentifier,\n} from '../../../../lib/cron/index.js';\nimport { parseFilePath, writeLargeCsv } from '../../../../lib/helpers/index.js';\nimport { logger } from '../../../../logger.js';\n\nexport interface PullProfilesCommandFlags {\n file: string;\n fileTarget: string;\n transcendUrl: string;\n auth: string;\n sombraAuth?: string;\n cronDataSiloId: string;\n targetDataSiloId: string;\n actions: RequestAction[];\n skipRequestCount: boolean;\n pageLimit: number;\n chunkSize: number;\n}\n\nexport async function pullProfiles(\n this: LocalContext,\n {\n file,\n fileTarget,\n transcendUrl,\n auth,\n sombraAuth,\n cronDataSiloId,\n targetDataSiloId,\n actions,\n skipRequestCount,\n pageLimit,\n chunkSize,\n }: PullProfilesCommandFlags,\n): Promise<void> {\n if (skipRequestCount) {\n logger.info(\n colors.yellow('Skipping request count as requested. This may help speed up the call.'),\n );\n }\n\n if (Number.isNaN(chunkSize) || chunkSize <= 0 || chunkSize % pageLimit !== 0) {\n logger.error(\n colors.red(\n `Invalid chunk size: \"${chunkSize}\". Must be a positive integer that is a multiple of ${pageLimit}.`,\n ),\n );\n this.process.exit(1);\n }\n\n doneInputValidation(this.process.exit);\n\n // Create GraphQL client to connect to Transcend backend\n const client = buildTranscendGraphQLClient(transcendUrl, auth);\n const { baseName, extension } = parseFilePath(file);\n const { baseName: baseNameTarget, extension: extensionTarget } = parseFilePath(fileTarget);\n\n let allIdentifiersCount = 0;\n let allTargetIdentifiersCount = 0;\n let fileCount = 0;\n // Create onSave callback to handle chunked processing\n const onSave = async (chunkToSave: CsvFormattedIdentifier[]): Promise<void> => {\n // Add to all identifiers\n allIdentifiersCount += chunkToSave.length;\n\n // Get unique request IDs from this chunk\n const requestIds = chunkToSave.map((d) => d.requestId as string);\n const uniqueRequestIds = uniq(requestIds);\n\n // Pull down target identifiers for this chunk\n const chunkedRequestIds = chunk(uniqueRequestIds, pageLimit);\n const results = await map(\n chunkedRequestIds,\n async (requestIds) => {\n logger.info(\n colors.magenta(`Fetching target identifiers for ${requestIds.length} requests`),\n );\n const results = await fetchRequestFilesForRequest(client, {\n logger,\n pageSize: pageLimit * 2,\n filterBy: {\n requestIds,\n dataSiloIds: [targetDataSiloId],\n },\n });\n return results.map(({ fileName, remoteId }) => {\n if (!remoteId) {\n throw new Error(`Failed to find remoteId for ${fileName}`);\n }\n return {\n RecordId: remoteId,\n Object: fileName.replace('.json', '').split('/').pop()?.replace(' Information', ''),\n Comment: 'Customer data deletion request submitted via transcend.io',\n };\n });\n },\n // We are grabbing all the request files for the 'pageLimit' # of requests at a time\n {\n concurrency: 1,\n },\n );\n\n allTargetIdentifiersCount += results.flat().length;\n\n // Write the identifiers and target identifiers to CSV\n const headers = uniq(chunkToSave.map((d) => Object.keys(d)).flat());\n const numberedFileName = `${baseName}-${fileCount}${extension}`;\n const numberedFileNameTarget = `${baseNameTarget}-${fileCount}${extensionTarget}`;\n await writeLargeCsv(numberedFileName, chunkToSave, headers);\n logger.info(\n colors.green(`Successfully wrote ${chunkToSave.length} identifiers to file \"${file}\"`),\n );\n\n const targetIdentifiers = results.flat();\n const headers2 = uniq(targetIdentifiers.map((d) => Object.keys(d)).flat());\n await writeLargeCsv(numberedFileNameTarget, targetIdentifiers, headers2);\n logger.info(\n colors.green(\n `Successfully wrote ${targetIdentifiers.length} identifiers to file \"${fileTarget}\"`,\n ),\n );\n\n logger.info(\n colors.blue(\n `Processed chunk of ${chunk.length} identifiers, found ${targetIdentifiers.length} target identifiers`,\n ),\n );\n fileCount += 1;\n };\n\n // Pull down outstanding identifiers using the new chunked function\n await pullChunkedCustomSiloOutstandingIdentifiers({\n dataSiloId: cronDataSiloId,\n auth,\n sombraAuth,\n actions,\n apiPageSize: pageLimit,\n savePageSize: chunkSize,\n onSave,\n transcendUrl,\n skipRequestCount,\n });\n\n logger.info(\n colors.green(`Successfully wrote ${allIdentifiersCount} identifiers to file \"${file}\"`),\n );\n logger.info(\n colors.green(\n `Successfully wrote ${allTargetIdentifiersCount} identifiers to file \"${fileTarget}\"`,\n ),\n );\n}\n"],"mappings":"6aA6BA,eAAsB,EAEpB,CACE,OACA,aACA,eACA,OACA,aACA,iBACA,mBACA,UACA,mBACA,YACA,aAEa,CACX,GACF,EAAO,KACL,EAAO,OAAO,wEAAwE,CACvF,EAGC,OAAO,MAAM,EAAU,EAAI,GAAa,GAAK,EAAY,IAAc,KACzE,EAAO,MACL,EAAO,IACL,wBAAwB,EAAU,sDAAsD,EAAU,GACnG,CACF,CACD,KAAK,QAAQ,KAAK,EAAE,EAGtB,EAAoB,KAAK,QAAQ,KAAK,CAGtC,IAAM,EAAS,EAA4B,EAAc,EAAK,CACxD,CAAE,WAAU,aAAc,EAAc,EAAK,CAC7C,CAAE,SAAU,EAAgB,UAAW,GAAoB,EAAc,EAAW,CAEtF,EAAsB,EACtB,EAA4B,EAC5B,EAAY,EAwEhB,MAAM,EAA4C,CAChD,WAAY,EACZ,OACA,aACA,UACA,YAAa,EACb,aAAc,EACd,YA7EoB,IAAyD,CAE7E,GAAuB,EAAY,OAQnC,IAAM,EAAU,MAAM,EADI,EAHD,EADN,EAAY,IAAK,GAAM,EAAE,UACJ,CAGQ,CAAE,EAE/B,CACjB,KAAO,KACL,EAAO,KACL,EAAO,QAAQ,mCAAmC,EAAW,OAAO,WAAW,CAChF,EASM,MARe,EAA4B,EAAQ,CACxD,SACA,SAAU,EAAY,EACtB,SAAU,CACR,aACA,YAAa,CAAC,EAAiB,CAChC,CACF,CAAC,EACa,KAAK,CAAE,WAAU,cAAe,CAC7C,GAAI,CAAC,EACH,MAAU,MAAM,+BAA+B,IAAW,CAE5D,MAAO,CACL,SAAU,EACV,OAAQ,EAAS,QAAQ,QAAS,GAAG,CAAC,MAAM,IAAI,CAAC,KAAK,EAAE,QAAQ,eAAgB,GAAG,CACnF,QAAS,4DACV,EACD,EAGJ,CACE,YAAa,EACd,CACF,CAED,GAA6B,EAAQ,MAAM,CAAC,OAG5C,IAAM,EAAU,EAAK,EAAY,IAAK,GAAM,OAAO,KAAK,EAAE,CAAC,CAAC,MAAM,CAAC,CAC7D,EAAmB,GAAG,EAAS,GAAG,IAAY,IAC9C,EAAyB,GAAG,EAAe,GAAG,IAAY,IAChE,MAAM,EAAc,EAAkB,EAAa,EAAQ,CAC3D,EAAO,KACL,EAAO,MAAM,sBAAsB,EAAY,OAAO,wBAAwB,EAAK,GAAG,CACvF,CAED,IAAM,EAAoB,EAAQ,MAAM,CAExC,MAAM,EAAc,EAAwB,EAD3B,EAAK,EAAkB,IAAK,GAAM,OAAO,KAAK,EAAE,CAAC,CAAC,MAAM,CACF,CAAC,CACxE,EAAO,KACL,EAAO,MACL,sBAAsB,EAAkB,OAAO,wBAAwB,EAAW,GACnF,CACF,CAED,EAAO,KACL,EAAO,KACL,sBAAsB,EAAM,OAAO,sBAAsB,EAAkB,OAAO,qBACnF,CACF,CACD,GAAa,GAYb,eACA,mBACD,CAAC,CAEF,EAAO,KACL,EAAO,MAAM,sBAAsB,EAAoB,wBAAwB,EAAK,GAAG,CACxF,CACD,EAAO,KACL,EAAO,MACL,sBAAsB,EAA0B,wBAAwB,EAAW,GACpF,CACF"}
1
+ {"version":3,"file":"impl-BVh3JHAk2.mjs","names":[],"sources":["../src/commands/request/cron/pull-profiles/impl.ts"],"sourcesContent":["import type { RequestAction } from '@transcend-io/privacy-types';\nimport { buildTranscendGraphQLClient, fetchRequestFilesForRequest } from '@transcend-io/sdk';\nimport { map } from '@transcend-io/utils';\nimport colors from 'colors';\nimport { uniq, chunk } from 'lodash-es';\n\nimport type { LocalContext } from '../../../../context.js';\nimport { doneInputValidation } from '../../../../lib/cli/done-input-validation.js';\nimport {\n pullChunkedCustomSiloOutstandingIdentifiers,\n type CsvFormattedIdentifier,\n} from '../../../../lib/cron/index.js';\nimport { parseFilePath, writeLargeCsv } from '../../../../lib/helpers/index.js';\nimport { logger } from '../../../../logger.js';\n\nexport interface PullProfilesCommandFlags {\n file: string;\n fileTarget: string;\n transcendUrl: string;\n auth: string;\n sombraAuth?: string;\n cronDataSiloId: string;\n targetDataSiloId: string;\n actions: RequestAction[];\n skipRequestCount: boolean;\n pageLimit: number;\n chunkSize: number;\n}\n\nexport async function pullProfiles(\n this: LocalContext,\n {\n file,\n fileTarget,\n transcendUrl,\n auth,\n sombraAuth,\n cronDataSiloId,\n targetDataSiloId,\n actions,\n skipRequestCount,\n pageLimit,\n chunkSize,\n }: PullProfilesCommandFlags,\n): Promise<void> {\n if (skipRequestCount) {\n logger.info(\n colors.yellow('Skipping request count as requested. This may help speed up the call.'),\n );\n }\n\n if (Number.isNaN(chunkSize) || chunkSize <= 0 || chunkSize % pageLimit !== 0) {\n logger.error(\n colors.red(\n `Invalid chunk size: \"${chunkSize}\". Must be a positive integer that is a multiple of ${pageLimit}.`,\n ),\n );\n this.process.exit(1);\n }\n\n doneInputValidation(this.process.exit);\n\n // Create GraphQL client to connect to Transcend backend\n const client = buildTranscendGraphQLClient(transcendUrl, auth);\n const { baseName, extension } = parseFilePath(file);\n const { baseName: baseNameTarget, extension: extensionTarget } = parseFilePath(fileTarget);\n\n let allIdentifiersCount = 0;\n let allTargetIdentifiersCount = 0;\n let fileCount = 0;\n // Create onSave callback to handle chunked processing\n const onSave = async (chunkToSave: CsvFormattedIdentifier[]): Promise<void> => {\n // Add to all identifiers\n allIdentifiersCount += chunkToSave.length;\n\n // Get unique request IDs from this chunk\n const requestIds = chunkToSave.map((d) => d.requestId as string);\n const uniqueRequestIds = uniq(requestIds);\n\n // Pull down target identifiers for this chunk\n const chunkedRequestIds = chunk(uniqueRequestIds, pageLimit);\n const results = await map(\n chunkedRequestIds,\n async (requestIds) => {\n logger.info(\n colors.magenta(`Fetching target identifiers for ${requestIds.length} requests`),\n );\n const results = await fetchRequestFilesForRequest(client, {\n logger,\n pageSize: pageLimit * 2,\n filterBy: {\n requestIds,\n dataSiloIds: [targetDataSiloId],\n },\n });\n return results.map(({ fileName, remoteId }) => {\n if (!remoteId) {\n throw new Error(`Failed to find remoteId for ${fileName}`);\n }\n return {\n RecordId: remoteId,\n Object: fileName.replace('.json', '').split('/').pop()?.replace(' Information', ''),\n Comment: 'Customer data deletion request submitted via transcend.io',\n };\n });\n },\n // We are grabbing all the request files for the 'pageLimit' # of requests at a time\n {\n concurrency: 1,\n },\n );\n\n allTargetIdentifiersCount += results.flat().length;\n\n // Write the identifiers and target identifiers to CSV\n const headers = uniq(chunkToSave.map((d) => Object.keys(d)).flat());\n const numberedFileName = `${baseName}-${fileCount}${extension}`;\n const numberedFileNameTarget = `${baseNameTarget}-${fileCount}${extensionTarget}`;\n await writeLargeCsv(numberedFileName, chunkToSave, headers);\n logger.info(\n colors.green(`Successfully wrote ${chunkToSave.length} identifiers to file \"${file}\"`),\n );\n\n const targetIdentifiers = results.flat();\n const headers2 = uniq(targetIdentifiers.map((d) => Object.keys(d)).flat());\n await writeLargeCsv(numberedFileNameTarget, targetIdentifiers, headers2);\n logger.info(\n colors.green(\n `Successfully wrote ${targetIdentifiers.length} identifiers to file \"${fileTarget}\"`,\n ),\n );\n\n logger.info(\n colors.blue(\n `Processed chunk of ${chunk.length} identifiers, found ${targetIdentifiers.length} target identifiers`,\n ),\n );\n fileCount += 1;\n };\n\n // Pull down outstanding identifiers using the new chunked function\n await pullChunkedCustomSiloOutstandingIdentifiers({\n dataSiloId: cronDataSiloId,\n auth,\n sombraAuth,\n actions,\n apiPageSize: pageLimit,\n savePageSize: chunkSize,\n onSave,\n transcendUrl,\n skipRequestCount,\n });\n\n logger.info(\n colors.green(`Successfully wrote ${allIdentifiersCount} identifiers to file \"${file}\"`),\n );\n logger.info(\n colors.green(\n `Successfully wrote ${allTargetIdentifiersCount} identifiers to file \"${fileTarget}\"`,\n ),\n );\n}\n"],"mappings":"6aA6BA,eAAsB,EAEpB,CACE,OACA,aACA,eACA,OACA,aACA,iBACA,mBACA,UACA,mBACA,YACA,aAEa,CACX,GACF,EAAO,KACL,EAAO,OAAO,wEAAwE,CACvF,EAGC,OAAO,MAAM,EAAU,EAAI,GAAa,GAAK,EAAY,IAAc,KACzE,EAAO,MACL,EAAO,IACL,wBAAwB,EAAU,sDAAsD,EAAU,GACnG,CACF,CACD,KAAK,QAAQ,KAAK,EAAE,EAGtB,EAAoB,KAAK,QAAQ,KAAK,CAGtC,IAAM,EAAS,EAA4B,EAAc,EAAK,CACxD,CAAE,WAAU,aAAc,EAAc,EAAK,CAC7C,CAAE,SAAU,EAAgB,UAAW,GAAoB,EAAc,EAAW,CAEtF,EAAsB,EACtB,EAA4B,EAC5B,EAAY,EAwEhB,MAAM,EAA4C,CAChD,WAAY,EACZ,OACA,aACA,UACA,YAAa,EACb,aAAc,EACd,YA7EoB,IAAyD,CAE7E,GAAuB,EAAY,OAQnC,IAAM,EAAU,MAAM,EADI,EAHD,EADN,EAAY,IAAK,GAAM,EAAE,UACJ,CAGQ,CAAE,EAE/B,CACjB,KAAO,KACL,EAAO,KACL,EAAO,QAAQ,mCAAmC,EAAW,OAAO,WAAW,CAChF,EASM,MARe,EAA4B,EAAQ,CACxD,SACA,SAAU,EAAY,EACtB,SAAU,CACR,aACA,YAAa,CAAC,EAAiB,CAChC,CACF,CAAC,EACa,KAAK,CAAE,WAAU,cAAe,CAC7C,GAAI,CAAC,EACH,MAAU,MAAM,+BAA+B,IAAW,CAE5D,MAAO,CACL,SAAU,EACV,OAAQ,EAAS,QAAQ,QAAS,GAAG,CAAC,MAAM,IAAI,CAAC,KAAK,EAAE,QAAQ,eAAgB,GAAG,CACnF,QAAS,4DACV,EACD,EAGJ,CACE,YAAa,EACd,CACF,CAED,GAA6B,EAAQ,MAAM,CAAC,OAG5C,IAAM,EAAU,EAAK,EAAY,IAAK,GAAM,OAAO,KAAK,EAAE,CAAC,CAAC,MAAM,CAAC,CAC7D,EAAmB,GAAG,EAAS,GAAG,IAAY,IAC9C,EAAyB,GAAG,EAAe,GAAG,IAAY,IAChE,MAAM,EAAc,EAAkB,EAAa,EAAQ,CAC3D,EAAO,KACL,EAAO,MAAM,sBAAsB,EAAY,OAAO,wBAAwB,EAAK,GAAG,CACvF,CAED,IAAM,EAAoB,EAAQ,MAAM,CAExC,MAAM,EAAc,EAAwB,EAD3B,EAAK,EAAkB,IAAK,GAAM,OAAO,KAAK,EAAE,CAAC,CAAC,MAAM,CACF,CAAC,CACxE,EAAO,KACL,EAAO,MACL,sBAAsB,EAAkB,OAAO,wBAAwB,EAAW,GACnF,CACF,CAED,EAAO,KACL,EAAO,KACL,sBAAsB,EAAM,OAAO,sBAAsB,EAAkB,OAAO,qBACnF,CACF,CACD,GAAa,GAYb,eACA,mBACD,CAAC,CAEF,EAAO,KACL,EAAO,MAAM,sBAAsB,EAAoB,wBAAwB,EAAK,GAAG,CACxF,CACD,EAAO,KACL,EAAO,MACL,sBAAsB,EAA0B,wBAAwB,EAAW,GACpF,CACF"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./bulkRestartRequests-0VBrEHER.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,requestReceiptFolder:r,sombraAuth:i,actions:a,statuses:o,requestIds:s,createdAt:c,emailIsVerified:l,silentModeBefore:u,sendEmailReceipt:d,copyIdentifiers:f,restartIdentifierStrategy:p,skipWaitingPeriod:m,createdAtBefore:h,createdAtAfter:g,updatedAtBefore:_,updatedAtAfter:v,concurrency:y,transcendUrl:b}){t(this.process.exit),await e({requestReceiptFolder:r,auth:n,sombraAuth:i,requestActions:a,requestStatuses:o,requestIds:s,createdAt:c,emailIsVerified:l,silentModeBefore:u,sendEmailReceipt:d,copyIdentifiers:f,restartIdentifierStrategy:p,skipWaitingPeriod:m,createdAtBefore:h,createdAtAfter:g,updatedAtBefore:_,updatedAtAfter:v,concurrency:y,transcendUrl:b})}export{n as restart};
2
- //# sourceMappingURL=impl-DJ37yGAw2.mjs.map
1
+ import{t as e}from"./bulkRestartRequests-n2_EwVEM.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,requestReceiptFolder:r,sombraAuth:i,actions:a,statuses:o,requestIds:s,createdAt:c,emailIsVerified:l,silentModeBefore:u,sendEmailReceipt:d,copyIdentifiers:f,restartIdentifierStrategy:p,skipWaitingPeriod:m,createdAtBefore:h,createdAtAfter:g,updatedAtBefore:_,updatedAtAfter:v,concurrency:y,transcendUrl:b}){t(this.process.exit),await e({requestReceiptFolder:r,auth:n,sombraAuth:i,requestActions:a,requestStatuses:o,requestIds:s,createdAt:c,emailIsVerified:l,silentModeBefore:u,sendEmailReceipt:d,copyIdentifiers:f,restartIdentifierStrategy:p,skipWaitingPeriod:m,createdAtBefore:h,createdAtAfter:g,updatedAtBefore:_,updatedAtAfter:v,concurrency:y,transcendUrl:b})}export{n as restart};
2
+ //# sourceMappingURL=impl-BYtnm2cU2.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-DJ37yGAw2.mjs","names":[],"sources":["../src/commands/request/restart/impl.ts"],"sourcesContent":["import type {\n RequestAction,\n RequestStatus,\n RestartIdentifierStrategy,\n} from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { bulkRestartRequests } from '../../../lib/requests/index.js';\n\nexport interface RestartCommandFlags {\n auth: string;\n actions: RequestAction[];\n statuses: RequestStatus[];\n transcendUrl: string;\n requestReceiptFolder: string;\n sombraAuth?: string;\n concurrency: number;\n requestIds?: string[];\n emailIsVerified: boolean;\n createdAt?: Date;\n silentModeBefore?: Date;\n createdAtBefore?: Date;\n createdAtAfter?: Date;\n updatedAtBefore?: Date;\n updatedAtAfter?: Date;\n sendEmailReceipt: boolean;\n copyIdentifiers: boolean;\n restartIdentifierStrategy?: RestartIdentifierStrategy;\n skipWaitingPeriod: boolean;\n}\n\nexport async function restart(\n this: LocalContext,\n {\n auth,\n requestReceiptFolder,\n sombraAuth,\n actions,\n statuses,\n requestIds,\n createdAt,\n emailIsVerified,\n silentModeBefore,\n sendEmailReceipt,\n copyIdentifiers,\n restartIdentifierStrategy,\n skipWaitingPeriod,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n concurrency,\n transcendUrl,\n }: RestartCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n await bulkRestartRequests({\n requestReceiptFolder,\n auth,\n sombraAuth,\n requestActions: actions,\n requestStatuses: statuses,\n requestIds,\n createdAt,\n emailIsVerified,\n silentModeBefore,\n sendEmailReceipt,\n copyIdentifiers,\n restartIdentifierStrategy,\n skipWaitingPeriod,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n concurrency,\n transcendUrl,\n });\n}\n"],"mappings":"2GAgCA,eAAsB,EAEpB,CACE,OACA,uBACA,aACA,UACA,WACA,aACA,YACA,kBACA,mBACA,mBACA,kBACA,4BACA,oBACA,kBACA,iBACA,kBACA,iBACA,cACA,gBAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,MAAM,EAAoB,CACxB,uBACA,OACA,aACA,eAAgB,EAChB,gBAAiB,EACjB,aACA,YACA,kBACA,mBACA,mBACA,kBACA,4BACA,oBACA,kBACA,iBACA,kBACA,iBACA,cACA,eACD,CAAC"}
1
+ {"version":3,"file":"impl-BYtnm2cU2.mjs","names":[],"sources":["../src/commands/request/restart/impl.ts"],"sourcesContent":["import type {\n RequestAction,\n RequestStatus,\n RestartIdentifierStrategy,\n} from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { bulkRestartRequests } from '../../../lib/requests/index.js';\n\nexport interface RestartCommandFlags {\n auth: string;\n actions: RequestAction[];\n statuses: RequestStatus[];\n transcendUrl: string;\n requestReceiptFolder: string;\n sombraAuth?: string;\n concurrency: number;\n requestIds?: string[];\n emailIsVerified: boolean;\n createdAt?: Date;\n silentModeBefore?: Date;\n createdAtBefore?: Date;\n createdAtAfter?: Date;\n updatedAtBefore?: Date;\n updatedAtAfter?: Date;\n sendEmailReceipt: boolean;\n copyIdentifiers: boolean;\n restartIdentifierStrategy?: RestartIdentifierStrategy;\n skipWaitingPeriod: boolean;\n}\n\nexport async function restart(\n this: LocalContext,\n {\n auth,\n requestReceiptFolder,\n sombraAuth,\n actions,\n statuses,\n requestIds,\n createdAt,\n emailIsVerified,\n silentModeBefore,\n sendEmailReceipt,\n copyIdentifiers,\n restartIdentifierStrategy,\n skipWaitingPeriod,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n concurrency,\n transcendUrl,\n }: RestartCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n await bulkRestartRequests({\n requestReceiptFolder,\n auth,\n sombraAuth,\n requestActions: actions,\n requestStatuses: statuses,\n requestIds,\n createdAt,\n emailIsVerified,\n silentModeBefore,\n sendEmailReceipt,\n copyIdentifiers,\n restartIdentifierStrategy,\n skipWaitingPeriod,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n concurrency,\n transcendUrl,\n });\n}\n"],"mappings":"2GAgCA,eAAsB,EAEpB,CACE,OACA,uBACA,aACA,UACA,WACA,aACA,YACA,kBACA,mBACA,mBACA,kBACA,4BACA,oBACA,kBACA,iBACA,kBACA,iBACA,cACA,gBAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,MAAM,EAAoB,CACxB,uBACA,OACA,aACA,eAAgB,EAChB,gBAAiB,EACjB,aACA,YACA,kBACA,mBACA,mBACA,kBACA,4BACA,oBACA,kBACA,iBACA,kBACA,iBACA,cACA,eACD,CAAC"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./bulkRetryEnrichers-D7t7iYbi.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,enricherId:r,actions:i,requestEnricherStatuses:a,requestIds:o,createdAtBefore:s,createdAtAfter:c,updatedAtBefore:l,updatedAtAfter:u,concurrency:d,transcendUrl:f}){t(this.process.exit),await e({auth:n,enricherId:r,requestActions:i,requestEnricherStatuses:a,requestIds:o,createdAtBefore:s?new Date(s):void 0,createdAtAfter:c?new Date(c):void 0,updatedAtBefore:l?new Date(l):void 0,updatedAtAfter:u?new Date(u):void 0,concurrency:d,transcendUrl:f})}export{n as enricherRestart};
2
- //# sourceMappingURL=impl-Ctagwhzp.mjs.map
1
+ import{t as e}from"./bulkRetryEnrichers-DDftLRtp.mjs";import{t}from"./done-input-validation-uqIgnJcw.mjs";async function n({auth:n,enricherId:r,actions:i,requestEnricherStatuses:a,requestIds:o,createdAtBefore:s,createdAtAfter:c,updatedAtBefore:l,updatedAtAfter:u,concurrency:d,transcendUrl:f}){t(this.process.exit),await e({auth:n,enricherId:r,requestActions:i,requestEnricherStatuses:a,requestIds:o,createdAtBefore:s?new Date(s):void 0,createdAtAfter:c?new Date(c):void 0,updatedAtBefore:l?new Date(l):void 0,updatedAtAfter:u?new Date(u):void 0,concurrency:d,transcendUrl:f})}export{n as enricherRestart};
2
+ //# sourceMappingURL=impl-BZ-EmLtv.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-Ctagwhzp.mjs","names":[],"sources":["../src/commands/request/enricher-restart/impl.ts"],"sourcesContent":["import type { RequestAction, RequestEnricherStatus } from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { bulkRetryEnrichers } from '../../../lib/requests/index.js';\n\nexport interface EnricherRestartCommandFlags {\n auth: string;\n enricherId: string;\n actions?: RequestAction[];\n requestEnricherStatuses?: RequestEnricherStatus[];\n transcendUrl: string;\n concurrency: number;\n requestIds?: string[];\n createdAtBefore?: Date;\n createdAtAfter?: Date;\n updatedAtBefore?: Date;\n updatedAtAfter?: Date;\n}\n\nexport async function enricherRestart(\n this: LocalContext,\n {\n auth,\n enricherId,\n actions,\n requestEnricherStatuses,\n requestIds,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n concurrency,\n transcendUrl,\n }: EnricherRestartCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n await bulkRetryEnrichers({\n auth,\n enricherId,\n requestActions: actions,\n requestEnricherStatuses,\n requestIds,\n createdAtBefore: createdAtBefore ? new Date(createdAtBefore) : undefined,\n createdAtAfter: createdAtAfter ? new Date(createdAtAfter) : undefined,\n updatedAtBefore: updatedAtBefore ? new Date(updatedAtBefore) : undefined,\n updatedAtAfter: updatedAtAfter ? new Date(updatedAtAfter) : undefined,\n concurrency,\n transcendUrl,\n });\n}\n"],"mappings":"0GAoBA,eAAsB,EAEpB,CACE,OACA,aACA,UACA,0BACA,aACA,kBACA,iBACA,kBACA,iBACA,cACA,gBAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,MAAM,EAAmB,CACvB,OACA,aACA,eAAgB,EAChB,0BACA,aACA,gBAAiB,EAAkB,IAAI,KAAK,EAAgB,CAAG,IAAA,GAC/D,eAAgB,EAAiB,IAAI,KAAK,EAAe,CAAG,IAAA,GAC5D,gBAAiB,EAAkB,IAAI,KAAK,EAAgB,CAAG,IAAA,GAC/D,eAAgB,EAAiB,IAAI,KAAK,EAAe,CAAG,IAAA,GAC5D,cACA,eACD,CAAC"}
1
+ {"version":3,"file":"impl-BZ-EmLtv.mjs","names":[],"sources":["../src/commands/request/enricher-restart/impl.ts"],"sourcesContent":["import type { RequestAction, RequestEnricherStatus } from '@transcend-io/privacy-types';\n\nimport type { LocalContext } from '../../../context.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { bulkRetryEnrichers } from '../../../lib/requests/index.js';\n\nexport interface EnricherRestartCommandFlags {\n auth: string;\n enricherId: string;\n actions?: RequestAction[];\n requestEnricherStatuses?: RequestEnricherStatus[];\n transcendUrl: string;\n concurrency: number;\n requestIds?: string[];\n createdAtBefore?: Date;\n createdAtAfter?: Date;\n updatedAtBefore?: Date;\n updatedAtAfter?: Date;\n}\n\nexport async function enricherRestart(\n this: LocalContext,\n {\n auth,\n enricherId,\n actions,\n requestEnricherStatuses,\n requestIds,\n createdAtBefore,\n createdAtAfter,\n updatedAtBefore,\n updatedAtAfter,\n concurrency,\n transcendUrl,\n }: EnricherRestartCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n await bulkRetryEnrichers({\n auth,\n enricherId,\n requestActions: actions,\n requestEnricherStatuses,\n requestIds,\n createdAtBefore: createdAtBefore ? new Date(createdAtBefore) : undefined,\n createdAtAfter: createdAtAfter ? new Date(createdAtAfter) : undefined,\n updatedAtBefore: updatedAtBefore ? new Date(updatedAtBefore) : undefined,\n updatedAtAfter: updatedAtAfter ? new Date(updatedAtAfter) : undefined,\n concurrency,\n transcendUrl,\n });\n}\n"],"mappings":"0GAoBA,eAAsB,EAEpB,CACE,OACA,aACA,UACA,0BACA,aACA,kBACA,iBACA,kBACA,iBACA,cACA,gBAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAEtC,MAAM,EAAmB,CACvB,OACA,aACA,eAAgB,EAChB,0BACA,aACA,gBAAiB,EAAkB,IAAI,KAAK,EAAgB,CAAG,IAAA,GAC/D,eAAgB,EAAiB,IAAI,KAAK,EAAe,CAAG,IAAA,GAC5D,gBAAiB,EAAkB,IAAI,KAAK,EAAgB,CAAG,IAAA,GAC/D,eAAgB,EAAiB,IAAI,KAAK,EAAe,CAAG,IAAA,GAC5D,cACA,eACD,CAAC"}
@@ -1,2 +1,2 @@
1
- import{t as e}from"./logger-Ckep4QXn.mjs";import{n as t}from"./buildXdiSyncEndpoint-CI91Blyp.mjs";import{t as n}from"./validateTranscendAuth-DhzCBA3F.mjs";import{t as r}from"./done-input-validation-uqIgnJcw.mjs";import{writeFileSync as i}from"node:fs";import a from"colors";async function o({auth:o,xdiLocation:s,file:c,removeIpAddresses:l,domainBlockList:u,xdiAllowedCommands:d,transcendUrl:f}){r(this.process.exit);let{syncGroups:p,html:m}=await t(await n(o),{xdiLocation:s,transcendUrl:f,removeIpAddresses:l,domainBlockList:u.length>0?u:void 0,xdiAllowedCommands:d});e.info(a.green(`Successfully constructed sync endpoint for sync groups: ${JSON.stringify(p,null,2)}`)),i(c,m),e.info(a.green(`Wrote configuration to file "${c}"!`))}export{o as buildXdiSyncEndpoint};
2
- //# sourceMappingURL=impl-BjlpBG3U.mjs.map
1
+ import{t as e}from"./logger-Ckep4QXn.mjs";import{n as t}from"./buildXdiSyncEndpoint-Bmr-hWLk.mjs";import{t as n}from"./validateTranscendAuth-CbYKgCP5.mjs";import{t as r}from"./done-input-validation-uqIgnJcw.mjs";import{writeFileSync as i}from"node:fs";import a from"colors";async function o({auth:o,xdiLocation:s,file:c,removeIpAddresses:l,domainBlockList:u,xdiAllowedCommands:d,transcendUrl:f}){r(this.process.exit);let{syncGroups:p,html:m}=await t(await n(o),{xdiLocation:s,transcendUrl:f,removeIpAddresses:l,domainBlockList:u.length>0?u:void 0,xdiAllowedCommands:d});e.info(a.green(`Successfully constructed sync endpoint for sync groups: ${JSON.stringify(p,null,2)}`)),i(c,m),e.info(a.green(`Wrote configuration to file "${c}"!`))}export{o as buildXdiSyncEndpoint};
2
+ //# sourceMappingURL=impl-BZ4pxOP_.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"impl-BjlpBG3U.mjs","names":["buildXdiSyncEndpointHelper"],"sources":["../src/commands/consent/build-xdi-sync-endpoint/impl.ts"],"sourcesContent":["import { writeFileSync } from 'node:fs';\n\nimport colors from 'colors';\n\nimport type { LocalContext } from '../../../context.js';\nimport { validateTranscendAuth } from '../../../lib/api-keys/index.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { buildXdiSyncEndpoint as buildXdiSyncEndpointHelper } from '../../../lib/consent-manager/index.js';\nimport { logger } from '../../../logger.js';\n\nexport interface BuildXdiSyncEndpointCommandFlags {\n auth: string;\n xdiLocation: string;\n file: string;\n removeIpAddresses: boolean;\n domainBlockList: string[];\n xdiAllowedCommands: string;\n transcendUrl: string;\n}\n\nexport async function buildXdiSyncEndpoint(\n this: LocalContext,\n {\n auth,\n xdiLocation,\n file,\n removeIpAddresses,\n domainBlockList,\n xdiAllowedCommands,\n transcendUrl,\n }: BuildXdiSyncEndpointCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n // Parse authentication as API key or path to list of API keys\n const apiKeyOrList = await validateTranscendAuth(auth);\n\n // Build the sync endpoint\n const { syncGroups, html } = await buildXdiSyncEndpointHelper(apiKeyOrList, {\n xdiLocation,\n transcendUrl,\n removeIpAddresses,\n domainBlockList: domainBlockList.length > 0 ? domainBlockList : undefined,\n xdiAllowedCommands,\n });\n\n // Log success\n logger.info(\n colors.green(\n `Successfully constructed sync endpoint for sync groups: ${JSON.stringify(\n syncGroups,\n null,\n 2,\n )}`,\n ),\n );\n\n // Write to disk\n writeFileSync(file, html);\n logger.info(colors.green(`Wrote configuration to file \"${file}\"!`));\n}\n"],"mappings":"kRAoBA,eAAsB,EAEpB,CACE,OACA,cACA,OACA,oBACA,kBACA,qBACA,gBAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAMtC,GAAM,CAAE,aAAY,QAAS,MAAMA,EAA2B,MAHnC,EAAsB,EAAK,CAGsB,CAC1E,cACA,eACA,oBACA,gBAAiB,EAAgB,OAAS,EAAI,EAAkB,IAAA,GAChE,qBACD,CAAC,CAGF,EAAO,KACL,EAAO,MACL,2DAA2D,KAAK,UAC9D,EACA,KACA,EACD,GACF,CACF,CAGD,EAAc,EAAM,EAAK,CACzB,EAAO,KAAK,EAAO,MAAM,gCAAgC,EAAK,IAAI,CAAC"}
1
+ {"version":3,"file":"impl-BZ4pxOP_.mjs","names":["buildXdiSyncEndpointHelper"],"sources":["../src/commands/consent/build-xdi-sync-endpoint/impl.ts"],"sourcesContent":["import { writeFileSync } from 'node:fs';\n\nimport colors from 'colors';\n\nimport type { LocalContext } from '../../../context.js';\nimport { validateTranscendAuth } from '../../../lib/api-keys/index.js';\nimport { doneInputValidation } from '../../../lib/cli/done-input-validation.js';\nimport { buildXdiSyncEndpoint as buildXdiSyncEndpointHelper } from '../../../lib/consent-manager/index.js';\nimport { logger } from '../../../logger.js';\n\nexport interface BuildXdiSyncEndpointCommandFlags {\n auth: string;\n xdiLocation: string;\n file: string;\n removeIpAddresses: boolean;\n domainBlockList: string[];\n xdiAllowedCommands: string;\n transcendUrl: string;\n}\n\nexport async function buildXdiSyncEndpoint(\n this: LocalContext,\n {\n auth,\n xdiLocation,\n file,\n removeIpAddresses,\n domainBlockList,\n xdiAllowedCommands,\n transcendUrl,\n }: BuildXdiSyncEndpointCommandFlags,\n): Promise<void> {\n doneInputValidation(this.process.exit);\n\n // Parse authentication as API key or path to list of API keys\n const apiKeyOrList = await validateTranscendAuth(auth);\n\n // Build the sync endpoint\n const { syncGroups, html } = await buildXdiSyncEndpointHelper(apiKeyOrList, {\n xdiLocation,\n transcendUrl,\n removeIpAddresses,\n domainBlockList: domainBlockList.length > 0 ? domainBlockList : undefined,\n xdiAllowedCommands,\n });\n\n // Log success\n logger.info(\n colors.green(\n `Successfully constructed sync endpoint for sync groups: ${JSON.stringify(\n syncGroups,\n null,\n 2,\n )}`,\n ),\n );\n\n // Write to disk\n writeFileSync(file, html);\n logger.info(colors.green(`Wrote configuration to file \"${file}\"!`));\n}\n"],"mappings":"kRAoBA,eAAsB,EAEpB,CACE,OACA,cACA,OACA,oBACA,kBACA,qBACA,gBAEa,CACf,EAAoB,KAAK,QAAQ,KAAK,CAMtC,GAAM,CAAE,aAAY,QAAS,MAAMA,EAA2B,MAHnC,EAAsB,EAAK,CAGsB,CAC1E,cACA,eACA,oBACA,gBAAiB,EAAgB,OAAS,EAAI,EAAkB,IAAA,GAChE,qBACD,CAAC,CAGF,EAAO,KACL,EAAO,MACL,2DAA2D,KAAK,UAC9D,EACA,KACA,EACD,GACF,CACF,CAGD,EAAc,EAAM,EAAK,CACzB,EAAO,KAAK,EAAO,MAAM,gCAAgC,EAAK,IAAI,CAAC"}