Skip to content
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .prettierignore
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
evm
/evm
/README.md
73 changes: 56 additions & 17 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,35 +8,74 @@ spoken - this is a very complex piece of software which targets a bleeding-edge,
Mistakes happen, and no matter how hard you try and whether you pay someone to audit it, it may eat your tokens, set
your printer on fire or startle your cat. Cryptocurrencies are a high-risk investment, no matter how fancy.

## Testing Flow
## Testing with Tilt

> 🚧 This is a work in progress!

First tilt up.
To run tests using Tilt, execute the following command:

```bash
tilt up
```

Next, deploy integration contracts to each chain.
This will spin up a local development environment with all necessary components including Anvil chains and the executor service.

After Tilt is running, the test suite will run automatically in the `e2e` step.

````

## Capabilities and Supported Platforms

| Capability | Status | Description |
|------------|--------|-------------|
| NTT V1 | ✅ Supported | Native Token Transfer protocol integration |
| VAA V1 | ✅ Supported | Verified Action Approvals V1 protocol |

| Platform | Status | Networks |
|----------|--------|----------|
| EVM | ✅ Supported | Ethereum, BSC, Polygon, Avalanche, etc. |

## Running the Docker Image

You can run the executor using the published Docker image. To override the default configuration:

```bash
forge create ExecutorVAAv1Integration -r http://localhost:8545 --broadcast --private-key 0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80 --constructor-args 0x4a8bc80Ed5a4067f1CCf107057b8270E0cC11A78 0xD0fb39f5a3361F21457653cB70F9D0C9bD86B66B 200
forge create ExecutorVAAv1Integration -r http://localhost:8546 --broadcast --private-key 0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80 --constructor-args 0x79A1027a6A159502049F10906D333EC57E95F083 0x51B47D493CBA7aB97e3F8F163D6Ce07592CE4482 200
```
docker run -v /path/to/your/config.json:/app/config.json \
-e CONFIG_PATH=/app/config.json \
example-executor:latest
````

The configuration file should contain your chain settings, RPC endpoints, and other necessary parameters.

Finally, bun test
## Customizing Your Anvil Environment

The local Anvil chains can be customized to deploy additional integration contracts or modify the blockchain state for testing purposes. You can:

- Deploy custom contracts using Forge or other deployment tools
- Modify chain state using Anvil's RPC methods
- Configure custom accounts and balances
- Set up specific testing scenarios

Example of deploying additional contracts:

```bash
bun test
forge create YourContract -r http://localhost:8545 --private-key <your-private-key>
```

Click the link! It should be `pending` at first and then after a couple seconds, refresh and it should be `submitted`!
## Deployed Contracts

The following contracts are used as part of this repository infrastructure:

