diff --git a/app/scripts/lib/createMethodMiddleware.js b/app/scripts/lib/createMethodMiddleware.js deleted file mode 100644 index 7a98ce531..000000000 --- a/app/scripts/lib/createMethodMiddleware.js +++ /dev/null @@ -1,42 +0,0 @@ - -const recordedWeb3Usage = {} - -/** - * Returns a middleware that implements the following RPC methods: - * - metamask_logInjectedWeb3Usage - * - * @param {Object} opts - The middleware options - * @param {string} opts.origin - The origin for the middleware stack - * @param {Function} opts.sendMetrics - A function for sending a metrics event - * @returns {(req: any, res: any, next: Function, end: Function) => void} - */ -export default function createMethodMiddleware ({ origin, sendMetrics }) { - return function methodMiddleware (req, res, next, end) { - switch (req.method) { - - case 'metamask_logInjectedWeb3Usage': { - - const { action, name } = req.params[0] - - if (!recordedWeb3Usage[origin]) { - recordedWeb3Usage[origin] = {} - } - if (!recordedWeb3Usage[origin][name]) { - recordedWeb3Usage[origin][name] = true - sendMetrics({ - action, - name, - customVariables: { origin }, - }) - } - - res.result = true - break - } - - default: - return next() - } - return end() - } -} diff --git a/app/scripts/lib/enums.js b/app/scripts/lib/enums.js index 4e6efc07e..b54c7069e 100644 --- a/app/scripts/lib/enums.js +++ b/app/scripts/lib/enums.js @@ -14,6 +14,7 @@ const MESSAGE_TYPE = { ETH_GET_ENCRYPTION_PUBLIC_KEY: 'eth_getEncryptionPublicKey', ETH_SIGN: 'eth_sign', ETH_SIGN_TYPED_DATA: 'eth_signTypedData', + LOG_WEB3_USAGE: 'metamask_logInjectedWeb3Usage', PERSONAL_SIGN: 'personal_sign', } diff --git a/app/scripts/lib/rpc-method-middleware/createMethodMiddleware.js b/app/scripts/lib/rpc-method-middleware/createMethodMiddleware.js new file mode 100644 index 000000000..106f38e44 --- /dev/null +++ b/app/scripts/lib/rpc-method-middleware/createMethodMiddleware.js @@ -0,0 +1,33 @@ +import handlers from './handlers' + +const handlerMap = handlers.reduce((map, handler) => { + map.set(handler.methodName, handler.implementation) + return map +}, new Map()) + +/** + * Returns a middleware that implements the RPC methods defined in the handlers + * directory. + * + * The purpose of this middleware is to create portable RPC method + * implementations that are decoupled from the rest of our background + * architecture. + * + * Handlers consume functions that hook into the background, and only depend + * on their signatures, not e.g. controller internals. + * + * Eventually, we'll want to extract this middleware into its own package. + * + * @param {Object} opts - The middleware options + * @param {string} opts.origin - The origin for the middleware stack + * @param {Function} opts.sendMetrics - A function for sending a metrics event + * @returns {(req: Object, res: Object, next: Function, end: Function) => void} + */ +export default function createMethodMiddleware (opts) { + return function methodMiddleware (req, res, next, end) { + if (handlerMap.has(req.method)) { + return handlerMap.get(req.method)(req, res, next, end, opts) + } + return next() + } +} diff --git a/app/scripts/lib/rpc-method-middleware/handlers/index.js b/app/scripts/lib/rpc-method-middleware/handlers/index.js new file mode 100644 index 000000000..3a538680b --- /dev/null +++ b/app/scripts/lib/rpc-method-middleware/handlers/index.js @@ -0,0 +1,6 @@ +import logWeb3Usage from './log-web3-usage' + +const handlers = [ + logWeb3Usage, +] +export default handlers diff --git a/app/scripts/lib/rpc-method-middleware/handlers/log-web3-usage.js b/app/scripts/lib/rpc-method-middleware/handlers/log-web3-usage.js new file mode 100644 index 000000000..dbdb2ca6b --- /dev/null +++ b/app/scripts/lib/rpc-method-middleware/handlers/log-web3-usage.js @@ -0,0 +1,57 @@ +import { MESSAGE_TYPE } from '../../enums' + +/** + * This RPC method is called by our inpage web3 proxy whenever window.web3 is + * accessed. We're collecting data on window.web3 usage so that we can warn + * website maintainers, and possibly our users, before we remove window.web3 + * by November 16, 2020. + */ + +const logWeb3Usage = { + methodName: MESSAGE_TYPE.LOG_WEB3_USAGE, + implementation: logWeb3UsageHandler, +} +export default logWeb3Usage + +const recordedWeb3Usage = {} + +/** + * @typedef {Object} LogWeb3UsageOptions + * @property {string} origin - The origin of the request. + * @property {Function} sendMetrics - A function that registers a metrics event. + */ + +/** + * @typedef {Object} LogWeb3UsageParam + * @property {string} action - The action taken (get or set). + * @property {string} name - The window.web3 property name subject to the action. + */ + +/** + * @param {import('json-rpc-engine').JsonRpcRequest<[LogWeb3UsageParam]>} req - The JSON-RPC request object. + * @param {import('json-rpc-engine').JsonRpcResponse} res - The JSON-RPC response object. + * @param {Function} _next - The json-rpc-engine 'next' callback. + * @param {Function} end - The json-rpc-engine 'end' callback. + * @param {LogWeb3UsageOptions} options + */ +function logWeb3UsageHandler ( + req, res, _next, end, + { origin, sendMetrics }, +) { + const { action, name } = req.params[0] + + if (!recordedWeb3Usage[origin]) { + recordedWeb3Usage[origin] = {} + } + if (!recordedWeb3Usage[origin][name]) { + recordedWeb3Usage[origin][name] = true + sendMetrics({ + action, + name, + customVariables: { origin }, + }) + } + + res.result = true + return end() +} diff --git a/app/scripts/lib/rpc-method-middleware/index.js b/app/scripts/lib/rpc-method-middleware/index.js new file mode 100644 index 000000000..224e060bd --- /dev/null +++ b/app/scripts/lib/rpc-method-middleware/index.js @@ -0,0 +1 @@ +export { default } from './createMethodMiddleware' diff --git a/app/scripts/metamask-controller.js b/app/scripts/metamask-controller.js index 46b8f0383..07d3c8b18 100644 --- a/app/scripts/metamask-controller.js +++ b/app/scripts/metamask-controller.js @@ -28,7 +28,7 @@ import { import ComposableObservableStore from './lib/ComposableObservableStore' import AccountTracker from './lib/account-tracker' import createLoggerMiddleware from './lib/createLoggerMiddleware' -import createMethodMiddleware from './lib/createMethodMiddleware' +import createMethodMiddleware from './lib/rpc-method-middleware' import createOriginMiddleware from './lib/createOriginMiddleware' import createTabIdMiddleware from './lib/createTabIdMiddleware' import createOnboardingMiddleware from './lib/createOnboardingMiddleware'