Skip to content

Commit

Permalink
Add Blocknative (#12)
Browse files Browse the repository at this point in the history
* Add Blocknative (#1)

* Add blocknative tx-preview

* Linitng

* Merge commits from public repo (#2)

* Feature | Misc updates (#3)

* Update per mds1 comments - add gasUsed field from simulation and console.log it

* Makefile save and Readme update
  • Loading branch information
alexcampbelling authored Mar 7, 2022
1 parent 782d204 commit 43ca8d5
Show file tree
Hide file tree
Showing 6 changed files with 90 additions and 0 deletions.
4 changes: 4 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@ export TENDERLY_ACCESS_TOKEN=yourAccessToken
# Tenderly project slug, found in the URL of your project: https://dashboard.tenderly.co/<username>/<project_slug>/transactions
export TENDERLY_PROJECT_SLUG=projectName

# keys required for Blocknative simulation -> https://explorer.blocknative.com/account
export BN_API_KEY = yourBlocknativeApiKey
export BN_SECRET_KEY = yourBlocknativeSecretKey

# clears caches for ganache and hardhat
export CLEAR_CACHE=0

Expand Down
1 change: 1 addition & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,5 @@ benchmark-dapptools :; bash scripts/benchmark-dapptools.sh
benchmark-foundry :; bash scripts/benchmark-foundry.sh
benchmark-ganache :; bash scripts/benchmark-ganache.sh
benchmark-hardhat :; bash scripts/benchmark-hardhat.sh
benchmark-blocknative :; bash scripts/benchmark-blocknative.sh
benchmark-tenderly :; bash scripts/benchmark-tenderly.sh
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ Notes:
- Foundry does not cache RPC results to disk between runs, so the "Local, With Cache" column has been left as N/A
- Ganache results are currently not shown due to a bug documented in issue [#7](https://github.com/mds1/convex-shutdown-simulation/issues/7)
- If Tenderly returns a 400, it's because the simulation timed out which may happen if they don't have data cached on the servers. Attempting to run the simulation in their UI seems to resolve this
- Blocknative simulates on tip block height currently, with archival node simulations are planned for historical simulation.
- Local benchmarks were run against a local Erigon node on macOS 11.6.2 with a 2.3 GHz 8-Core Intel Core i9 and 32 GB 2667 MHz DDR4 (The goal is to benchmark tool performance, which is why a local node is used&mdash;if benchmarking against a remote node such as Infura or Alchemy, network calls become the driver of execution time)
- Just because gas used differs between tools does not mean only one is correct. For example, Foundry and Dapptools exclude the 21,064 intrinsic gas from the reported gas used, but other tools may not. However, at this time it is not known which value is the truth value. Similarly, dapptools does not include refunds in their reported gas used

Expand Down
3 changes: 3 additions & 0 deletions scripts/benchmark-all.sh
Original file line number Diff line number Diff line change
Expand Up @@ -10,5 +10,8 @@ bash scripts/benchmark-ganache.sh
echo -e "\n--- BENCHMARKING HARDHAT ---"
bash scripts/benchmark-hardhat.sh

echo -e "\n--- BENCHMARKING BLOCKNATIVE ---"
bash scripts/benchmark-blocknative.sh

echo -e "\n--- BENCHMARKING TENDERLY ---"
bash scripts/benchmark-tenderly.sh
3 changes: 3 additions & 0 deletions scripts/benchmark-blocknative.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
. ./.env

time yarn ts-node ./scripts/convex.blocknative.ts
78 changes: 78 additions & 0 deletions scripts/convex.blocknative.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
import fetchUrl, { FETCH_OPT } from 'micro-ftch'
import { Contract } from '@ethersproject/contracts'
import { JsonRpcProvider } from '@ethersproject/providers'

// Add your keys via .env
const credentials = process.env.BN_API_KEY + ':' + process.env.BN_SECRET_KEY
const bnEndPoint = 'https://api.blocknative.com/simulate'

async function main(): Promise<void> {
// Get owner address - gracefully copied homework from the Tenderly benchmark script :^)
const convexAddr = '0xF403C135812408BFbE8713b5A23a04b3D48AAE31'
const provider = new JsonRpcProvider(process.env.ETH_RPC_URL)
const abi = ['function owner() view external returns (address)']
const convex = new Contract(convexAddr, abi, provider)

// We use current blocknumber owner as Blocknative simulates on tip block number as of now
const ownerAddr = await convex.owner()

// Double check the keys were given above!
if (credentials === ':') {
throw new Error('No credentials for simulation endpoint given!')
}

// Information to how tx-preview works is here:
// https://docs.blocknative.com/simulation-platform/transaction-preview-api
const fetchOptions = <Partial<FETCH_OPT>>{
method: 'POST',
type: 'json',
full: true,
expectStatusCode: false,
headers: {
'Content-Type': 'application/json',
'credentials': credentials
},
data: {
system: "ethereum",
network: "main",
transaction: {
to: convexAddr,
from: ownerAddr,
gas: Number(process.env.GAS_LIMIT),
gasPrice: 0,
input: "0x354af919",
value: 0
}
}
}

console.time('Simulate-shutdown')

// Fetch simulation via Blocknative RESTful endpoint
const response = await fetchUrl(bnEndPoint, fetchOptions)

if (response.status !== 200) {
console.log(`Simulation error code: ${response.status} - ${JSON.stringify(response.body)}`)
process.exit(1)
}

console.timeEnd('Simulate-shutdown')

// Print the response with decoded internal transactions, address
// balance changes of ETH and tokens, and any errors in EVm execution
// console.log(JSON.stringify(response.body, null, 2))

// Print gasUsed for execution during certain block
console.log(`Simulation generated on blocknumber: ${response.body.simulatedBlockNumber}`)
console.log(`Gas used: ${response.body.gasUsed}`)

// Blocknative's E2E latency
console.log(`Blocknative's end to end latency: ${response.body.simDetails.e2eMs}ms`)
}

main()
.then(() => process.exit(0))
.catch((error: Error) => {
console.error(error)
process.exit(1)
});

0 comments on commit 43ca8d5

Please sign in to comment.