Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Router contract example #214

Draft
wants to merge 77 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
77 commits
Select commit Hold shift + click to select a range
936b7ab
Router contract example
fadeev Nov 4, 2024
ce805f1
test authenticated and arbitrary calls
fadeev Nov 4, 2024
e5698aa
wip
fadeev Nov 6, 2024
d9327b1
fix arbitrary call
fadeev Nov 7, 2024
bee6e01
wip
fadeev Nov 7, 2024
c58d68c
it works now
fadeev Nov 7, 2024
4ec97a0
refactor
fadeev Nov 7, 2024
dc9aaa3
check localnet
fadeev Nov 8, 2024
2b827bc
Update hello to auth calls
fadeev Nov 8, 2024
afa11f1
remove omnichain examples
fadeev Nov 8, 2024
b6a444d
wip
fadeev Nov 8, 2024
a5e15a1
swap works
fadeev Nov 8, 2024
50e7217
swap
fadeev Nov 9, 2024
f8357ad
deps and remove omnichain swap
fadeev Nov 11, 2024
b0f3d1b
nft: update toolkit
fadeev Nov 11, 2024
3150e9c
nft: sender and update localnet
fadeev Nov 11, 2024
d687d9c
hello: rename contracts to universal and connected
fadeev Nov 11, 2024
ff28b85
rename hello to calls
fadeev Nov 11, 2024
e5f6c5f
Merge branch 'main' into auth-call-hello-swap
fadeev Nov 11, 2024
b6886bf
rename to call
fadeev Nov 11, 2024
d420ab7
rename to call
fadeev Nov 11, 2024
936d399
call: depositAndCall
fadeev Nov 11, 2024
7476874
call: add deposit function
fadeev Nov 11, 2024
c2410f0
call: universal withdraw
fadeev Nov 11, 2024
ed3e800
call: withdraw and call arbitrary
fadeev Nov 11, 2024
68217a5
call: fix withdraw and call
fadeev Nov 12, 2024
c5e2348
onCall: remove return
fadeev Nov 12, 2024
5e05fb0
call: deposit/depositAndCall ERC-20s
fadeev Nov 12, 2024
deffb4d
returns bytes 4
fadeev Nov 12, 2024
382e08c
slither
fadeev Nov 12, 2024
f05a97c
call: reverts
fadeev Nov 12, 2024
f7b583a
hello example
fadeev Nov 13, 2024
5eb0da9
remove unused improts
fadeev Nov 13, 2024
1d72aee
slither
fadeev Nov 13, 2024
5b6234f
wip
fadeev Nov 15, 2024
44f7d72
nft: fix localnet
fadeev Nov 15, 2024
57ceeb8
rename test.sh to localnet.sh
fadeev Nov 16, 2024
6513b52
rename test.sh to localnet.sh
fadeev Nov 16, 2024
c1ab35e
rename test.sh to localnet.sh
fadeev Nov 16, 2024
8331f22
token: consistency
fadeev Nov 17, 2024
01700ef
wip
fadeev Nov 17, 2024
29bb170
fix
fadeev Nov 17, 2024
0b7ac4c
immutable
fadeev Nov 17, 2024
34e87b4
import types
fadeev Nov 17, 2024
822cb23
fix revert
fadeev Nov 17, 2024
85f91be
nft: rename sender to receiver
fadeev Nov 18, 2024
1495357
replace system contract with uniswap router
fadeev Nov 18, 2024
1df6664
token: deploy task
fadeev Nov 18, 2024
f5ad522
token: replace system contract with uniswap router
fadeev Nov 18, 2024
051ee41
default addresses
fadeev Nov 18, 2024
cfaf6fb
default addresses
fadeev Nov 18, 2024
9985dc7
add localnet to gitignore
fadeev Nov 18, 2024
757c438
remove default uniswap address
fadeev Nov 18, 2024
0cbaa24
nft: withdrawAndCall
fadeev Nov 18, 2024
13f3299
nft: return extra tokens to sender, handle a case where receiver is n…
fadeev Nov 18, 2024
75438c3
token: return to sender
fadeev Nov 18, 2024
aa55fa3
nft/token: handle revert on zetachain
fadeev Nov 18, 2024
fd03f00
fix
fadeev Nov 18, 2024
91b8121
remove placeholder event
fadeev Nov 18, 2024
1bda9b7
token: zero address validation
fadeev Nov 19, 2024
84beed4
swap: zero address validation
fadeev Nov 19, 2024
4cfaa55
immutable gas limit
fadeev Nov 19, 2024
16d8c13
rename counterparty
fadeev Nov 20, 2024
5013b00
rename counterparty
fadeev Nov 20, 2024
6a15652
rename counterparty
fadeev Nov 20, 2024
52251cf
update localnet
fadeev Nov 20, 2024
0bb2382
Merge branch 'auth-call-hello-swap' into router-example
fadeev Nov 20, 2024
b570b43
rename script
fadeev Nov 20, 2024
8a7516b
refactor
fadeev Nov 20, 2024
66ec893
refactor
fadeev Nov 20, 2024
58c95da
refactor
fadeev Nov 20, 2024
5ee524f
base contract
fadeev Nov 20, 2024
33281e8
amount
fadeev Nov 21, 2024
d9c5566
support for erc20 target tokens (blocked)
fadeev Nov 21, 2024
6d8c76e
wip
fadeev Nov 28, 2024
11af7b7
merge main
fadeev Nov 29, 2024
cee34b6
remove bytes to address
fadeev Nov 29, 2024
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
6 changes: 6 additions & 0 deletions examples/router/.eslintignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
.yarn
artifacts
cache
coverage
node_modules
typechain-types
47 changes: 47 additions & 0 deletions examples/router/.eslintrc.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
const path = require("path");

