-
Notifications
You must be signed in to change notification settings - Fork 10
/
Copy pathmock.mjs
77 lines (65 loc) · 2.75 KB
/
mock.mjs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
import { strict as assert } from 'assert';
import { readFileSync, readdirSync } from "fs";
import { join } from 'path';
import { JsonRpcProvider } from 'ethers';
const BYTECODE_PATH = './test/mainnet';
/** @type {{[address_: string]: string}} */
const resolve = {};
for (const file of readdirSync(BYTECODE_PATH)) {
assert(file.endsWith('.json'));
const [, address] = file.replace('.json', '').split('-');
assert(address, `Unable to register address with file \`${file}\``);
resolve[address.toLowerCase()] = file;
}
/**
* @param {string} address
* @returns {Promise<string>}
*/
function getCode(address) {
const file = resolve[address.toLowerCase()];
assert(file, `unable to find bytecode for address ${address}`);
const bytecodePath = join(BYTECODE_PATH, file);
// Normalize path so snapshot are the same in both Windows and *nixes
console.info('[DEBUG mock.mjs]', address, bytecodePath.replace(/\\/g, '/'));
const { bytecode } = JSON.parse(readFileSync(bytecodePath, 'utf-8'));
return Promise.resolve(bytecode);
}
// Patch the following to avoid requests in `::examples` tests
JsonRpcProvider.prototype.getCode = getCode;
// Patch the following to avoid requests in `::bin/provider` tests
global.fetch = async function (url, payload) {
assert(typeof url === 'string');
console.info('[DEBUG mock.mjs]', `url='${url}'`, `payload=${JSON.stringify(payload)}`);
if (payload?.method === 'POST') {
assert(typeof payload === 'object');
assert(typeof payload['body'] === 'string');
const { id, jsonrpc, method, params } = JSON.parse(payload['body']);
assert(id);
assert(jsonrpc === '2.0');
assert(method === 'eth_getCode');
if (url.startsWith('error://'))
return Response.error();
const [address] = params;
const code = await getCode(address);
const resp = JSON.stringify({ id, jsonrpc, result: code });
return Promise.resolve(new Response(resp, payload));
}
assert(payload === undefined);
assert(url.startsWith('https://api.openchain.xyz/signature-database/v1/lookup?'));
url = new URL(url);
const getHashes = (/**@type {'function'|'event'}*/kind, /**@type{URL}*/url) => {
const selectors = url.searchParams.get(kind);
assert(selectors !== null);
const hashes = JSON.parse(readFileSync(`./4bytedb/${kind}Hashes.min.json`, 'utf-8'));
return Object.fromEntries(selectors
.split(',')
.map(s => [s, [{ name: hashes[s.slice(2)], filtered: false }]]));
};
const resp = JSON.stringify({
result: {
function: getHashes('function', url),
event: getHashes('event', url),
}
});
return Promise.resolve(new Response(resp, payload));
};