@actsecurity/iam-lens 0.1.156

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 (383) hide show
  1. package/LICENSE.txt +661 -0
  2. package/README.md +203 -0
  3. package/dist/cjs/cli.d.ts +3 -0
  4. package/dist/cjs/cli.d.ts.map +1 -0
  5. package/dist/cjs/cli.js +206 -0
  6. package/dist/cjs/cli.js.map +1 -0
  7. package/dist/cjs/collect/client.d.ts +550 -0
  8. package/dist/cjs/collect/client.d.ts.map +1 -0
  9. package/dist/cjs/collect/client.js +1119 -0
  10. package/dist/cjs/collect/client.js.map +1 -0
  11. package/dist/cjs/collect/collect.d.ts +44 -0
  12. package/dist/cjs/collect/collect.d.ts.map +1 -0
  13. package/dist/cjs/collect/collect.js +55 -0
  14. package/dist/cjs/collect/collect.js.map +1 -0
  15. package/dist/cjs/collect/inMemoryClient.d.ts +6 -0
  16. package/dist/cjs/collect/inMemoryClient.d.ts.map +1 -0
  17. package/dist/cjs/collect/inMemoryClient.js +11 -0
  18. package/dist/cjs/collect/inMemoryClient.js.map +1 -0
  19. package/dist/cjs/index.d.ts +13 -0
  20. package/dist/cjs/index.d.ts.map +1 -0
  21. package/dist/cjs/index.js +28 -0
  22. package/dist/cjs/index.js.map +1 -0
  23. package/dist/cjs/package.json +3 -0
  24. package/dist/cjs/principalCan/permission.d.ts +125 -0
  25. package/dist/cjs/principalCan/permission.d.ts.map +1 -0
  26. package/dist/cjs/principalCan/permission.js +1229 -0
  27. package/dist/cjs/principalCan/permission.js.map +1 -0
  28. package/dist/cjs/principalCan/permissionSet.d.ts +140 -0
  29. package/dist/cjs/principalCan/permissionSet.d.ts.map +1 -0
  30. package/dist/cjs/principalCan/permissionSet.js +437 -0
  31. package/dist/cjs/principalCan/permissionSet.js.map +1 -0
  32. package/dist/cjs/principalCan/principalCan.d.ts +26 -0
  33. package/dist/cjs/principalCan/principalCan.d.ts.map +1 -0
  34. package/dist/cjs/principalCan/principalCan.js +195 -0
  35. package/dist/cjs/principalCan/principalCan.js.map +1 -0
  36. package/dist/cjs/principalCan/principalConstraints.d.ts +147 -0
  37. package/dist/cjs/principalCan/principalConstraints.d.ts.map +1 -0
  38. package/dist/cjs/principalCan/principalConstraints.js +472 -0
  39. package/dist/cjs/principalCan/principalConstraints.js.map +1 -0
  40. package/dist/cjs/principalCan/resources/actions.d.ts +9 -0
  41. package/dist/cjs/principalCan/resources/actions.d.ts.map +1 -0
  42. package/dist/cjs/principalCan/resources/actions.js +27 -0
  43. package/dist/cjs/principalCan/resources/actions.js.map +1 -0
  44. package/dist/cjs/principalCan/resources/resourceTypes/iamRoles.d.ts +31 -0
  45. package/dist/cjs/principalCan/resources/resourceTypes/iamRoles.d.ts.map +1 -0
  46. package/dist/cjs/principalCan/resources/resourceTypes/iamRoles.js +114 -0
  47. package/dist/cjs/principalCan/resources/resourceTypes/iamRoles.js.map +1 -0
  48. package/dist/cjs/principalCan/resources/resourceTypes/kmsKeys.d.ts +30 -0
  49. package/dist/cjs/principalCan/resources/resourceTypes/kmsKeys.d.ts.map +1 -0
  50. package/dist/cjs/principalCan/resources/resourceTypes/kmsKeys.js +110 -0
  51. package/dist/cjs/principalCan/resources/resourceTypes/kmsKeys.js.map +1 -0
  52. package/dist/cjs/principalCan/resources/resourceTypes/s3Buckets.d.ts +18 -0
  53. package/dist/cjs/principalCan/resources/resourceTypes/s3Buckets.d.ts.map +1 -0
  54. package/dist/cjs/principalCan/resources/resourceTypes/s3Buckets.js +123 -0
  55. package/dist/cjs/principalCan/resources/resourceTypes/s3Buckets.js.map +1 -0
  56. package/dist/cjs/principalCan/resources/statements.d.ts +27 -0
  57. package/dist/cjs/principalCan/resources/statements.d.ts.map +1 -0
  58. package/dist/cjs/principalCan/resources/statements.js +119 -0
  59. package/dist/cjs/principalCan/resources/statements.js.map +1 -0
  60. package/dist/cjs/principalIndex/makePrincipalIndex.d.ts +8 -0
  61. package/dist/cjs/principalIndex/makePrincipalIndex.d.ts.map +1 -0
  62. package/dist/cjs/principalIndex/makePrincipalIndex.js +105 -0
  63. package/dist/cjs/principalIndex/makePrincipalIndex.js.map +1 -0
  64. package/dist/cjs/principals.d.ts +54 -0
  65. package/dist/cjs/principals.d.ts.map +1 -0
  66. package/dist/cjs/principals.js +143 -0
  67. package/dist/cjs/principals.js.map +1 -0
  68. package/dist/cjs/resources.d.ts +32 -0
  69. package/dist/cjs/resources.d.ts.map +1 -0
  70. package/dist/cjs/resources.js +71 -0
  71. package/dist/cjs/resources.js.map +1 -0
  72. package/dist/cjs/simulate/contextKeys.d.ts +68 -0
  73. package/dist/cjs/simulate/contextKeys.d.ts.map +1 -0
  74. package/dist/cjs/simulate/contextKeys.js +293 -0
  75. package/dist/cjs/simulate/contextKeys.js.map +1 -0
  76. package/dist/cjs/simulate/simulate.d.ts +72 -0
  77. package/dist/cjs/simulate/simulate.d.ts.map +1 -0
  78. package/dist/cjs/simulate/simulate.js +296 -0
  79. package/dist/cjs/simulate/simulate.js.map +1 -0
  80. package/dist/cjs/test-datasets/testClient.d.ts +17 -0
  81. package/dist/cjs/test-datasets/testClient.d.ts.map +1 -0
  82. package/dist/cjs/test-datasets/testClient.js +58 -0
  83. package/dist/cjs/test-datasets/testClient.js.map +1 -0
  84. package/dist/cjs/utils/arn.d.ts +22 -0
  85. package/dist/cjs/utils/arn.d.ts.map +1 -0
  86. package/dist/cjs/utils/arn.js +49 -0
  87. package/dist/cjs/utils/arn.js.map +1 -0
  88. package/dist/cjs/utils/bitset.d.ts +45 -0
  89. package/dist/cjs/utils/bitset.d.ts.map +1 -0
  90. package/dist/cjs/utils/bitset.js +149 -0
  91. package/dist/cjs/utils/bitset.js.map +1 -0
  92. package/dist/cjs/utils/dynamicImport.d.ts +31 -0
  93. package/dist/cjs/utils/dynamicImport.d.ts.map +1 -0
  94. package/dist/cjs/utils/dynamicImport.js +64 -0
  95. package/dist/cjs/utils/dynamicImport.js.map +1 -0
  96. package/dist/cjs/utils/packageVersion.d.ts +5 -0
  97. package/dist/cjs/utils/packageVersion.d.ts.map +1 -0
  98. package/dist/cjs/utils/packageVersion.js +25 -0
  99. package/dist/cjs/utils/packageVersion.js.map +1 -0
  100. package/dist/cjs/utils/readPackageFile.d.ts +3 -0
  101. package/dist/cjs/utils/readPackageFile.d.ts.map +1 -0
  102. package/dist/cjs/utils/readPackageFile.js +16 -0
  103. package/dist/cjs/utils/readPackageFile.js.map +1 -0
  104. package/dist/cjs/utils/s3Abac.d.ts +3 -0
  105. package/dist/cjs/utils/s3Abac.d.ts.map +1 -0
  106. package/dist/cjs/utils/s3Abac.js +5 -0
  107. package/dist/cjs/utils/s3Abac.js.map +1 -0
  108. package/dist/cjs/utils/stringOrFileArgument.d.ts +9 -0
  109. package/dist/cjs/utils/stringOrFileArgument.d.ts.map +1 -0
  110. package/dist/cjs/utils/stringOrFileArgument.js +25 -0
  111. package/dist/cjs/utils/stringOrFileArgument.js.map +1 -0
  112. package/dist/cjs/utils/sts.d.ts +2 -0
  113. package/dist/cjs/utils/sts.d.ts.map +1 -0
  114. package/dist/cjs/utils/sts.js +9 -0
  115. package/dist/cjs/utils/sts.js.map +1 -0
  116. package/dist/cjs/utils/testUtils.d.ts +56 -0
  117. package/dist/cjs/utils/testUtils.d.ts.map +1 -0
  118. package/dist/cjs/utils/testUtils.js +95 -0
  119. package/dist/cjs/utils/testUtils.js.map +1 -0
  120. package/dist/cjs/utils/workerScript.d.ts +8 -0
  121. package/dist/cjs/utils/workerScript.d.ts.map +1 -0
  122. package/dist/cjs/utils/workerScript.js +23 -0
  123. package/dist/cjs/utils/workerScript.js.map +1 -0
  124. package/dist/cjs/whoCan/WhoCanMainThreadWorker.d.ts +73 -0
  125. package/dist/cjs/whoCan/WhoCanMainThreadWorker.d.ts.map +1 -0
  126. package/dist/cjs/whoCan/WhoCanMainThreadWorker.js +80 -0
  127. package/dist/cjs/whoCan/WhoCanMainThreadWorker.js.map +1 -0
  128. package/dist/cjs/whoCan/WhoCanProcessor.d.ts +400 -0
  129. package/dist/cjs/whoCan/WhoCanProcessor.d.ts.map +1 -0
  130. package/dist/cjs/whoCan/WhoCanProcessor.js +1088 -0
  131. package/dist/cjs/whoCan/WhoCanProcessor.js.map +1 -0
  132. package/dist/cjs/whoCan/WhoCanWorker.d.ts +87 -0
  133. package/dist/cjs/whoCan/WhoCanWorker.d.ts.map +1 -0
  134. package/dist/cjs/whoCan/WhoCanWorker.js +201 -0
  135. package/dist/cjs/whoCan/WhoCanWorker.js.map +1 -0
  136. package/dist/cjs/whoCan/WhoCanWorkerThreadWorker.d.ts +2 -0
  137. package/dist/cjs/whoCan/WhoCanWorkerThreadWorker.d.ts.map +1 -0
  138. package/dist/cjs/whoCan/WhoCanWorkerThreadWorker.js +189 -0
  139. package/dist/cjs/whoCan/WhoCanWorkerThreadWorker.js.map +1 -0
  140. package/dist/cjs/whoCan/principalArnFilter.d.ts +84 -0
  141. package/dist/cjs/whoCan/principalArnFilter.d.ts.map +1 -0
  142. package/dist/cjs/whoCan/principalArnFilter.js +258 -0
  143. package/dist/cjs/whoCan/principalArnFilter.js.map +1 -0
  144. package/dist/cjs/whoCan/principalScope.d.ts +35 -0
  145. package/dist/cjs/whoCan/principalScope.d.ts.map +1 -0
  146. package/dist/cjs/whoCan/principalScope.js +104 -0
  147. package/dist/cjs/whoCan/principalScope.js.map +1 -0
  148. package/dist/cjs/whoCan/requestAnalysis.d.ts +73 -0
  149. package/dist/cjs/whoCan/requestAnalysis.d.ts.map +1 -0
  150. package/dist/cjs/whoCan/requestAnalysis.js +87 -0
  151. package/dist/cjs/whoCan/requestAnalysis.js.map +1 -0
  152. package/dist/cjs/whoCan/untrustingActions.d.ts +7 -0
  153. package/dist/cjs/whoCan/untrustingActions.d.ts.map +1 -0
  154. package/dist/cjs/whoCan/untrustingActions.js +30 -0
  155. package/dist/cjs/whoCan/untrustingActions.js.map +1 -0
  156. package/dist/cjs/whoCan/whoCan.d.ts +295 -0
  157. package/dist/cjs/whoCan/whoCan.d.ts.map +1 -0
  158. package/dist/cjs/whoCan/whoCan.js +574 -0
  159. package/dist/cjs/whoCan/whoCan.js.map +1 -0
  160. package/dist/cjs/whoCan/workerBootstrapPlugin.d.ts +17 -0
  161. package/dist/cjs/whoCan/workerBootstrapPlugin.d.ts.map +1 -0
  162. package/dist/cjs/whoCan/workerBootstrapPlugin.js +3 -0
  163. package/dist/cjs/whoCan/workerBootstrapPlugin.js.map +1 -0
  164. package/dist/cjs/workers/ArrayStreamingWorkQueue.d.ts +15 -0
  165. package/dist/cjs/workers/ArrayStreamingWorkQueue.d.ts.map +1 -0
  166. package/dist/cjs/workers/ArrayStreamingWorkQueue.js +35 -0
  167. package/dist/cjs/workers/ArrayStreamingWorkQueue.js.map +1 -0
  168. package/dist/cjs/workers/JobRunner.d.ts +47 -0
  169. package/dist/cjs/workers/JobRunner.d.ts.map +1 -0
  170. package/dist/cjs/workers/JobRunner.js +101 -0
  171. package/dist/cjs/workers/JobRunner.js.map +1 -0
  172. package/dist/cjs/workers/RingQueue.d.ts +14 -0
  173. package/dist/cjs/workers/RingQueue.d.ts.map +1 -0
  174. package/dist/cjs/workers/RingQueue.js +43 -0
  175. package/dist/cjs/workers/RingQueue.js.map +1 -0
  176. package/dist/cjs/workers/SharedArrayBufferMainCache.d.ts +10 -0
  177. package/dist/cjs/workers/SharedArrayBufferMainCache.d.ts.map +1 -0
  178. package/dist/cjs/workers/SharedArrayBufferMainCache.js +37 -0
  179. package/dist/cjs/workers/SharedArrayBufferMainCache.js.map +1 -0
  180. package/dist/cjs/workers/SharedArrayBufferWorkerCache.d.ts +10 -0
  181. package/dist/cjs/workers/SharedArrayBufferWorkerCache.d.ts.map +1 -0
  182. package/dist/cjs/workers/SharedArrayBufferWorkerCache.js +49 -0
  183. package/dist/cjs/workers/SharedArrayBufferWorkerCache.js.map +1 -0
  184. package/dist/cjs/workers/StreamingWorkQueue.d.ts +18 -0
  185. package/dist/cjs/workers/StreamingWorkQueue.d.ts.map +1 -0
  186. package/dist/cjs/workers/StreamingWorkQueue.js +67 -0
  187. package/dist/cjs/workers/StreamingWorkQueue.js.map +1 -0
  188. package/dist/cjs/workers/buffers.d.ts +4 -0
  189. package/dist/cjs/workers/buffers.d.ts.map +1 -0
  190. package/dist/cjs/workers/buffers.js +26 -0
  191. package/dist/cjs/workers/buffers.js.map +1 -0
  192. package/dist/esm/cli.d.ts +3 -0
  193. package/dist/esm/cli.d.ts.map +1 -0
  194. package/dist/esm/cli.js +204 -0
  195. package/dist/esm/cli.js.map +1 -0
  196. package/dist/esm/collect/client.d.ts +550 -0
  197. package/dist/esm/collect/client.d.ts.map +1 -0
  198. package/dist/esm/collect/client.js +1114 -0
  199. package/dist/esm/collect/client.js.map +1 -0
  200. package/dist/esm/collect/collect.d.ts +44 -0
  201. package/dist/esm/collect/collect.d.ts.map +1 -0
  202. package/dist/esm/collect/collect.js +51 -0
  203. package/dist/esm/collect/collect.js.map +1 -0
  204. package/dist/esm/collect/inMemoryClient.d.ts +6 -0
  205. package/dist/esm/collect/inMemoryClient.d.ts.map +1 -0
  206. package/dist/esm/collect/inMemoryClient.js +8 -0
  207. package/dist/esm/collect/inMemoryClient.js.map +1 -0
  208. package/dist/esm/index.d.ts +13 -0
  209. package/dist/esm/index.d.ts.map +1 -0
  210. package/dist/esm/index.js +11 -0
  211. package/dist/esm/index.js.map +1 -0
  212. package/dist/esm/package.json +3 -0
  213. package/dist/esm/principalCan/permission.d.ts +125 -0
  214. package/dist/esm/principalCan/permission.d.ts.map +1 -0
  215. package/dist/esm/principalCan/permission.js +1212 -0
  216. package/dist/esm/principalCan/permission.js.map +1 -0
  217. package/dist/esm/principalCan/permissionSet.d.ts +140 -0
  218. package/dist/esm/principalCan/permissionSet.d.ts.map +1 -0
  219. package/dist/esm/principalCan/permissionSet.js +429 -0
  220. package/dist/esm/principalCan/permissionSet.js.map +1 -0
  221. package/dist/esm/principalCan/principalCan.d.ts +26 -0
  222. package/dist/esm/principalCan/principalCan.d.ts.map +1 -0
  223. package/dist/esm/principalCan/principalCan.js +193 -0
  224. package/dist/esm/principalCan/principalCan.js.map +1 -0
  225. package/dist/esm/principalCan/principalConstraints.d.ts +147 -0
  226. package/dist/esm/principalCan/principalConstraints.d.ts.map +1 -0
  227. package/dist/esm/principalCan/principalConstraints.js +456 -0
  228. package/dist/esm/principalCan/principalConstraints.js.map +1 -0
  229. package/dist/esm/principalCan/resources/actions.d.ts +9 -0
  230. package/dist/esm/principalCan/resources/actions.d.ts.map +1 -0
  231. package/dist/esm/principalCan/resources/actions.js +24 -0
  232. package/dist/esm/principalCan/resources/actions.js.map +1 -0
  233. package/dist/esm/principalCan/resources/resourceTypes/iamRoles.d.ts +31 -0
  234. package/dist/esm/principalCan/resources/resourceTypes/iamRoles.d.ts.map +1 -0
  235. package/dist/esm/principalCan/resources/resourceTypes/iamRoles.js +110 -0
  236. package/dist/esm/principalCan/resources/resourceTypes/iamRoles.js.map +1 -0
  237. package/dist/esm/principalCan/resources/resourceTypes/kmsKeys.d.ts +30 -0
  238. package/dist/esm/principalCan/resources/resourceTypes/kmsKeys.d.ts.map +1 -0
  239. package/dist/esm/principalCan/resources/resourceTypes/kmsKeys.js +106 -0
  240. package/dist/esm/principalCan/resources/resourceTypes/kmsKeys.js.map +1 -0
  241. package/dist/esm/principalCan/resources/resourceTypes/s3Buckets.d.ts +18 -0
  242. package/dist/esm/principalCan/resources/resourceTypes/s3Buckets.d.ts.map +1 -0
  243. package/dist/esm/principalCan/resources/resourceTypes/s3Buckets.js +120 -0
  244. package/dist/esm/principalCan/resources/resourceTypes/s3Buckets.js.map +1 -0
  245. package/dist/esm/principalCan/resources/statements.d.ts +27 -0
  246. package/dist/esm/principalCan/resources/statements.d.ts.map +1 -0
  247. package/dist/esm/principalCan/resources/statements.js +117 -0
  248. package/dist/esm/principalCan/resources/statements.js.map +1 -0
  249. package/dist/esm/principalIndex/makePrincipalIndex.d.ts +8 -0
  250. package/dist/esm/principalIndex/makePrincipalIndex.d.ts.map +1 -0
  251. package/dist/esm/principalIndex/makePrincipalIndex.js +104 -0
  252. package/dist/esm/principalIndex/makePrincipalIndex.js.map +1 -0
  253. package/dist/esm/principals.d.ts +54 -0
  254. package/dist/esm/principals.d.ts.map +1 -0
  255. package/dist/esm/principals.js +133 -0
  256. package/dist/esm/principals.js.map +1 -0
  257. package/dist/esm/resources.d.ts +32 -0
  258. package/dist/esm/resources.d.ts.map +1 -0
  259. package/dist/esm/resources.js +69 -0
  260. package/dist/esm/resources.js.map +1 -0
  261. package/dist/esm/simulate/contextKeys.d.ts +68 -0
  262. package/dist/esm/simulate/contextKeys.d.ts.map +1 -0
  263. package/dist/esm/simulate/contextKeys.js +287 -0
  264. package/dist/esm/simulate/contextKeys.js.map +1 -0
  265. package/dist/esm/simulate/simulate.d.ts +72 -0
  266. package/dist/esm/simulate/simulate.d.ts.map +1 -0
  267. package/dist/esm/simulate/simulate.js +295 -0
  268. package/dist/esm/simulate/simulate.js.map +1 -0
  269. package/dist/esm/test-datasets/testClient.d.ts +17 -0
  270. package/dist/esm/test-datasets/testClient.d.ts.map +1 -0
  271. package/dist/esm/test-datasets/testClient.js +56 -0
  272. package/dist/esm/test-datasets/testClient.js.map +1 -0
  273. package/dist/esm/utils/arn.d.ts +22 -0
  274. package/dist/esm/utils/arn.d.ts.map +1 -0
  275. package/dist/esm/utils/arn.js +43 -0
  276. package/dist/esm/utils/arn.js.map +1 -0
  277. package/dist/esm/utils/bitset.d.ts +45 -0
  278. package/dist/esm/utils/bitset.d.ts.map +1 -0
  279. package/dist/esm/utils/bitset.js +141 -0
  280. package/dist/esm/utils/bitset.js.map +1 -0
  281. package/dist/esm/utils/dynamicImport.d.ts +31 -0
  282. package/dist/esm/utils/dynamicImport.d.ts.map +1 -0
  283. package/dist/esm/utils/dynamicImport.js +60 -0
  284. package/dist/esm/utils/dynamicImport.js.map +1 -0
  285. package/dist/esm/utils/packageVersion.d.ts +5 -0
  286. package/dist/esm/utils/packageVersion.d.ts.map +1 -0
  287. package/dist/esm/utils/packageVersion.js +22 -0
  288. package/dist/esm/utils/packageVersion.js.map +1 -0
  289. package/dist/esm/utils/readPackageFile.d.ts +3 -0
  290. package/dist/esm/utils/readPackageFile.d.ts.map +1 -0
  291. package/dist/esm/utils/readPackageFile.js +15 -0
  292. package/dist/esm/utils/readPackageFile.js.map +1 -0
  293. package/dist/esm/utils/readPackageFileEsm.d.ts.map +1 -0
  294. package/dist/esm/utils/s3Abac.d.ts +3 -0
  295. package/dist/esm/utils/s3Abac.d.ts.map +1 -0
  296. package/dist/esm/utils/s3Abac.js +2 -0
  297. package/dist/esm/utils/s3Abac.js.map +1 -0
  298. package/dist/esm/utils/stringOrFileArgument.d.ts +9 -0
  299. package/dist/esm/utils/stringOrFileArgument.d.ts.map +1 -0
  300. package/dist/esm/utils/stringOrFileArgument.js +22 -0
  301. package/dist/esm/utils/stringOrFileArgument.js.map +1 -0
  302. package/dist/esm/utils/sts.d.ts +2 -0
  303. package/dist/esm/utils/sts.d.ts.map +1 -0
  304. package/dist/esm/utils/sts.js +6 -0
  305. package/dist/esm/utils/sts.js.map +1 -0
  306. package/dist/esm/utils/testUtils.d.ts +56 -0
  307. package/dist/esm/utils/testUtils.d.ts.map +1 -0
  308. package/dist/esm/utils/testUtils.js +90 -0
  309. package/dist/esm/utils/testUtils.js.map +1 -0
  310. package/dist/esm/utils/workerScript.d.ts +8 -0
  311. package/dist/esm/utils/workerScript.d.ts.map +1 -0
  312. package/dist/esm/utils/workerScript.js +18 -0
  313. package/dist/esm/utils/workerScript.js.map +1 -0
  314. package/dist/esm/utils/workerScriptEsm.d.ts.map +1 -0
  315. package/dist/esm/whoCan/WhoCanMainThreadWorker.d.ts +73 -0
  316. package/dist/esm/whoCan/WhoCanMainThreadWorker.d.ts.map +1 -0
  317. package/dist/esm/whoCan/WhoCanMainThreadWorker.js +81 -0
  318. package/dist/esm/whoCan/WhoCanMainThreadWorker.js.map +1 -0
  319. package/dist/esm/whoCan/WhoCanProcessor.d.ts +400 -0
  320. package/dist/esm/whoCan/WhoCanProcessor.d.ts.map +1 -0
  321. package/dist/esm/whoCan/WhoCanProcessor.js +1080 -0
  322. package/dist/esm/whoCan/WhoCanProcessor.js.map +1 -0
  323. package/dist/esm/whoCan/WhoCanWorker.d.ts +87 -0
  324. package/dist/esm/whoCan/WhoCanWorker.d.ts.map +1 -0
  325. package/dist/esm/whoCan/WhoCanWorker.js +198 -0
  326. package/dist/esm/whoCan/WhoCanWorker.js.map +1 -0
  327. package/dist/esm/whoCan/WhoCanWorkerThreadWorker.d.ts +2 -0
  328. package/dist/esm/whoCan/WhoCanWorkerThreadWorker.d.ts.map +1 -0
  329. package/dist/esm/whoCan/WhoCanWorkerThreadWorker.js +193 -0
  330. package/dist/esm/whoCan/WhoCanWorkerThreadWorker.js.map +1 -0
  331. package/dist/esm/whoCan/principalArnFilter.d.ts +84 -0
  332. package/dist/esm/whoCan/principalArnFilter.d.ts.map +1 -0
  333. package/dist/esm/whoCan/principalArnFilter.js +253 -0
  334. package/dist/esm/whoCan/principalArnFilter.js.map +1 -0
  335. package/dist/esm/whoCan/principalScope.d.ts +35 -0
  336. package/dist/esm/whoCan/principalScope.d.ts.map +1 -0
  337. package/dist/esm/whoCan/principalScope.js +102 -0
  338. package/dist/esm/whoCan/principalScope.js.map +1 -0
  339. package/dist/esm/whoCan/requestAnalysis.d.ts +73 -0
  340. package/dist/esm/whoCan/requestAnalysis.d.ts.map +1 -0
  341. package/dist/esm/whoCan/requestAnalysis.js +83 -0
  342. package/dist/esm/whoCan/requestAnalysis.js.map +1 -0
  343. package/dist/esm/whoCan/untrustingActions.d.ts +7 -0
  344. package/dist/esm/whoCan/untrustingActions.d.ts.map +1 -0
  345. package/dist/esm/whoCan/untrustingActions.js +27 -0
  346. package/dist/esm/whoCan/untrustingActions.js.map +1 -0
  347. package/dist/esm/whoCan/whoCan.d.ts +295 -0
  348. package/dist/esm/whoCan/whoCan.d.ts.map +1 -0
  349. package/dist/esm/whoCan/whoCan.js +571 -0
  350. package/dist/esm/whoCan/whoCan.js.map +1 -0
  351. package/dist/esm/whoCan/workerBootstrapPlugin.d.ts +17 -0
  352. package/dist/esm/whoCan/workerBootstrapPlugin.d.ts.map +1 -0
  353. package/dist/esm/whoCan/workerBootstrapPlugin.js +2 -0
  354. package/dist/esm/whoCan/workerBootstrapPlugin.js.map +1 -0
  355. package/dist/esm/workers/ArrayStreamingWorkQueue.d.ts +15 -0
  356. package/dist/esm/workers/ArrayStreamingWorkQueue.d.ts.map +1 -0
  357. package/dist/esm/workers/ArrayStreamingWorkQueue.js +31 -0
  358. package/dist/esm/workers/ArrayStreamingWorkQueue.js.map +1 -0
  359. package/dist/esm/workers/JobRunner.d.ts +47 -0
  360. package/dist/esm/workers/JobRunner.d.ts.map +1 -0
  361. package/dist/esm/workers/JobRunner.js +94 -0
  362. package/dist/esm/workers/JobRunner.js.map +1 -0
  363. package/dist/esm/workers/RingQueue.d.ts +14 -0
  364. package/dist/esm/workers/RingQueue.d.ts.map +1 -0
  365. package/dist/esm/workers/RingQueue.js +36 -0
  366. package/dist/esm/workers/RingQueue.js.map +1 -0
  367. package/dist/esm/workers/SharedArrayBufferMainCache.d.ts +10 -0
  368. package/dist/esm/workers/SharedArrayBufferMainCache.d.ts.map +1 -0
  369. package/dist/esm/workers/SharedArrayBufferMainCache.js +34 -0
  370. package/dist/esm/workers/SharedArrayBufferMainCache.js.map +1 -0
  371. package/dist/esm/workers/SharedArrayBufferWorkerCache.d.ts +10 -0
  372. package/dist/esm/workers/SharedArrayBufferWorkerCache.d.ts.map +1 -0
  373. package/dist/esm/workers/SharedArrayBufferWorkerCache.js +46 -0
  374. package/dist/esm/workers/SharedArrayBufferWorkerCache.js.map +1 -0
  375. package/dist/esm/workers/StreamingWorkQueue.d.ts +18 -0
  376. package/dist/esm/workers/StreamingWorkQueue.d.ts.map +1 -0
  377. package/dist/esm/workers/StreamingWorkQueue.js +61 -0
  378. package/dist/esm/workers/StreamingWorkQueue.js.map +1 -0
  379. package/dist/esm/workers/buffers.d.ts +4 -0
  380. package/dist/esm/workers/buffers.d.ts.map +1 -0
  381. package/dist/esm/workers/buffers.js +21 -0
  382. package/dist/esm/workers/buffers.js.map +1 -0
  383. package/package.json +132 -0