| Contract | Network | Address | Description |
|----------|---------|---------|-------------|
| NTT Shim Contract | Sepolia | [0x54DD7080aE169DD923fE56d0C4f814a0a17B8f41](https://sepolia.etherscan.io/address/0x54DD7080aE169DD923fE56d0C4f814a0a17B8f41) | Handles NTT protocol integration |
| Executor | Sepolia | [0xD0fb39f5a3361F21457653cB70F9D0C9bD86B66B](https://sepolia.etherscan.io/address/0xD0fb39f5a3361F21457653cB70F9D0C9bD86B66B) | Main executor contract |
| MultiReceiveWithGasDropOff | Base Sepolia | [0xe3cc16Cffa085C78e5D8144C74Fa97e4Fe53d68d](https://sepolia.basescan.org/address/0xe3cc16Cffa085C78e5D8144C74Fa97e4Fe53d68d) | Manages multi-receiver operations |

Next steps
## Using the Executor Explorer

You can monitor and explore executor transactions using the Executor Explorer. For local development:

```
https://wormholelabs-xyz.github.io/executor-explorer/#/chain/10002/tx/${hash}?endpoint=http%3A%2F%2Flocalhost%3A3000&env=Testnet
```

- Support NTT v1
- Publish the executor docker image
- Support passing the executor chain config from env or command line so that someone using the docker image can configure the chain info
- Deploy the contracts within the e2e test and actually confirm the messages send both ways and update the contract number.
- Trigger the e2e test in CI
Replace `${hash}` with your transaction hash. The explorer will connect to your local executor instance running on port 3000.
3 changes: 3 additions & 0 deletions bun.lock
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
"@types/express": "^5.0.3",
"@wormhole-foundation/sdk-base": "^2.4.0",
"@wormhole-foundation/sdk-definitions": "^2.4.0",
"@wormhole-foundation/sdk-definitions-ntt": "^1.0.2",
"axios": "^1.10.0",
"binary-layout": "^1.3.0",
"cors": "^2.8.5",
Expand Down Expand Up @@ -70,6 +71,8 @@

"@wormhole-foundation/sdk-definitions": ["@wormhole-foundation/[email protected]", "", { "dependencies": { "@noble/curves": "^1.4.0", "@noble/hashes": "^1.3.1", "@wormhole-foundation/sdk-base": "2.4.0" } }, "sha512-Aqx3/XLaBzbt5kt70N0lnVj3acGe/DYN66R4lG7AVv7VvDTSj2PKC0qOdbKgMh+bzFbjKK03fJkpUzl/d6eo+A=="],

"@wormhole-foundation/sdk-definitions-ntt": ["@wormhole-foundation/[email protected]", "", { "peerDependencies": { "@wormhole-foundation/sdk-base": "^2.1.0", "@wormhole-foundation/sdk-definitions": "^2.1.0" } }, "sha512-HXPlWaLc/tp26WyfXCl1ndRtIJq81yunI/UqWyYcMKRabtgZUQRNJqBPYdVOV8lKVtE+4Tx3FF0OWyw7KIrNZw=="],

"abitype": ["[email protected]", "", { "peerDependencies": { "typescript": ">=5.0.4", "zod": "^3 >=3.22.0" }, "optionalPeers": ["typescript", "zod"] }, "sha512-ZeiI6h3GnW06uYDLx0etQtX/p8E24UaHHBj57RSjK7YBFe7iuVn07EDpOeP451D06sF27VOz9JJPlIKJmXgkEg=="],

"accepts": ["[email protected]", "", { "dependencies": { "mime-types": "^3.0.0", "negotiator": "^1.0.0" } }, "sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng=="],
Expand Down
6 changes: 4 additions & 2 deletions chains.example.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,9 @@
"nativeDecimals": 18,
"executorAddress": "0xD0fb39f5a3361F21457653cB70F9D0C9bD86B66B",
"coreContractAddress": "0x4a8bc80Ed5a4067f1CCf107057b8270E0cC11A78",
"nttMultiReceiveWithGasDropOffAddress": "0xe3cc16Cffa085C78e5D8144C74Fa97e4Fe53d68d",
"capabilities": {
"requestPrefixes": ["ERV1"],
"requestPrefixes": ["ERV1", "ERN1"],
"gasDropOffLimit": "100000000000",
"maxGasLimit": "1000000",
"maxMsgValue": "200000000000"
Expand All @@ -30,8 +31,9 @@
"nativeDecimals": 18,
"coreContractAddress": "0x79A1027a6A159502049F10906D333EC57E95F083",
"executorAddress": "0x51B47D493CBA7aB97e3F8F163D6Ce07592CE4482",
"nttMultiReceiveWithGasDropOffAddress": "0xe3cc16Cffa085C78e5D8144C74Fa97e4Fe53d68d",
"capabilities": {
"requestPrefixes": ["ERV1"],
"requestPrefixes": ["ERV1", "ERN1"],
"gasDropOffLimit": "100000000000",
"maxGasLimit": "1000000",
"maxMsgValue": "200000000000"
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
"@types/express": "^5.0.3",
"@wormhole-foundation/sdk-base": "^2.4.0",
"@wormhole-foundation/sdk-definitions": "^2.4.0",
"@wormhole-foundation/sdk-definitions-ntt": "^1.0.2",
"axios": "^1.10.0",
"binary-layout": "^1.3.0",
"cors": "^2.8.5",
Expand Down
44 changes: 44 additions & 0 deletions src/abis/nttV1MultiReceiveWithGasDropOff.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
export const nttV1multiReceiveWithGasDropOffAbi = [
{
type: "function",
name: "VERSION",
inputs: [],
outputs: [{ name: "", type: "string", internalType: "string" }],
stateMutability: "view",
},
{
type: "function",
name: "receiveMessages",
inputs: [
{
name: "contracts",
type: "address[]",
internalType: "address[]",
},
{ name: "messages", type: "bytes[]", internalType: "bytes[]" },
{
name: "payeeAddress",
type: "address",
internalType: "address",
},
],
outputs: [],
stateMutability: "payable",
},
{
type: "error",
name: "DropOffFailed",
inputs: [
{ name: "", type: "address", internalType: "address" },
{ name: "", type: "uint256", internalType: "uint256" },
],
},
{
type: "error",
name: "InvalidParameters",
inputs: [
{ name: "", type: "uint256", internalType: "uint256" },
{ name: "", type: "uint256", internalType: "uint256" },
],
},
] as const;
4 changes: 2 additions & 2 deletions src/api/quote.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import {
getTotalGasLimitAndMsgValue,
signQuote,
} from "../utils";
import { EvmHandler } from "../relay/platform/evm";
import { evmHandler } from "../relay/evm";

export const quoteHandler = async (req: Request, res: Response) => {
const enabledChainIds = Object.keys(enabledChains);
Expand Down Expand Up @@ -59,7 +59,7 @@ export const quoteHandler = async (req: Request, res: Response) => {
const expiryTime = new Date();
expiryTime.setHours(expiryTime.getHours() + 1);

const dstGasPrice = await EvmHandler.getGasPrice(dstChain);
const dstGasPrice = await evmHandler.getGasPrice(dstChain);

const quote: Quote = {
quote: {
Expand Down
8 changes: 3 additions & 5 deletions src/api/status.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,12 @@
import { type Request, type Response } from "express";
import { messageQueue } from "../relay/queue";
import {
EvmHandler,
type RequestForExecutionWithId,
} from "../relay/platform/evm";
import { evmHandler } from "../relay/evm";
import { enabledChains, type ChainConfig } from "../chains";
import {
RelayStatus,
type Capabilities,
type RelayRequestData,
type RequestForExecutionWithId,
} from "../types";
import {
fromHex,
Expand Down Expand Up @@ -88,7 +86,7 @@ export const statusHandler = async (req: Request, res: Response) => {
return;
}

const requestsForExecution = await EvmHandler.getRequestsForExecution(
const requestsForExecution = await evmHandler.getRequestsForExecution(
txHash,
chainConfig,
);
Expand Down
1 change: 1 addition & 0 deletions src/chains.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ export interface ChainConfig {
nativeDecimals: number;
capabilities: Capabilities;
coreContractAddress: string;
nttMultiReceiveWithGasDropOffAddress: string;
viemChain?: Chain;
}

Expand Down
3 changes: 3 additions & 0 deletions src/consts.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,6 @@ export const EMPTY_ADDRESS = padHex(
"0x0000000000000000000000000000000000000000000000000000000000000000",
{ size: 32 },
);

export const NTT_TOKEN_BALANCE_STORE =
"0x52c63247e1f47db19d5ce0460030c497f067ca4cebf71ba98eeadabe20bace00";
Loading
Loading