/**
* @type {import("eslint").Linter.Config}
*/
module.exports = {
env: {
browser: false,
es2021: true,
mocha: true,
node: true,
},
extends: ["plugin:prettier/recommended"],
parser: "@typescript-eslint/parser",
parserOptions: {
ecmaVersion: 12,
},
plugins: [
"@typescript-eslint",
"prettier",
"simple-import-sort",
"sort-keys-fix",
"typescript-sort-keys",
],
rules: {
"@typescript-eslint/sort-type-union-intersection-members": "error",
camelcase: "off",
"simple-import-sort/exports": "error",
"simple-import-sort/imports": "error",
"sort-keys-fix/sort-keys-fix": "error",
"typescript-sort-keys/interface": "error",
"typescript-sort-keys/string-enum": "error",
},
settings: {
"import/parsers": {
"@typescript-eslint/parser": [".js", ".jsx", ".ts", ".tsx", ".d.ts"],
},
"import/resolver": {
node: {
extensions: [".js", ".jsx", ".ts", ".tsx", ".d.ts"],
},
typescript: {
project: path.join(__dirname, "tsconfig.json"),
},
},
},
};
19 changes: 19 additions & 0 deletions examples/router/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
node_modules
.env
coverage
coverage.json
typechain
typechain-types
dependencies

# Hardhat files
cache
artifacts

# Foundry files
out
cache_forge

access_token

localnet.json
21 changes: 21 additions & 0 deletions examples/router/LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
MIT License

Copyright (c) 2023 ZetaChain

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
4 changes: 4 additions & 0 deletions examples/router/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# NFT Example

This example currently only works with localnet `v4.0.0-rc*`, which supports
authenticated calls and multiple EVM chains.
85 changes: 85 additions & 0 deletions examples/router/contracts/Connected.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;

import "./ConnectedRouter.sol";

