Giter Club home page Giter Club logo

721's Introduction

Foundry template

Initialisation

forge init myProject
cd myProject

Install dependencies

cd myProject
forge install <https://github.com/library-to-import>@branch

Import lib in contracts (via remappings)

forge remappings > remappings.txt
# ./remappings.txt
ds-test/=lib/forge-std/lib/ds-test/src/
forge-std/=lib/forge-std/src/
openzeppelin-contracts/=lib/openzeppelin-contracts/contracts

Import in contract:

// SPDX-License-Identifier: UNLICENSED

pragma solidity ^0.8.13;

import {Ownable} from "openzeppelin-contracts/access/Ownable.sol";

contract AnyContract is Ownable {}

Compile contract

Set compiler version in foundry.toml

solc = "0.8.13"

Compile and log contracts sizes:

forge build --sizes

Inspect compiled contracts:

forge inspect <contract_name> <element_to_inspect>

Contract metadata:

forge inspect <contract_name> metadata

bytecode:

forge inspect <contract_name> bytecode

abi:

forge inspect <contract_name> abi

Inspect storage can be very useful:

forge inspect <contract_name> storage --pretty

Unit testing

Create file in test/AnyContract.t.sol

Import the testing library in the test contract:

// SPDX-License-Identifier: UNLICENSED

pragma solidity ^0.8.13;

import {Test} from "forge-std/Test.sol";
import {VmSafe} from "forge-std/Vm.sol";

import {AnyContract} from "src/AnyContract.sol";

contract AnyContract_test is Test {}

Add a setUp function for "beforeAll" conditions:

{...}
import {AnyContract} from "src/AnyContract.sol";

contract AnyContract_test is Test {
  function setUp() public {
    AnyContract anyContract = new AnyContract();
  }
}

Create an unit test with function starting with test:

{...}

contract AnyContract_test is Test {
  {...}

  function test_functionName_ConditionToTest() public {}
}

Run tests with differents amount of details

forge test
forge test -vv
forge test -vvvv

Read about the Test library: Assertion cheatcodes Execution environment cheatcode

Forking a network in tests

Set a network in foundry.toml:

[rpc_endpoints]
anvil = "http://localhost:8545/"
goerli = "https://ethereum-goerli-rpc.allthatnode.com"

RPC urls can be founds on chainlist.org, consider using an API KEY with nodes providers (like Infura, POKT network, ...) for large amount of transactions or calls.

Fork the network for the whole tests:

forge test -f goerli

Fork the network only in specific tests:

{...}

contract AnyContract_test is Test {
  {...}

  function test_functionName_ForkCondition() public {
    vm.createSelectFork("goerli");

    // try by logging chain variable
    emit log_named_uint("chain ID", block.chainid);
    emit log_named_uint("block height", block.number);
  }
}

Increase tests speed by caching calls to the forked network:

{...}

contract AnyContract_test is Test {
  {...}

  function test_functionName_ForkCondition() public {
    // stick to a specific block number
    vm.createSelectFork("goerli", 8486194);

    emit log_named_uint("chain ID", block.chainid);
    emit log_named_uint("block height", block.number);
  }
}

Foundry will cache all calls sended to the forked network, so the next time forge test is run, data are fetched in the cache instead of the network.

Check Foundry cache:

forge cache ls

Deploy contracts

Write scripts in script/my_script.s.sol and import the script library:

// SPDX-License-Identifier: UNLICENSED

pragma solidity ^0.8.13;

import "forge-std/Script.sol";

import {AnyContract} from "src/AnyContract.sol";

contract deploy is Script {}

You can add private keys in .env and read them in the script:

DEPLOYER_ANVIL=ac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80

Add the "broadcast" block to sign transaction with a specific private key:

contract deploy is Script {
  function run() public {
    // read private key in .env
    uint256 pk = vm.envUint("DEPLOYER_ANVIL");
    address deployer = vm.addr(pk);

    // broadcast block
    vm.startBroadcast(pk);

    // deploy and call contracts here

    vm.stopBroadcast();
  }
}

Test your script with:

forge script deploy

Foundry will execute the function run() in your script.

Using local blockchain

Launch the local blockchain with:

anvil

Dry run your script on the network:

forge script deploy --rpc-url anvil

Dry allow to run your script and create transaction which can be checked in broadcast

Run and broadcast transaction:

forge script deploy --rpc-url anvil --broadcast

Using testnet

Dry run your script is always a good practice:

forge script deploy --rpc-url goerli

Then:

forge script deploy --rpc-url goerli --broadcast

Verify contract

Sourcify:

forge verify-contract <address> <contract_name> --chain <chain_id> --verifier sourcify

Etherscan: Make sure you have set the ETHERSCAN_KEY in .env

source .env
forge verify-contract <address> <contract_name> --chain <network_alias | chain_id> $ETHERSCAN_KEY --watch

If the contract has been deployed with arguments:

cast abi-encode "constructor(address,uint256)" 0xdaab... 500000

Then add the flag --constructor-args with the above result to the forge verify-contract command


Contributors: Raph, xDrKush, Yamakhala, Amine

721's People

Contributors

benmissi-a avatar

Watchers

 avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.