@@ -0,0 +1,1119 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.IamCollectClient = exports.NoCacheProvider = exports.InMemoryCacheProvider = void 0;
4
+ const log_1 = require("@actsecurity/log");
5
+ const iam_expand_1 = require("@actsecurity/iam-expand");
6
+ const iam_policy_1 = require("@actsecurity/iam-policy");
7
+ const iam_utils_1 = require("@actsecurity/iam-utils");
8
+ const bitset_1 = require("bitset");
9
+ const zlib_1 = require("zlib");
10
+ const bitset_js_1 = require("../utils/bitset.js");
11
+ /**
12
+ * Normalize an S3 bucket or object ARN to the bucket ARN used by iam-collect bucket metadata.
13
+ *
14
+ * @param bucketOrObjectArn The S3 bucket or object ARN to normalize
15
+ * @returns The bucket ARN without an object key suffix
16
+ */
17
+ function bucketArnFromBucketOrObjectArn(bucketOrObjectArn) {
18
+ // S3 bucket ARNs use the first slash to separate the bucket name from the object key.
19
+ if (bucketOrObjectArn.includes('/')) {
20
+ return bucketOrObjectArn.split('/').at(0);
21
+ }
22
+ return bucketOrObjectArn;
23
+ }
24
+ /**
25
+ * A cache provider that stores results in memory for a single worker.
26
+ */
27
+ class InMemoryCacheProvider {
28
+ cache = {};
29
+ async withCache(cacheKey, fetcher) {
30
+ if (cacheKey in this.cache) {
31
+ return this.cache[cacheKey];
32
+ }
33
+ const value = await fetcher();
34
+ this.cache[cacheKey] = value;
35
+ return value;
36
+ }
37
+ }
38
+ exports.InMemoryCacheProvider = InMemoryCacheProvider;
39
+ /**
40
+ * A cache provider that does not cache results.
41
+ */
42
+ class NoCacheProvider {
43
+ async withCache(cacheKey, fetcher) {
44
+ return fetcher();
45
+ }
46
+ }
47
+ exports.NoCacheProvider = NoCacheProvider;
48
+ /**
49
+ * A client for simplifying access to the IAM collect data store.
50
+ */
51
+ class IamCollectClient {
52
+ storageClient;
53
+ cacheProvider;
54
+ /**
55
+ * Creates a new instance of the IamCollectClient.
56
+ *
57
+ * @param storageClient the iam-collect storage client to use for data access
58
+ * @param clientOptions optional configuration options for the client. By default, uses an in-memory cache provider.
59
+ */
60
+ constructor(storageClient, clientOptions) {
61
+ this.storageClient = storageClient;
62
+ if (clientOptions?.cacheProvider === undefined) {
63
+ this.cacheProvider = new InMemoryCacheProvider();
64
+ }
65
+ else {
66
+ this.cacheProvider = clientOptions.cacheProvider;
67
+ }
68
+ }
69
+ getStore() {
70
+ return this.storageClient;
71
+ }
72
+ /**
73
+ * Returns the cache provider used by this client.
74
+ *
75
+ * @returns The {@link CacheProvider} instance in use.
76
+ */
77
+ getCacheProvider() {
78
+ return this.cacheProvider;
79
+ }
80
+ async withCache(cacheKey, fetcher) {
81
+ return this.cacheProvider.withCache(cacheKey, fetcher);
82
+ }
83
+ /**
84
+ * Checks if an account exists in the store.
85
+ * @param accountId The ID of the account to check.
86
+ * @returns True if the account exists, false otherwise.
87
+ */
88
+ async accountExists(accountId) {
89
+ const cacheKey = `accountExists:${accountId}`;
90
+ return this.withCache(cacheKey, async () => {
91
+ const accounts = await this.storageClient.listAccountIds();
92
+ return accounts.includes(accountId);
93
+ });
94
+ }
95
+ /**
96
+ * Get all account IDs in the store.
97
+ *
98
+ * @returns all account IDs in the store
99
+ */
100
+ async allAccounts() {
101
+ const cacheKey = `allAccounts`;
102
+ return this.withCache(cacheKey, async () => {
103
+ return this.storageClient.listAccountIds();
104
+ });
105
+ }
106
+ /**
107
+ * Resolves a principal ARN to the canonical ARN stored in the collect data.
108
+ *
109
+ * STS assumed-role ARNs are first converted to their IAM role ARN form. Exact metadata
110
+ * matches are returned first. If an IAM role ARN is not found exactly, the role is
111
+ * resolved by role name within the same account. This supports STS assumed-role
112
+ * session ARNs because those session ARNs do not include the IAM role path.
113
+ *
114
+ * @param principalArn The ARN of the principal to resolve.
115
+ * @returns The canonical stored principal ARN, or undefined if no matching principal exists.
116
+ */
117
+ async resolvePrincipalArn(principalArn) {
118
+ const cacheKey = `resolvePrincipalArn:${principalArn}`;
119
+ return this.withCache(cacheKey, async () => {
120
+ const lookupPrincipalArn = (0, iam_utils_1.isAssumedRoleArn)(principalArn)
121
+ ? (0, iam_utils_1.convertAssumedRoleArnToRoleArn)(principalArn)
122
+ : principalArn;
123
+ const arnParts = (0, iam_utils_1.splitArnParts)(lookupPrincipalArn);
124
+ const accountId = arnParts.accountId;
125
+ const principalData = await this.storageClient.getResourceMetadata(accountId, lookupPrincipalArn, 'metadata');
126
+ if (principalData) {
127
+ return principalData.arn ?? lookupPrincipalArn;
128
+ }
129
+ if (arnParts.service !== 'iam' || arnParts.resourceType !== 'role') {
130
+ return undefined;
131
+ }
132
+ const roleName = arnParts.resourcePath?.split('/').at(-1)?.toLowerCase();
133
+ if (!roleName) {
134
+ return undefined;
135
+ }
136
+ const accountPrincipals = await this.getAllPrincipalsInAccount(accountId);
137
+ const matchingRole = accountPrincipals.find((candidateArn) => {
138
+ const candidateParts = (0, iam_utils_1.splitArnParts)(candidateArn);
139
+ return (candidateParts.service === 'iam' &&
140
+ candidateParts.resourceType === 'role' &&
141
+ candidateParts.resourcePath?.split('/').at(-1)?.toLowerCase() === roleName);
142
+ });
143
+ return matchingRole;
144
+ });
145
+ }
146
+ /**
147
+ * Checks if a principal exists in the store.
148
+ * @param principalArn The ARN of the principal to check.
149
+ * @returns True if the principal exists, false otherwise.
150
+ */
151
+ async principalExists(principalArn) {
152
+ const cacheKey = `principalExists:${principalArn}`;
153
+ return this.withCache(cacheKey, async () => {
154
+ return !!(await this.resolvePrincipalArn(principalArn));
155
+ });
156
+ }
157
+ /**
158
+ * Gets the SCP Hierarchy for an account. The first element is the root, the last element is the account itself.
159
+ * @param accountId The ID of the account to get the SCP Hierarchy for.
160
+ * @returns The SCP Hierarchy for the account.
161
+ */
162
+ async getScpHierarchyForAccount(accountId) {
163
+ return this.getOrgPolicyHierarchyForAccount(accountId, 'scps');
164
+ }
165
+ /**
166
+ * Gets the policy hierarchy for an account for a given policy type.
167
+ * @param accountId The ID of the account.
168
+ * @param policyType The type of policy ('scps' or 'rcps').
169
+ * @returns The policy hierarchy for the account.
170
+ */
171
+ async getOrgPolicyHierarchyForAccount(accountId, policyType) {
172
+ const cacheKey = `orgPolicyHierarchy:${accountId}:${policyType}`;
173
+ return this.withCache(cacheKey, async () => {
174
+ const orgId = await this.getOrgIdForAccount(accountId);
175
+ if (!orgId) {
176
+ return [];
177
+ }
178
+ // SCPs and RCPs do not apply to the root account
179
+ const orgMetadata = await this.getOrganizationMetadata(orgId);
180
+ if (orgMetadata.rootAccountId === accountId) {
181
+ return [];
182
+ }
183
+ const policyHierarchy = [];
184
+ const orgHierarchy = await this.getOrgUnitHierarchyForAccount(accountId);
185
+ for (const ouId of orgHierarchy) {
186
+ const policies = await this.getOrgPoliciesForOrgUnit(orgId, ouId, policyType);
187
+ policyHierarchy.push({
188
+ orgIdentifier: ouId,
189
+ policies: policies.map((p) => ({
190
+ name: p.arn,
191
+ policy: p.policy
192
+ }))
193
+ });
194
+ }
195
+ const accountPolicies = await this.getOrgPoliciesForAccount(accountId, policyType);
196
+ policyHierarchy.push({
197
+ orgIdentifier: accountId,
198
+ policies: accountPolicies.map((p) => ({
199
+ name: p.arn,
200
+ policy: p.policy
201
+ }))
202
+ });
203
+ return policyHierarchy;
204
+ });
205
+ }
206
+ /**
207
+ * Gets the OUs for an account. The first element is the root,
208
+ * the last element is the parent OU of the account.
209
+ * @param accountId The ID of the account to get the OUs for.
210
+ * @returns The OUs for the account.
211
+ */
212
+ async getOrgUnitHierarchyForAccount(accountId) {
213
+ const cacheKey = `orgUnitHierarchy:${accountId}`;
214
+ return this.withCache(cacheKey, async () => {
215
+ const orgId = await this.getOrgIdForAccount(accountId);
216
+ if (!orgId) {
217
+ return [];
218
+ }
219
+ const ouIds = [];
220
+ let ouId = await this.getOrgUnitIdForAccount(accountId);
221
+ ouIds.push(ouId);
222
+ while (ouId) {
223
+ const parentOuId = await this.getParentOrgUnitIdForOrgUnit(orgId, ouId);
224
+ if (parentOuId) {
225
+ ouIds.unshift(parentOuId);
226
+ }
227
+ ouId = parentOuId;
228
+ }
229
+ return ouIds;
230
+ });
231
+ }
232
+ /**
233
+ * Gets the org unit ID for an account.
234
+ * @param accountId The ID of the account.
235
+ * @returns The org unit ID for the account, or undefined if not found.
236
+ */
237
+ async getOrgUnitIdForAccount(accountId) {
238
+ const cacheKey = `orgUnitId:${accountId}`;
239
+ return this.withCache(cacheKey, async () => {
240
+ const orgId = await this.getOrgIdForAccount(accountId);
241
+ if (!orgId) {
242
+ return undefined;
243
+ }
244
+ const accounts = (await this.getAccountDataForOrg(orgId));
245
+ return accounts[accountId].ou;
246
+ });
247
+ }
248
+ /**
249
+ * Gets the parent org unit ID for a given org unit.
250
+ * @param orgId The ID of the organization.
251
+ * @param ouId The ID of the org unit.
252
+ * @returns The parent org unit ID, or undefined if not found.
253
+ */
254
+ async getParentOrgUnitIdForOrgUnit(orgId, ouId) {
255
+ const cacheKey = `parentOrgUnit:${orgId}:${ouId}`;
256
+ return this.withCache(cacheKey, async () => {
257
+ const ouData = await this.getOrgUnitsDataForOrg(orgId);
258
+ const ou = ouData[ouId];
259
+ return ou.parent;
260
+ });
261
+ }
262
+ /**
263
+ * Gets the SCPs for an account.
264
+ * @param accountId The ID of the account.
265
+ * @returns The SCPs for the account.
266
+ */
267
+ async getScpsForAccount(accountId) {
268
+ return this.getOrgPoliciesForAccount(accountId, 'scps');
269
+ }
270
+ /**
271
+ * Gets the org policies for an account for a given policy type.
272
+ * @param accountId The ID of the account.
273
+ * @param policyType The type of policy ('scps' or 'rcps').
274
+ * @returns The org policies for the account.
275
+ */
276
+ async getOrgPoliciesForAccount(accountId, policyType) {
277
+ const cacheKey = `orgPoliciesForAccount:${accountId}:${policyType}`;
278
+ return this.withCache(cacheKey, async () => {
279
+ const orgId = await this.getOrgIdForAccount(accountId);
280
+ if (!orgId) {
281
+ return [];
282
+ }
283
+ const accounts = (await this.getAccountDataForOrg(orgId));
284
+ const orgInformation = accounts[accountId];
285
+ const policyArns = orgInformation[policyType];
286
+ const policies = [];
287
+ for (const policyArn of policyArns) {
288
+ const policyInfo = await this.getOrgPolicy(orgId, policyType, policyArn);
289
+ policies.push(policyInfo);
290
+ }
291
+ return policies;
292
+ });
293
+ }
294
+ /**
295
+ * Gets the account data for an organization.
296
+ * @param orgId The ID of the organization.
297
+ * @returns The account data for the organization.
298
+ */
299
+ async getAccountDataForOrg(orgId) {
300
+ const cacheKey = `accountDataForOrg:${orgId}`;
301
+ return this.withCache(cacheKey, async () => {
302
+ return this.storageClient.getOrganizationMetadata(orgId, 'accounts');
303
+ });
304
+ }
305
+ /**
306
+ * Gets the org units data for an organization.
307
+ * @param orgId The ID of the organization.
308
+ * @returns The org units data for the organization.
309
+ */
310
+ async getOrgUnitsDataForOrg(orgId) {
311
+ const cacheKey = `orgUnitsDataForOrg:${orgId}`;
312
+ return this.withCache(cacheKey, async () => {
313
+ return this.storageClient.getOrganizationMetadata(orgId, 'ous');
314
+ });
315
+ }
316
+ /**
317
+ * Gets a specific org policy.
318
+ * @param orgId The ID of the organization.
319
+ * @param policyType The type of policy ('scps' or 'rcps').
320
+ * @param policyArn The ARN of the policy.
321
+ * @returns The org policy.
322
+ */
323
+ async getOrgPolicy(orgId, policyType, policyArn) {
324
+ const cacheKey = `orgPolicy:${orgId}:${policyType}:${policyArn}`;
325
+ return this.withCache(cacheKey, async () => {
326
+ const policyId = policyArn.split('/').at(-1);
327
+ const policyData = await this.storageClient.getOrganizationPolicyMetadata(orgId, policyType, policyId, 'metadata');
328
+ const policyDocument = await this.storageClient.getOrganizationPolicyMetadata(orgId, policyType, policyId, 'policy');
329
+ if (!policyDocument) {
330
+ log_1.log.warn(`Policy document not found for ${policyArn} in org ${orgId}`);
331
+ }
332
+ const validateFn = policyType === 'scps' ? iam_policy_1.validateServiceControlPolicy : iam_policy_1.validateResourceControlPolicy;
333
+ return {
334
+ arn: policyData.arn,
335
+ name: policyData.name,
336
+ policy: (0, iam_policy_1.createValidatedPolicy)(policyDocument, validateFn, { name: policyData.arn })
337
+ };
338
+ });
339
+ }
340
+ /**
341
+ * Gets the RCPs for an account.
342
+ * @param accountId The ID of the account.
343
+ * @returns The RCPs for the account.
344
+ */
345
+ async getRcpsForAccount(accountId) {
346
+ return this.getOrgPoliciesForAccount(accountId, 'rcps');
347
+ }
348
+ /**
349
+ * Gets the RCP hierarchy for an account.
350
+ * @param accountId The ID of the account.
351
+ * @returns The RCP hierarchy for the account.
352
+ */
353
+ async getRcpHierarchyForAccount(accountId) {
354
+ return this.getOrgPolicyHierarchyForAccount(accountId, 'rcps');
355
+ }
356
+ /**
357
+ * Gets the SCPs for an org unit.
358
+ * @param orgId The ID of the organization.
359
+ * @param orgUnitId The ID of the org unit.
360
+ * @returns The SCPs for the org unit.
361
+ */
362
+ async getScpsForOrgUnit(orgId, orgUnitId) {
363
+ return this.getOrgPoliciesForOrgUnit(orgId, orgUnitId, 'scps');
364
+ }
365
+ /**
366
+ * Gets the org policies for an org unit for a given policy type.
367
+ * @param orgId The ID of the organization.
368
+ * @param orgUnitId The ID of the org unit.
369
+ * @param policyType The type of policy ('scps' or 'rcps').
370
+ * @returns The org policies for the org unit.
371
+ */
372
+ async getOrgPoliciesForOrgUnit(orgId, orgUnitId, policyType) {
373
+ const cacheKey = `orgPoliciesForOrgUnit:${orgId}:${orgUnitId}:${policyType}`;
374
+ return this.withCache(cacheKey, async () => {
375
+ const orgUnitInformation = await this.getOrgUnitsDataForOrg(orgId);
376
+ const orgUnit = orgUnitInformation[orgUnitId];
377
+ const orgPolicies = orgUnit[policyType];
378
+ const policies = [];
379
+ for (const policyArn of orgPolicies) {
380
+ const policyInfo = await this.getOrgPolicy(orgId, policyType, policyArn);
381
+ policies.push(policyInfo);
382
+ }
383
+ return policies;
384
+ });
385
+ }
386
+ /**
387
+ * Gets the RCPs for an org unit.
388
+ * @param orgId The ID of the organization.
389
+ * @param orgUnitId The ID of the org unit.
390
+ * @returns The RCPs for the org unit.
391
+ */
392
+ async getRcpsForOrgUnit(orgId, orgUnitId) {
393
+ return this.getOrgPoliciesForOrgUnit(orgId, orgUnitId, 'rcps');
394
+ }
395
+ /**
396
+ * Gets the org ID for an account.
397
+ * @param accountId The ID of the account.
398
+ * @returns The org ID for the account, or undefined if not found.
399
+ */
400
+ async getOrgIdForAccount(accountId) {
401
+ const index = await this.getIndex('accounts-to-orgs', {});
402
+ const accountToOrgMap = index.data;
403
+ return accountToOrgMap[accountId];
404
+ }
405
+ async getIndex(indexName, defaultValue) {
406
+ const cacheKey = `index:${indexName}`;
407
+ return this.withCache(cacheKey, async () => {
408
+ return this.storageClient.getIndex(indexName, defaultValue);
409
+ });
410
+ }
411
+ /**
412
+ * Get the account ID for a given S3 bucket name.
413
+ *
414
+ * @param bucketName The name of the bucket.
415
+ * @returns The account ID for the bucket, or undefined if not found.
416
+ */
417
+ async getAccountIdForBucket(bucketName) {
418
+ const index = await this.getIndex('buckets-to-accounts', {});
419
+ const bucketToAccountMap = index.data;
420
+ return bucketToAccountMap[bucketName]?.accountId;
421
+ }
422
+ /**
423
+ * Check if ABAC is enabled for a specific S3 bucket
424
+ *
425
+ * @param accountId The account ID of the bucket
426
+ * @param bucketOrObjectArn The ARN of the bucket or object
427
+ * @returns true if ABAC is enabled for the bucket, false otherwise
428
+ */
429
+ async getAbacEnabledForBucket(accountId, bucketOrObjectArn) {
430
+ const bucketArn = bucketArnFromBucketOrObjectArn(bucketOrObjectArn);
431
+ return this.withCache(`abacEnabledForBucket:${bucketArn}`, async () => {
432
+ const bucketMetadata = await this.storageClient.getResourceMetadata(accountId, bucketArn, 'metadata', {});
433
+ return !!bucketMetadata.abacEnabled;
434
+ });
435
+ }
436
+ /**
437
+ * Check if S3 Block Public Access RestrictPublicBuckets is enabled for a specific S3 bucket.
438
+ * Bucket-level and account-level settings both apply, so the effective setting is enabled
439
+ * when either collected metadata source has RestrictPublicBuckets set to true.
440
+ *
441
+ * @param accountId The account ID of the bucket
442
+ * @param bucketOrObjectArn The ARN of the bucket or object
443
+ * @returns true if RestrictPublicBuckets is enabled at the bucket or account level
444
+ */
445
+ async getBlockPublicAccessEnabledForBucket(accountId, bucketOrObjectArn) {
446
+ const bucketArn = bucketArnFromBucketOrObjectArn(bucketOrObjectArn);
447
+ return this.withCache(`bpaEnabledForBucket:${accountId}:${bucketArn}`, async () => {
448
+ const [bucketBpa, accountBpa] = await Promise.all([
449
+ this.storageClient.getResourceMetadata(accountId, bucketArn, 'bpa', {}),
450
+ this.storageClient.getAccountMetadata(accountId, 's3-bpa', {})
451
+ ]);
452
+ return bucketBpa.RestrictPublicBuckets === true || accountBpa.RestrictPublicBuckets === true;
453
+ });
454
+ }
455
+ /**
456
+ * Gets the account ID for a given API Gateway ARN.
457
+ * @param apiArn The ARN of the API Gateway.
458
+ * @returns The account ID for the API Gateway, or undefined if not found.
459
+ */
460
+ async getAccountIdForRestApi(apiArn) {
461
+ const index = await this.getIndex('apigateways-to-accounts', {});
462
+ const gatewayToAccountMap = index.data;
463
+ return gatewayToAccountMap[apiArn];
464
+ }
465
+ /**
466
+ * Gets the managed policies attached to a user.
467
+ * @param userArn The ARN of the user.
468
+ * @returns The managed policies for the user.
469
+ */
470
+ async getManagedPoliciesForUser(userArn) {
471
+ const cacheKey = `userManagedPolicies:${userArn}`;
472
+ return this.withCache(cacheKey, async () => {
473
+ const accountId = (0, iam_utils_1.splitArnParts)(userArn).accountId;
474
+ const managedPolicies = await this.storageClient.getResourceMetadata(accountId, userArn, 'managed-policies', []);
475
+ const results = [];
476
+ for (const policyArn of managedPolicies) {
477
+ results.push(await this.getManagedPolicy(accountId, policyArn));
478
+ }
479
+ return results;
480
+ });
481
+ }
482
+ async getManagedPolicy(accountId, policyArn) {
483
+ const cacheKey = `managedPolicy:${accountId}:${policyArn}`;
484
+ return this.withCache(cacheKey, async () => {
485
+ const policyMetadata = await this.storageClient.getResourceMetadata(accountId, policyArn, 'metadata');
486
+ const policyDocument = await this.storageClient.getResourceMetadata(accountId, policyArn, 'current-policy');
487
+ if (!policyDocument) {
488
+ log_1.log.warn(`Policy document not found for ${policyArn} in account ${accountId}`);
489
+ }
490
+ return {
491
+ arn: policyMetadata.arn,
492
+ name: policyMetadata.name,
493
+ policy: (0, iam_policy_1.createValidatedPolicy)(policyDocument, iam_policy_1.validateIdentityPolicy, {
494
+ name: policyArn
495
+ })
496
+ };
497
+ });
498
+ }
499
+ /**
500
+ * Gets the inline policies attached to a user.
501
+ * @param userArn The ARN of the user.
502
+ * @returns The inline policies for the user.
503
+ */
504
+ async getInlinePoliciesForUser(userArn) {
505
+ const cacheKey = `userInlinePolicies:${userArn}`;
506
+ return this.withCache(cacheKey, async () => {
507
+ const accountId = (0, iam_utils_1.splitArnParts)(userArn).accountId;
508
+ const inlinePolicies = await this.storageClient.getResourceMetadata(accountId, userArn, 'inline-policies', []);
509
+ return inlinePolicies.map((p) => ({
510
+ name: p.PolicyName,
511
+ policy: (0, iam_policy_1.createValidatedPolicy)(p.PolicyDocument, iam_policy_1.validateIdentityPolicy, {
512
+ name: `${userArn}#${p.PolicyName}`
513
+ })
514
+ }));
515
+ });
516
+ }
517
+ /**
518
+ * Gets metadata for an IAM user.
519
+ *
520
+ * @param userArn the ARN of the user.
521
+ * @returns the metadata for the user, or undefined if not found.
522
+ */
523
+ async getIamUserMetadata(userArn) {
524
+ const cacheKey = `iamUserMetadata:${userArn}`;
525
+ return this.withCache(cacheKey, async () => {
526
+ const accountId = (0, iam_utils_1.splitArnParts)(userArn).accountId;
527
+ // The permissions boundary is stored as a policy ARN on the user resource metadata
528
+ return this.storageClient.getResourceMetadata(accountId, userArn, 'metadata');
529
+ });
530
+ }
531
+ /**
532
+ * Gets the permissions boundary policy attached to a user, if any.
533
+ *
534
+ * @param userArn The ARN of the user.
535
+ * @returns The permissions boundary policy as an OrgPolicy, or undefined if none is set.
536
+ */
537
+ async getPermissionsBoundaryForUser(userArn) {
538
+ const cacheKey = `userPermissionBoundary:${userArn}`;
539
+ return this.withCache(cacheKey, async () => {
540
+ const accountId = (0, iam_utils_1.splitArnParts)(userArn).accountId;
541
+ // The permissions boundary is stored as a policy ARN on the user resource metadata
542
+ const userMetadata = await this.getIamUserMetadata(userArn);
543
+ if (!userMetadata) {
544
+ return undefined;
545
+ }
546
+ const permissionsBoundaryArn = userMetadata.permissionBoundary;
547
+ if (!permissionsBoundaryArn) {
548
+ return undefined;
549
+ }
550
+ return this.getManagedPolicy(accountId, permissionsBoundaryArn);
551
+ });
552
+ }
553
+ /**
554
+ * Gets the group ARNs that the user is a member of.
555
+ * @param userArn The ARN of the user.
556
+ * @returns An array of group ARNs the user belongs to.
557
+ */
558
+ async getGroupsForUser(userArn) {
559
+ const cacheKey = `groupsForUser:${userArn}`;
560
+ return this.withCache(cacheKey, async () => {
561
+ const accountId = (0, iam_utils_1.splitArnParts)(userArn).accountId;
562
+ const groups = await this.storageClient.getResourceMetadata(accountId, userArn, 'groups', []);
563
+ return groups;
564
+ });
565
+ }
566
+ /**
567
+ * Gets the managed policies attached to a group.
568
+ *
569
+ * @param groupArn The ARN of the group.
570
+ * @returns The managed policies for the group.
571
+ */
572
+ async getManagedPoliciesForGroup(groupArn) {
573
+ const cacheKey = `groupManagedPolicies:${groupArn}`;
574
+ return this.withCache(cacheKey, async () => {
575
+ const accountId = (0, iam_utils_1.splitArnParts)(groupArn).accountId;
576
+ const managedPolicies = await this.storageClient.getResourceMetadata(accountId, groupArn, 'managed-policies', []);
577
+ const results = [];
578
+ for (const policyArn of managedPolicies) {
579
+ results.push(await this.getManagedPolicy(accountId, policyArn));
580
+ }
581
+ return results;
582
+ });
583
+ }
584
+ /**
585
+ * Get the inline policies attached to a group.
586
+ *
587
+ * @param groupArn the ARN of the group.
588
+ * @returns the inline policies for the group.
589
+ */
590
+ async getInlinePoliciesForGroup(groupArn) {
591
+ const cacheKey = `groupInlinePolicies:${groupArn}`;
592
+ return this.withCache(cacheKey, async () => {
593
+ const accountId = (0, iam_utils_1.splitArnParts)(groupArn).accountId;
594
+ const inlinePolicies = await this.storageClient.getResourceMetadata(accountId, groupArn, 'inline-policies', []);
595
+ return inlinePolicies.map((p) => ({
596
+ name: p.PolicyName,
597
+ policy: (0, iam_policy_1.createValidatedPolicy)(p.PolicyDocument, iam_policy_1.validateIdentityPolicy, {
598
+ name: `${groupArn}#${p.PolicyName}`
599
+ })
600
+ }));
601
+ });
602
+ }
603
+ /**
604
+ * Gets the managed policies attached to a role.
605
+ * @param roleArn the ARN of the role.
606
+ * @returns the managed policies attached to the role.
607
+ */
608
+ async getManagedPoliciesForRole(roleArn) {
609
+ const cacheKey = `managedPoliciesForRole:${roleArn}`;
610
+ return this.withCache(cacheKey, async () => {
611
+ const accountId = (0, iam_utils_1.splitArnParts)(roleArn).accountId;
612
+ const managedPolicies = await this.storageClient.getResourceMetadata(accountId, roleArn, 'managed-policies', []);
613
+ const results = [];
614
+ for (const policyArn of managedPolicies) {
615
+ results.push(await this.getManagedPolicy(accountId, policyArn));
616
+ }
617
+ return results;
618
+ });
619
+ }
620
+ /**
621
+ * Get the inline policies attached to a role.
622
+ *
623
+ * @param roleArn the ARN of the role.
624
+ * @returns the inline policies for the role.
625
+ */
626
+ async getInlinePoliciesForRole(roleArn) {
627
+ const cacheKey = `inlinePoliciesForRole:${roleArn}`;
628
+ return this.withCache(cacheKey, async () => {
629
+ const accountId = (0, iam_utils_1.splitArnParts)(roleArn).accountId;
630
+ const inlinePolicies = await this.storageClient.getResourceMetadata(accountId, roleArn, 'inline-policies', []);
631
+ return inlinePolicies.map((p) => ({
632
+ name: p.PolicyName,
633
+ policy: (0, iam_policy_1.createValidatedPolicy)(p.PolicyDocument, iam_policy_1.validateIdentityPolicy, {
634
+ name: `${roleArn}#${p.PolicyName}`
635
+ })
636
+ }));
637
+ });
638
+ }
639
+ /**
640
+ * Get the permissions boundary policy attached to a role, if any.
641
+ * @param roleArn the ARN of the role.
642
+ * @returns the permissions boundary policy as a ManagedPolicy, or undefined if none is set.
643
+ */
644
+ async getPermissionsBoundaryForRole(roleArn) {
645
+ const cacheKey = `permissionBoundaryForRole:${roleArn}`;
646
+ return this.withCache(cacheKey, async () => {
647
+ const accountId = (0, iam_utils_1.splitArnParts)(roleArn).accountId;
648
+ // The permissions boundary is stored as a policy ARN on the user resource metadata
649
+ const roleMetadata = await this.getIamUserMetadata(roleArn);
650
+ if (!roleMetadata) {
651
+ return undefined;
652
+ }
653
+ const permissionsBoundaryArn = roleMetadata.permissionBoundary;
654
+ if (!permissionsBoundaryArn) {
655
+ return undefined;
656
+ }
657
+ return this.getManagedPolicy(accountId, permissionsBoundaryArn);
658
+ });
659
+ }
660
+ /**
661
+ * Get the metadata for an organization.
662
+ *
663
+ * @param organizationId the id of the organization
664
+ * @returns the metadata for the organization
665
+ */
666
+ async getOrganizationMetadata(organizationId) {
667
+ const cacheKey = `organizationMetadata:${organizationId}`;
668
+ return this.withCache(cacheKey, async () => {
669
+ return this.storageClient.getOrganizationMetadata(organizationId, 'metadata');
670
+ });
671
+ }
672
+ /**
673
+ * Gets the resource policy for a given resource ARN and account.
674
+ *
675
+ * @param resourceArn The ARN of the resource.
676
+ * @param accountId The ID of the account.
677
+ * @returns The resource policy, or undefined if not found.
678
+ */
679
+ async getResourcePolicyForArn(resourceArn, accountId) {
680
+ const arnParts = (0, iam_utils_1.splitArnParts)(resourceArn);
681
+ if (arnParts.service === 's3' && arnParts.region === '' && arnParts.accountId === '') {
682
+ resourceArn = resourceArn.split('/')[0];
683
+ }
684
+ const cacheKey = `resourcePolicy:${accountId}:${resourceArn}`;
685
+ return this.withCache(cacheKey, async () => {
686
+ const isTrustPolicy = arnParts.service === 'iam' && arnParts.resourceType === 'role';
687
+ const metadataKey = isTrustPolicy ? 'trust-policy' : 'policy';
688
+ const validateFn = isTrustPolicy ? iam_policy_1.validateTrustPolicy : iam_policy_1.validateResourcePolicy;
689
+ const rawPolicy = await this.storageClient.getResourceMetadata(accountId, resourceArn, metadataKey);
690
+ if (!rawPolicy)
691
+ return undefined;
692
+ return (0, iam_policy_1.createValidatedPolicy)(rawPolicy, validateFn, { name: resourceArn });
693
+ });
694
+ }
695
+ /**
696
+ * Gets the RAM share policy for a given resource ARN and account.
697
+ *
698
+ * @param resourceArn The ARN of the resource.
699
+ * @param accountId The ID of the account.
700
+ * @returns The RAM share policy, or undefined if not found.
701
+ */
702
+ async getRamSharePolicyForArn(resourceArn, accountId) {
703
+ const cacheKey = `ramSharePolicy:${accountId}:${resourceArn}`;
704
+ return this.withCache(cacheKey, async () => {
705
+ const armSharePolicy = await this.storageClient.getRamResource(accountId, resourceArn);
706
+ if (!armSharePolicy?.policy)
707
+ return undefined;
708
+ return (0, iam_policy_1.createValidatedPolicy)(armSharePolicy.policy, iam_policy_1.validateResourcePolicy, {
709
+ name: resourceArn
710
+ });
711
+ });
712
+ }
713
+ /**
714
+ * Gets the tags for a given resource ARN and account.
715
+ *
716
+ * @param resourceArn The ARN of the resource.
717
+ * @param accountId The ID of the account.
718
+ * @returns an object to indicate if the resource is present and its tags (if any)
719
+ */
720
+ async getTagsForResource(resourceArn, accountId) {
721
+ const cacheKey = `tagsForResource:${accountId}:${resourceArn}`;
722
+ return this.withCache(cacheKey, async () => {
723
+ const presentPromise = this.storageClient.getResourceMetadata(accountId, resourceArn, 'metadata');
724
+ const tagsPromise = this.storageClient.getResourceMetadata(accountId, resourceArn, 'tags');
725
+ const [present, tags] = await Promise.all([presentPromise, tagsPromise]);
726
+ return { present: !!present, tags: tags || {} };
727
+ });
728
+ }
729
+ /**
730
+ * Gets a unique ID for an IAM resource based on its ARN and account ID.
731
+ * Used specifically for IAM Users and Roles
732
+ *
733
+ * @param resourceArn the ARN of the IAM resource
734
+ * @param accountId the ID of the account the resource belongs to
735
+ * @returns a unique ID for the resource, or undefined if not found
736
+ */
737
+ async getUniqueIdForIamResource(resourceArn) {
738
+ const cacheKey = `uniqueIdForIamResource:${resourceArn}`;
739
+ return this.withCache(cacheKey, async () => {
740
+ const accountId = (0, iam_utils_1.splitArnParts)(resourceArn).accountId;
741
+ const resourceMetadata = await this.storageClient.getResourceMetadata(accountId, resourceArn, 'metadata');
742
+ return resourceMetadata?.id;
743
+ });
744
+ }
745
+ /**
746
+ * Get the account IDs for an organization.
747
+ *
748
+ * @param organizationId the ID of the organization
749
+ * @returns a tuple containing a boolean indicating success and an array of account IDs
750
+ */
751
+ async getAccountsForOrganization(organizationId) {
752
+ const organizationAccounts = await this.getAccountDataForOrg(organizationId);
753
+ if (!organizationAccounts) {
754
+ return [false, []];
755
+ }
756
+ const accountIds = Object.keys(organizationAccounts);
757
+ return [true, accountIds];
758
+ }
759
+ /**
760
+ * Get the organization structure or an organization.
761
+ *
762
+ * @param orgId the ID of the organization
763
+ * @returns returns the organization structure or undefined if not found
764
+ */
765
+ async getOrganizationStructure(orgId) {
766
+ const cacheKey = `organizationStructure:${orgId}`;
767
+ return this.withCache(cacheKey, async () => {
768
+ return this.storageClient.getOrganizationMetadata(orgId, 'structure');
769
+ });
770
+ }
771
+ /**
772
+ * Get the accounts for a given organization path, includes
773
+ * accounts directly under the OU and in child OUs.
774
+ *
775
+ * @param orgId the ID of the organization
776
+ * @param ouIds the ids of the organizational units in the path
777
+ * @returns a tuple containing a boolean indicating success and an array of account IDs
778
+ */
779
+ async getAccountsForOrgPath(orgId, ouIds) {
780
+ const cacheKey = `accountsForOrgPath:${orgId}:${ouIds.join('/')}`;
781
+ return this.withCache(cacheKey, async () => {
782
+ const orgUnits = await this.getOrganizationStructure(orgId);
783
+ if (!orgUnits || ouIds.length === 0) {
784
+ return [false, []];
785
+ }
786
+ const rootOu = orgUnits[ouIds[0]];
787
+ // Now look through the structure to find the OU
788
+ let currentStructure = rootOu;
789
+ for (const ou of ouIds.slice(1)) {
790
+ currentStructure = currentStructure.children?.[ou];
791
+ if (!currentStructure) {
792
+ return [false, []]; // OU not found in the structure
793
+ }
794
+ }
795
+ const getAccountId = (a) => a.split('/').at(-1);
796
+ const accounts = [];
797
+ if (currentStructure.accounts) {
798
+ accounts.push(...currentStructure.accounts?.map(getAccountId));
799
+ }
800
+ const children = Object.values(currentStructure.children || {});
801
+ // Traverse the children to collect all accounts
802
+ while (children.length > 0) {
803
+ const child = children.shift();
804
+ if (child?.accounts) {
805
+ accounts.push(...child.accounts.map(getAccountId));
806
+ }
807
+ if (child?.children) {
808
+ children.push(...Object.values(child.children));
809
+ }
810
+ }
811
+ return [true, accounts];
812
+ });
813
+ }
814
+ /**
815
+ * Get all the principals (users and roles) in a given account.
816
+ *
817
+ * @param accountId the ID of the account
818
+ * @returns a list of all principal ARNs in the account
819
+ */
820
+ async getAllPrincipalsInAccount(accountId) {
821
+ const cacheKey = `allPrincipalsInAccount:${accountId}`;
822
+ return this.withCache(cacheKey, async () => {
823
+ const iamUsers = await this.storageClient.findResourceMetadata(accountId, {
824
+ service: 'iam',
825
+ resourceType: 'user',
826
+ account: accountId
827
+ });
828
+ const iamRoles = await this.storageClient.findResourceMetadata(accountId, {
829
+ service: 'iam',
830
+ resourceType: 'role',
831
+ account: accountId
832
+ });
833
+ return [...iamUsers.map((user) => user.arn), ...iamRoles.map((role) => role.arn)];
834
+ });
835
+ }
836
+ /**
837
+ * Get the VPC endpoint policy for a given VPC endpoint ARN.
838
+ *
839
+ * @param vpcEndpointArn the ARN of the VPC endpoint
840
+ * @returns the VPC endpoint policy, or undefined if not found
841
+ */
842
+ async getVpcEndpointPolicyForArn(vpcEndpointArn) {
843
+ const cacheKey = `vpcEndpointPolicy:${vpcEndpointArn}`;
844
+ return this.withCache(cacheKey, async () => {
845
+ const accountId = (0, iam_utils_1.splitArnParts)(vpcEndpointArn).accountId;
846
+ const rawPolicy = await this.storageClient.getResourceMetadata(accountId, vpcEndpointArn, 'endpoint-policy');
847
+ if (!rawPolicy)
848
+ return undefined;
849
+ return (0, iam_policy_1.createValidatedPolicy)(rawPolicy, iam_policy_1.validateEndpointPolicy, { name: vpcEndpointArn });
850
+ });
851
+ }
852
+ /**
853
+ * Get the ARN of a VPC endpoint given its ID.
854
+ * @param vpcEndpointId the ID of the VPC endpoint
855
+ * @returns the ARN of the VPC endpoint, or undefined if not found
856
+ */
857
+ async getVpcEndpointArnForVpcEndpointId(vpcEndpointId) {
858
+ const index = await this.getIndex('vpcs', {
859
+ endpoints: {},
860
+ vpcs: {}
861
+ });
862
+ return index.data.endpoints[vpcEndpointId]?.arn;
863
+ }
864
+ /**
865
+ * Gets the VPC endpoint ID for a given VPC ID and service name.
866
+ *
867
+ * @param vpcIdOrArn the ID or ARN of the VPC
868
+ * @param service the service name of the VPC endpoint (e.g., s3, ec2, etc.)
869
+ * @returns the VPC endpoint ID, or undefined if not found
870
+ */
871
+ async getVpcEndpointIdForVpcService(vpcIdOrArn, service) {
872
+ const index = await this.getIndex('vpcs', {
873
+ endpoints: {},
874
+ vpcs: {}
875
+ });
876
+ if (vpcIdOrArn.startsWith('arn:')) {
877
+ const arnParts = (0, iam_utils_1.splitArnParts)(vpcIdOrArn);
878
+ vpcIdOrArn = arnParts.resourcePath;
879
+ }
880
+ const vpc = index.data.vpcs[vpcIdOrArn];
881
+ if (!vpc) {
882
+ return undefined;
883
+ }
884
+ const endpoint = vpc.endpoints.find((ep) => ep.service === service);
885
+ return endpoint?.id;
886
+ }
887
+ /**
888
+ * Lookup the VPC ID for a given VPC endpoint ID.
889
+ *
890
+ * @param vpcEndpointId the ID of the VPC endpoint
891
+ * @returns the VPC ID, or undefined if not found
892
+ */
893
+ async getVpcIdForVpcEndpointId(vpcEndpointId) {
894
+ const index = await this.getIndex('vpcs', {
895
+ endpoints: {},
896
+ vpcs: {}
897
+ });
898
+ return index.data.endpoints[vpcEndpointId]?.vpc;
899
+ }
900
+ /**
901
+ * Lookup the VPC ARN for a given VPC endpoint ID.
902
+ *
903
+ * @param vpcEndpointId the ID of the VPC endpoint
904
+ * @returns the VPC ARN, or undefined if not found
905
+ */
906
+ async getVpcArnForVpcEndpointId(vpcEndpointId) {
907
+ const vpcId = await this.getVpcIdForVpcEndpointId(vpcEndpointId);
908
+ if (!vpcId) {
909
+ return undefined;
910
+ }
911
+ const index = await this.getIndex('vpcs', {
912
+ endpoints: {},
913
+ vpcs: {}
914
+ });
915
+ return index.data.vpcs[vpcId]?.arn;
916
+ }
917
+ /**
918
+ * Lookup the account ID for a given VPC endpoint ID.
919
+ *
920
+ * @param vpcEndpointId the ID of the VPC endpoint
921
+ * @returns the account ID, or undefined if not found
922
+ */
923
+ async getAccountIdForVpcEndpointId(vpcEndpointId) {
924
+ const index = await this.getIndex('vpcs', {
925
+ endpoints: {},
926
+ vpcs: {}
927
+ });
928
+ const vpcArn = index.data.endpoints[vpcEndpointId]?.arn;
929
+ if (!vpcArn) {
930
+ return undefined;
931
+ }
932
+ return (0, iam_utils_1.splitArnParts)(vpcArn).accountId;
933
+ }
934
+ /**
935
+ * Get the organization ID for a given VPC endpoint ID.
936
+ *
937
+ * @param vpcEndpointId the ID of the VPC endpoint
938
+ * @returns the organization ID, or undefined if not found
939
+ */
940
+ async getOrgIdForVpcEndpointId(vpcEndpointId) {
941
+ const accountId = await this.getAccountIdForVpcEndpointId(vpcEndpointId);
942
+ if (!accountId) {
943
+ return undefined;
944
+ }
945
+ return this.getOrgIdForAccount(accountId);
946
+ }
947
+ /**
948
+ * Get the organization unit hierarchy for a given VPC endpoint ID.
949
+ *
950
+ * @param vpcEndpointId the ID of the VPC endpoint
951
+ * @returns the organization unit hierarchy, or undefined if not found
952
+ */
953
+ async getOrgUnitHierarchyForVpcEndpointId(vpcEndpointId) {
954
+ const accountId = await this.getAccountIdForVpcEndpointId(vpcEndpointId);
955
+ if (!accountId) {
956
+ return undefined;
957
+ }
958
+ const hierarchy = await this.getOrgUnitHierarchyForAccount(accountId);
959
+ if (hierarchy.length === 0) {
960
+ return undefined;
961
+ }
962
+ return hierarchy;
963
+ }
964
+ /**
965
+ * Get all the policies for a principal that should be used to populate the cache
966
+ *
967
+ * @param collectClient The IAM collect client to use for data access
968
+ * @param accountId The ID of the account
969
+ * @param principalArn The ARN of the principal
970
+ * @returns An array of policies for the principal
971
+ */
972
+ async getAllowPoliciesForPrincipal(principalArn) {
973
+ const arnParts = (0, iam_utils_1.splitArnParts)(principalArn);
974
+ const policies = [];
975
+ if (arnParts.resourceType === 'user') {
976
+ const managedPolicies = await this.getManagedPoliciesForUser(principalArn);
977
+ managedPolicies.forEach((mp) => policies.push((0, iam_policy_1.loadPolicy)(mp.policy)));
978
+ const inlinePolicies = await this.getInlinePoliciesForUser(principalArn);
979
+ inlinePolicies.forEach((ip) => policies.push((0, iam_policy_1.loadPolicy)(ip.policy)));
980
+ const groups = await this.getGroupsForUser(principalArn);
981
+ for (const group of groups) {
982
+ const groupManagedPolicies = await this.getManagedPoliciesForGroup(group);
983
+ const groupInlinePolicies = await this.getInlinePoliciesForGroup(group);
984
+ groupManagedPolicies.forEach((mp) => policies.push((0, iam_policy_1.loadPolicy)(mp.policy)));
985
+ groupInlinePolicies.forEach((ip) => policies.push((0, iam_policy_1.loadPolicy)(ip.policy)));
986
+ }
987
+ }
988
+ else if (arnParts.resourceType === 'role') {
989
+ const managedPolicies = await this.getManagedPoliciesForRole(principalArn);
990
+ managedPolicies.forEach((mp) => policies.push((0, iam_policy_1.loadPolicy)(mp.policy)));
991
+ const inlinePolicies = await this.getInlinePoliciesForRole(principalArn);
992
+ inlinePolicies.forEach((ip) => policies.push((0, iam_policy_1.loadPolicy)(ip.policy)));
993
+ }
994
+ return policies;
995
+ }
996
+ async savePrincipalIndex(type, principalIndex) {
997
+ const indexName = `principal-index-${type}`;
998
+ const currentData = await this.storageClient.getIndex(indexName, {});
999
+ const currentLockId = currentData.lockId;
1000
+ // Stringify and compress the data, then convert to base64 string before saving
1001
+ const jsonString = JSON.stringify(principalIndex);
1002
+ const compressedBuffer = (0, zlib_1.gzipSync)(Buffer.from(jsonString, 'utf8'));
1003
+ const base64String = compressedBuffer.toString('base64');
1004
+ await this.storageClient.saveIndex(indexName, base64String, currentLockId);
1005
+ }
1006
+ async getPrincipalIndex(type) {
1007
+ const key = `principal-index-${type}`;
1008
+ return this.withCache(key, async () => {
1009
+ const rawIndex = await this.storageClient.getIndex(key, undefined);
1010
+ if (!rawIndex.data) {
1011
+ return undefined;
1012
+ }
1013
+ try {
1014
+ // Convert base64 string back to buffer, then decompress and parse
1015
+ const compressedBuffer = Buffer.from(rawIndex.data, 'base64');
1016
+ const decompressedData = (0, zlib_1.gunzipSync)(compressedBuffer);
1017
+ const jsonString = decompressedData.toString('utf8');
1018
+ return JSON.parse(jsonString);
1019
+ }
1020
+ catch (error) {
1021
+ log_1.log.error('Failed to decompress or parse principal index', { error });
1022
+ return undefined;
1023
+ }
1024
+ });
1025
+ }
1026
+ async principalIndexExists() {
1027
+ const index = await this.getPrincipalIndex('principals');
1028
+ return !!index;
1029
+ }
1030
+ /**
1031
+ * Get the principals that may have permission to perform a specific action.
1032
+ *
1033
+ * If the data is available it will return a subset of principals that may
1034
+ * have permission to perform the action. If the data is not available, it
1035
+ * will return undefined.
1036
+ *
1037
+ * @param allFromAccount The account ID from which to include all principals in the result, regardless of the action filter. When `undefined`, no account receives this treatment — only principals matching the action filter are returned.
1038
+ * @param accountIds The list of account IDs to check for principals that may have permission to perform the specified action. Only principals from these accounts that may have the action allowed will be included.
1039
+ * @param action The action to check.
1040
+ * @returns A list of principals that may have permission to perform the action, or undefined if the data is not available.
1041
+ */
1042
+ async getPrincipalsWithActionAllowed(allFromAccount, accountIds, action) {
1043
+ const principals = (await this.getPrincipalIndex('principals'));
1044
+ if (!principals) {
1045
+ return undefined;
1046
+ }
1047
+ const principalBitSets = [];
1048
+ const wildcardIndex = (await this.getPrincipalIndex('actions-wildcard'));
1049
+ const [service, serviceAction] = action.toLowerCase().split(':');
1050
+ //Global wildcards match
1051
+ if (wildcardIndex?.['*']) {
1052
+ principalBitSets.push(wildcardIndex['*']);
1053
+ }
1054
+ const serviceIndex = (await this.getPrincipalIndex(`actions-${service}`));
1055
+ // Look through service actions
1056
+ if (serviceIndex) {
1057
+ for (const [actionPattern, bitset] of Object.entries(serviceIndex)) {
1058
+ if ((0, iam_expand_1.actionMatchesPattern)(serviceAction, actionPattern)) {
1059
+ principalBitSets.push(bitset);
1060
+ }
1061
+ }
1062
+ }
1063
+ const notActionIndex = (await this.getPrincipalIndex(`not-actions`));
1064
+ if (notActionIndex) {
1065
+ for (const [notActionService, notActions] of Object.entries(notActionIndex)) {
1066
+ if (notActionService === service) {
1067
+ for (const [notActionPattern, bitset] of Object.entries(notActions)) {
1068
+ if (!(0, iam_expand_1.actionMatchesPattern)(serviceAction, notActionPattern)) {
1069
+ principalBitSets.push(bitset);
1070
+ }
1071
+ }
1072
+ }
1073
+ else {
1074
+ for (const bitset of Object.values(notActions)) {
1075
+ principalBitSets.push(bitset);
1076
+ }
1077
+ }
1078
+ }
1079
+ }
1080
+ const actionBitset = principalBitSets.reduce((acc, bs) => acc.or((0, bitset_js_1.decodeBitSet)(bs)), new bitset_1.default());
1081
+ const accountsIndex = (await this.getPrincipalIndex('accounts'));
1082
+ if (!accountsIndex) {
1083
+ throw new Error('Accounts index not found in principal index');
1084
+ }
1085
+ const accountBitset = accountIds.reduce((acc, accountId) => {
1086
+ const bs = accountsIndex[accountId];
1087
+ if (bs) {
1088
+ return acc.or((0, bitset_js_1.decodeBitSet)(bs));
1089
+ }
1090
+ return acc;
1091
+ }, new bitset_1.default());
1092
+ let finalBitset = accountBitset.and(actionBitset);
1093
+ if (allFromAccount && accountsIndex[allFromAccount]) {
1094
+ finalBitset = finalBitset.or((0, bitset_js_1.decodeBitSet)(accountsIndex[allFromAccount]));
1095
+ }
1096
+ return finalBitset
1097
+ .toArray()
1098
+ .map((i) => (0, bitset_js_1.decompressPrincipalString)(principals.principals[i], principals.prefix));
1099
+ }
1100
+ async listResources(accountId, service, resourceType, region) {
1101
+ if (service === 's3' && resourceType === 'bucket') {
1102
+ const resources = await this.storageClient.findResourceMetadata(accountId, {
1103
+ account: accountId,
1104
+ service,
1105
+ region
1106
+ });
1107
+ return resources.map((r) => r.arn);
1108
+ }
1109
+ const resources = await this.storageClient.findResourceMetadata(accountId, {
1110
+ account: accountId,
1111
+ service,
1112
+ resourceType,
1113
+ region
1114
+ });
1115
+ return resources.map((r) => r.arn);
1116
+ }
1117
+ }
1118
+ exports.IamCollectClient = IamCollectClient;
1119
+ //# sourceMappingURL=client.js.map