From fbae24ccaff7b911a2ef72e1c47434e6dfd73d9f Mon Sep 17 00:00:00 2001 From: "Mark S. Miller" Date: Wed, 11 Dec 2024 08:55:57 -0800 Subject: [PATCH] fix(client-utils): only call `fetch` as a function, not a method (#10671) closes: #XXXX refs: https://github.com/endojs/endo/issues/31#issuecomment-1255624116 ## Description Testing on Brave, the browser's global `fetch` function works when called with its `this` bound to either `undefined` or the browser global object, but does not work if its `this` is bound to something else. The code this PR fixes was misbehaving because it was calling `powers.fetch(...)`, i.e., happening to call it as a method with its `this` bound to the irrelevant `powers` object. This refactor just expresses the intention of this code, which is just to call the `fetch` function without passing it some object as its `this` binding. This seems to fix the problem. Not at all addressed by this PR: The fact that this problem happened from a programming patterns that seems correct and would have passed review indicates a deeper hazard. This PR does nothing to mitigate this deeper hazard. It only fixes this case where we fell into the hazard. ### Security Considerations none ### Scaling Considerations none ### Documentation Considerations none, except as needed to address the more general hazard. ### Testing Considerations Only tested `fetch` behavior on Brave. Based on that, proceeding under untested assumption that this refactor will work on all supported browsers. ### Upgrade Considerations none --- a3p-integration/proposals/z:acceptance/test-lib/rpc.js | 4 ++-- packages/client-utils/src/vstorage.js | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/a3p-integration/proposals/z:acceptance/test-lib/rpc.js b/a3p-integration/proposals/z:acceptance/test-lib/rpc.js index 955f1235477..2a25b534911 100644 --- a/a3p-integration/proposals/z:acceptance/test-lib/rpc.js +++ b/a3p-integration/proposals/z:acceptance/test-lib/rpc.js @@ -43,12 +43,12 @@ export { networkConfig }; * @param {typeof window.fetch} powers.fetch * @param {MinimalNetworkConfig} config */ -export const makeVStorage = (powers, config = networkConfig) => { +export const makeVStorage = ({ fetch }, config = networkConfig) => { /** @param {string} path */ const getJSON = path => { const url = config.rpcAddrs[0] + path; // console.warn('fetching', url); - return powers.fetch(url, { keepalive: true }).then(res => res.json()); + return fetch(url, { keepalive: true }).then(res => res.json()); }; // height=0 is the same as omitting height and implies the highest block const url = (path = 'published', { kind = 'children', height = 0 } = {}) => diff --git a/packages/client-utils/src/vstorage.js b/packages/client-utils/src/vstorage.js index b8eec61330e..be365debf3d 100644 --- a/packages/client-utils/src/vstorage.js +++ b/packages/client-utils/src/vstorage.js @@ -9,12 +9,12 @@ * @param {typeof window.fetch} powers.fetch * @param {MinimalNetworkConfig} config */ -export const makeVStorage = (powers, config) => { +export const makeVStorage = ({ fetch }, config) => { /** @param {string} path */ const getJSON = path => { const url = config.rpcAddrs[0] + path; // console.warn('fetching', url); - return powers.fetch(url, { keepalive: true }).then(res => res.json()); + return fetch(url, { keepalive: true }).then(res => res.json()); }; // height=0 is the same as omitting height and implies the highest block const url = (path = 'published', { kind = 'children', height = 0 } = {}) =>