@metamask/snaps-cli 0.15.0 → 0.16.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.
- package/CHANGELOG.md +11 -1
- package/README.md +2 -2
- package/dist/cmds/build/bundle.d.ts +1 -0
- package/dist/cmds/build/bundle.js +8 -2
- package/dist/cmds/build/bundle.js.map +1 -1
- package/dist/cmds/eval/eval-worker.js +11 -3
- package/dist/cmds/eval/eval-worker.js.map +1 -1
- package/dist/cmds/eval/mock.js +0 -1
- package/dist/cmds/eval/mock.js.map +1 -1
- package/dist/cmds/init/init-template.json +1 -1
- package/dist/utils/snap-config.d.ts +1 -0
- package/package.json +8 -7
package/CHANGELOG.md
CHANGED
|
@@ -6,6 +6,15 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
6
6
|
|
|
7
7
|
## [Unreleased]
|
|
8
8
|
|
|
9
|
+
## [0.16.0]
|
|
10
|
+
### Changed
|
|
11
|
+
- **BREAKING:** Snaps are now required to export `onRpcRequest` to receive RPC requests ([#481](https://github.com/MetaMask/snaps-skunkworks/pull/481), [#533](https://github.com/MetaMask/snaps-skunkworks/pull/533), [#538](https://github.com/MetaMask/snaps-skunkworks/pull/538), [#541](https://github.com/MetaMask/snaps-skunkworks/pull/541), [#544](https://github.com/MetaMask/snaps-skunkworks/pull/544))
|
|
12
|
+
- The type of the function is available in `@metamask/snap-types` as `OnRpcRequestHandler`.
|
|
13
|
+
|
|
14
|
+
### Fixed
|
|
15
|
+
- Fix importing local files in TypeScript Snaps ([#527](https://github.com/MetaMask/snaps-skunkworks/pull/527))
|
|
16
|
+
- Fix `build` command when the CLI is installed globally ([#542](https://github.com/MetaMask/snaps-skunkworks/pull/542))
|
|
17
|
+
|
|
9
18
|
## [0.15.0]
|
|
10
19
|
### Added
|
|
11
20
|
- Add support for building TypeScript Snaps ([#443](https://github.com/MetaMask/snaps-skunkworks/pull/443))
|
|
@@ -185,7 +194,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
185
194
|
- Example snaps ([#72](https://github.com/MetaMask/snaps-skunkworks/pull/72))
|
|
186
195
|
- The examples now live in their own package, [`@metamask/snap-examples`](https://npmjs.com/package/@metamask/snap-examples).
|
|
187
196
|
|
|
188
|
-
[Unreleased]: https://github.com/MetaMask/snaps-skunkworks/compare/v0.
|
|
197
|
+
[Unreleased]: https://github.com/MetaMask/snaps-skunkworks/compare/v0.16.0...HEAD
|
|
198
|
+
[0.16.0]: https://github.com/MetaMask/snaps-skunkworks/compare/v0.15.0...v0.16.0
|
|
189
199
|
[0.15.0]: https://github.com/MetaMask/snaps-skunkworks/compare/v0.14.0...v0.15.0
|
|
190
200
|
[0.14.0]: https://github.com/MetaMask/snaps-skunkworks/compare/v0.13.0...v0.14.0
|
|
191
201
|
[0.13.0]: https://github.com/MetaMask/snaps-skunkworks/compare/v0.12.0...v0.13.0
|
package/README.md
CHANGED
|
@@ -112,7 +112,7 @@ The defaults can be overwritten using the `snap.config.json` [config file](#conf
|
|
|
112
112
|
|
|
113
113
|
### Configuration File
|
|
114
114
|
|
|
115
|
-
`snap.config.js`
|
|
115
|
+
`snap.config.js` should be placed in the project root directory. It can override cli options - the property `cliOptions` should have string keys matching command arguments. Values become argument defaults, which can still be overridden on the command line.
|
|
116
116
|
|
|
117
117
|
Example:
|
|
118
118
|
|
|
@@ -126,7 +126,7 @@ module.exports = {
|
|
|
126
126
|
};
|
|
127
127
|
```
|
|
128
128
|
|
|
129
|
-
|
|
129
|
+
If you want to customize the Browserify build process, you can provide `bundlerCustomizer` property. It's a function that takes one argument - [browserify object](https://github.com/browserify/browserify#api-example) which we use internally to bundle the snap. You can transform it in any way you want, for example adding plugins.
|
|
130
130
|
|
|
131
131
|
Example:
|
|
132
132
|
|
|
@@ -5,6 +5,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
6
|
exports.bundle = void 0;
|
|
7
7
|
const browserify_1 = __importDefault(require("browserify"));
|
|
8
|
+
const snaps_browserify_plugin_1 = __importDefault(require("@metamask/snaps-browserify-plugin"));
|
|
8
9
|
const builders_1 = require("../../builders");
|
|
9
10
|
const utils_1 = require("./utils");
|
|
10
11
|
// We need to statically import all Browserify transforms and all Babel presets
|
|
@@ -25,7 +26,12 @@ function bundle(src, dest, argv, bundlerTransform) {
|
|
|
25
26
|
const { sourceMaps: debug, transpilationMode } = argv;
|
|
26
27
|
const babelifyOptions = (0, utils_1.processDependencies)(argv);
|
|
27
28
|
return new Promise((resolve, _reject) => {
|
|
28
|
-
const bundler = (0, browserify_1.default)(src, {
|
|
29
|
+
const bundler = (0, browserify_1.default)(src, {
|
|
30
|
+
debug,
|
|
31
|
+
extensions: ['.js', '.ts'],
|
|
32
|
+
// Standalone is required to properly support Snaps using module.exports
|
|
33
|
+
standalone: '<snap>',
|
|
34
|
+
});
|
|
29
35
|
if (transpilationMode !== builders_1.TranspilationModes.none) {
|
|
30
36
|
bundler.transform(require('babelify'), {
|
|
31
37
|
global: transpilationMode === builders_1.TranspilationModes.localAndDeps,
|
|
@@ -52,7 +58,7 @@ function bundle(src, dest, argv, bundlerTransform) {
|
|
|
52
58
|
});
|
|
53
59
|
}
|
|
54
60
|
bundlerTransform?.(bundler);
|
|
55
|
-
bundler.plugin(
|
|
61
|
+
bundler.plugin(snaps_browserify_plugin_1.default, {
|
|
56
62
|
stripComments: argv.stripComments,
|
|
57
63
|
transformHtmlComments: argv.transformHtmlComments,
|
|
58
64
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bundle.js","sourceRoot":"","sources":["../../../src/cmds/build/bundle.ts"],"names":[],"mappings":";;;;;;AAAA,4DAA0D;AAC1D,6CAAoD;AAEpD,mCAA+D;AAE/D,+EAA+E;AAC/E,mEAAmE;AACnE,mHAAmH;AAEnH;;;;;;;;;;GAUG;AACH,SAAgB,MAAM,CACpB,GAAW,EACX,IAAY,EACZ,IAAe,EACf,gBAAsD;IAEtD,MAAM,EAAE,UAAU,EAAE,KAAK,EAAE,iBAAiB,EAAE,GAAG,IAAI,CAAC;IACtD,MAAM,eAAe,GAAG,IAAA,2BAAmB,EAAC,IAAW,CAAC,CAAC;IACzD,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,OAAO,EAAE,EAAE;QACtC,MAAM,OAAO,GAAG,IAAA,oBAAU,EAAC,GAAG,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"bundle.js","sourceRoot":"","sources":["../../../src/cmds/build/bundle.ts"],"names":[],"mappings":";;;;;;AAAA,4DAA0D;AAC1D,gGAAuD;AACvD,6CAAoD;AAEpD,mCAA+D;AAE/D,+EAA+E;AAC/E,mEAAmE;AACnE,mHAAmH;AAEnH;;;;;;;;;;GAUG;AACH,SAAgB,MAAM,CACpB,GAAW,EACX,IAAY,EACZ,IAAe,EACf,gBAAsD;IAEtD,MAAM,EAAE,UAAU,EAAE,KAAK,EAAE,iBAAiB,EAAE,GAAG,IAAI,CAAC;IACtD,MAAM,eAAe,GAAG,IAAA,2BAAmB,EAAC,IAAW,CAAC,CAAC;IACzD,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,OAAO,EAAE,EAAE;QACtC,MAAM,OAAO,GAAG,IAAA,oBAAU,EAAC,GAAG,EAAE;YAC9B,KAAK;YACL,UAAU,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC;YAC1B,wEAAwE;YACxE,UAAU,EAAE,QAAQ;SACrB,CAAC,CAAC;QAEH,IAAI,iBAAiB,KAAK,6BAAkB,CAAC,IAAI,EAAE;YACjD,OAAO,CAAC,SAAS,CAAC,OAAO,CAAC,UAAU,CAAC,EAAE;gBACrC,MAAM,EAAE,iBAAiB,KAAK,6BAAkB,CAAC,YAAY;gBAC7D,UAAU,EAAE,CAAC,KAAK,EAAE,KAAK,CAAC;gBAC1B,OAAO,EAAE;oBACP,OAAO,CAAC,0BAA0B,CAAC;oBACnC;wBACE,OAAO,CAAC,mBAAmB,CAAC;wBAC5B;4BACE,OAAO,EAAE;gCACP,QAAQ,EAAE,CAAC,cAAc,EAAE,eAAe,CAAC;6BAC5C;yBACF;qBACF;iBACF;gBACD,OAAO,EAAE;oBACP,OAAO,CAAC,iCAAiC,CAAC;oBAC1C,OAAO,CAAC,yCAAyC,CAAC;oBAClD,OAAO,CAAC,2CAA2C,CAAC;oBACpD,OAAO,CAAC,0CAA0C,CAAC;oBACnD,OAAO,CAAC,oDAAoD,CAAC;iBAC9D;gBACD,GAAI,eAAuB;aAC5B,CAAC,CAAC;SACJ;QAED,gBAAgB,EAAE,CAAC,OAAO,CAAC,CAAC;QAE5B,OAAO,CAAC,MAAM,CAAC,iCAAM,EAAE;YACrB,aAAa,EAAE,IAAI,CAAC,aAAa;YACjC,qBAAqB,EAAE,IAAI,CAAC,qBAAqB;SAClD,CAAC,CAAC;QAEH,OAAO,CAAC,MAAM,CACZ,KAAK,EAAE,WAAW,EAAE,YAAoB,EAAE,EAAE,CAC1C,MAAM,IAAA,uBAAe,EAAC;YACpB,WAAW;YACX,YAAY;YACZ,GAAG;YACH,IAAI;YACJ,OAAO;SACR,CAAC,CACL,CAAC;IACJ,CAAC,CAAC,CAAC;AACL,CAAC;AA5DD,wBA4DC","sourcesContent":["import browserify, { BrowserifyObject } from 'browserify';\nimport plugin from '@metamask/snaps-browserify-plugin';\nimport { TranspilationModes } from '../../builders';\nimport { YargsArgs } from '../../types/yargs';\nimport { processDependencies, writeBundleFile } from './utils';\n\n// We need to statically import all Browserify transforms and all Babel presets\n// and plugins, and calling `require` is the sanest way to do that.\n/* eslint-disable @typescript-eslint/no-require-imports, @typescript-eslint/no-var-requires, node/global-require */\n\n/**\n * Builds a Snap bundle JS file from its JavaScript source.\n *\n * @param src - The source file path.\n * @param dest - The destination file path.\n * @param argv - arguments as an object generated by yargs.\n * @param argv.sourceMaps - Whether to output sourcemaps.\n * @param argv.stripComments - Whether to remove comments from code.\n * @param argv.transpilationMode - The Babel transpilation mode.\n * @param bundlerTransform\n */\nexport function bundle(\n src: string,\n dest: string,\n argv: YargsArgs,\n bundlerTransform?: (bundler: BrowserifyObject) => void,\n): Promise<boolean> {\n const { sourceMaps: debug, transpilationMode } = argv;\n const babelifyOptions = processDependencies(argv as any);\n return new Promise((resolve, _reject) => {\n const bundler = browserify(src, {\n debug,\n extensions: ['.js', '.ts'],\n // Standalone is required to properly support Snaps using module.exports\n standalone: '<snap>',\n });\n\n if (transpilationMode !== TranspilationModes.none) {\n bundler.transform(require('babelify'), {\n global: transpilationMode === TranspilationModes.localAndDeps,\n extensions: ['.js', '.ts'],\n presets: [\n require('@babel/preset-typescript'),\n [\n require('@babel/preset-env'),\n {\n targets: {\n browsers: ['chrome >= 66', 'firefox >= 68'],\n },\n },\n ],\n ],\n plugins: [\n require('@babel/plugin-transform-runtime'),\n require('@babel/plugin-proposal-class-properties'),\n require('@babel/plugin-proposal-object-rest-spread'),\n require('@babel/plugin-proposal-optional-chaining'),\n require('@babel/plugin-proposal-nullish-coalescing-operator'),\n ],\n ...(babelifyOptions as any),\n });\n }\n\n bundlerTransform?.(bundler);\n\n bundler.plugin(plugin, {\n stripComments: argv.stripComments,\n transformHtmlComments: argv.transformHtmlComments,\n });\n\n bundler.bundle(\n async (bundleError, bundleBuffer: Buffer) =>\n await writeBundleFile({\n bundleError,\n bundleBuffer,\n src,\n dest,\n resolve,\n }),\n );\n });\n}\n"]}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
const worker_threads_1 = require("worker_threads");
|
|
4
3
|
const fs_1 = require("fs");
|
|
5
|
-
const mock_1 = require("./mock");
|
|
6
4
|
// eslint-disable-next-line import/no-unassigned-import
|
|
7
5
|
require("ses/lockdown");
|
|
6
|
+
const worker_threads_1 = require("worker_threads");
|
|
7
|
+
const mock_1 = require("./mock");
|
|
8
8
|
lockdown({
|
|
9
9
|
consoleTaming: 'unsafe',
|
|
10
10
|
errorTaming: 'unsafe',
|
|
@@ -15,7 +15,15 @@ lockdown({
|
|
|
15
15
|
if (worker_threads_1.parentPort !== null) {
|
|
16
16
|
worker_threads_1.parentPort.on('message', (message) => {
|
|
17
17
|
const { snapFilePath } = message;
|
|
18
|
-
|
|
18
|
+
const snapModule = { exports: {} };
|
|
19
|
+
new Compartment({
|
|
20
|
+
...getMockEndowments(),
|
|
21
|
+
module: snapModule,
|
|
22
|
+
exports: snapModule.exports,
|
|
23
|
+
}).evaluate((0, fs_1.readFileSync)(snapFilePath, 'utf8'));
|
|
24
|
+
if (!snapModule.exports?.onRpcRequest) {
|
|
25
|
+
console.warn("The Snap doesn't have onRpcRequest export defined");
|
|
26
|
+
}
|
|
19
27
|
setTimeout(() => process.exit(0), 1000); // Hack to ensure worker exits
|
|
20
28
|
});
|
|
21
29
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"eval-worker.js","sourceRoot":"","sources":["../../../src/cmds/eval/eval-worker.ts"],"names":[],"mappings":";;AAAA,
|
|
1
|
+
{"version":3,"file":"eval-worker.js","sourceRoot":"","sources":["../../../src/cmds/eval/eval-worker.ts"],"names":[],"mappings":";;AAAA,2BAAkC;AAClC,uDAAuD;AACvD,wBAAsB;AACtB,mDAA4C;AAC5C,iCAAgD;AAIhD,QAAQ,CAAC;IACP,aAAa,EAAE,QAAQ;IACvB,WAAW,EAAE,QAAQ;IACrB,UAAU,EAAE,QAAQ;IACpB,UAAU,EAAE,QAAQ;IACpB,cAAc,EAAE,QAAQ;CACzB,CAAC,CAAC;AAEH,IAAI,2BAAU,KAAK,IAAI,EAAE;IACvB,2BAAU,CAAC,EAAE,CAAC,SAAS,EAAE,CAAC,OAAiC,EAAE,EAAE;QAC7D,MAAM,EAAE,YAAY,EAAE,GAAG,OAAO,CAAC;QAEjC,MAAM,UAAU,GAAsB,EAAE,OAAO,EAAE,EAAE,EAAE,CAAC;QAEtD,IAAI,WAAW,CAAC;YACd,GAAG,iBAAiB,EAAE;YACtB,MAAM,EAAE,UAAU;YAClB,OAAO,EAAE,UAAU,CAAC,OAAO;SAC5B,CAAC,CAAC,QAAQ,CAAC,IAAA,iBAAY,EAAC,YAAY,EAAE,MAAM,CAAC,CAAC,CAAC;QAEhD,IAAI,CAAC,UAAU,CAAC,OAAO,EAAE,YAAY,EAAE;YACrC,OAAO,CAAC,IAAI,CAAC,mDAAmD,CAAC,CAAC;SACnE;QAED,UAAU,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,CAAC,8BAA8B;IACzE,CAAC,CAAC,CAAC;CACJ;AAED,SAAS,iBAAiB;IACxB,MAAM,UAAU,GAAG,IAAA,6BAAsB,GAAE,CAAC;IAC5C,OAAO;QACL,GAAG,UAAU;QACb,MAAM,EAAE,UAAU;QAClB,IAAI,EAAE,UAAU;KACjB,CAAC;AACJ,CAAC","sourcesContent":["import { readFileSync } from 'fs';\n// eslint-disable-next-line import/no-unassigned-import\nimport 'ses/lockdown';\nimport { parentPort } from 'worker_threads';\nimport { generateMockEndowments } from './mock';\n\ndeclare let lockdown: any, Compartment: any;\n\nlockdown({\n consoleTaming: 'unsafe',\n errorTaming: 'unsafe',\n mathTaming: 'unsafe',\n dateTaming: 'unsafe',\n overrideTaming: 'severe',\n});\n\nif (parentPort !== null) {\n parentPort.on('message', (message: { snapFilePath: string }) => {\n const { snapFilePath } = message;\n\n const snapModule: { exports?: any } = { exports: {} };\n\n new Compartment({\n ...getMockEndowments(),\n module: snapModule,\n exports: snapModule.exports,\n }).evaluate(readFileSync(snapFilePath, 'utf8'));\n\n if (!snapModule.exports?.onRpcRequest) {\n console.warn(\"The Snap doesn't have onRpcRequest export defined\");\n }\n\n setTimeout(() => process.exit(0), 1000); // Hack to ensure worker exits\n });\n}\n\nfunction getMockEndowments() {\n const endowments = generateMockEndowments();\n return {\n ...endowments,\n window: endowments,\n self: endowments,\n };\n}\n"]}
|
package/dist/cmds/eval/mock.js
CHANGED
|
@@ -11,7 +11,6 @@ const NETWORK_APIS = ['fetch', 'WebSocket'];
|
|
|
11
11
|
exports.ALL_APIS = [...snap_controllers_1.DEFAULT_ENDOWMENTS, ...NETWORK_APIS];
|
|
12
12
|
function getMockSnapProvider() {
|
|
13
13
|
const mockProvider = new events_1.default();
|
|
14
|
-
mockProvider.registerRpcMessageHandler = () => true;
|
|
15
14
|
mockProvider.request = async () => true;
|
|
16
15
|
return mockProvider;
|
|
17
16
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"mock.js","sourceRoot":"","sources":["../../../src/cmds/eval/mock.ts"],"names":[],"mappings":";;;;;;AAAA,oDAAkC;AAClC,oDAA4B;AAC5B,iEAAgE;AAEhE,MAAM,YAAY,GAAG,CAAC,OAAO,EAAE,WAAW,CAAC,CAAC;AAE/B,QAAA,QAAQ,GAAa,CAAC,GAAG,qCAAkB,EAAE,GAAG,YAAY,CAAC,CAAC;AAO3E,SAAS,mBAAmB;IAC1B,MAAM,YAAY,GAAG,IAAI,gBAAY,EAA+B,CAAC;IACrE,YAAY,CAAC,
|
|
1
|
+
{"version":3,"file":"mock.js","sourceRoot":"","sources":["../../../src/cmds/eval/mock.ts"],"names":[],"mappings":";;;;;;AAAA,oDAAkC;AAClC,oDAA4B;AAC5B,iEAAgE;AAEhE,MAAM,YAAY,GAAG,CAAC,OAAO,EAAE,WAAW,CAAC,CAAC;AAE/B,QAAA,QAAQ,GAAa,CAAC,GAAG,qCAAkB,EAAE,GAAG,YAAY,CAAC,CAAC;AAO3E,SAAS,mBAAmB;IAC1B,MAAM,YAAY,GAAG,IAAI,gBAAY,EAA+B,CAAC;IACrE,YAAY,CAAC,OAAO,GAAG,KAAK,IAAI,EAAE,CAAC,IAAI,CAAC;IACxC,OAAO,YAAgC,CAAC;AAC1C,CAAC;AAEM,MAAM,aAAa,GAAG,CAAC,KAAU,EAAE,EAAE,CAC1C,OAAO,CAAC,OAAO,KAAK,EAAE,SAAS,EAAE,WAAW,EAAE,IAAI,KAAK,QAAQ,CAAC,CAAC;AADtD,QAAA,aAAa,iBACyC;AAEnE,MAAM,YAAY,GAAG,GAAG,EAAE,CAAC,IAAI,CAAC;AAChC,MAAM,SAAS;CAAG;AAElB,MAAM,OAAO,GAAG;IACd,SAAS,CAAC,MAAW,EAAE,IAAW;QAChC,OAAO,IAAI,KAAK,CAAC,IAAI,MAAM,CAAC,GAAG,IAAI,CAAC,EAAE,OAAO,CAAC,CAAC;IACjD,CAAC;IACD,GAAG,CAAC,OAAY,EAAE,KAAU;QAC1B,OAAO,YAAY,CAAC;IACtB,CAAC;CACF,CAAC;AAEF,MAAM,iBAAiB,GAAG,CAAC,KAAU,EAAE,EAAE;IACvC,OAAO,IAAI,KAAK,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC;AACnC,CAAC,CAAC;AAEF,8IAA8I;AAC9I,MAAM,UAAU,GAAG;IACjB,SAAS,EAAE,SAAS;IACpB,MAAM,EAAN,gBAAM;IACN,YAAY,EAAE,SAAS;CACxB,CAAC;AAEF,MAAM,qBAAqB,GAAG,CAAC,GAAW,EAAE,EAAE;IAC5C,MAAM,WAAW,GAAI,UAAkB,CAAC,GAAG,CAAC,CAAC;IAE7C,+CAA+C;IAC/C,IAAI,WAAW,IAAI,qCAAkB,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE;QACnD,OAAO,WAAW,CAAC;KACpB;IAED,4EAA4E;IAC5E,MAAM,cAAc,GAAG,WAAW,IAAK,UAAkB,CAAC,GAAG,CAAC,CAAC;IAE/D,MAAM,IAAI,GAAG,OAAO,cAAc,CAAC;IACnC,MAAM,UAAU,GAAG,IAAI,KAAK,UAAU,CAAC;IACvC,IAAI,UAAU,IAAI,IAAA,qBAAa,EAAC,cAAc,CAAC,EAAE;QAC/C,OAAO,iBAAiB,CAAC,cAAc,CAAC,CAAC;KAC1C;SAAM,IAAI,UAAU,IAAI,CAAC,cAAc,EAAE;QACxC,qCAAqC;QACrC,OAAO,YAAY,CAAC;KACrB;IACD,OAAO,cAAc,CAAC;AACxB,CAAC,CAAC;AAEK,MAAM,sBAAsB,GAAG,GAAG,EAAE;IACzC,OAAO,gBAAQ,CAAC,MAAM,CACpB,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,CAAC,CAAC,EAAE,GAAG,GAAG,EAAE,CAAC,GAAG,CAAC,EAAE,qBAAqB,CAAC,GAAG,CAAC,EAAE,CAAC,EAC7D,EAAE,MAAM,EAAE,mBAAmB,EAAE,EAAE,CAClC,CAAC;AACJ,CAAC,CAAC;AALW,QAAA,sBAAsB,0BAKjC","sourcesContent":["import EventEmitter from 'events';\nimport crypto from 'crypto';\nimport { DEFAULT_ENDOWMENTS } from '@metamask/snap-controllers';\n\nconst NETWORK_APIS = ['fetch', 'WebSocket'];\n\nexport const ALL_APIS: string[] = [...DEFAULT_ENDOWMENTS, ...NETWORK_APIS];\n\ntype MockSnapProvider = EventEmitter & {\n registerRpcMessageHandler: () => any;\n request: () => Promise<any>;\n};\n\nfunction getMockSnapProvider(): MockSnapProvider {\n const mockProvider = new EventEmitter() as Partial<MockSnapProvider>;\n mockProvider.request = async () => true;\n return mockProvider as MockSnapProvider;\n}\n\nexport const isConstructor = (value: any) =>\n Boolean(typeof value?.prototype?.constructor?.name === 'string');\n\nconst mockFunction = () => true;\nclass MockClass {}\n\nconst handler = {\n construct(Target: any, args: any[]): any {\n return new Proxy(new Target(...args), handler);\n },\n get(_target: any, _prop: any) {\n return mockFunction;\n },\n};\n\nconst generateMockClass = (value: any) => {\n return new Proxy(value, handler);\n};\n\n// Things not currently auto-mocked because of NodeJS, by adding them here we have types for them and can use that to generate mocks if needed\nconst mockWindow = {\n WebSocket: MockClass,\n crypto,\n SubtleCrypto: MockClass,\n};\n\nconst generateMockEndowment = (key: string) => {\n const globalValue = (globalThis as any)[key];\n\n // Default exposed APIs don't need to be mocked\n if (globalValue && DEFAULT_ENDOWMENTS.includes(key)) {\n return globalValue;\n }\n\n // Fall back to mockWindow for certain APIs not exposed in global in Node.JS\n const globalOrMocked = globalValue ?? (mockWindow as any)[key];\n\n const type = typeof globalOrMocked;\n const isFunction = type === 'function';\n if (isFunction && isConstructor(globalOrMocked)) {\n return generateMockClass(globalOrMocked);\n } else if (isFunction || !globalOrMocked) {\n // Fall back to function mock for now\n return mockFunction;\n }\n return globalOrMocked;\n};\n\nexport const generateMockEndowments = () => {\n return ALL_APIS.reduce<Record<string, any>>(\n (acc, cur) => ({ ...acc, [cur]: generateMockEndowment(cur) }),\n { wallet: getMockSnapProvider() },\n );\n};\n"]}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
{
|
|
2
2
|
"html": "<!doctype html>\n<html>\n <head>\n <title>Hello, Snaps!</title>\n <link rel=\"icon\" type=\"image/svg\" href=\"./images/icon.svg\"/>\n </head>\n\n <body>\n <h1>Hello, Snaps!</h1>\n <details>\n <summary>Instructions</summary>\n <ul>\n <li>First, click \"Connect\". Then, try out the other buttons!</li>\n <li>Please note that:</li>\n <ul>\n <li>\n The <code>snap.manifest.json</code> and <code>package.json</code> must be located in the server root directory..\n </li>\n <li>\n The Snap bundle must be hosted at the location specified by the <code>location</code> field of <code>snap.manifest.json</code>.\n </li>\n </ul>\n </ul>\n </details>\n <br/>\n\n <button class=\"connect\">Connect</button>\n <button class=\"sendHello\">Send Hello</button>\n </body>\n\n <script>\n const snapId = `local:${window.location.href}`;\n\n const connectButton = document.querySelector('button.connect')\n const sendButton = document.querySelector('button.sendHello')\n\n connectButton.addEventListener('click', connect)\n sendButton.addEventListener('click', send)\n\n // here we get permissions to interact with and install the snap\n async function connect () {\n await ethereum.request({\n method: 'wallet_enable',\n params: [{\n wallet_snap: { [snapId]: {} },\n }]\n })\n }\n\n // here we call the snap's \"hello\" method\n async function send () {\n try {\n const response = await ethereum.request({\n method: 'wallet_invokeSnap',\n params: [snapId, {\n method: 'hello'\n }]\n })\n } catch (err) {\n console.error(err)\n alert('Problem happened: ' + err.message || err)\n }\n }\n </script>\n</html>\n",
|
|
3
|
-
"source": "
|
|
3
|
+
"source": "module.exports.onRpcRequest = async ({ origin, request }) => {\n switch (request.method) {\n case 'hello':\n return wallet.request({\n method: 'snap_confirm',\n params: [\n {\n prompt: `Hello, ${origin}!`,\n description:\n 'This custom confirmation is just for display purposes.',\n textAreaContent:\n 'But you can edit the snap source code to make it do something, if you want to!',\n },\n ],\n });\n default:\n throw new Error('Method not found.');\n }\n};\n"
|
|
4
4
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@metamask/snaps-cli",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.16.0",
|
|
4
4
|
"description": "A CLI for developing MetaMask Snaps.",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -47,8 +47,8 @@
|
|
|
47
47
|
"@babel/plugin-transform-runtime": "^7.16.7",
|
|
48
48
|
"@babel/preset-env": "^7.16.7",
|
|
49
49
|
"@babel/preset-typescript": "^7.16.7",
|
|
50
|
-
"@metamask/snap-controllers": "^0.
|
|
51
|
-
"@metamask/snaps-browserify-plugin": "^0.
|
|
50
|
+
"@metamask/snap-controllers": "^0.16.0",
|
|
51
|
+
"@metamask/snaps-browserify-plugin": "^0.16.0",
|
|
52
52
|
"@metamask/utils": "^2.0.0",
|
|
53
53
|
"babelify": "^10.0.0",
|
|
54
54
|
"browserify": "^17.0.0",
|
|
@@ -64,7 +64,7 @@
|
|
|
64
64
|
"yargs-parser": "^20.2.2"
|
|
65
65
|
},
|
|
66
66
|
"devDependencies": {
|
|
67
|
-
"@lavamoat/allow-scripts": "^
|
|
67
|
+
"@lavamoat/allow-scripts": "^2.0.3",
|
|
68
68
|
"@metamask/auto-changelog": "^2.6.0",
|
|
69
69
|
"@metamask/eslint-config": "^8.0.0",
|
|
70
70
|
"@metamask/eslint-config-jest": "^8.0.0",
|
|
@@ -73,7 +73,7 @@
|
|
|
73
73
|
"@types/browserify": "^12.0.36",
|
|
74
74
|
"@types/init-package-json": "^1.10.0",
|
|
75
75
|
"@types/is-url": "^1.2.28",
|
|
76
|
-
"@types/jest": "^
|
|
76
|
+
"@types/jest": "^27.5.1",
|
|
77
77
|
"@types/mkdirp": "^1.0.2",
|
|
78
78
|
"@types/node": "^14.14.25",
|
|
79
79
|
"@types/rimraf": "^3.0.0",
|
|
@@ -89,13 +89,14 @@
|
|
|
89
89
|
"eslint-plugin-node": "^11.1.0",
|
|
90
90
|
"eslint-plugin-prettier": "^3.4.0",
|
|
91
91
|
"execa": "^5.1.1",
|
|
92
|
-
"jest": "^
|
|
92
|
+
"jest": "^27.5.1",
|
|
93
93
|
"jest-it-up": "^2.0.0",
|
|
94
94
|
"patch-package": "^6.4.7",
|
|
95
95
|
"prettier": "^2.3.2",
|
|
96
|
+
"prettier-plugin-packagejson": "^2.2.11",
|
|
96
97
|
"rimraf": "^3.0.2",
|
|
97
98
|
"ts-auto-guard": "^2.3.0",
|
|
98
|
-
"ts-jest": "^
|
|
99
|
+
"ts-jest": "^27.1.5",
|
|
99
100
|
"ts-node": "^9.1.1",
|
|
100
101
|
"tsc-watch": "^4.5.0",
|
|
101
102
|
"typescript": "^4.4.0"
|