Renamed getStorageAt to getStorage and homestead to mainnet and fixed several Provider formatting bugs.

This commit is contained in:
Richard Moore 2022-09-29 21:55:13 -04:00
parent e14cca31ba
commit 0ce18366b1
10 changed files with 52 additions and 39 deletions

@ -251,7 +251,7 @@ export type PerformActionRequest = {
method: "getLogs",
filter: PerformActionFilter
} | {
method: "getStorageAt",
method: "getStorage",
address: string, position: bigint, blockTag: BlockTag
} | {
method: "getTransaction",
@ -273,7 +273,7 @@ export type PerformActionRequest = {
type _PerformAccountRequest = {
method: "getBalance" | "getTransactionCount" | "getCode"
} | {
method: "getStorageAt", position: bigint
method: "getStorage", position: bigint
}
type CcipArgs = {
@ -795,9 +795,9 @@ export class AbstractProvider implements Provider {
return hexlify(await this.#getAccountValue({ method: "getCode" }, address, blockTag));
}
async getStorageAt(address: AddressLike, _position: BigNumberish, blockTag?: BlockTag): Promise<string> {
async getStorage(address: AddressLike, _position: BigNumberish, blockTag?: BlockTag): Promise<string> {
const position = getBigInt(_position, "position");
return hexlify(await this.#getAccountValue({ method: "getStorageAt", position }, address, blockTag));
return hexlify(await this.#getAccountValue({ method: "getStorage", position }, address, blockTag));
}
// Write

@ -54,7 +54,7 @@ export function injectCommonNetworks(): void {
}
}
registerEth("homestead", 1, { ensNetwork: 1, altNames: [ "mainnet" ] });
registerEth("mainnet", 1, { ensNetwork: 1, altNames: [ "homestead" ] });
registerEth("ropsten", 3, { ensNetwork: 3 });
registerEth("rinkeby", 4, { ensNetwork: 4 });
registerEth("goerli", 5, { ensNetwork: 5 });

@ -1,5 +1,6 @@
import { getAddress, getCreateAddress } from "../address/index.js";
import { Signature } from "../crypto/index.js"
import { accessListify } from "../transaction/index.js";
import {
getBigInt, getNumber, hexlify, isHexString, zeroPadValue,
@ -133,21 +134,23 @@ export const formatReceiptLog = object({
address: getAddress,
topics: arrayOf(formatHash),
data: formatData,
logIndex: getNumber,
index: getNumber,
blockHash: formatHash,
}, {
index: [ "logIndex" ]
});
export const formatTransactionReceipt = object({
to: allowNull(getAddress, null),
from: allowNull(getAddress, null),
contractAddress: allowNull(getAddress, null),
transactionIndex: getNumber,
// should be allowNull(hash), but broken-EIP-658 support is handled in receipt
index: getNumber,
root: allowNull(hexlify),
gasUsed: getBigInt,
logsBloom: allowNull(formatData),
blockHash: formatHash,
transactionHash: formatHash,
hash: formatHash,
logs: arrayOf(formatReceiptLog),
blockNumber: getNumber,
confirmations: allowNull(getNumber, null),
@ -156,7 +159,9 @@ export const formatTransactionReceipt = object({
status: allowNull(getNumber),
type: getNumber
}, {
effectiveGasPrice: [ "gasPrice" ]
effectiveGasPrice: [ "gasPrice" ],
hash: [ "transactionHash" ],
index: [ "transactionIndex" ],
});
export function formatTransactionResponse(value: any) {
@ -195,10 +200,6 @@ export function formatTransactionResponse(value: any) {
nonce: getNumber,
data: formatData,
r: allowNull(formatUint256),
s: allowNull(formatUint256),
v: allowNull(getNumber),
creates: allowNull(getAddress, null),
chainId: allowNull(getBigInt, null)
@ -216,9 +217,19 @@ export function formatTransactionResponse(value: any) {
// Add an access list to supported transaction types
if ((value.type === 1 || value.type === 2) && value.accessList == null) {
value.accessList = [ ];
result.accessList = [ ];
}
// Compute the signature
result.signature = Signature.from(value);
// Some backends omit ChainId on legacy transactions, but we can compute it
if (result.chainId == null) {
const chainId = result.signature.legacyChainId;
if (chainId != null) { result.chainId = chainId; }
}
// @TODO: check chainID
/*
if (value.chainId != null) {

@ -177,7 +177,7 @@ export class Network {
*/
static from(network?: Networkish): Network {
// Default network
if (network == null) { return Network.from("homestead"); }
if (network == null) { return Network.from("mainnet"); }
// Canonical name or chain ID
if (typeof(network) === "number") { network = BigInt(network); }

@ -16,7 +16,7 @@ const defaultApiKey = "_gg7wSSi0KMBsdKnGVfHDueq6xMB9EkC"
function getHost(name: string): string {
switch(name) {
case "homestead":
case "mainnet":
return "eth-mainnet.alchemyapi.io";
case "ropsten":
return "eth-ropsten.alchemyapi.io";
@ -46,7 +46,7 @@ function getHost(name: string): string {
export class AlchemyProvider extends JsonRpcProvider implements CommunityResourcable {
readonly apiKey!: string;
constructor(_network: Networkish = "homestead", apiKey?: null | string) {
constructor(_network: Networkish = "mainnet", apiKey?: null | string) {
const network = Network.from(_network);
if (apiKey == null) { apiKey = defaultApiKey; }

@ -15,7 +15,7 @@ const defaultApiKey = "9f7d929b018cdffb338517efa06f58359e86ff1ffd350bc8897385236
function getHost(name: string): string {
switch (name) {
case "homestead":
case "mainnet":
return "rpc.ankr.com/eth";
case "ropsten":
return "rpc.ankr.com/eth_ropsten";
@ -35,7 +35,7 @@ function getHost(name: string): string {
export class AnkrProvider extends JsonRpcProvider implements CommunityResourcable {
readonly apiKey!: string;
constructor(_network: Networkish = "homestead", apiKey?: null | string) {
constructor(_network: Networkish = "mainnet", apiKey?: null | string) {
const network = Network.from(_network);
if (apiKey == null) { apiKey = defaultApiKey; }

@ -7,9 +7,9 @@ import type { Networkish } from "./network.js";
export class CloudflareProvider extends JsonRpcProvider {
constructor(_network: Networkish = "homestead") {
constructor(_network: Networkish = "mainnet") {
const network = Network.from(_network);
if (network.name !== "homestead") {
if (network.name !== "mainnet") {
return throwArgumentError("unsupported network", "network", _network);
}
super("https:/\/cloudflare-eth.com/", network, { staticNetwork: network });

@ -80,7 +80,7 @@ export class BaseEtherscanProvider extends AbstractProvider {
if (this.#plugin) { return this.#plugin.baseUrl; }
switch(this.network.name) {
case "homestead":
case "mainnet":
return "https:/\/api.etherscan.io";
case "ropsten":
return "https:/\/api-ropsten.etherscan.io";
@ -353,7 +353,7 @@ export class BaseEtherscanProvider extends AbstractProvider {
tag: req.blockTag
});
case "getStorageAt":
case "getStorage":
return this.fetch("proxy", {
action: "eth_getStorageAt",
address: req.address,
@ -486,7 +486,7 @@ export class BaseEtherscanProvider extends AbstractProvider {
}
async getEtherPrice(): Promise<number> {
if (this.network.name !== "homestead") { return 0.0; }
if (this.network.name !== "mainnet") { return 0.0; }
return parseFloat((await this.fetch("stats", { action: "ethprice" })).ethusd);
}

@ -148,7 +148,7 @@ function normalize(provider: AbstractProvider, value: any, req: PerformActionReq
return getNumber(value).toString();
case "getCode":
return hexlify(value);
case "getStorageAt":
case "getStorage":
return hexlify(value);
case "getBlock":
if (req.includeTransactions) {
@ -450,7 +450,7 @@ export class FallbackProvider extends AbstractProvider {
case "getBalance":
case "getTransactionCount":
case "getCode":
case "getStorageAt":
case "getStorage":
case "getTransaction":
case "getTransactionReceipt":
case "getLogs":

@ -232,7 +232,7 @@ export class Block<T extends string | TransactionResponse> implements BlockParam
this.#transactions = Object.freeze(block.transactions.map((tx) => {
if (typeof(tx) !== "string" && tx.provider !== provider) {
throw new Error("provider mismatch");
return <T>(new TransactionResponse(tx, provider));
}
return <T>tx;
}));;
@ -433,14 +433,15 @@ export interface TransactionReceiptParams {
blockNumber: number;
logsBloom: string;
logs: ReadonlyArray<Log>;
logs: ReadonlyArray<LogParams>;
gasUsed: bigint;
cumulativeGasUsed: bigint;
gasPrice?: null | bigint;
effectiveGasPrice?: null | bigint;
byzantium: boolean;
type: number;
//byzantium: boolean;
status: null | number;
root: null | string;
}
@ -478,7 +479,8 @@ export class TransactionReceipt implements TransactionReceiptParams, Iterable<Lo
readonly cumulativeGasUsed!: bigint;
readonly gasPrice!: bigint;
readonly byzantium!: boolean;
readonly type!: number;
//readonly byzantium!: boolean;
readonly status!: null | number;
readonly root!: null | string;
@ -486,11 +488,7 @@ export class TransactionReceipt implements TransactionReceiptParams, Iterable<Lo
constructor(tx: TransactionReceiptParams, provider: Provider) {
this.#logs = Object.freeze(tx.logs.map((log) => {
if (provider !== log.provider) {
//return log.connect(provider);
throw new Error("provider mismatch");
}
return log;
return new Log(log, provider);
}));
defineProperties<TransactionReceipt>(this, {
@ -512,7 +510,8 @@ export class TransactionReceipt implements TransactionReceiptParams, Iterable<Lo
cumulativeGasUsed: tx.cumulativeGasUsed,
gasPrice: ((tx.effectiveGasPrice || tx.gasPrice) as bigint),
byzantium: tx.byzantium,
type: tx.type,
//byzantium: tx.byzantium,
status: tx.status,
root: tx.root
});
@ -527,12 +526,15 @@ export class TransactionReceipt implements TransactionReceiptParams, Iterable<Lo
toJSON(): any {
const {
to, from, contractAddress, hash, index, blockHash, blockNumber, logsBloom,
logs, byzantium, status, root
logs, //byzantium,
status, root
} = this;
return {
_type: "TransactionReceipt",
blockHash, blockNumber, byzantium, contractAddress,
blockHash, blockNumber,
//byzantium,
contractAddress,
cumulativeGasUsed: toJson(this.cumulativeGasUsed),
from,
gasPrice: toJson(this.gasPrice),
@ -1104,7 +1106,7 @@ export interface Provider extends ContractRunner, EventEmitterable<ProviderEvent
* @note On nodes without archive access enabled, the %%blockTag%% may be
* **silently ignored** by the node, which may cause issues if relied on.
*/
getStorageAt(address: AddressLike, position: BigNumberish, blockTag?: BlockTag): Promise<string>
getStorage(address: AddressLike, position: BigNumberish, blockTag?: BlockTag): Promise<string>
////////////////////