Commit 6c685d5f authored by Mark Tyneway's avatar Mark Tyneway

integration-tests-bedrock: clean up package

Also lint now that linting rules apply
parent f71b40e7
......@@ -8,7 +8,7 @@
"lint:fix": "yarn lint:check --fix",
"lint:check": "eslint . --max-warnings=0",
"build:contracts": "forge build --root . -c contracts -o artifacts",
"test": "ts-mocha --timeout 30000 test/**/*.spec.ts",
"test": "echo 'no unit tests'",
"test:actor": "IS_LIVE_NETWORK=true ts-node actor-tests/lib/runner.ts",
"test:integration:live": "NO_NETWORK=true IS_LIVE_NETWORK=true hardhat --network optimism test",
"clean": "rimraf cache artifacts"
......@@ -31,40 +31,17 @@
"@eth-optimism/core-utils": "0.8.5",
"@eth-optimism/sdk": "1.1.6",
"@ethersproject/abstract-provider": "^5.6.1",
"@ethersproject/providers": "^5.6.8",
"@ethersproject/transactions": "^5.6.2",
"@types/chai": "^4.2.18",
"@types/chai-as-promised": "^7.1.4",
"@types/mocha": "^8.2.2",
"@types/rimraf": "^3.0.0",
"@typescript-eslint/eslint-plugin": "^4.26.0",
"@typescript-eslint/parser": "^4.26.0",
"async-mutex": "^0.3.2",
"babel-eslint": "^10.1.0",
"chai": "^4.3.4",
"chai-as-promised": "^7.1.1",
"commander": "^8.3.0",
"chai": "^4.3.4",
"dotenv": "^10.0.0",
"envalid": "^7.1.0",
"eslint": "^7.27.0",
"eslint-config-prettier": "^8.3.0",
"eslint-plugin-import": "^2.23.4",
"eslint-plugin-jsdoc": "^35.1.2",
"eslint-plugin-prefer-arrow": "^1.2.3",
"eslint-plugin-prettier": "^3.4.0",
"eslint-plugin-react": "^7.24.0",
"eslint-plugin-unicorn": "^32.0.1",
"ethereum-waffle": "^3.3.0",
"ethers": "^5.6.8",
"mocha": "^8.4.0",
"node-fetch": "^2.6.7",
"prom-client": "^14.0.1",
"rimraf": "^3.0.2",
"ts-node": "^10.7.0",
"typescript": "^4.3.5"
"ts-node": "^10.7.0"
},
"dependencies": {
"ts-mocha": "^9.0.2",
"rlp": "^3.0.0",
"winston": "^3.7.2"
}
}
......@@ -2,30 +2,41 @@
// can fall behind.
/* Imports: External */
import { BigNumber, constants, Contract, ContractReceipt, utils, Wallet } from 'ethers'
import {
BigNumber,
constants,
Contract,
ContractReceipt,
utils,
Wallet,
} from 'ethers'
import { awaitCondition } from '@eth-optimism/core-utils'
import * as rlp from 'rlp'
import { Block } from '@ethersproject/abstract-provider'
/* Imports: Internal */
import env from './shared/env'
import { expect } from './shared/setup'
import winston from 'winston'
import { predeploys } from '@eth-optimism/contracts'
const l2ToL1MessagePasserArtifact = require('../../contracts/artifacts/contracts/L2/L2ToL1MessagePasser.sol/L2ToL1MessagePasser.json')
const l2OOracleArtifact = require('../../contracts/artifacts/contracts/L1/L2OutputOracle.sol/L2OutputOracle.json')
import env from './shared/env'
import { expect } from './shared/setup'
import l2ToL1MessagePasserArtifact from '../../contracts-bedrock/artifacts/contracts/L2/L2ToL1MessagePasser.sol/L2ToL1MessagePasser.json'
import l2OOracleArtifact from '../../contracts-bedrock/artifacts/contracts/L1/L2OutputOracle.sol/L2OutputOracle.json'
/**
* Calculates the target output timestamp to make the withdrawal proof against. ie. the first
* output with a timestamp greater than the burn block timestamp.
*
* @param {Contract} oracle Address of the L2 Output Oracle.
* @param {number} withdrawalTimestamp L2 timestamp of the block the withdrawal was made in.
*/
const getTargetOutput = async (oracle: Contract, withdrawalTimestamp: number) => {
const getTargetOutput = async (
oracle: Contract,
withdrawalTimestamp: number
) => {
const submissionInterval = (await oracle.SUBMISSION_INTERVAL()).toNumber()
const startingBlockTimestamp = (await oracle.STARTING_BLOCK_TIMESTAMP()).toNumber()
let nextTimestamp = (await oracle.nextTimestamp()).toNumber()
const startingBlockTimestamp = (
await oracle.STARTING_BLOCK_TIMESTAMP()
).toNumber()
const nextTimestamp = (await oracle.nextTimestamp()).toNumber()
let targetOutputTimestamp
if (withdrawalTimestamp < nextTimestamp) {
// Just use the next timestamp
......@@ -34,17 +45,15 @@ const getTargetOutput = async (oracle: Contract, withdrawalTimestamp: number) =>
// Calculate the first timestamp greater than the burnBlock which will be appended.
targetOutputTimestamp =
Math.ceil(
(withdrawalTimestamp - startingBlockTimestamp)
/ submissionInterval
)
* submissionInterval
+ startingBlockTimestamp
(withdrawalTimestamp - startingBlockTimestamp) / submissionInterval
) *
submissionInterval +
startingBlockTimestamp
}
return targetOutputTimestamp
}
describe('Withdrawals', () => {
let logger: winston.Logger
let portal: Contract
......@@ -58,7 +67,7 @@ describe('Withdrawals', () => {
withdrawer = new Contract(
predeploys.OVM_L2ToL1MessagePasser,
l2ToL1MessagePasserArtifact.abi,
l2ToL1MessagePasserArtifact.abi
)
})
......@@ -78,7 +87,9 @@ describe('Withdrawals', () => {
recipient: recipient.address,
})
logger.info('Depositing to new address on L2')
let tx = await portal.connect(env.l1Wallet).depositTransaction(
let tx = await portal
.connect(env.l1Wallet)
.depositTransaction(
recipient.address,
utils.parseEther('1.337'),
gasLimit,
......@@ -86,7 +97,7 @@ describe('Withdrawals', () => {
[],
{
value: utils.parseEther('1.337'),
},
}
)
await tx.wait()
......@@ -111,7 +122,7 @@ describe('Withdrawals', () => {
[],
{
value,
},
}
)
const receipt: ContractReceipt = await tx.wait()
expect(receipt.events!.length).to.eq(1)
......@@ -135,8 +146,8 @@ describe('Withdrawals', () => {
value,
gasLimit,
'0x',
],
),
]
)
)
const included = await withdrawer.sentMessages(withdrawalHash)
......@@ -150,22 +161,30 @@ describe('Withdrawals', () => {
portal = portal.connect(recipient)
const oracle = new Contract(
await portal.L2_ORACLE(),
l2OOracleArtifact.abi,
l2OOracleArtifact.abi
).connect(recipient)
const targetOutputTimestamp = await getTargetOutput(oracle, burnBlock.timestamp)
const targetOutputTimestamp = await getTargetOutput(
oracle,
burnBlock.timestamp
)
// Set the timeout based on the diff between latest output and target output timestamp.
let latestBlockTimestamp = (await oracle.latestBlockTimestamp()).toNumber()
let latestBlockTimestamp = (
await oracle.latestBlockTimestamp()
).toNumber()
let difference = targetOutputTimestamp - latestBlockTimestamp
this.timeout(difference * 5000)
let output: string
await awaitCondition(async () => {
await awaitCondition(
async () => {
const proposal = await oracle.getL2Output(targetOutputTimestamp)
output = proposal.outputRoot
latestBlockTimestamp = (await oracle.latestBlockTimestamp()).toNumber()
if(targetOutputTimestamp - latestBlockTimestamp < difference){
latestBlockTimestamp = (
await oracle.latestBlockTimestamp()
).toNumber()
if (targetOutputTimestamp - latestBlockTimestamp < difference) {
// Only log when a new output has been appended
difference = targetOutputTimestamp - latestBlockTimestamp
logger.info('Waiting for output submission', {
......@@ -175,14 +194,19 @@ describe('Withdrawals', () => {
output,
})
}
return output != constants.HashZero
}, 2000, 2*difference)
return output !== constants.HashZero
},
2000,
2 * difference
)
// suppress compilation errors since Typescript cannot detect
// that awaitCondition above will throw if it times out.
output = output!
const blocksSinceBurn = Math.floor((targetOutputTimestamp - burnBlock.timestamp) / 2)
const blocksSinceBurn = Math.floor(
(targetOutputTimestamp - burnBlock.timestamp) / 2
)
const targetBlockNum = burnBlock.number + blocksSinceBurn + 1
const targetBlockNumHex = utils.hexValue(targetBlockNum)
const storageSlot = '00'.repeat(31) + '01' // i.e the second variable declared in the contract
......@@ -192,19 +216,19 @@ describe('Withdrawals', () => {
targetBlockNumHex,
])
const {stateRoot: targetStateRoot, hash: targetHash} = await env.l2Provider.send(
'eth_getBlockByNumber',
[
const { stateRoot: targetStateRoot, hash: targetHash } =
await env.l2Provider.send('eth_getBlockByNumber', [
targetBlockNumHex,
false,
],
)
])
const finalizationPeriod = (await portal.FINALIZATION_PERIOD()).toNumber()
logger.info('Waiting finalization period', {
seconds: finalizationPeriod,
})
await new Promise((resolve) => setTimeout(resolve, finalizationPeriod * 1000))
await new Promise((resolve) =>
setTimeout(resolve, finalizationPeriod * 1000)
)
logger.info('Finalizing withdrawal')
const initialBal = await recipient.getBalance()
......@@ -225,7 +249,7 @@ describe('Withdrawals', () => {
rlp.encode(proof.storageProof[0].proof),
{
gasLimit,
},
}
)
await tx.wait()
const finalBal = await recipient.getBalance()
......
......@@ -5,9 +5,8 @@ import { awaitCondition } from '@eth-optimism/core-utils'
/* Imports: Internal */
import { defaultTransactionFactory } from './shared/utils'
import env from './shared/env'
const counterArtifact = require('../artifacts/Counter.sol/Counter.json')
const multiDepositorArtifact = require('../artifacts/MultiDepositor.sol/MultiDepositor.json')
import counterArtifact from '../artifacts/Counter.sol/Counter.json'
import multiDepositorArtifact from '../artifacts/MultiDepositor.sol/MultiDepositor.json'
describe('Deposits', () => {
let portal: Contract
......@@ -29,7 +28,7 @@ describe('Deposits', () => {
[],
{
value: tx.value,
},
}
)
await result.wait()
......@@ -44,7 +43,7 @@ describe('Deposits', () => {
const value = utils.parseEther('0.1')
const factory = new ContractFactory(
multiDepositorArtifact.abi,
multiDepositorArtifact.bytecode.object,
multiDepositorArtifact.bytecode.object
).connect(env.l1Wallet)
const contract = await factory.deploy(portal.address)
await contract.deployed()
......@@ -63,7 +62,7 @@ describe('Deposits', () => {
const value = utils.parseEther('0.1')
const factory = new ContractFactory(
counterArtifact.abi,
counterArtifact.bytecode.object,
counterArtifact.bytecode.object
)
const tx = await factory.getDeployTransaction()
const result = await portal.depositTransaction(
......@@ -73,8 +72,8 @@ describe('Deposits', () => {
true,
tx.data,
{
value: value,
},
value,
}
)
await result.wait()
const l2Nonce = await env.l2Wallet.getTransactionCount()
......
......@@ -5,8 +5,7 @@ import { ContractFactory, Wallet } from 'ethers'
import { expect } from './shared/setup'
import { defaultTransactionFactory } from './shared/utils'
import env from './shared/env'
const counterArtifact = require('../artifacts/Counter.sol/Counter.json')
import counterArtifact from '../artifacts/Counter.sol/Counter.json'
describe('RPCs', () => {
let wallet: Wallet
......@@ -38,10 +37,10 @@ describe('RPCs', () => {
it('should correctly process a contract creation', async () => {
const factory = new ContractFactory(
counterArtifact.abi,
counterArtifact.bytecode.object,
counterArtifact.bytecode.object
).connect(wallet)
const counter = await factory.deploy({
gasLimit: 1_000_000
gasLimit: 1_000_000,
})
await counter.deployed()
expect(await env.l2Provider.getCode(counter.address)).not.to.equal('0x')
......
......@@ -2,27 +2,26 @@
import { Wallet, providers, Contract } from 'ethers'
import { bool, cleanEnv, num, str } from 'envalid'
import dotenv from 'dotenv'
import winston, { info } from 'winston'
import winston from 'winston'
const {combine, timestamp, printf, colorize, align} = winston.format
const { combine, timestamp, printf, colorize, align } = winston.format
/* Imports: Internal */
const portalArtifact = require('../../../contracts/artifacts/contracts/L1/OptimismPortal.sol/OptimismPortal.json')
import portalArtifact from '../../../contracts-bedrock/artifacts/contracts/L1/OptimismPortal.sol/OptimismPortal.json'
dotenv.config()
const procEnv = cleanEnv(process.env, {
L1_URL: str({default: 'http://localhost:8545'}),
L1_POLLING_INTERVAL: num({default: 10}),
L1_URL: str({ default: 'http://localhost:8545' }),
L1_POLLING_INTERVAL: num({ default: 10 }),
L2_URL: str({default: 'http://localhost:9545'}),
L2_POLLING_INTERVAL: num({default: 1}),
L2_URL: str({ default: 'http://localhost:9545' }),
L2_POLLING_INTERVAL: num({ default: 1 }),
OPTIMISM_PORTAL_ADDRESS: str(),
PRIVATE_KEY: str({
default:
'ac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80',
default: 'ac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80',
}),
MOCHA_TIMEOUT: num({
......@@ -72,13 +71,13 @@ export class OptimismEnv {
this.l2Provider = l2Provider
this.optimismPortal = new Contract(
procEnv.OPTIMISM_PORTAL_ADDRESS,
portalArtifact.abi,
portalArtifact.abi
)
this.logger = winston.createLogger({
level: process.env.LOG_LEVEL || 'info',
format: combine(
{
transform(info) {
transform: (info) => {
// @ts-ignore
const args = info[Symbol.for('splat')]
const meta = args ? args[0] : null
......@@ -87,16 +86,18 @@ export class OptimismEnv {
return info
},
},
colorize({all: true}),
colorize({ all: true }),
timestamp({
format: 'YYYY-MM-DD hh:mm:ss.SSS A',
}),
align(),
printf((info) => `[${info.timestamp}] ${info.level}: ${info.message}`),
printf((info) => `[${info.timestamp}] ${info.level}: ${info.message}`)
),
transports: [new winston.transports.Stream({
transports: [
new winston.transports.Stream({
stream: process.stderr,
})],
}),
],
})
}
}
......
......@@ -8,4 +8,3 @@ export const defaultTransactionFactory = () => {
value: BigNumber.from(0),
}
}
{
"extends": "../../tsconfig.json",
"compilerOptions": {
"target": "es2018",
"module": "commonjs",
"strict": true,
"esModuleInterop": true,
"outDir": "dist",
"declaration": true,
"resolveJsonModule": true
"outDir": "./dist"
},
"include": [
"src/**/*",
"./test",
"./artifacts/**/*.json",
"./tasks/**/*.ts",
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment