@metamask/snaps-execution-environments 1.0.1 → 2.0.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 (234) hide show
  1. package/CHANGELOG.md +37 -273
  2. package/dist/browserify/iframe/bundle.js +6 -4
  3. package/dist/browserify/iframe/index.html +2 -0
  4. package/dist/browserify/node-process/bundle.js +8 -2
  5. package/dist/browserify/node-thread/bundle.js +8 -2
  6. package/dist/browserify/offscreen/bundle.js +6 -9
  7. package/dist/browserify/offscreen/index.html +2 -0
  8. package/dist/browserify/worker-executor/bundle.js +12157 -0
  9. package/dist/browserify/worker-pool/bundle.js +7 -0
  10. package/dist/browserify/worker-pool/index.html +12152 -0
  11. package/dist/cjs/common/BaseSnapExecutor.js +423 -0
  12. package/dist/cjs/common/BaseSnapExecutor.js.map +1 -0
  13. package/dist/cjs/common/commands.js +81 -0
  14. package/dist/cjs/common/commands.js.map +1 -0
  15. package/dist/cjs/common/endowments/commonEndowmentFactory.js +147 -0
  16. package/dist/cjs/common/endowments/commonEndowmentFactory.js.map +1 -0
  17. package/dist/cjs/common/endowments/console.js +134 -0
  18. package/dist/cjs/common/endowments/console.js.map +1 -0
  19. package/dist/cjs/common/endowments/crypto.js +44 -0
  20. package/dist/cjs/common/endowments/crypto.js.map +1 -0
  21. package/dist/cjs/common/endowments/date.js +53 -0
  22. package/dist/cjs/common/endowments/date.js.map +1 -0
  23. package/dist/cjs/common/endowments/index.js +91 -0
  24. package/dist/cjs/common/endowments/index.js.map +1 -0
  25. package/dist/cjs/common/endowments/interval.js +61 -0
  26. package/dist/cjs/common/endowments/interval.js.map +1 -0
  27. package/dist/cjs/common/endowments/math.js +67 -0
  28. package/dist/cjs/common/endowments/math.js.map +1 -0
  29. package/dist/cjs/common/endowments/network.js +216 -0
  30. package/dist/cjs/common/endowments/network.js.map +1 -0
  31. package/dist/cjs/common/endowments/textDecoder.js +28 -0
  32. package/dist/cjs/common/endowments/textDecoder.js.map +1 -0
  33. package/dist/cjs/common/endowments/textEncoder.js +28 -0
  34. package/dist/cjs/common/endowments/textEncoder.js.map +1 -0
  35. package/dist/cjs/common/endowments/timeout.js +63 -0
  36. package/dist/cjs/common/endowments/timeout.js.map +1 -0
  37. package/dist/cjs/common/globalEvents.js +39 -0
  38. package/dist/cjs/common/globalEvents.js.map +1 -0
  39. package/dist/cjs/common/globalObject.js +53 -0
  40. package/dist/{common → cjs/common}/globalObject.js.map +1 -1
  41. package/dist/cjs/common/lockdown/lockdown-events.js +74 -0
  42. package/dist/cjs/common/lockdown/lockdown-events.js.map +1 -0
  43. package/dist/cjs/common/lockdown/lockdown-more.js +73 -0
  44. package/dist/cjs/common/lockdown/lockdown-more.js.map +1 -0
  45. package/dist/cjs/common/lockdown/lockdown.js +30 -0
  46. package/dist/cjs/common/lockdown/lockdown.js.map +1 -0
  47. package/dist/cjs/common/sortParams.js +26 -0
  48. package/dist/cjs/common/sortParams.js.map +1 -0
  49. package/dist/cjs/common/utils.js +132 -0
  50. package/dist/cjs/common/utils.js.map +1 -0
  51. package/dist/cjs/common/validation.js +118 -0
  52. package/dist/cjs/common/validation.js.map +1 -0
  53. package/dist/cjs/iframe/IFrameSnapExecutor.js +50 -0
  54. package/dist/cjs/iframe/IFrameSnapExecutor.js.map +1 -0
  55. package/dist/cjs/iframe/index.js +13 -0
  56. package/dist/cjs/iframe/index.js.map +1 -0
  57. package/dist/cjs/logging.js +15 -0
  58. package/dist/cjs/logging.js.map +1 -0
  59. package/dist/cjs/node-process/ChildProcessSnapExecutor.js +39 -0
  60. package/dist/cjs/node-process/ChildProcessSnapExecutor.js.map +1 -0
  61. package/dist/cjs/node-process/index.js +11 -0
  62. package/dist/cjs/node-process/index.js.map +1 -0
  63. package/dist/cjs/node-thread/ThreadSnapExecutor.js +39 -0
  64. package/dist/cjs/node-thread/ThreadSnapExecutor.js.map +1 -0
  65. package/dist/cjs/node-thread/index.js +11 -0
  66. package/dist/cjs/node-thread/index.js.map +1 -0
  67. package/dist/cjs/offscreen/OffscreenSnapExecutor.js +173 -0
  68. package/dist/cjs/offscreen/OffscreenSnapExecutor.js.map +1 -0
  69. package/dist/cjs/offscreen/index.js +19 -0
  70. package/dist/cjs/offscreen/index.js.map +1 -0
  71. package/dist/cjs/webworker/executor/WebWorkerSnapExecutor.js +45 -0
  72. package/dist/cjs/webworker/executor/WebWorkerSnapExecutor.js.map +1 -0
  73. package/dist/cjs/webworker/executor/index.js +13 -0
  74. package/dist/cjs/webworker/executor/index.js.map +1 -0
  75. package/dist/cjs/webworker/pool/WebWorkerPool.js +248 -0
  76. package/dist/cjs/webworker/pool/WebWorkerPool.js.map +1 -0
  77. package/dist/cjs/webworker/pool/index.js +13 -0
  78. package/dist/cjs/webworker/pool/index.js.map +1 -0
  79. package/dist/esm/common/BaseSnapExecutor.js +408 -0
  80. package/dist/esm/common/BaseSnapExecutor.js.map +1 -0
  81. package/dist/esm/common/commands.js +80 -0
  82. package/dist/esm/common/commands.js.map +1 -0
  83. package/dist/esm/common/endowments/commonEndowmentFactory.js +132 -0
  84. package/dist/esm/common/endowments/commonEndowmentFactory.js.map +1 -0
  85. package/dist/esm/common/endowments/console.js +116 -0
  86. package/dist/esm/common/endowments/console.js.map +1 -0
  87. package/dist/esm/common/endowments/crypto.js +26 -0
  88. package/dist/esm/common/endowments/crypto.js.map +1 -0
  89. package/dist/{common → esm/common}/endowments/date.js +20 -16
  90. package/dist/esm/common/endowments/date.js.map +1 -0
  91. package/dist/{common → esm/common}/endowments/index.js +34 -36
  92. package/dist/esm/common/endowments/index.js.map +1 -0
  93. package/dist/{common → esm/common}/endowments/interval.js +13 -12
  94. package/dist/esm/common/endowments/interval.js.map +1 -0
  95. package/dist/{common → esm/common}/endowments/math.js +21 -15
  96. package/dist/esm/common/endowments/math.js.map +1 -0
  97. package/dist/esm/common/endowments/network.js +206 -0
  98. package/dist/esm/common/endowments/network.js.map +1 -0
  99. package/dist/esm/common/endowments/textDecoder.js +18 -0
  100. package/dist/esm/common/endowments/textDecoder.js.map +1 -0
  101. package/dist/esm/common/endowments/textEncoder.js +18 -0
  102. package/dist/esm/common/endowments/textEncoder.js.map +1 -0
  103. package/dist/{common → esm/common}/endowments/timeout.js +14 -13
  104. package/dist/esm/common/endowments/timeout.js.map +1 -0
  105. package/dist/esm/common/globalEvents.js +35 -0
  106. package/dist/esm/common/globalEvents.js.map +1 -0
  107. package/dist/esm/common/globalObject.js +36 -0
  108. package/dist/esm/common/globalObject.js.map +1 -0
  109. package/dist/esm/common/lockdown/lockdown-events.js +66 -0
  110. package/dist/esm/common/lockdown/lockdown-events.js.map +1 -0
  111. package/dist/{common → esm/common}/lockdown/lockdown-more.js +15 -22
  112. package/dist/esm/common/lockdown/lockdown-more.js.map +1 -0
  113. package/dist/{common → esm/common}/lockdown/lockdown.js +6 -11
  114. package/dist/esm/common/lockdown/lockdown.js.map +1 -0
  115. package/dist/{common → esm/common}/sortParams.js +7 -13
  116. package/dist/esm/common/sortParams.js.map +1 -0
  117. package/dist/{common → esm/common}/utils.js +43 -56
  118. package/dist/esm/common/utils.js.map +1 -0
  119. package/dist/esm/common/validation.js +94 -0
  120. package/dist/esm/common/validation.js.map +1 -0
  121. package/dist/esm/iframe/IFrameSnapExecutor.js +35 -0
  122. package/dist/esm/iframe/IFrameSnapExecutor.js.map +1 -0
  123. package/dist/esm/iframe/index.js +9 -0
  124. package/dist/esm/iframe/index.js.map +1 -0
  125. package/dist/esm/logging.js +10 -0
  126. package/dist/esm/logging.js.map +1 -0
  127. package/dist/esm/node-process/ChildProcessSnapExecutor.js +24 -0
  128. package/dist/esm/node-process/ChildProcessSnapExecutor.js.map +1 -0
  129. package/dist/esm/node-process/index.js +7 -0
  130. package/dist/esm/node-process/index.js.map +1 -0
  131. package/dist/esm/node-thread/ThreadSnapExecutor.js +24 -0
  132. package/dist/esm/node-thread/ThreadSnapExecutor.js.map +1 -0
  133. package/dist/esm/node-thread/index.js +7 -0
  134. package/dist/esm/node-thread/index.js.map +1 -0
  135. package/dist/esm/offscreen/OffscreenSnapExecutor.js +176 -0
  136. package/dist/esm/offscreen/OffscreenSnapExecutor.js.map +1 -0
  137. package/dist/esm/offscreen/index.js +15 -0
  138. package/dist/esm/offscreen/index.js.map +1 -0
  139. package/dist/esm/webworker/executor/WebWorkerSnapExecutor.js +30 -0
  140. package/dist/esm/webworker/executor/WebWorkerSnapExecutor.js.map +1 -0
  141. package/dist/esm/webworker/executor/index.js +9 -0
  142. package/dist/esm/webworker/executor/index.js.map +1 -0
  143. package/dist/esm/webworker/pool/WebWorkerPool.js +245 -0
  144. package/dist/esm/webworker/pool/WebWorkerPool.js.map +1 -0
  145. package/dist/esm/webworker/pool/index.js +9 -0
  146. package/dist/esm/webworker/pool/index.js.map +1 -0
  147. package/dist/{common → types/common}/BaseSnapExecutor.d.ts +7 -7
  148. package/dist/{common → types/common}/commands.d.ts +2 -2
  149. package/dist/{common → types/common}/endowments/commonEndowmentFactory.d.ts +5 -1
  150. package/dist/types/common/endowments/console.d.ts +45 -0
  151. package/dist/{common → types/common}/endowments/crypto.d.ts +4 -0
  152. package/dist/{common → types/common}/endowments/index.d.ts +5 -3
  153. package/dist/types/common/endowments/network.d.ts +22 -0
  154. package/dist/{common → types/common}/globalEvents.d.ts +1 -0
  155. package/dist/{common → types/common}/sortParams.d.ts +1 -1
  156. package/dist/{common → types/common}/utils.d.ts +5 -4
  157. package/dist/{common → types/common}/validation.d.ts +26 -10
  158. package/dist/{iframe → types/iframe}/IFrameSnapExecutor.d.ts +1 -1
  159. package/dist/{offscreen → types/offscreen}/OffscreenSnapExecutor.d.ts +2 -1
  160. package/dist/types/webworker/executor/WebWorkerSnapExecutor.d.ts +13 -0
  161. package/dist/types/webworker/executor/index.d.ts +1 -0
  162. package/dist/types/webworker/pool/WebWorkerPool.d.ts +23 -0
  163. package/dist/types/webworker/pool/index.d.ts +1 -0
  164. package/package.json +52 -41
  165. package/dist/common/BaseSnapExecutor.js +0 -370
  166. package/dist/common/BaseSnapExecutor.js.map +0 -1
  167. package/dist/common/commands.js +0 -65
  168. package/dist/common/commands.js.map +0 -1
  169. package/dist/common/endowments/commonEndowmentFactory.js +0 -75
  170. package/dist/common/endowments/commonEndowmentFactory.js.map +0 -1
  171. package/dist/common/endowments/crypto.js +0 -28
  172. package/dist/common/endowments/crypto.js.map +0 -1
  173. package/dist/common/endowments/date.js.map +0 -1
  174. package/dist/common/endowments/index.js.map +0 -1
  175. package/dist/common/endowments/interval.js.map +0 -1
  176. package/dist/common/endowments/math.js.map +0 -1
  177. package/dist/common/endowments/network.d.ts +0 -8
  178. package/dist/common/endowments/network.js +0 -170
  179. package/dist/common/endowments/network.js.map +0 -1
  180. package/dist/common/endowments/textDecoder.js +0 -18
  181. package/dist/common/endowments/textDecoder.js.map +0 -1
  182. package/dist/common/endowments/textEncoder.js +0 -18
  183. package/dist/common/endowments/textEncoder.js.map +0 -1
  184. package/dist/common/endowments/timeout.js.map +0 -1
  185. package/dist/common/globalEvents.js +0 -47
  186. package/dist/common/globalEvents.js.map +0 -1
  187. package/dist/common/globalObject.js +0 -50
  188. package/dist/common/keyring.d.ts +0 -12
  189. package/dist/common/keyring.js +0 -42
  190. package/dist/common/keyring.js.map +0 -1
  191. package/dist/common/lockdown/lockdown-events.js +0 -60
  192. package/dist/common/lockdown/lockdown-events.js.map +0 -1
  193. package/dist/common/lockdown/lockdown-more.js.map +0 -1
  194. package/dist/common/lockdown/lockdown.js.map +0 -1
  195. package/dist/common/sortParams.js.map +0 -1
  196. package/dist/common/utils.js.map +0 -1
  197. package/dist/common/validation.js +0 -109
  198. package/dist/common/validation.js.map +0 -1
  199. package/dist/iframe/IFrameSnapExecutor.js +0 -42
  200. package/dist/iframe/IFrameSnapExecutor.js.map +0 -1
  201. package/dist/iframe/index.js +0 -10
  202. package/dist/iframe/index.js.map +0 -1
  203. package/dist/logging.js +0 -13
  204. package/dist/logging.js.map +0 -1
  205. package/dist/node-process/ChildProcessSnapExecutor.js +0 -30
  206. package/dist/node-process/ChildProcessSnapExecutor.js.map +0 -1
  207. package/dist/node-process/index.js +0 -8
  208. package/dist/node-process/index.js.map +0 -1
  209. package/dist/node-thread/ThreadSnapExecutor.js +0 -30
  210. package/dist/node-thread/ThreadSnapExecutor.js.map +0 -1
  211. package/dist/node-thread/index.js +0 -8
  212. package/dist/node-thread/index.js.map +0 -1
  213. package/dist/offscreen/OffscreenSnapExecutor.js +0 -104
  214. package/dist/offscreen/OffscreenSnapExecutor.js.map +0 -1
  215. package/dist/offscreen/index.js +0 -16
  216. package/dist/offscreen/index.js.map +0 -1
  217. package/dist/openrpc.json +0 -210
  218. /package/dist/{common → types/common}/endowments/date.d.ts +0 -0
  219. /package/dist/{common → types/common}/endowments/interval.d.ts +0 -0
  220. /package/dist/{common → types/common}/endowments/math.d.ts +0 -0
  221. /package/dist/{common → types/common}/endowments/textDecoder.d.ts +0 -0
  222. /package/dist/{common → types/common}/endowments/textEncoder.d.ts +0 -0
  223. /package/dist/{common → types/common}/endowments/timeout.d.ts +0 -0
  224. /package/dist/{common → types/common}/globalObject.d.ts +0 -0
  225. /package/dist/{common → types/common}/lockdown/lockdown-events.d.ts +0 -0
  226. /package/dist/{common → types/common}/lockdown/lockdown-more.d.ts +0 -0
  227. /package/dist/{common → types/common}/lockdown/lockdown.d.ts +0 -0
  228. /package/dist/{iframe → types/iframe}/index.d.ts +0 -0
  229. /package/dist/{logging.d.ts → types/logging.d.ts} +0 -0
  230. /package/dist/{node-process → types/node-process}/ChildProcessSnapExecutor.d.ts +0 -0
  231. /package/dist/{node-process → types/node-process}/index.d.ts +0 -0
  232. /package/dist/{node-thread → types/node-thread}/ThreadSnapExecutor.d.ts +0 -0
  233. /package/dist/{node-thread → types/node-thread}/index.d.ts +0 -0
  234. /package/dist/{offscreen → types/offscreen}/index.d.ts +0 -0
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/common/endowments/index.ts"],"names":[],"mappings":";;;;;;AAEA,uDAAmD;AACnD,2CAA8C;AAE9C,kDAAkD;AAClD,sFAA6D;AAe7D;;GAEG;AACH,MAAM,oBAAoB,GAAG,IAAA,gCAAqB,GAAE,CAAC;AAErD;;;;GAIG;AACH,MAAM,kBAAkB,GAAG,oBAAoB,CAAC,MAAM,CAAC,CAAC,SAAS,EAAE,OAAO,EAAE,EAAE;IAC5E,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,IAAI,EAAE,EAAE;QAC7B,SAAS,CAAC,GAAG,CAAC,IAAI,EAAE,OAAO,CAAC,OAAO,CAAC,CAAC;IACvC,CAAC,CAAC,CAAC;IACH,OAAO,SAAS,CAAC;AACnB,CAAC,EAAE,IAAI,GAAG,EAAwC,CAAC,CAAC;AAEpD;;;;;;;;;;;GAWG;AACH,SAAgB,gBAAgB,CAC9B,IAAuB,EACvB,QAAwB,EACxB,aAAuB,EAAE;IAEzB,MAAM,oBAAoB,GAA4B,EAAE,CAAC;IAEzD,0EAA0E;IAC1E,yEAAyE;IACzE,2CAA2C;IAC3C,MAAM,MAAM,GAAG,UAAU,CAAC,MAAM,CAI9B,CAAC,EAAE,aAAa,EAAE,SAAS,EAAE,EAAE,aAAa,EAAE,EAAE;QAC9C,oEAAoE;QACpE,IAAI,kBAAkB,CAAC,GAAG,CAAC,aAAa,CAAC,EAAE;YACzC,IAAI,CAAC,IAAA,mBAAW,EAAC,oBAAoB,EAAE,aAAa,CAAC,EAAE;gBACrD,uEAAuE;gBACvE,gEAAgE;gBAChE,wEAAwE;gBACxE,4CAA4C;gBAC5C,2DAA2D;gBAE3D,mEAAmE;gBACnE,MAAM,EAAE,gBAAgB,EAAE,GAAG,SAAS,EAAE;gBACtC,oEAAoE;gBACpE,kBAAkB,CAAC,GAAG,CAAC,aAAa,CAAE,EAAE,CAAC;gBAC3C,MAAM,CAAC,MAAM,CAAC,oBAAoB,EAAE,SAAS,CAAC,CAAC;gBAC/C,IAAI,gBAAgB,EAAE;oBACpB,SAAS,CAAC,IAAI,CAAC,gBAAgB,CAAC,CAAC;iBAClC;aACF;YAED,aAAa,CAAC,aAAa,CAAC,GAAG,oBAAoB,CAAC,aAAa,CAAC,CAAC;SACpE;aAAM,IAAI,aAAa,KAAK,UAAU,EAAE;YACvC,iDAAiD;YACjD,aAAa,CAAC,aAAa,CAAC,GAAG,QAAQ,CAAC;SACzC;aAAM,IAAI,aAAa,IAAI,8BAAe,EAAE;YAC3C,IAAA,wBAAU,EAAC,+BAA+B,aAAa,GAAG,CAAC,CAAC;YAC5D,uEAAuE;YACvE,iBAAiB;YACjB,MAAM,WAAW,GAAI,8BAA2C,CAC9D,aAAa,CACd,CAAC;YACF,aAAa,CAAC,aAAa,CAAC,GAAG,WAAW,CAAC;SAC5C;aAAM;YACL,uEAAuE;YACvE,oCAAoC;YACpC,MAAM,IAAI,KAAK,CAAC,uBAAuB,aAAa,IAAI,CAAC,CAAC;SAC3D;QACD,OAAO,EAAE,aAAa,EAAE,SAAS,EAAE,CAAC;IACtC,CAAC,EACD;QACE,aAAa,EAAE,EAAE,IAAI,EAAE;QACvB,SAAS,EAAE,EAAE;KACd,CACF,CAAC;IAEF,MAAM,QAAQ,GAAG,KAAK,IAAI,EAAE;QAC1B,MAAM,OAAO,CAAC,GAAG,CACf,MAAM,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,gBAAgB,EAAE,EAAE,CAAC,gBAAgB,EAAE,CAAC,CAC/D,CAAC;IACJ,CAAC,CAAC;IACF,OAAO,EAAE,UAAU,EAAE,MAAM,CAAC,aAAa,EAAE,QAAQ,EAAE,CAAC;AACxD,CAAC;AAjED,4CAiEC","sourcesContent":["import { StreamProvider } from '@metamask/providers';\nimport { SnapsGlobalObject } from '@metamask/rpc-methods';\nimport { logWarning } from '@metamask/snaps-utils';\nimport { hasProperty } from '@metamask/utils';\n\nimport { rootRealmGlobal } from '../globalObject';\nimport buildCommonEndowments from './commonEndowmentFactory';\n\ntype EndowmentFactoryResult = {\n /**\n * A function that performs any necessary teardown when the snap becomes idle.\n *\n * NOTE:** The endowments are not reconstructed if the snap is re-invoked\n * before being terminated, so the teardown operation must not render the\n * endowments unusable; it should simply restore the endowments to their\n * original state.\n */\n teardownFunction?: () => Promise<void> | void;\n [key: string]: unknown;\n};\n\n/**\n * Retrieve consolidated endowment factories for common endowments.\n */\nconst registeredEndowments = buildCommonEndowments();\n\n/**\n * A map of endowment names to their factory functions. Some endowments share\n * the same factory function, but we only call each factory once for each snap.\n * See {@link createEndowments} for details.\n */\nconst endowmentFactories = registeredEndowments.reduce((factories, builder) => {\n builder.names.forEach((name) => {\n factories.set(name, builder.factory);\n });\n return factories;\n}, new Map<string, () => EndowmentFactoryResult>());\n\n/**\n * Gets the endowments for a particular Snap. Some endowments, like `setTimeout`\n * and `clearTimeout`, must be attenuated so that they can only affect behavior\n * within the Snap's own realm. Therefore, we use factory functions to create\n * such attenuated / modified endowments. Otherwise, the value that's on the\n * root realm global will be used.\n *\n * @param snap - The Snaps global API object.\n * @param ethereum - The Snap's EIP-1193 provider object.\n * @param endowments - The list of endowments to provide to the snap.\n * @returns An object containing the Snap's endowments.\n */\nexport function createEndowments(\n snap: SnapsGlobalObject,\n ethereum: StreamProvider,\n endowments: string[] = [],\n): { endowments: Record<string, unknown>; teardown: () => Promise<void> } {\n const attenuatedEndowments: Record<string, unknown> = {};\n\n // TODO: All endowments should be hardened to prevent covert communication\n // channels. Hardening the returned objects breaks tests elsewhere in the\n // monorepo, so further research is needed.\n const result = endowments.reduce<{\n allEndowments: Record<string, unknown>;\n teardowns: (() => Promise<void> | void)[];\n }>(\n ({ allEndowments, teardowns }, endowmentName) => {\n // First, check if the endowment has a factory, and default to that.\n if (endowmentFactories.has(endowmentName)) {\n if (!hasProperty(attenuatedEndowments, endowmentName)) {\n // Call the endowment factory for the current endowment. If the factory\n // creates multiple endowments, they will all be assigned to the\n // `attenuatedEndowments` object, but will only be passed on to the snap\n // if explicitly listed among its endowment.\n // This may not have an actual use case, but, safety first.\n\n // We just confirmed that endowmentFactories has the specified key.\n const { teardownFunction, ...endowment } =\n // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n endowmentFactories.get(endowmentName)!();\n Object.assign(attenuatedEndowments, endowment);\n if (teardownFunction) {\n teardowns.push(teardownFunction);\n }\n }\n\n allEndowments[endowmentName] = attenuatedEndowments[endowmentName];\n } else if (endowmentName === 'ethereum') {\n // Special case for adding the EIP-1193 provider.\n allEndowments[endowmentName] = ethereum;\n } else if (endowmentName in rootRealmGlobal) {\n logWarning(`Access to unhardened global ${endowmentName}.`);\n // If the endowment doesn't have a factory, just use whatever is on the\n // global object.\n const globalValue = (rootRealmGlobal as Record<string, unknown>)[\n endowmentName\n ];\n allEndowments[endowmentName] = globalValue;\n } else {\n // If we get to this point, we've been passed an endowment that doesn't\n // exist in our current environment.\n throw new Error(`Unknown endowment: \"${endowmentName}\".`);\n }\n return { allEndowments, teardowns };\n },\n {\n allEndowments: { snap },\n teardowns: [],\n },\n );\n\n const teardown = async () => {\n await Promise.all(\n result.teardowns.map((teardownFunction) => teardownFunction()),\n );\n };\n return { endowments: result.allEndowments, teardown };\n}\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"interval.js","sourceRoot":"","sources":["../../../src/common/endowments/interval.ts"],"names":[],"mappings":";;AAAA,MAAM,gBAAgB,GAAG,EAAE,CAAC;AAE5B;;;;;;;;;GASG;AACH,MAAM,cAAc,GAAG,GAAG,EAAE;IAC1B,MAAM,iBAAiB,GAAG,IAAI,GAAG,EAAoB,CAAC;IAEtD,MAAM,YAAY,GAAG,CAAC,OAAqB,EAAE,OAAgB,EAAW,EAAE;QACxE,IAAI,OAAO,OAAO,KAAK,UAAU,EAAE;YACjC,MAAM,IAAI,KAAK,CACb,sDAAsD,OAAO,OAAO,EAAE,CACvE,CAAC;SACH;QACD,MAAM,CAAC,OAAO,CAAC,CAAC;QAChB,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;QAClD,MAAM,cAAc,GAAG,WAAW,CAChC,OAAO,EACP,IAAI,CAAC,GAAG,CAAC,gBAAgB,EAAE,OAAO,IAAI,CAAC,CAAC,CACzC,CAAC;QACF,iBAAiB,CAAC,GAAG,CAAC,MAAM,EAAE,cAAc,CAAC,CAAC;QAC9C,OAAO,MAAM,CAAC;IAChB,CAAC,CAAC;IAEF,MAAM,cAAc,GAAG,CAAC,MAAe,EAAQ,EAAE;QAC/C,MAAM,CAAC,MAAM,CAAC,CAAC;QACf,MAAM,cAAc,GAAG,iBAAiB,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;QACrD,IAAI,cAAc,KAAK,SAAS,EAAE;YAChC,aAAa,CAAC,cAAqB,CAAC,CAAC;YACrC,iBAAiB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;SAClC;IACH,CAAC,CAAC;IAEF,MAAM,gBAAgB,GAAG,GAAS,EAAE;QAClC,KAAK,MAAM,MAAM,IAAI,iBAAiB,CAAC,IAAI,EAAE,EAAE;YAC7C,cAAc,CAAC,MAAM,CAAC,CAAC;SACxB;IACH,CAAC,CAAC;IAEF,OAAO;QACL,WAAW,EAAE,MAAM,CAAC,YAAY,CAAC;QACjC,aAAa,EAAE,MAAM,CAAC,cAAc,CAAC;QACrC,gBAAgB;KACR,CAAC;AACb,CAAC,CAAC;AAEF,MAAM,eAAe,GAAG;IACtB,KAAK,EAAE,CAAC,aAAa,EAAE,eAAe,CAAU;IAChD,OAAO,EAAE,cAAc;CACxB,CAAC;AACF,kBAAe,eAAe,CAAC","sourcesContent":["const MINIMUM_INTERVAL = 10;\n\n/**\n * Creates a pair of `setInterval` and `clearInterval` functions attenuated such\n * that:\n * - `setInterval` throws if its \"handler\" parameter is not a function.\n * - `clearInterval` only clears timeouts created by its sibling `setInterval`,\n * or else no-ops.\n *\n * @returns An object with the attenuated `setInterval` and `clearInterval`\n * functions.\n */\nconst createInterval = () => {\n const registeredHandles = new Map<unknown, unknown>();\n\n const _setInterval = (handler: TimerHandler, timeout?: number): unknown => {\n if (typeof handler !== 'function') {\n throw new Error(\n `The interval handler must be a function. Received: ${typeof handler}`,\n );\n }\n harden(handler);\n const handle = Object.freeze(Object.create(null));\n const platformHandle = setInterval(\n handler,\n Math.max(MINIMUM_INTERVAL, timeout ?? 0),\n );\n registeredHandles.set(handle, platformHandle);\n return handle;\n };\n\n const _clearInterval = (handle: unknown): void => {\n harden(handle);\n const platformHandle = registeredHandles.get(handle);\n if (platformHandle !== undefined) {\n clearInterval(platformHandle as any);\n registeredHandles.delete(handle);\n }\n };\n\n const teardownFunction = (): void => {\n for (const handle of registeredHandles.keys()) {\n _clearInterval(handle);\n }\n };\n\n return {\n setInterval: harden(_setInterval),\n clearInterval: harden(_clearInterval),\n teardownFunction,\n } as const;\n};\n\nconst endowmentModule = {\n names: ['setInterval', 'clearInterval'] as const,\n factory: createInterval,\n};\nexport default endowmentModule;\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"math.js","sourceRoot":"","sources":["../../../src/common/endowments/math.ts"],"names":[],"mappings":";;AAAA,kDAAkD;AAElD;;;;;;GAMG;AACH,SAAS,UAAU;IACjB,yEAAyE;IACzE,wDAAwD;IACxD,MAAM,IAAI,GAAG,MAAM,CAAC,mBAAmB,CACrC,8BAAe,CAAC,IAAI,CACI,CAAC;IAE3B,MAAM,IAAI,GAAG,IAAI,CAAC,MAAM,CAAgB,CAAC,MAAM,EAAE,GAAG,EAAE,EAAE;QACtD,IAAI,GAAG,KAAK,QAAQ,EAAE;YACpB,OAAO,MAAM,CAAC;SACf;QAED,OAAO,EAAE,GAAG,MAAM,EAAE,CAAC,GAAG,CAAC,EAAE,8BAAe,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;IACzD,CAAC,EAAE,EAAE,CAAC,CAAC;IAEP,OAAO,MAAM,CAAC;QACZ,IAAI,EAAE;YACJ,GAAG,IAAI;YACP,MAAM,EAAE,GAAG,EAAE;gBACX,qEAAqE;gBACrE,wEAAwE;gBACxE,wEAAwE;gBACxE,gEAAgE;gBAChE,WAAW;gBACX,EAAE;gBACF,mEAAmE;gBACnE,qEAAqE;gBACrE,0BAA0B;gBAC1B,EAAE;gBACF,sEAAsE;gBACtE,sEAAsE;gBACtE,OAAO;gBACP,EAAE;gBACF,8EAA8E;gBAC9E,4EAA4E;gBAC5E,OAAO,MAAM,CAAC,eAAe,CAAC,IAAI,WAAW,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,IAAI,EAAE,CAAC;YACjE,CAAC;SACF;KACF,CAAC,CAAC;AACL,CAAC;AAED,MAAM,eAAe,GAAG;IACtB,KAAK,EAAE,CAAC,MAAM,CAAU;IACxB,OAAO,EAAE,UAAU;CACpB,CAAC;AAEF,kBAAe,eAAe,CAAC","sourcesContent":["import { rootRealmGlobal } from '../globalObject';\n\n/**\n * Create a {@link Math} object, with the same properties as the global\n * {@link Math} object, but with the {@link Math.random} method replaced.\n *\n * @returns The {@link Math} object with the {@link Math.random} method\n * replaced.\n */\nfunction createMath() {\n // `Math` does not work with `Object.keys`, `Object.entries`, etc., so we\n // need to create a new object with the same properties.\n const keys = Object.getOwnPropertyNames(\n rootRealmGlobal.Math,\n ) as (keyof typeof Math)[];\n\n const math = keys.reduce<Partial<Math>>((target, key) => {\n if (key === 'random') {\n return target;\n }\n\n return { ...target, [key]: rootRealmGlobal.Math[key] };\n }, {});\n\n return harden({\n Math: {\n ...math,\n random: () => {\n // NOTE: This is not intended to be a secure replacement for the weak\n // random number generator used by `Math.random`. It is only intended to\n // prevent side channel attacks of `Math.random` by replacing it with an\n // alternative implementation that is not vulnerable to the same\n // attacks.\n //\n // This does not mean that this implementation is secure. It is not\n // intended to be used in a security context, and this implementation\n // may change at any time.\n //\n // To securely generate random numbers, use a cryptographically secure\n // random number generator, such as the one provided by the Web Crypto\n // API:\n //\n // - https://developer.mozilla.org/en-US/docs/Web/API/SubtleCrypto/generateKey\n // - https://developer.mozilla.org/en-US/docs/Web/API/Crypto/getRandomValues\n return crypto.getRandomValues(new Uint32Array(1))[0] / 2 ** 32;\n },\n },\n });\n}\n\nconst endowmentModule = {\n names: ['Math'] as const,\n factory: createMath,\n};\n\nexport default endowmentModule;\n"]}
@@ -1,8 +0,0 @@
1
- declare const endowmentModule: {
2
- names: readonly ["fetch"];
3
- factory: () => {
4
- fetch: typeof fetch;
5
- teardownFunction: () => Promise<void>;
6
- };
7
- };
8
- export default endowmentModule;
@@ -1,170 +0,0 @@
1
- "use strict";
2
- var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
3
- if (kind === "m") throw new TypeError("Private method is not writable");
4
- if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
5
- if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
6
- return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
7
- };
8
- var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
9
- if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
10
- if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
11
- return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
12
- };
13
- var _ResponseWrapper_teardownRef, _ResponseWrapper_ogResponse;
14
- Object.defineProperty(exports, "__esModule", { value: true });
15
- const utils_1 = require("../utils");
16
- /**
17
- * This class wraps a Response object.
18
- * That way, a teardown process can stop any processes left.
19
- */
20
- class ResponseWrapper {
21
- constructor(ogResponse, teardownRef) {
22
- _ResponseWrapper_teardownRef.set(this, void 0);
23
- _ResponseWrapper_ogResponse.set(this, void 0);
24
- __classPrivateFieldSet(this, _ResponseWrapper_ogResponse, ogResponse, "f");
25
- __classPrivateFieldSet(this, _ResponseWrapper_teardownRef, teardownRef, "f");
26
- }
27
- get body() {
28
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").body;
29
- }
30
- get bodyUsed() {
31
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").bodyUsed;
32
- }
33
- get headers() {
34
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").headers;
35
- }
36
- get ok() {
37
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").ok;
38
- }
39
- get redirected() {
40
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").redirected;
41
- }
42
- get status() {
43
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").status;
44
- }
45
- get statusText() {
46
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").statusText;
47
- }
48
- get type() {
49
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").type;
50
- }
51
- get url() {
52
- return __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").url;
53
- }
54
- async text() {
55
- return (0, utils_1.withTeardown)(__classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").text(), this);
56
- }
57
- async arrayBuffer() {
58
- return (0, utils_1.withTeardown)(__classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").arrayBuffer(), this);
59
- }
60
- async blob() {
61
- return (0, utils_1.withTeardown)(__classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").blob(), this);
62
- }
63
- clone() {
64
- const newResponse = __classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").clone();
65
- return new ResponseWrapper(newResponse, __classPrivateFieldGet(this, _ResponseWrapper_teardownRef, "f"));
66
- }
67
- async formData() {
68
- return (0, utils_1.withTeardown)(__classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").formData(), this);
69
- }
70
- async json() {
71
- return (0, utils_1.withTeardown)(__classPrivateFieldGet(this, _ResponseWrapper_ogResponse, "f").json(), this);
72
- }
73
- }
74
- _ResponseWrapper_teardownRef = new WeakMap(), _ResponseWrapper_ogResponse = new WeakMap();
75
- /**
76
- * Create a network endowment, consisting of a `fetch` function.
77
- * This allows us to provide a teardown function, so that we can cancel
78
- * any pending requests, connections, streams, etc. that may be open when a snap
79
- * is terminated.
80
- *
81
- * This wraps the original implementation of `fetch`,
82
- * to ensure that a bad actor cannot get access to the original function, thus
83
- * potentially preventing the network requests from being torn down.
84
- *
85
- * @returns An object containing a wrapped `fetch`
86
- * function, as well as a teardown function.
87
- */
88
- const createNetwork = () => {
89
- // Open fetch calls or open body streams
90
- const openConnections = new Set();
91
- // Track last teardown count
92
- const teardownRef = { lastTeardown: 0 };
93
- // Remove items from openConnections after they were garbage collected
94
- const cleanup = new FinalizationRegistry(
95
- /* istanbul ignore next: can't test garbage collection without modifying node parameters */
96
- (callback) => callback());
97
- const _fetch = async (input, init) => {
98
- const abortController = new AbortController();
99
- if (init?.signal !== null && init?.signal !== undefined) {
100
- const originalSignal = init.signal;
101
- // Merge abort controllers
102
- originalSignal.addEventListener('abort', () => {
103
- abortController.abort(originalSignal.reason);
104
- }, { once: true });
105
- }
106
- let res;
107
- let openFetchConnection;
108
- try {
109
- const fetchPromise = fetch(input, {
110
- ...init,
111
- signal: abortController.signal,
112
- });
113
- openFetchConnection = {
114
- cancel: async () => {
115
- abortController.abort();
116
- try {
117
- await fetchPromise;
118
- }
119
- catch {
120
- /* do nothing */
121
- }
122
- },
123
- };
124
- openConnections.add(openFetchConnection);
125
- res = new ResponseWrapper(await (0, utils_1.withTeardown)(fetchPromise, teardownRef), teardownRef);
126
- }
127
- finally {
128
- if (openFetchConnection !== undefined) {
129
- openConnections.delete(openFetchConnection);
130
- }
131
- }
132
- if (res.body !== null) {
133
- const body = new WeakRef(res.body);
134
- const openBodyConnection = {
135
- cancel:
136
- /* istanbul ignore next: see it.todo('can be torn down during body read') test */
137
- async () => {
138
- try {
139
- await body.deref()?.cancel();
140
- }
141
- catch {
142
- /* do nothing */
143
- }
144
- },
145
- };
146
- openConnections.add(openBodyConnection);
147
- cleanup.register(res.body,
148
- /* istanbul ignore next: can't test garbage collection without modifying node parameters */
149
- () => openConnections.delete(openBodyConnection));
150
- }
151
- return harden(res);
152
- };
153
- const teardownFunction = async () => {
154
- teardownRef.lastTeardown += 1;
155
- const promises = [];
156
- openConnections.forEach(({ cancel }) => promises.push(cancel()));
157
- openConnections.clear();
158
- await Promise.all(promises);
159
- };
160
- return {
161
- fetch: harden(_fetch),
162
- teardownFunction,
163
- };
164
- };
165
- const endowmentModule = {
166
- names: ['fetch'],
167
- factory: createNetwork,
168
- };
169
- exports.default = endowmentModule;
170
- //# sourceMappingURL=network.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"network.js","sourceRoot":"","sources":["../../../src/common/endowments/network.ts"],"names":[],"mappings":"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","sourcesContent":["import { withTeardown } from '../utils';\n\n/**\n * This class wraps a Response object.\n * That way, a teardown process can stop any processes left.\n */\nclass ResponseWrapper implements Response {\n readonly #teardownRef: { lastTeardown: number };\n\n #ogResponse: Response;\n\n constructor(ogResponse: Response, teardownRef: { lastTeardown: number }) {\n this.#ogResponse = ogResponse;\n this.#teardownRef = teardownRef;\n }\n\n get body(): ReadableStream<Uint8Array> | null {\n return this.#ogResponse.body;\n }\n\n get bodyUsed() {\n return this.#ogResponse.bodyUsed;\n }\n\n get headers() {\n return this.#ogResponse.headers;\n }\n\n get ok() {\n return this.#ogResponse.ok;\n }\n\n get redirected() {\n return this.#ogResponse.redirected;\n }\n\n get status() {\n return this.#ogResponse.status;\n }\n\n get statusText() {\n return this.#ogResponse.statusText;\n }\n\n get type() {\n return this.#ogResponse.type;\n }\n\n get url() {\n return this.#ogResponse.url;\n }\n\n async text() {\n return withTeardown<string>(this.#ogResponse.text(), this as any);\n }\n\n async arrayBuffer(): Promise<ArrayBuffer> {\n return withTeardown<ArrayBuffer>(\n this.#ogResponse.arrayBuffer(),\n this as any,\n );\n }\n\n async blob(): Promise<Blob> {\n return withTeardown<Blob>(this.#ogResponse.blob(), this as any);\n }\n\n clone(): Response {\n const newResponse = this.#ogResponse.clone();\n return new ResponseWrapper(newResponse, this.#teardownRef);\n }\n\n async formData(): Promise<FormData> {\n return withTeardown<FormData>(this.#ogResponse.formData(), this as any);\n }\n\n async json(): Promise<any> {\n return withTeardown(this.#ogResponse.json(), this as any);\n }\n}\n\n/**\n * Create a network endowment, consisting of a `fetch` function.\n * This allows us to provide a teardown function, so that we can cancel\n * any pending requests, connections, streams, etc. that may be open when a snap\n * is terminated.\n *\n * This wraps the original implementation of `fetch`,\n * to ensure that a bad actor cannot get access to the original function, thus\n * potentially preventing the network requests from being torn down.\n *\n * @returns An object containing a wrapped `fetch`\n * function, as well as a teardown function.\n */\nconst createNetwork = () => {\n // Open fetch calls or open body streams\n const openConnections = new Set<{ cancel: () => Promise<void> }>();\n // Track last teardown count\n const teardownRef = { lastTeardown: 0 };\n\n // Remove items from openConnections after they were garbage collected\n const cleanup = new FinalizationRegistry<() => void>(\n /* istanbul ignore next: can't test garbage collection without modifying node parameters */\n (callback) => callback(),\n );\n\n const _fetch: typeof fetch = async (\n input: RequestInfo | URL,\n init?: RequestInit,\n ): Promise<Response> => {\n const abortController = new AbortController();\n if (init?.signal !== null && init?.signal !== undefined) {\n const originalSignal = init.signal;\n // Merge abort controllers\n originalSignal.addEventListener(\n 'abort',\n () => {\n abortController.abort((originalSignal as any).reason);\n },\n { once: true },\n );\n }\n\n let res: Response;\n let openFetchConnection: { cancel: () => Promise<void> } | undefined;\n try {\n const fetchPromise = fetch(input, {\n ...init,\n signal: abortController.signal,\n });\n\n openFetchConnection = {\n cancel: async () => {\n abortController.abort();\n try {\n await fetchPromise;\n } catch {\n /* do nothing */\n }\n },\n };\n openConnections.add(openFetchConnection);\n\n res = new ResponseWrapper(\n await withTeardown(fetchPromise, teardownRef),\n teardownRef,\n );\n } finally {\n if (openFetchConnection !== undefined) {\n openConnections.delete(openFetchConnection);\n }\n }\n\n if (res.body !== null) {\n const body = new WeakRef<ReadableStream>(res.body);\n\n const openBodyConnection = {\n cancel:\n /* istanbul ignore next: see it.todo('can be torn down during body read') test */\n async () => {\n try {\n await body.deref()?.cancel();\n } catch {\n /* do nothing */\n }\n },\n };\n openConnections.add(openBodyConnection);\n cleanup.register(\n res.body,\n /* istanbul ignore next: can't test garbage collection without modifying node parameters */\n () => openConnections.delete(openBodyConnection),\n );\n }\n return harden(res);\n };\n\n const teardownFunction = async () => {\n teardownRef.lastTeardown += 1;\n const promises: Promise<void>[] = [];\n openConnections.forEach(({ cancel }) => promises.push(cancel()));\n openConnections.clear();\n await Promise.all(promises);\n };\n\n return {\n fetch: harden(_fetch),\n teardownFunction,\n };\n};\n\nconst endowmentModule = {\n names: ['fetch'] as const,\n factory: createNetwork,\n};\nexport default endowmentModule;\n"]}
@@ -1,18 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- /**
4
- * Creates TextDecoder function hardened by SES.
5
- *
6
- * @returns An object with the attenuated `TextDecoder` function.
7
- */
8
- const createTextDecoder = () => {
9
- return {
10
- TextDecoder: harden(TextDecoder),
11
- };
12
- };
13
- const endowmentModule = {
14
- names: ['TextDecoder'],
15
- factory: createTextDecoder,
16
- };
17
- exports.default = endowmentModule;
18
- //# sourceMappingURL=textDecoder.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"textDecoder.js","sourceRoot":"","sources":["../../../src/common/endowments/textDecoder.ts"],"names":[],"mappings":";;AAAA;;;;GAIG;AACH,MAAM,iBAAiB,GAAG,GAAG,EAAE;IAC7B,OAAO;QACL,WAAW,EAAE,MAAM,CAAC,WAAW,CAAC;KACxB,CAAC;AACb,CAAC,CAAC;AAEF,MAAM,eAAe,GAAG;IACtB,KAAK,EAAE,CAAC,aAAa,CAAU;IAC/B,OAAO,EAAE,iBAAiB;CAC3B,CAAC;AACF,kBAAe,eAAe,CAAC","sourcesContent":["/**\n * Creates TextDecoder function hardened by SES.\n *\n * @returns An object with the attenuated `TextDecoder` function.\n */\nconst createTextDecoder = () => {\n return {\n TextDecoder: harden(TextDecoder),\n } as const;\n};\n\nconst endowmentModule = {\n names: ['TextDecoder'] as const,\n factory: createTextDecoder,\n};\nexport default endowmentModule;\n"]}
@@ -1,18 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- /**
4
- * Creates TextEncoder function hardened by SES.
5
- *
6
- * @returns An object with the attenuated `TextEncoder` function.
7
- */
8
- const createTextEncoder = () => {
9
- return {
10
- TextEncoder: harden(TextEncoder),
11
- };
12
- };
13
- const endowmentModule = {
14
- names: ['TextEncoder'],
15
- factory: createTextEncoder,
16
- };
17
- exports.default = endowmentModule;
18
- //# sourceMappingURL=textEncoder.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"textEncoder.js","sourceRoot":"","sources":["../../../src/common/endowments/textEncoder.ts"],"names":[],"mappings":";;AAAA;;;;GAIG;AACH,MAAM,iBAAiB,GAAG,GAAG,EAAE;IAC7B,OAAO;QACL,WAAW,EAAE,MAAM,CAAC,WAAW,CAAC;KACxB,CAAC;AACb,CAAC,CAAC;AAEF,MAAM,eAAe,GAAG;IACtB,KAAK,EAAE,CAAC,aAAa,CAAU;IAC/B,OAAO,EAAE,iBAAiB;CAC3B,CAAC;AACF,kBAAe,eAAe,CAAC","sourcesContent":["/**\n * Creates TextEncoder function hardened by SES.\n *\n * @returns An object with the attenuated `TextEncoder` function.\n */\nconst createTextEncoder = () => {\n return {\n TextEncoder: harden(TextEncoder),\n } as const;\n};\n\nconst endowmentModule = {\n names: ['TextEncoder'] as const,\n factory: createTextEncoder,\n};\nexport default endowmentModule;\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"timeout.js","sourceRoot":"","sources":["../../../src/common/endowments/timeout.ts"],"names":[],"mappings":";;AAAA,MAAM,eAAe,GAAG,EAAE,CAAC;AAE3B;;;;;;;;;GASG;AACH,MAAM,aAAa,GAAG,GAAG,EAAE;IACzB,MAAM,iBAAiB,GAAG,IAAI,GAAG,EAAoB,CAAC;IACtD,MAAM,WAAW,GAAG,CAAC,OAAqB,EAAE,OAAgB,EAAW,EAAE;QACvE,IAAI,OAAO,OAAO,KAAK,UAAU,EAAE;YACjC,MAAM,IAAI,KAAK,CACb,qDAAqD,OAAO,OAAO,EAAE,CACtE,CAAC;SACH;QACD,MAAM,CAAC,OAAO,CAAC,CAAC;QAChB,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;QAClD,MAAM,cAAc,GAAG,UAAU,CAAC,GAAG,EAAE;YACrC,iBAAiB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;YACjC,OAAO,EAAE,CAAC;QACZ,CAAC,EAAE,IAAI,CAAC,GAAG,CAAC,eAAe,EAAE,OAAO,IAAI,CAAC,CAAC,CAAC,CAAC;QAE5C,iBAAiB,CAAC,GAAG,CAAC,MAAM,EAAE,cAAc,CAAC,CAAC;QAC9C,OAAO,MAAM,CAAC;IAChB,CAAC,CAAC;IAEF,MAAM,aAAa,GAAG,CAAC,MAAe,EAAQ,EAAE;QAC9C,MAAM,cAAc,GAAG,iBAAiB,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;QACrD,IAAI,cAAc,KAAK,SAAS,EAAE;YAChC,YAAY,CAAC,cAAqB,CAAC,CAAC;YACpC,iBAAiB,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;SAClC;IACH,CAAC,CAAC;IAEF,MAAM,gBAAgB,GAAG,GAAS,EAAE;QAClC,KAAK,MAAM,MAAM,IAAI,iBAAiB,CAAC,IAAI,EAAE,EAAE;YAC7C,aAAa,CAAC,MAAM,CAAC,CAAC;SACvB;IACH,CAAC,CAAC;IAEF,OAAO;QACL,UAAU,EAAE,MAAM,CAAC,WAAW,CAAC;QAC/B,YAAY,EAAE,MAAM,CAAC,aAAa,CAAC;QACnC,gBAAgB;KACR,CAAC;AACb,CAAC,CAAC;AAEF,MAAM,eAAe,GAAG;IACtB,KAAK,EAAE,CAAC,YAAY,EAAE,cAAc,CAAU;IAC9C,OAAO,EAAE,aAAa;CACvB,CAAC;AACF,kBAAe,eAAe,CAAC","sourcesContent":["const MINIMUM_TIMEOUT = 10;\n\n/**\n * Creates a pair of `setTimeout` and `clearTimeout` functions attenuated such\n * that:\n * - `setTimeout` throws if its \"handler\" parameter is not a function.\n * - `clearTimeout` only clears timeouts created by its sibling `setTimeout`,\n * or else no-ops.\n *\n * @returns An object with the attenuated `setTimeout` and `clearTimeout`\n * functions.\n */\nconst createTimeout = () => {\n const registeredHandles = new Map<unknown, unknown>();\n const _setTimeout = (handler: TimerHandler, timeout?: number): unknown => {\n if (typeof handler !== 'function') {\n throw new Error(\n `The timeout handler must be a function. Received: ${typeof handler}`,\n );\n }\n harden(handler);\n const handle = Object.freeze(Object.create(null));\n const platformHandle = setTimeout(() => {\n registeredHandles.delete(handle);\n handler();\n }, Math.max(MINIMUM_TIMEOUT, timeout ?? 0));\n\n registeredHandles.set(handle, platformHandle);\n return handle;\n };\n\n const _clearTimeout = (handle: unknown): void => {\n const platformHandle = registeredHandles.get(handle);\n if (platformHandle !== undefined) {\n clearTimeout(platformHandle as any);\n registeredHandles.delete(handle);\n }\n };\n\n const teardownFunction = (): void => {\n for (const handle of registeredHandles.keys()) {\n _clearTimeout(handle);\n }\n };\n\n return {\n setTimeout: harden(_setTimeout),\n clearTimeout: harden(_clearTimeout),\n teardownFunction,\n } as const;\n};\n\nconst endowmentModule = {\n names: ['setTimeout', 'clearTimeout'] as const,\n factory: createTimeout,\n};\nexport default endowmentModule;\n"]}
@@ -1,47 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.removeEventListener = exports.addEventListener = void 0;
4
- const globalObject_1 = require("./globalObject");
5
- /**
6
- * Adds an event listener platform agnostically, trying both `globalThis.addEventListener` and `globalThis.process.on`
7
- *
8
- * @param event - The event to listen for.
9
- * @param listener - The listener to be triggered when the event occurs.
10
- * @returns The result of the platform agnostic operation if any.
11
- * @throws If none of the platform options are present.
12
- */
13
- function addEventListener(event, listener) {
14
- if ('addEventListener' in globalObject_1.rootRealmGlobal &&
15
- typeof globalObject_1.rootRealmGlobal.addEventListener === 'function') {
16
- return globalObject_1.rootRealmGlobal.addEventListener(event.toLowerCase(), listener);
17
- }
18
- if (globalObject_1.rootRealmGlobal.process &&
19
- 'on' in globalObject_1.rootRealmGlobal.process &&
20
- typeof globalObject_1.rootRealmGlobal.process.on === 'function') {
21
- return globalObject_1.rootRealmGlobal.process.on(event, listener);
22
- }
23
- throw new Error('Platform agnostic addEventListener failed');
24
- }
25
- exports.addEventListener = addEventListener;
26
- /**
27
- * Removes an event listener platform agnostically, trying both `globalThis.removeEventListener` and `globalThis.process.removeListener`
28
- *
29
- * @param event - The event to remove the listener for.
30
- * @param listener - The currently attached listener.
31
- * @returns The result of the platform agnostic operation if any.
32
- * @throws If none of the platform options are present.
33
- */
34
- function removeEventListener(event, listener) {
35
- if ('removeEventListener' in globalObject_1.rootRealmGlobal &&
36
- typeof globalObject_1.rootRealmGlobal.removeEventListener === 'function') {
37
- return globalObject_1.rootRealmGlobal.removeEventListener(event.toLowerCase(), listener);
38
- }
39
- if (globalObject_1.rootRealmGlobal.process &&
40
- 'removeListener' in globalObject_1.rootRealmGlobal.process &&
41
- typeof globalObject_1.rootRealmGlobal.process.removeListener === 'function') {
42
- return globalObject_1.rootRealmGlobal.process.removeListener(event, listener);
43
- }
44
- throw new Error('Platform agnostic removeEventListener failed');
45
- }
46
- exports.removeEventListener = removeEventListener;
47
- //# sourceMappingURL=globalEvents.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"globalEvents.js","sourceRoot":"","sources":["../../src/common/globalEvents.ts"],"names":[],"mappings":";;;AAAA,iDAAiD;AAEjD;;;;;;;GAOG;AACH,SAAgB,gBAAgB,CAC9B,KAAa,EACb,QAAkC;IAElC,IACE,kBAAkB,IAAI,8BAAe;QACrC,OAAO,8BAAe,CAAC,gBAAgB,KAAK,UAAU,EACtD;QACA,OAAO,8BAAe,CAAC,gBAAgB,CAAC,KAAK,CAAC,WAAW,EAAE,EAAE,QAAQ,CAAC,CAAC;KACxE;IAED,IACE,8BAAe,CAAC,OAAO;QACvB,IAAI,IAAI,8BAAe,CAAC,OAAO;QAC/B,OAAO,8BAAe,CAAC,OAAO,CAAC,EAAE,KAAK,UAAU,EAChD;QACA,OAAO,8BAAe,CAAC,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;KACpD;IAED,MAAM,IAAI,KAAK,CAAC,2CAA2C,CAAC,CAAC;AAC/D,CAAC;AApBD,4CAoBC;AAED;;;;;;;GAOG;AACH,SAAgB,mBAAmB,CACjC,KAAa,EACb,QAAkC;IAElC,IACE,qBAAqB,IAAI,8BAAe;QACxC,OAAO,8BAAe,CAAC,mBAAmB,KAAK,UAAU,EACzD;QACA,OAAO,8BAAe,CAAC,mBAAmB,CAAC,KAAK,CAAC,WAAW,EAAE,EAAE,QAAQ,CAAC,CAAC;KAC3E;IAED,IACE,8BAAe,CAAC,OAAO;QACvB,gBAAgB,IAAI,8BAAe,CAAC,OAAO;QAC3C,OAAO,8BAAe,CAAC,OAAO,CAAC,cAAc,KAAK,UAAU,EAC5D;QACA,OAAO,8BAAe,CAAC,OAAO,CAAC,cAAc,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;KAChE;IAED,MAAM,IAAI,KAAK,CAAC,8CAA8C,CAAC,CAAC;AAClE,CAAC;AApBD,kDAoBC","sourcesContent":["import { rootRealmGlobal } from './globalObject';\n\n/**\n * Adds an event listener platform agnostically, trying both `globalThis.addEventListener` and `globalThis.process.on`\n *\n * @param event - The event to listen for.\n * @param listener - The listener to be triggered when the event occurs.\n * @returns The result of the platform agnostic operation if any.\n * @throws If none of the platform options are present.\n */\nexport function addEventListener(\n event: string,\n listener: (...args: any[]) => void,\n) {\n if (\n 'addEventListener' in rootRealmGlobal &&\n typeof rootRealmGlobal.addEventListener === 'function'\n ) {\n return rootRealmGlobal.addEventListener(event.toLowerCase(), listener);\n }\n\n if (\n rootRealmGlobal.process &&\n 'on' in rootRealmGlobal.process &&\n typeof rootRealmGlobal.process.on === 'function'\n ) {\n return rootRealmGlobal.process.on(event, listener);\n }\n\n throw new Error('Platform agnostic addEventListener failed');\n}\n\n/**\n * Removes an event listener platform agnostically, trying both `globalThis.removeEventListener` and `globalThis.process.removeListener`\n *\n * @param event - The event to remove the listener for.\n * @param listener - The currently attached listener.\n * @returns The result of the platform agnostic operation if any.\n * @throws If none of the platform options are present.\n */\nexport function removeEventListener(\n event: string,\n listener: (...args: any[]) => void,\n) {\n if (\n 'removeEventListener' in rootRealmGlobal &&\n typeof rootRealmGlobal.removeEventListener === 'function'\n ) {\n return rootRealmGlobal.removeEventListener(event.toLowerCase(), listener);\n }\n\n if (\n rootRealmGlobal.process &&\n 'removeListener' in rootRealmGlobal.process &&\n typeof rootRealmGlobal.process.removeListener === 'function'\n ) {\n return rootRealmGlobal.process.removeListener(event, listener);\n }\n\n throw new Error('Platform agnostic removeEventListener failed');\n}\n"]}
@@ -1,50 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.rootRealmGlobalName = exports.rootRealmGlobal = void 0;
4
- var GlobalObjectNames;
5
- (function (GlobalObjectNames) {
6
- // The globalThis entry is incorrectly identified as shadowing the global
7
- // globalThis.
8
- /* eslint-disable @typescript-eslint/naming-convention */
9
- // eslint-disable-next-line @typescript-eslint/no-shadow
10
- GlobalObjectNames["globalThis"] = "globalThis";
11
- GlobalObjectNames["global"] = "global";
12
- GlobalObjectNames["self"] = "self";
13
- GlobalObjectNames["window"] = "window";
14
- /* eslint-enavle @typescript-eslint/naming-convention */
15
- })(GlobalObjectNames || (GlobalObjectNames = {}));
16
- let _rootRealmGlobal;
17
- let _rootRealmGlobalName;
18
- /* istanbul ignore next */
19
- /* eslint-disable no-negated-condition */
20
- if (typeof globalThis !== 'undefined') {
21
- _rootRealmGlobal = globalThis;
22
- _rootRealmGlobalName = GlobalObjectNames.globalThis;
23
- }
24
- else if (typeof self !== 'undefined') {
25
- _rootRealmGlobal = self;
26
- _rootRealmGlobalName = GlobalObjectNames.self;
27
- }
28
- else if (typeof window !== 'undefined') {
29
- _rootRealmGlobal = window;
30
- _rootRealmGlobalName = GlobalObjectNames.window;
31
- }
32
- else if (typeof global !== 'undefined') {
33
- _rootRealmGlobal = global;
34
- _rootRealmGlobalName = GlobalObjectNames.global;
35
- }
36
- else {
37
- throw new Error('Unknown realm type; failed to identify global object.');
38
- }
39
- /* eslint-enable no-negated-condition */
40
- /**
41
- * A platform-agnostic alias for the root realm global object.
42
- */
43
- const rootRealmGlobal = _rootRealmGlobal;
44
- exports.rootRealmGlobal = rootRealmGlobal;
45
- /**
46
- * The string literal corresponding to the name of the root realm global object.
47
- */
48
- const rootRealmGlobalName = _rootRealmGlobalName;
49
- exports.rootRealmGlobalName = rootRealmGlobalName;
50
- //# sourceMappingURL=globalObject.js.map
@@ -1,12 +0,0 @@
1
- import { SnapKeyring } from '@metamask/snaps-utils';
2
- import { Json, JsonRpcNotification, JsonRpcRequest } from '@metamask/utils';
3
- /**
4
- * Wraps a SnapKeyring class, returning a handler that can route requests to the exposed functions by the class.
5
- *
6
- * @param notify - The BaseSnapExecutor notify function, used for event communication.
7
- * @param keyring - The SnapKeyring instance.
8
- * @returns A handler function.
9
- */
10
- export declare function wrapKeyring(notify: (requestObject: Omit<JsonRpcNotification<Record<string, Json> | Json[]>, 'jsonrpc'>) => void, keyring?: SnapKeyring): ({ request }: {
11
- request: JsonRpcRequest<Json[]>;
12
- }) => unknown;
@@ -1,42 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.wrapKeyring = void 0;
4
- const utils_1 = require("@metamask/utils");
5
- /**
6
- * Wraps a SnapKeyring class, returning a handler that can route requests to the exposed functions by the class.
7
- *
8
- * @param notify - The BaseSnapExecutor notify function, used for event communication.
9
- * @param keyring - The SnapKeyring instance.
10
- * @returns A handler function.
11
- */
12
- function wrapKeyring(notify, keyring) {
13
- if (!keyring) {
14
- throw new Error('Keyring not exported');
15
- }
16
- const keyringHandler = ({ request }) => {
17
- const { method, params } = request;
18
- if (!(method in keyring)) {
19
- throw new Error(`Keyring does not expose ${method}`);
20
- }
21
- let args = (params ?? []);
22
- const keyringMethod = keyring[method];
23
- (0, utils_1.assert)(keyringMethod !== undefined);
24
- const func = keyringMethod.bind(keyring);
25
- // Special case for registering events
26
- if (method === 'on') {
27
- const data = args[0];
28
- const listener = (...listenerArgs) => {
29
- (0, utils_1.assert)((0, utils_1.isValidJson)(listenerArgs), new TypeError('Keyrings .on listener received non-JSON-serializable value.'));
30
- return notify({
31
- method: 'SnapKeyringEvent',
32
- params: { data, args: listenerArgs },
33
- });
34
- };
35
- args = [data, listener];
36
- }
37
- return func(...args);
38
- };
39
- return keyringHandler;
40
- }
41
- exports.wrapKeyring = wrapKeyring;
42
- //# sourceMappingURL=keyring.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"keyring.js","sourceRoot":"","sources":["../../src/common/keyring.ts"],"names":[],"mappings":";;;AACA,2CAMyB;AAEzB;;;;;;GAMG;AACH,SAAgB,WAAW,CACzB,MAKS,EACT,OAAqB;IAErB,IAAI,CAAC,OAAO,EAAE;QACZ,MAAM,IAAI,KAAK,CAAC,sBAAsB,CAAC,CAAC;KACzC;IAED,MAAM,cAAc,GAAG,CAAC,EAAE,OAAO,EAAuC,EAAE,EAAE;QAC1E,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC;QACnC,IAAI,CAAC,CAAC,MAAM,IAAI,OAAO,CAAC,EAAE;YACxB,MAAM,IAAI,KAAK,CAAC,2BAA2B,MAAM,EAAE,CAAC,CAAC;SACtD;QACD,IAAI,IAAI,GAAG,CAAC,MAAM,IAAI,EAAE,CAAc,CAAC;QACvC,MAAM,aAAa,GAAG,OAAO,CAAC,MAA2B,CAAC,CAAC;QAC3D,IAAA,cAAM,EAAC,aAAa,KAAK,SAAS,CAAC,CAAC;QACpC,MAAM,IAAI,GAAG,aAAa,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;QACzC,sCAAsC;QACtC,IAAI,MAAM,KAAK,IAAI,EAAE;YACnB,MAAM,IAAI,GAAG,IAAI,CAAC,CAAC,CAAS,CAAC;YAC7B,MAAM,QAAQ,GAAG,CAAC,GAAG,YAAuB,EAAE,EAAE;gBAC9C,IAAA,cAAM,EACJ,IAAA,mBAAW,EAAC,YAAY,CAAC,EACzB,IAAI,SAAS,CACX,6DAA6D,CAC9D,CACF,CAAC;gBACF,OAAO,MAAM,CAAC;oBACZ,MAAM,EAAE,kBAAkB;oBAC1B,MAAM,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,YAAY,EAAE;iBACrC,CAAC,CAAC;YACL,CAAC,CAAC;YACF,IAAI,GAAG,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC;SACzB;QACD,OAAQ,IAAqC,CAAC,GAAG,IAAI,CAAC,CAAC;IACzD,CAAC,CAAC;IACF,OAAO,cAAc,CAAC;AACxB,CAAC;AA1CD,kCA0CC","sourcesContent":["import { SnapKeyring } from '@metamask/snaps-utils';\nimport {\n assert,\n isValidJson,\n Json,\n JsonRpcNotification,\n JsonRpcRequest,\n} from '@metamask/utils';\n\n/**\n * Wraps a SnapKeyring class, returning a handler that can route requests to the exposed functions by the class.\n *\n * @param notify - The BaseSnapExecutor notify function, used for event communication.\n * @param keyring - The SnapKeyring instance.\n * @returns A handler function.\n */\nexport function wrapKeyring(\n notify: (\n requestObject: Omit<\n JsonRpcNotification<Record<string, Json> | Json[]>,\n 'jsonrpc'\n >,\n ) => void,\n keyring?: SnapKeyring,\n) {\n if (!keyring) {\n throw new Error('Keyring not exported');\n }\n\n const keyringHandler = ({ request }: { request: JsonRpcRequest<Json[]> }) => {\n const { method, params } = request;\n if (!(method in keyring)) {\n throw new Error(`Keyring does not expose ${method}`);\n }\n let args = (params ?? []) as unknown[];\n const keyringMethod = keyring[method as keyof SnapKeyring];\n assert(keyringMethod !== undefined);\n const func = keyringMethod.bind(keyring);\n // Special case for registering events\n if (method === 'on') {\n const data = args[0] as Json;\n const listener = (...listenerArgs: unknown[]) => {\n assert(\n isValidJson(listenerArgs),\n new TypeError(\n 'Keyrings .on listener received non-JSON-serializable value.',\n ),\n );\n return notify({\n method: 'SnapKeyringEvent',\n params: { data, args: listenerArgs },\n });\n };\n args = [data, listener];\n }\n return (func as (..._: unknown[]) => unknown)(...args);\n };\n return keyringHandler;\n}\n"]}
@@ -1,60 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.executeLockdownEvents = void 0;
4
- // When creating a sandbox, limitation of the events from leaking
5
- // sensitive objects is required. This is done by overriding own properties
6
- // of prototypes of all existing events.
7
- const utils_1 = require("@metamask/utils");
8
- /**
9
- * Targeted Event objects and properties.
10
- * Note: This is a map of the prototypes that inherit from Events with
11
- * properties that are identified to leak sensitive objects.
12
- * Not all browsers support all event types, so checking its existence is required.
13
- */
14
- const targetEvents = new Map();
15
- if ((0, utils_1.hasProperty)(globalThis, 'UIEvent')) {
16
- targetEvents.set(UIEvent.prototype, ['view']);
17
- }
18
- if ((0, utils_1.hasProperty)(globalThis, 'MutationEvent')) {
19
- targetEvents.set(MutationEvent.prototype, ['relatedNode']);
20
- }
21
- if ((0, utils_1.hasProperty)(globalThis, 'MessageEvent')) {
22
- targetEvents.set(MessageEvent.prototype, ['source']);
23
- }
24
- if ((0, utils_1.hasProperty)(globalThis, 'FocusEvent')) {
25
- targetEvents.set(FocusEvent.prototype, ['relatedTarget']);
26
- }
27
- if ((0, utils_1.hasProperty)(globalThis, 'MouseEvent')) {
28
- targetEvents.set(MouseEvent.prototype, [
29
- 'relatedTarget',
30
- 'fromElement',
31
- 'toElement',
32
- ]);
33
- }
34
- if ((0, utils_1.hasProperty)(globalThis, 'TouchEvent')) {
35
- targetEvents.set(TouchEvent.prototype, ['targetTouches', 'touches']);
36
- }
37
- if ((0, utils_1.hasProperty)(globalThis, 'Event')) {
38
- targetEvents.set(Event.prototype, [
39
- 'target',
40
- 'currentTarget',
41
- 'srcElement',
42
- 'composedPath',
43
- ]);
44
- }
45
- /**
46
- * Attenuate Event objects by replacing its own properties.
47
- */
48
- function executeLockdownEvents() {
49
- targetEvents.forEach((properties, prototype) => {
50
- for (const property of properties) {
51
- Object.defineProperty(prototype, property, {
52
- value: undefined,
53
- configurable: false,
54
- writable: false,
55
- });
56
- }
57
- });
58
- }
59
- exports.executeLockdownEvents = executeLockdownEvents;
60
- //# sourceMappingURL=lockdown-events.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"lockdown-events.js","sourceRoot":"","sources":["../../../src/common/lockdown/lockdown-events.ts"],"names":[],"mappings":";;;AAAA,iEAAiE;AACjE,2EAA2E;AAC3E,wCAAwC;AACxC,2CAA8C;AAE9C;;;;;GAKG;AACH,MAAM,YAAY,GAAG,IAAI,GAAG,EAAE,CAAC;AAC/B,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,SAAS,CAAC,EAAE;IACtC,YAAY,CAAC,GAAG,CAAC,OAAO,CAAC,SAAS,EAAE,CAAC,MAAM,CAAC,CAAC,CAAC;CAC/C;AACD,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,eAAe,CAAC,EAAE;IAC5C,YAAY,CAAC,GAAG,CAAC,aAAa,CAAC,SAAS,EAAE,CAAC,aAAa,CAAC,CAAC,CAAC;CAC5D;AACD,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,cAAc,CAAC,EAAE;IAC3C,YAAY,CAAC,GAAG,CAAC,YAAY,CAAC,SAAS,EAAE,CAAC,QAAQ,CAAC,CAAC,CAAC;CACtD;AACD,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,YAAY,CAAC,EAAE;IACzC,YAAY,CAAC,GAAG,CAAC,UAAU,CAAC,SAAS,EAAE,CAAC,eAAe,CAAC,CAAC,CAAC;CAC3D;AACD,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,YAAY,CAAC,EAAE;IACzC,YAAY,CAAC,GAAG,CAAC,UAAU,CAAC,SAAS,EAAE;QACrC,eAAe;QACf,aAAa;QACb,WAAW;KACZ,CAAC,CAAC;CACJ;AACD,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,YAAY,CAAC,EAAE;IACzC,YAAY,CAAC,GAAG,CAAC,UAAU,CAAC,SAAS,EAAE,CAAC,eAAe,EAAE,SAAS,CAAC,CAAC,CAAC;CACtE;AACD,IAAI,IAAA,mBAAW,EAAC,UAAU,EAAE,OAAO,CAAC,EAAE;IACpC,YAAY,CAAC,GAAG,CAAC,KAAK,CAAC,SAAS,EAAE;QAChC,QAAQ;QACR,eAAe;QACf,YAAY;QACZ,cAAc;KACf,CAAC,CAAC;CACJ;AAED;;GAEG;AACH,SAAgB,qBAAqB;IACnC,YAAY,CAAC,OAAO,CAAC,CAAC,UAAU,EAAE,SAAS,EAAE,EAAE;QAC7C,KAAK,MAAM,QAAQ,IAAI,UAAU,EAAE;YACjC,MAAM,CAAC,cAAc,CAAC,SAAS,EAAE,QAAQ,EAAE;gBACzC,KAAK,EAAE,SAAS;gBAChB,YAAY,EAAE,KAAK;gBACnB,QAAQ,EAAE,KAAK;aAChB,CAAC,CAAC;SACJ;IACH,CAAC,CAAC,CAAC;AACL,CAAC;AAVD,sDAUC","sourcesContent":["// When creating a sandbox, limitation of the events from leaking\n// sensitive objects is required. This is done by overriding own properties\n// of prototypes of all existing events.\nimport { hasProperty } from '@metamask/utils';\n\n/**\n * Targeted Event objects and properties.\n * Note: This is a map of the prototypes that inherit from Events with\n * properties that are identified to leak sensitive objects.\n * Not all browsers support all event types, so checking its existence is required.\n */\nconst targetEvents = new Map();\nif (hasProperty(globalThis, 'UIEvent')) {\n targetEvents.set(UIEvent.prototype, ['view']);\n}\nif (hasProperty(globalThis, 'MutationEvent')) {\n targetEvents.set(MutationEvent.prototype, ['relatedNode']);\n}\nif (hasProperty(globalThis, 'MessageEvent')) {\n targetEvents.set(MessageEvent.prototype, ['source']);\n}\nif (hasProperty(globalThis, 'FocusEvent')) {\n targetEvents.set(FocusEvent.prototype, ['relatedTarget']);\n}\nif (hasProperty(globalThis, 'MouseEvent')) {\n targetEvents.set(MouseEvent.prototype, [\n 'relatedTarget',\n 'fromElement',\n 'toElement',\n ]);\n}\nif (hasProperty(globalThis, 'TouchEvent')) {\n targetEvents.set(TouchEvent.prototype, ['targetTouches', 'touches']);\n}\nif (hasProperty(globalThis, 'Event')) {\n targetEvents.set(Event.prototype, [\n 'target',\n 'currentTarget',\n 'srcElement',\n 'composedPath',\n ]);\n}\n\n/**\n * Attenuate Event objects by replacing its own properties.\n */\nexport function executeLockdownEvents() {\n targetEvents.forEach((properties, prototype) => {\n for (const property of properties) {\n Object.defineProperty(prototype, property, {\n value: undefined,\n configurable: false,\n writable: false,\n });\n }\n });\n}\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"lockdown-more.js","sourceRoot":"","sources":["../../../src/common/lockdown/lockdown-more.ts"],"names":[],"mappings":";AAAA,qFAAqF;AACrF,mEAAmE;;;AAEnE,uDAAiD;AAEjD;;;;;;;;;;;;;;;;;;;GAmBG;AACH,SAAgB,mBAAmB;IACjC,gEAAgE;IAChE,oDAAoD;IACpD,gEAAgE;IAChE,oBAAoB;IACpB,IAAI;QACF,MAAM,eAAe,GAAG,OAAO,CAAC,OAAO,CAAC,IAAI,WAAW,EAAE,CAAC,UAAU,CAAC,CAAC;QAEtE,sEAAsE;QACtE,MAAM,oBAAoB,GAAG,IAAI,GAAG,CAAkB,CAAC,MAAM,EAAE,UAAU,CAAC,CAAC,CAAC;QAE5E,MAAM,gBAAgB,GAAG,IAAI,GAAG,CAAC;YAC/B,yEAAyE;YACzE,oEAAoE;YACpE,8CAA8C;YAC9C,GAAG,eAAe;YAElB,gDAAgD;YAChD,sDAAsD;YACtD,8BAA8B;SAC/B,CAAC,CAAC;QAEH,gBAAgB,CAAC,OAAO,CAAC,CAAC,YAAY,EAAE,EAAE;YACxC,MAAM,UAAU,GAAG,OAAO,CAAC,wBAAwB,CACjD,UAAU,EACV,YAAY,CACb,CAAC;YAEF,IAAI,UAAU,EAAE;gBACd,IAAI,UAAU,CAAC,YAAY,EAAE;oBAC3B,yDAAyD;oBACzD,mEAAmE;oBACnE,gBAAgB;oBAChB,IAAI,WAAW,CAAC,UAAU,CAAC,EAAE;wBAC3B,MAAM,CAAC,cAAc,CAAC,UAAU,EAAE,YAAY,EAAE;4BAC9C,YAAY,EAAE,KAAK;yBACpB,CAAC,CAAC;qBACJ;yBAAM;wBACL,MAAM,CAAC,cAAc,CAAC,UAAU,EAAE,YAAY,EAAE;4BAC9C,YAAY,EAAE,KAAK;4BACnB,QAAQ,EAAE,KAAK;yBAChB,CAAC,CAAC;qBACJ;iBACF;gBAED,IAAI,oBAAoB,CAAC,GAAG,CAAC,YAAY,CAAC,EAAE;oBAC1C,MAAM,CAAE,UAAkB,CAAC,YAAY,CAAC,CAAC,CAAC;iBAC3C;aACF;QACH,CAAC,CAAC,CAAC;KACJ;IAAC,OAAO,KAAK,EAAE;QACd,IAAA,sBAAQ,EAAC,+BAA+B,EAAE,KAAK,CAAC,CAAC;QACjD,MAAM,KAAK,CAAC;KACb;AACH,CAAC;AAtDD,kDAsDC;AAED;;;;;;;;;GASG;AACH,SAAS,WAAW,CAAC,UAAe;IAClC,OAAO,KAAK,IAAI,UAAU,IAAI,KAAK,IAAI,UAAU,CAAC;AACpD,CAAC","sourcesContent":["// eslint-disable-next-line @typescript-eslint/triple-slash-reference, spaced-comment\n/// <reference path=\"../../../../../node_modules/ses/types.d.ts\" />\n\nimport { logError } from '@metamask/snaps-utils';\n\n/**\n * The SES `lockdown` function only hardens the properties enumerated by the\n * universalPropertyNames constant specified in 'ses/src/whitelist'. This\n * function makes all function and object properties on the start compartment\n * global non-configurable and non-writable, unless they are already\n * non-configurable.\n *\n * It is critical that this function runs at the right time during\n * initialization, which should always be immediately after `lockdown` has been\n * called. At the time of writing, the modifications this function makes to the\n * runtime environment appear to be non-breaking, but that could change with\n * the addition of dependencies, or the order of our scripts in our HTML files.\n * Exercise caution.\n *\n * See inline comments for implementation details.\n *\n * We write this function in IIFE format to avoid polluting global scope.\n *\n * @throws If the lockdown failed.\n */\nexport function executeLockdownMore() {\n // Make all \"object\" and \"function\" own properties of globalThis\n // non-configurable and non-writable, when possible.\n // We call a property that is non-configurable and non-writable,\n // \"non-modifiable\".\n try {\n const namedIntrinsics = Reflect.ownKeys(new Compartment().globalThis);\n\n // These named intrinsics are not automatically hardened by `lockdown`\n const shouldHardenManually = new Set<symbol | string>(['eval', 'Function']);\n\n const globalProperties = new Set([\n // universalPropertyNames is a constant added by lockdown to global scope\n // at the time of writing, it is initialized in 'ses/src/whitelist'.\n // These properties tend to be non-enumerable.\n ...namedIntrinsics,\n\n // TODO: Also include the named platform globals\n // This grabs every enumerable property on globalThis.\n // ...Object.keys(globalThis),\n ]);\n\n globalProperties.forEach((propertyName) => {\n const descriptor = Reflect.getOwnPropertyDescriptor(\n globalThis,\n propertyName,\n );\n\n if (descriptor) {\n if (descriptor.configurable) {\n // If the property on globalThis is configurable, make it\n // non-configurable. If it has no accessor properties, also make it\n // non-writable.\n if (hasAccessor(descriptor)) {\n Object.defineProperty(globalThis, propertyName, {\n configurable: false,\n });\n } else {\n Object.defineProperty(globalThis, propertyName, {\n configurable: false,\n writable: false,\n });\n }\n }\n\n if (shouldHardenManually.has(propertyName)) {\n harden((globalThis as any)[propertyName]);\n }\n }\n });\n } catch (error) {\n logError('Protecting intrinsics failed:', error);\n throw error;\n }\n}\n\n/**\n * Checks whether the given propertyName descriptor has any accessors, i.e. the\n * properties `get` or `set`.\n *\n * We want to make globals non-writable, and we can't set the `writable`\n * property and accessor properties at the same time.\n *\n * @param descriptor - The propertyName descriptor to check.\n * @returns Whether the propertyName descriptor has any accessors.\n */\nfunction hasAccessor(descriptor: any): boolean {\n return 'set' in descriptor || 'get' in descriptor;\n}\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"lockdown.js","sourceRoot":"","sources":["../../../src/common/lockdown/lockdown.ts"],"names":[],"mappings":";AAAA,qFAAqF;AACrF,mEAAmE;;;AAEnE,uDAAiD;AAEjD;;;;GAIG;AACH,SAAgB,eAAe;IAC7B,IAAI;QACF,QAAQ,CAAC;YACP,aAAa,EAAE,QAAQ;YACvB,WAAW,EAAE,QAAQ;YACrB,UAAU,EAAE,QAAQ;YACpB,UAAU,EAAE,QAAQ;YACpB,cAAc,EAAE,QAAQ;SACzB,CAAC,CAAC;KACJ;IAAC,OAAO,KAAK,EAAE;QACd,gFAAgF;QAChF,IAAA,sBAAQ,EAAC,kBAAkB,EAAE,KAAK,CAAC,CAAC;QACpC,MAAM,KAAK,CAAC;KACb;AACH,CAAC;AAdD,0CAcC","sourcesContent":["// eslint-disable-next-line @typescript-eslint/triple-slash-reference, spaced-comment\n/// <reference path=\"../../../../../node_modules/ses/types.d.ts\" />\n\nimport { logError } from '@metamask/snaps-utils';\n\n/**\n * Execute SES lockdown in the current context, i.e., the current iframe.\n *\n * @throws If the SES lockdown failed.\n */\nexport function executeLockdown() {\n try {\n lockdown({\n consoleTaming: 'unsafe',\n errorTaming: 'unsafe',\n mathTaming: 'unsafe',\n dateTaming: 'unsafe',\n overrideTaming: 'severe',\n });\n } catch (error) {\n // If the `lockdown` call throws an exception, it should not be able to continue\n logError('Lockdown failed:', error);\n throw error;\n }\n}\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"sortParams.js","sourceRoot":"","sources":["../../src/common/sortParams.ts"],"names":[],"mappings":";AAAA,8IAA8I;;;AAI9I;;;;;;;;;;;;;GAaG;AACI,MAAM,aAAa,GAAG,CAC3B,YAAsB,EACtB,MAAsB,EACtB,EAAE;IACF,IAAI,CAAC,MAAM,EAAE;QACX,OAAO,EAAE,CAAC;KACX;IAED,IAAI,MAAM,YAAY,KAAK,EAAE;QAC3B,OAAO,MAAM,CAAC;KACf;IAED,MAAM,iBAAiB,GAA4B,YAAY,CAAC,MAAM,CACpE,CAAC,cAAc,EAAE,UAAU,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC;QAClC,GAAG,cAAc;QACjB,CAAC,UAAU,CAAC,EAAE,CAAC;KAChB,CAAC,EACF,EAAE,CACH,CAAC;IAEF,OAAO,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC;SAC1B,IAAI,CACH,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,EAAE,CAAC,KAAK,EAAE,EAAE,CAAC,EAAE,EAAE,CAC3B,iBAAiB,CAAC,KAAK,CAAC,GAAG,iBAAiB,CAAC,KAAK,CAAC,CACtD;SACA,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,GAAG,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,CAAC;AAC5B,CAAC,CAAC;AA1BW,QAAA,aAAa,iBA0BxB","sourcesContent":["// original source sortParamKeys from: https://github.com/etclabscore/sig.tools/blob/master/src/postMessageServer/postMessageServer.ts#L75-L77\n\nimport { JsonRpcParams } from '@metamask/utils';\n\n/**\n * Deterministically sort JSON-RPC parameter keys. This makes it possible to\n * support both arrays and objects as parameters. Objects are sorted and turned\n * into arrays, for easier consumption by the snap.\n *\n * The order is defined by the `method` parameter.\n *\n * @param methodParams - The parameters of the JSON-RPC method, which\n * determines the ordering for the parameters.\n * @param params - JSON-RPC parameters as object or array.\n * @returns The values for the sorted keys. If `params` is not provided, this\n * returns an empty array. If `params` is an array, this returns the same\n * `params`.\n */\nexport const sortParamKeys = (\n methodParams: string[],\n params?: JsonRpcParams,\n) => {\n if (!params) {\n return [];\n }\n\n if (params instanceof Array) {\n return params;\n }\n\n const methodParamsOrder: { [k: string]: number } = methodParams.reduce(\n (paramsOrderObj, paramsName, i) => ({\n ...paramsOrderObj,\n [paramsName]: i,\n }),\n {},\n );\n\n return Object.entries(params)\n .sort(\n ([name1, _1], [name2, _2]) =>\n methodParamsOrder[name1] - methodParamsOrder[name2],\n )\n .map(([_, val]) => val);\n};\n"]}
@@ -1 +0,0 @@
1
- {"version":3,"file":"utils.js","sourceRoot":"","sources":["../../src/common/utils.ts"],"names":[],"mappings":"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","sourcesContent":["import { StreamProvider } from '@metamask/providers';\nimport { RequestArguments } from '@metamask/providers/dist/BaseProvider';\nimport { assert, assertStruct, JsonStruct } from '@metamask/utils';\nimport { ethErrors } from 'eth-rpc-errors';\n\nimport { log } from '../logging';\n\n/**\n * Takes an error that was thrown, determines if it is\n * an error object. If it is then it will return that. Otherwise,\n * an error object is created with the original error message.\n *\n * @param originalError - The error that was originally thrown.\n * @returns An error object.\n */\nexport function constructError(originalError: unknown) {\n let _originalError: Error | undefined;\n if (originalError instanceof Error) {\n _originalError = originalError;\n } else if (typeof originalError === 'string') {\n _originalError = new Error(originalError);\n // The stack is useless in this case.\n delete _originalError.stack;\n }\n return _originalError;\n}\n\n/**\n * Make proxy for Promise and handle the teardown process properly.\n * If the teardown is called in the meanwhile, Promise result will not be\n * exposed to the snap anymore and warning will be logged to the console.\n *\n * @param originalPromise - Original promise.\n * @param teardownRef - Reference containing teardown count.\n * @param teardownRef.lastTeardown - Number of the last teardown.\n * @returns New proxy promise.\n */\nexport async function withTeardown<T>(\n originalPromise: Promise<T>,\n teardownRef: { lastTeardown: number },\n): Promise<T> {\n const myTeardown = teardownRef.lastTeardown;\n return new Promise<T>((resolve, reject) => {\n originalPromise\n .then((value) => {\n if (teardownRef.lastTeardown === myTeardown) {\n resolve(value);\n } else {\n log(\n 'Late promise received after Snap finished execution. Promise will be dropped.',\n );\n }\n })\n .catch((reason) => {\n if (teardownRef.lastTeardown === myTeardown) {\n reject(reason);\n } else {\n log(\n 'Late promise received after Snap finished execution. Promise will be dropped.',\n );\n }\n });\n });\n}\n\n/**\n * Returns a Proxy that narrows down (attenuates) the fields available on\n * the StreamProvider and replaces the request implementation.\n *\n * @param provider - Instance of a StreamProvider to be limited.\n * @param request - Custom attenuated request object.\n * @returns Proxy to the StreamProvider instance.\n */\nexport function proxyStreamProvider(\n provider: StreamProvider,\n request: unknown,\n): StreamProvider {\n // Proxy target is intentionally set to be an empty object, to ensure\n // that access to the prototype chain is not possible.\n const proxy = new Proxy(\n {},\n {\n has(_target: object, prop: string | symbol) {\n return (\n typeof prop === 'string' &&\n ['request', 'on', 'removeListener'].includes(prop)\n );\n },\n get(_target, prop: keyof StreamProvider) {\n if (prop === 'request') {\n return request;\n } else if (['on', 'removeListener'].includes(prop)) {\n return provider[prop];\n }\n\n return undefined;\n },\n },\n );\n\n return proxy as StreamProvider;\n}\n\n// We're blocking these RPC methods for v1, will revisit later.\nconst BLOCKED_RPC_METHODS = Object.freeze([\n 'wallet_requestSnaps',\n 'wallet_requestPermissions',\n // We disallow all of these confirmations for now, since the screens are not ready for Snaps.\n 'eth_sendRawTransaction',\n 'eth_sendTransaction',\n 'eth_sign',\n 'eth_signTypedData',\n 'eth_signTypedData_v1',\n 'eth_signTypedData_v3',\n 'eth_signTypedData_v4',\n 'eth_decrypt',\n 'eth_getEncryptionPublicKey',\n 'wallet_addEthereumChain',\n 'wallet_switchEthereumChain',\n 'wallet_watchAsset',\n 'wallet_registerOnboarding',\n 'wallet_scanQRCode',\n]);\n\n/**\n * Asserts the validity of request arguments for a snap outbound request using the `snap.request` API.\n *\n * @param args - The arguments to validate.\n */\nexport function assertSnapOutboundRequest(args: RequestArguments) {\n // Disallow any non `wallet_` or `snap_` methods for separation of concerns.\n assert(\n String.prototype.startsWith.call(args.method, 'wallet_') ||\n String.prototype.startsWith.call(args.method, 'snap_'),\n 'The global Snap API only allows RPC methods starting with `wallet_*` and `snap_*`.',\n );\n assert(\n !BLOCKED_RPC_METHODS.includes(args.method),\n ethErrors.rpc.methodNotFound({\n data: {\n method: args.method,\n },\n }),\n );\n assertStruct(args, JsonStruct, 'Provided value is not JSON-RPC compatible');\n}\n\n/**\n * Asserts the validity of request arguments for an ethereum outbound request using the `ethereum.request` API.\n *\n * @param args - The arguments to validate.\n */\nexport function assertEthereumOutboundRequest(args: RequestArguments) {\n // Disallow snaps methods for separation of concerns.\n assert(\n !String.prototype.startsWith.call(args.method, 'snap_'),\n ethErrors.rpc.methodNotFound({\n data: {\n method: args.method,\n },\n }),\n );\n assert(\n !BLOCKED_RPC_METHODS.includes(args.method),\n ethErrors.rpc.methodNotFound({\n data: {\n method: args.method,\n },\n }),\n );\n assertStruct(args, JsonStruct, 'Provided value is not JSON-RPC compatible');\n}\n"]}