contract Connected is ConnectedRouter {
event OnMessageReceiveEvent();
event OnMessageRevertEvent();

constructor(
address payable gateway,
address owner,
address router
) ConnectedRouter(gateway, owner, router) {}

function onMessageReceive(
bytes memory data,
address sender,
uint256 amount
) internal override {
emit OnMessageReceiveEvent();
}

function onMessageRevert(
bytes memory data,
address sender,
uint256 amount
) internal override {
emit OnMessageRevertEvent();
// Revert from destination chain
}

function onRevert(
RevertContext calldata context
) external payable override onlyGateway {
if (context.sender != router) revert("Unauthorized");
emit OnRevertEvent("Event from onRevert()", context);
// Revert from ZetaChain
}

function sendMessage(
address targetToken,
bytes memory data,
CallOptions memory callOptions,
RevertOptions memory revertOptions
) external payable {
bytes memory message = abi.encode(
abi.encodePacked(counterparty),
targetToken,
data,
callOptions,
revertOptions
);
gateway.depositAndCall{value: msg.value}(
router,
message,
revertOptions
);
}

// function sendMessage(
// address targetToken,
// uint256 amount,
// address asset,
// bytes memory data,
// CallOptions memory callOptions,
// RevertOptions memory revertOptions
// ) external {
// bytes memory message = abi.encode(
// abi.encodePacked(counterparty),
// targetToken,
// data,
// callOptions,
// revertOptions
// );
// if (!IERC20(asset).transferFrom(msg.sender, address(this), amount)) {
// revert TransferFailed();
// }
// if (!IERC20(asset).approve(address(gateway), amount)) {
// revert ApprovalFailed();
// }

// gateway.depositAndCall(router, amount, asset, message, revertOptions);
// }
}
86 changes: 86 additions & 0 deletions examples/router/contracts/ConnectedRouter.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
// SPDX-License-Identifier: MIT
pragma solidity 0.8.26;

import "@openzeppelin/contracts/access/Ownable.sol";
import "@zetachain/protocol-contracts/contracts/evm/GatewayEVM.sol";
import {RevertContext} from "@zetachain/protocol-contracts/contracts/Revert.sol";
import {CallOptions} from "@zetachain/protocol-contracts/contracts/zevm/interfaces/IGatewayZEVM.sol";

contract ConnectedRouter is Ownable {
GatewayEVM public immutable gateway;
uint256 private _nextTokenId;
address public counterparty;
address public router;

event HelloEvent(string, string);
event OnCallEvent(string);
event OnRevertEvent(string, RevertContext);

error Unauthorized();
error TransferFailed();
error ApprovalFailed();

function setCounterparty(address contractAddress) external onlyOwner {
counterparty = contractAddress;
}

modifier onlyGateway() {
if (msg.sender != address(gateway)) revert Unauthorized();
_;
}

constructor(
address payable gatewayAddress,
address ownerAddress,
address routerAddress
) Ownable(ownerAddress) {
gateway = GatewayEVM(gatewayAddress);
router = routerAddress;
}

function onCall(
MessageContext calldata context,
bytes calldata message
) external payable onlyGateway returns (bytes4) {
if (context.sender != router) revert Unauthorized();
(bytes memory data, address sender, uint256 amount, bool isCall) = abi
.decode(message, (bytes, address, uint256, bool));

if (sender != counterparty) revert Unauthorized();

if (isCall) {
onMessageReceive(data, sender, amount);
} else {
onMessageRevert(data, sender, amount);
}
return "";
}

// onRevert is executed when router's onCall reverts
function onRevert(
RevertContext calldata context
) external payable virtual onlyGateway {
if (context.sender != router) revert("Unauthorized");
emit OnRevertEvent("Event from onRevert()", context);
}

function onMessageReceive(
bytes memory data,
address sender,
uint256 amount
) internal virtual {
// To be overridden in the child contract
}

function onMessageRevert(
bytes memory data,
address sender,
uint256 amount
) internal virtual {
// To be overridden in the child contract
}

receive() external payable {}

fallback() external payable {}
}
Loading
Loading