2020-01-10 01:01:00 -05:00
|
|
|
_section: Addresses @<addresses>
|
2019-08-21 01:53:47 -04:00
|
|
|
|
|
|
|
Explain addresses,formats and checksumming here.
|
|
|
|
|
2019-12-13 22:05:10 -05:00
|
|
|
Also see: [constants.AddressZero](constants)
|
2019-08-21 01:53:47 -04:00
|
|
|
|
2020-01-10 01:01:00 -05:00
|
|
|
_subsection: Address Formats @<address-formats>
|
2019-08-21 01:53:47 -04:00
|
|
|
|
2020-02-01 03:39:21 -05:00
|
|
|
|
|
|
|
_heading: Address @<address>
|
|
|
|
|
2020-05-08 03:24:40 -04:00
|
|
|
An **Address** is a [[DataHexString]] of 20 bytes (40 nibbles), with optional
|
2020-02-01 03:39:21 -05:00
|
|
|
mixed case.
|
|
|
|
|
|
|
|
If the case is mixed, it is a **Checksum Address**, which uses a specific pattern
|
|
|
|
of uppercase and lowercase letters within a given address to reduce the risk
|
|
|
|
of errors introduced from typing an address or cut and paste issues.
|
|
|
|
|
|
|
|
All functions that return an Address will return a Checksum Address.
|
|
|
|
|
2020-01-10 01:01:00 -05:00
|
|
|
_heading: ICAP Address @<address-icap>
|
2020-02-01 03:39:21 -05:00
|
|
|
|
|
|
|
The **ICAP Address Format** was an early attempt to introduce a checksum
|
|
|
|
into Ethereum addresses using the popular banking industry's
|
2020-02-02 07:58:29 -05:00
|
|
|
[IBAN](link-wiki-iban)
|
2020-02-01 03:39:21 -05:00
|
|
|
format with the country code specified as **XE**.
|
|
|
|
|
|
|
|
Due to the way IBAN encodes address, only addresses that fit into 30 base-36
|
|
|
|
characters are actually compatible, so the format was adapted to support 31
|
|
|
|
base-36 characters which is large enough for a full Ethereum address, however
|
|
|
|
the preferred method was to select a private key whose address has a ``0`` as
|
|
|
|
the first byte, which allows the address to be formatted as a fully compatibly
|
|
|
|
standard IBAN address with 30 base-36 characters.
|
|
|
|
|
|
|
|
In general this format is no longer widely supported anymore, however any function that
|
|
|
|
accepts an address can receive an ICAP address, and it will be converted internally.
|
|
|
|
|
|
|
|
To convert an address into the ICAP format, see [getIcapAddress](utils-getIcapAddress).
|
|
|
|
|
2020-01-10 01:01:00 -05:00
|
|
|
|
2020-05-08 03:24:40 -04:00
|
|
|
_subsection: Converting and Verifying @<utils--address>
|
2020-01-10 01:01:00 -05:00
|
|
|
|
2020-02-25 14:57:11 -05:00
|
|
|
_property: ethers.utils.getAddress(address) => string<[[address]]> @<utils-getAddress> @SRC<address>
|
2019-12-13 22:05:10 -05:00
|
|
|
Returns //address// as a Checksum Address.
|
2019-08-21 01:53:47 -04:00
|
|
|
|
2020-05-08 03:24:40 -04:00
|
|
|
If //address// is an invalid 40-nibble [[HexString]] or if it contains mixed case and
|
2021-02-04 18:59:51 -05:00
|
|
|
the checksum is invalid, an [INVALID_ARGUMENT](errors--invalid-argument) Error is thrown.
|
2019-08-21 01:53:47 -04:00
|
|
|
|
2019-12-13 22:05:10 -05:00
|
|
|
The value of //address// may be any supported address format.
|
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const getAddress = ethers.utils.getAddress;
|
|
|
|
|
|
|
|
// Injects the checksum (via upper-casing specific letters)
|
|
|
|
//_result:
|
|
|
|
getAddress("0x8ba1f109551bd432803012645ac136ddd64dba72");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Converts and injects the checksum
|
|
|
|
//_result:
|
|
|
|
getAddress("XE65GB6LDNXYOFTX0NSV3FUWKOWIXAMJK36");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Throws if a checksummed address is provided, but a
|
|
|
|
// letter is the wrong case
|
|
|
|
// ------------v (should be lower-case)
|
|
|
|
//_throws:
|
|
|
|
getAddress("0x8Ba1f109551bD432803012645Ac136ddd64DBA72")
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Throws if the ICAP/IBAN checksum fails
|
|
|
|
//_throws:
|
|
|
|
getIcapAddress("XE65GB6LDNXYOFTX0NSV3FUWKOWIXAMJK37");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Throws if the address is invalid, in general
|
|
|
|
//_throws:
|
|
|
|
getIcapAddress("I like turtles!");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
|
2020-04-19 02:18:20 -04:00
|
|
|
_property: ethers.utils.getIcapAddress(address) => string<[IcapAddress](address-icap)> @<utils-getIcapAddress> @SRC<address>
|
|
|
|
Returns //address// as an [ICAP address](link-icap).
|
2021-02-04 18:59:51 -05:00
|
|
|
Supports the same restrictions as [getAddress](utils-getAddress).
|
2019-12-13 22:05:10 -05:00
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const getIcapAddress = ethers.utils.getIcapAddress;
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
getIcapAddress("0x8ba1f109551bd432803012645ac136ddd64dba72");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
getIcapAddress("XE65GB6LDNXYOFTX0NSV3FUWKOWIXAMJK36");
|
|
|
|
//_log:
|
|
|
|
|
2020-02-25 14:57:11 -05:00
|
|
|
_property: ethers.utils.isAddress(address) => boolean @<utils-isAddress> @SRC<address>
|
2019-12-13 22:05:10 -05:00
|
|
|
Returns true if //address// is valid (in any supported format).
|
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const isAddress = ethers.utils.isAddress;
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
isAddress("0x8ba1f109551bd432803012645ac136ddd64dba72");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
isAddress("XE65GB6LDNXYOFTX0NSV3FUWKOWIXAMJK36");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
isAddress("I like turtles.");
|
|
|
|
//_log:
|
2019-12-13 22:05:10 -05:00
|
|
|
|
2020-05-08 03:24:40 -04:00
|
|
|
_subsection: Derivation @<utils--address-derivation>
|
2020-04-19 02:18:20 -04:00
|
|
|
|
|
|
|
_property: ethers.utils.computeAddress(publicOrPrivateKey) => string<[[address]]> @<utils-computeAddress> @SRC<transactions>
|
|
|
|
Returns the address for //publicOrPrivateKey//. A public key may be
|
|
|
|
compressed or uncompressed, and a private key will be converted
|
|
|
|
automatically to a public key for the derivation.
|
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const computeAddress = ethers.utils.computeAddress;
|
|
|
|
|
|
|
|
// Private Key
|
|
|
|
//_result:
|
|
|
|
computeAddress("0xb976778317b23a1385ec2d483eda6904d9319135b89f1d8eee9f6d2593e2665d");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Public Key (compressed)
|
|
|
|
//_result:
|
|
|
|
computeAddress("0x0376698beebe8ee5c74d8cc50ab84ac301ee8f10af6f28d0ffd6adf4d6d3b9b762");
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Public Key (uncompressed)
|
|
|
|
//_result:
|
|
|
|
computeAddress("0x0476698beebe8ee5c74d8cc50ab84ac301ee8f10af6f28d0ffd6adf4d6d3b9b762d46ca56d3dad2ce13213a6f42278dabbb53259f2d92681ea6a0b98197a719be3");
|
|
|
|
//_log:
|
|
|
|
|
2020-04-19 02:18:20 -04:00
|
|
|
_property: ethers.utils.recoverAddress(digest, signature) => string<[[address]]> @<utils-recoverAddress> @SRC<transactions>
|
|
|
|
Use [[link-wiki-ecrecover]] to determine the address that signed //digest// to
|
|
|
|
which generated //signature//.
|
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const recoverAddress = ethers.utils.recoverAddress;
|
|
|
|
|
|
|
|
const digest = "0x7c5ea36004851c764c44143b1dcb59679b11c9a68e5f41497f6cf3d480715331";
|
|
|
|
|
|
|
|
// Using an expanded Signature
|
|
|
|
//_result:
|
|
|
|
recoverAddress(digest, {
|
|
|
|
r: "0x528459e4aec8934dc2ee94c4f3265cf6ce00d47cf42bb106afda3642c72e25eb",
|
|
|
|
s: "0x42544137118256121502784e5a6425e6183ca964421ecd577db6c66ba9bccdcf",
|
|
|
|
v: 27
|
|
|
|
});
|
|
|
|
//_log:
|
|
|
|
|
|
|
|
// Using a flat Signature
|
|
|
|
const signature = "0x528459e4aec8934dc2ee94c4f3265cf6ce00d47cf42bb106afda3642c72e25eb42544137118256121502784e5a6425e6183ca964421ecd577db6c66ba9bccdcf1b";
|
|
|
|
//_result:
|
|
|
|
recoverAddress(digest, signature);
|
|
|
|
//_log:
|
2020-04-19 02:18:20 -04:00
|
|
|
|
|
|
|
_subsection: Contracts Addresses @<utils--contract-addresses>
|
|
|
|
|
|
|
|
_property: ethers.utils.getContractAddress(transaction) => string<[[address]]> @<utils-getContractAddress> @SRC<address>
|
2019-12-13 22:05:10 -05:00
|
|
|
Returns the contract address that would result if //transaction// was
|
|
|
|
used to deploy a contract.
|
2020-01-10 01:01:00 -05:00
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const getContractAddress = ethers.utils.getContractAddress;
|
|
|
|
|
|
|
|
const from = "0x8ba1f109551bD432803012645Ac136ddd64DBA72";
|
|
|
|
const nonce = 5;
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
getContractAddress({ from, nonce });
|
|
|
|
//_log:
|
|
|
|
|
2020-02-25 14:57:11 -05:00
|
|
|
_property: ethers.utils.getCreate2Address(from, salt, initCodeHash) => string<[[address]]> @<utils-getCreate2Address> @SRC<address>
|
2020-01-10 01:01:00 -05:00
|
|
|
Returns the contract address that would result from the given
|
2020-02-02 07:58:29 -05:00
|
|
|
[CREATE2](link-eip-1014) call.
|
2020-04-19 02:18:20 -04:00
|
|
|
|
2021-06-10 17:38:38 -04:00
|
|
|
_code: @lang<javascript>
|
|
|
|
|
|
|
|
//_hide: const getCreate2Address = ethers.utils.getCreate2Address;
|
|
|
|
//_hide: const keccak256 = ethers.utils.keccak256;
|
|
|
|
|
|
|
|
const from = "0x8ba1f109551bD432803012645Ac136ddd64DBA72";
|
|
|
|
const salt = "0x7c5ea36004851c764c44143b1dcb59679b11c9a68e5f41497f6cf3d480715331";
|
|
|
|
const initCode = "0x6394198df16000526103ff60206004601c335afa6040516060f3";
|
|
|
|
const initCodeHash = keccak256(initCode);
|
|
|
|
|
|
|
|
//_result:
|
|
|
|
getCreate2Address(from, salt, initCodeHash);
|
|
|
|
//_log:
|
2020-04-19 02:18:20 -04:00
|
|
|
|
|
|
|
|