Commit bee9113c authored by mergify[bot]'s avatar mergify[bot] Committed by GitHub

Merge branch 'develop' into sc/cmon-init

parents 4ee0efca 70fd8913
---
'@eth-optimism/common-ts': minor
---
Add option to configure body parser
.github .github
.vscode
node_modules node_modules
**/node_modules
.env .env
**/.env **/.env
......
...@@ -3,21 +3,18 @@ package batcher ...@@ -3,21 +3,18 @@ package batcher
import ( import (
"context" "context"
"fmt" "fmt"
"math/big"
_ "net/http/pprof" _ "net/http/pprof"
"os" "os"
"os/signal" "os/signal"
"syscall" "syscall"
"time" "time"
"github.com/urfave/cli"
oplog "github.com/ethereum-optimism/optimism/op-service/log" oplog "github.com/ethereum-optimism/optimism/op-service/log"
opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics" opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics"
oppprof "github.com/ethereum-optimism/optimism/op-service/pprof" oppprof "github.com/ethereum-optimism/optimism/op-service/pprof"
oprpc "github.com/ethereum-optimism/optimism/op-service/rpc" oprpc "github.com/ethereum-optimism/optimism/op-service/rpc"
opsigner "github.com/ethereum-optimism/optimism/op-signer/client"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
"github.com/urfave/cli"
) )
const ( const (
...@@ -30,98 +27,75 @@ const ( ...@@ -30,98 +27,75 @@ const (
// closure that executes the service and blocks until the service exits. The use // closure that executes the service and blocks until the service exits. The use
// of a closure allows the parameters bound to the top-level main package, e.g. // of a closure allows the parameters bound to the top-level main package, e.g.
// GitVersion, to be captured and used once the function is executed. // GitVersion, to be captured and used once the function is executed.
func Main(version string) func(cliCtx *cli.Context) error { func Main(version string, cliCtx *cli.Context) error {
return func(cliCtx *cli.Context) error { cfg := NewConfig(cliCtx)
cfg := NewConfig(cliCtx) if err := cfg.Check(); err != nil {
if err := cfg.Check(); err != nil { return fmt.Errorf("invalid CLI flags: %w", err)
return fmt.Errorf("invalid CLI flags: %w", err) }
}
l := oplog.NewLogger(cfg.LogConfig)
l.Info("Initializing Batch Submitter")
var batchSubmitter *BatchSubmitter l := oplog.NewLogger(cfg.LogConfig)
if !cfg.SignerConfig.Enabled() { l.Info("Initializing Batch Submitter")
bs, err := NewBatchSubmitter(cfg, l)
if err != nil {
l.Error("Unable to create Batch Submitter", "error", err)
return err
}
batchSubmitter = bs
} else {
signerClient, err := opsigner.NewSignerClientFromConfig(l, cfg.SignerConfig)
if err != nil {
l.Error("Unable to create Signer Client", "error", err)
return err
}
signer := func(chainID *big.Int) SignerFn {
return func(ctx context.Context, rawTx types.TxData) (*types.Transaction, error) {
tx := types.NewTx(rawTx)
return signerClient.SignTransaction(ctx, chainID, tx)
}
}
bs, err := NewBatchSubmitterWithSigner(cfg, common.HexToAddress(cfg.SignerConfig.Address), signer, l)
if err != nil {
l.Error("Unable to create Batch Submitter with signer", "error", err)
return err
}
batchSubmitter = bs
}
l.Info("Starting Batch Submitter") batchSubmitter, err := NewBatchSubmitterFromCLIConfig(cfg, l)
if err != nil {
l.Error("Unable to create Batch Submitter", "error", err)
return err
}
if err := batchSubmitter.Start(); err != nil { l.Info("Starting Batch Submitter")
l.Error("Unable to start Batch Submitter", "error", err)
return err
}
defer batchSubmitter.Stop()
ctx, cancel := context.WithCancel(context.Background()) if err := batchSubmitter.Start(); err != nil {
l.Error("Unable to start Batch Submitter", "error", err)
return err
}
defer batchSubmitter.Stop()
l.Info("Batch Submitter started") ctx, cancel := context.WithCancel(context.Background())
pprofConfig := cfg.PprofConfig
if pprofConfig.Enabled {
l.Info("starting pprof", "addr", pprofConfig.ListenAddr, "port", pprofConfig.ListenPort)
go func() {
if err := oppprof.ListenAndServe(ctx, pprofConfig.ListenAddr, pprofConfig.ListenPort); err != nil {
l.Error("error starting pprof", "err", err)
}
}()
}
registry := opmetrics.NewRegistry() l.Info("Batch Submitter started")
metricsCfg := cfg.MetricsConfig pprofConfig := cfg.PprofConfig
if metricsCfg.Enabled { if pprofConfig.Enabled {
l.Info("starting metrics server", "addr", metricsCfg.ListenAddr, "port", metricsCfg.ListenPort) l.Info("starting pprof", "addr", pprofConfig.ListenAddr, "port", pprofConfig.ListenPort)
go func() { go func() {
if err := opmetrics.ListenAndServe(ctx, registry, metricsCfg.ListenAddr, metricsCfg.ListenPort); err != nil { if err := oppprof.ListenAndServe(ctx, pprofConfig.ListenAddr, pprofConfig.ListenPort); err != nil {
l.Error("error starting metrics server", err) l.Error("error starting pprof", "err", err)
} }
}() }()
opmetrics.LaunchBalanceMetrics(ctx, l, registry, "", batchSubmitter.cfg.L1Client, batchSubmitter.addr) }
}
rpcCfg := cfg.RPCConfig registry := opmetrics.NewRegistry()
server := oprpc.NewServer( metricsCfg := cfg.MetricsConfig
rpcCfg.ListenAddr, if metricsCfg.Enabled {
rpcCfg.ListenPort, l.Info("starting metrics server", "addr", metricsCfg.ListenAddr, "port", metricsCfg.ListenPort)
version, go func() {
) if err := opmetrics.ListenAndServe(ctx, registry, metricsCfg.ListenAddr, metricsCfg.ListenPort); err != nil {
if err := server.Start(); err != nil { l.Error("error starting metrics server", err)
cancel() }
return fmt.Errorf("error starting RPC server: %w", err) }()
} opmetrics.LaunchBalanceMetrics(ctx, l, registry, "", batchSubmitter.L1Client, batchSubmitter.From)
}
interruptChannel := make(chan os.Signal, 1) rpcCfg := cfg.RPCConfig
signal.Notify(interruptChannel, []os.Signal{ server := oprpc.NewServer(
os.Interrupt, rpcCfg.ListenAddr,
os.Kill, rpcCfg.ListenPort,
syscall.SIGTERM, version,
syscall.SIGQUIT, )
}...) if err := server.Start(); err != nil {
<-interruptChannel
cancel() cancel()
_ = server.Stop() return fmt.Errorf("error starting RPC server: %w", err)
return nil
} }
interruptChannel := make(chan os.Signal, 1)
signal.Notify(interruptChannel, []os.Signal{
os.Interrupt,
os.Kill,
syscall.SIGTERM,
syscall.SIGQUIT,
}...)
<-interruptChannel
cancel()
_ = server.Stop()
return nil
} }
package batcher package batcher
import ( import (
"math/big"
"time" "time"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/ethclient"
"github.com/ethereum/go-ethereum/log"
"github.com/urfave/cli" "github.com/urfave/cli"
"github.com/ethereum-optimism/optimism/op-batcher/flags" "github.com/ethereum-optimism/optimism/op-batcher/flags"
"github.com/ethereum-optimism/optimism/op-node/sources"
opcrypto "github.com/ethereum-optimism/optimism/op-service/crypto"
oplog "github.com/ethereum-optimism/optimism/op-service/log" oplog "github.com/ethereum-optimism/optimism/op-service/log"
opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics" opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics"
oppprof "github.com/ethereum-optimism/optimism/op-service/pprof" oppprof "github.com/ethereum-optimism/optimism/op-service/pprof"
oprpc "github.com/ethereum-optimism/optimism/op-service/rpc" oprpc "github.com/ethereum-optimism/optimism/op-service/rpc"
"github.com/ethereum-optimism/optimism/op-service/txmgr"
opsigner "github.com/ethereum-optimism/optimism/op-signer/client" opsigner "github.com/ethereum-optimism/optimism/op-signer/client"
) )
type Config struct { type Config struct {
log log.Logger
L1Client *ethclient.Client
L2Client *ethclient.Client
RollupNode *sources.RollupClient
PollInterval time.Duration
TxManagerConfig txmgr.Config
From common.Address
SignerFnFactory opcrypto.SignerFactory
ChainID *big.Int
// Where to send the batch txs to.
BatchInboxAddress common.Address
// Channel creation parameters
Channel ChannelConfig
}
type CLIConfig struct {
/* Required Params */ /* Required Params */
// L1EthRpc is the HTTP provider URL for L1. // L1EthRpc is the HTTP provider URL for L1.
...@@ -89,7 +114,7 @@ type Config struct { ...@@ -89,7 +114,7 @@ type Config struct {
SignerConfig opsigner.CLIConfig SignerConfig opsigner.CLIConfig
} }
func (c Config) Check() error { func (c CLIConfig) Check() error {
if err := c.RPCConfig.Check(); err != nil { if err := c.RPCConfig.Check(); err != nil {
return err return err
} }
...@@ -109,8 +134,8 @@ func (c Config) Check() error { ...@@ -109,8 +134,8 @@ func (c Config) Check() error {
} }
// NewConfig parses the Config from the provided flags or environment variables. // NewConfig parses the Config from the provided flags or environment variables.
func NewConfig(ctx *cli.Context) Config { func NewConfig(ctx *cli.Context) CLIConfig {
return Config{ return CLIConfig{
/* Required Flags */ /* Required Flags */
L1EthRpc: ctx.GlobalString(flags.L1EthRpcFlag.Name), L1EthRpc: ctx.GlobalString(flags.L1EthRpcFlag.Name),
L2EthRpc: ctx.GlobalString(flags.L2EthRpcFlag.Name), L2EthRpc: ctx.GlobalString(flags.L2EthRpcFlag.Name),
......
...@@ -2,34 +2,28 @@ package batcher ...@@ -2,34 +2,28 @@ package batcher
import ( import (
"context" "context"
"crypto/ecdsa"
"errors" "errors"
"fmt" "fmt"
"io" "io"
"math/big" "math/big"
"strings" _ "net/http/pprof"
"sync" "sync"
"time" "time"
hdwallet "github.com/ethereum-optimism/go-ethereum-hdwallet"
"github.com/ethereum-optimism/optimism/op-node/eth" "github.com/ethereum-optimism/optimism/op-node/eth"
opcrypto "github.com/ethereum-optimism/optimism/op-service/crypto"
"github.com/ethereum-optimism/optimism/op-service/txmgr" "github.com/ethereum-optimism/optimism/op-service/txmgr"
"github.com/ethereum/go-ethereum/accounts"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
) )
// BatchSubmitter encapsulates a service responsible for submitting L2 tx // BatchSubmitter encapsulates a service responsible for submitting L2 tx
// batches to L1 for availability. // batches to L1 for availability.
type BatchSubmitter struct { type BatchSubmitter struct {
Config // directly embed the config + sources
txMgr *TransactionManager txMgr *TransactionManager
addr common.Address
cfg DriverConfig
wg sync.WaitGroup wg sync.WaitGroup
done chan struct{} done chan struct{}
log log.Logger
ctx context.Context ctx context.Context
cancel context.CancelFunc cancel context.CancelFunc
...@@ -40,63 +34,16 @@ type BatchSubmitter struct { ...@@ -40,63 +34,16 @@ type BatchSubmitter struct {
state *channelManager state *channelManager
} }
// NewBatchSubmitter initializes the BatchSubmitter, gathering any resources // NewBatchSubmitterFromCLIConfig initializes the BatchSubmitter, gathering any resources
// that will be needed during operation. // that will be needed during operation.
func NewBatchSubmitter(cfg Config, l log.Logger) (*BatchSubmitter, error) { func NewBatchSubmitterFromCLIConfig(cfg CLIConfig, l log.Logger) (*BatchSubmitter, error) {
var err error ctx := context.Background()
var sequencerPrivKey *ecdsa.PrivateKey
var addr common.Address
if cfg.PrivateKey != "" && cfg.Mnemonic != "" {
return nil, errors.New("cannot specify both a private key and a mnemonic")
}
if cfg.PrivateKey == "" {
// Parse wallet private key that will be used to submit L2 txs to the batch
// inbox address.
wallet, err := hdwallet.NewFromMnemonic(cfg.Mnemonic)
if err != nil {
return nil, err
}
acc := accounts.Account{
URL: accounts.URL{
Path: cfg.SequencerHDPath,
},
}
addr, err = wallet.Address(acc)
if err != nil {
return nil, err
}
sequencerPrivKey, err = wallet.PrivateKey(acc)
if err != nil {
return nil, err
}
} else {
sequencerPrivKey, err = crypto.HexToECDSA(strings.TrimPrefix(cfg.PrivateKey, "0x"))
if err != nil {
return nil, err
}
addr = crypto.PubkeyToAddress(sequencerPrivKey.PublicKey)
}
signer := func(chainID *big.Int) SignerFn { signer, fromAddress, err := opcrypto.SignerFactoryFromConfig(l, cfg.PrivateKey, cfg.Mnemonic, cfg.SequencerHDPath, cfg.SignerConfig)
s := types.LatestSignerForChainID(chainID) if err != nil {
return func(_ context.Context, rawTx types.TxData) (*types.Transaction, error) { return nil, err
return types.SignNewTx(sequencerPrivKey, s, rawTx)
}
} }
return NewBatchSubmitterWithSigner(cfg, addr, signer, l)
}
type SignerFactory func(chainID *big.Int) SignerFn
func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerFactory, l log.Logger) (*BatchSubmitter, error) {
ctx := context.Background()
batchInboxAddress, err := parseAddress(cfg.SequencerBatchInboxAddress) batchInboxAddress, err := parseAddress(cfg.SequencerBatchInboxAddress)
if err != nil { if err != nil {
return nil, err return nil, err
...@@ -124,13 +71,6 @@ func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerF ...@@ -124,13 +71,6 @@ func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerF
return nil, err return nil, err
} }
sequencerBalance, err := l1Client.BalanceAt(ctx, addr, nil)
if err != nil {
return nil, err
}
log.Info("starting batch submitter", "submitter_addr", addr, "submitter_bal", sequencerBalance)
txManagerConfig := txmgr.Config{ txManagerConfig := txmgr.Config{
Log: l, Log: l,
Name: "Batch Submitter", Name: "Batch Submitter",
...@@ -140,12 +80,15 @@ func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerF ...@@ -140,12 +80,15 @@ func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerF
SafeAbortNonceTooLowCount: cfg.SafeAbortNonceTooLowCount, SafeAbortNonceTooLowCount: cfg.SafeAbortNonceTooLowCount,
} }
batcherCfg := DriverConfig{ batcherCfg := Config{
Log: l,
Name: "Batch Submitter",
L1Client: l1Client, L1Client: l1Client,
L2Client: l2Client, L2Client: l2Client,
RollupNode: rollupClient, RollupNode: rollupClient,
ChainID: chainID,
PollInterval: cfg.PollInterval,
TxManagerConfig: txManagerConfig,
From: fromAddress,
SignerFnFactory: signer,
BatchInboxAddress: batchInboxAddress, BatchInboxAddress: batchInboxAddress,
Channel: ChannelConfig{ Channel: ChannelConfig{
ChannelTimeout: cfg.ChannelTimeout, ChannelTimeout: cfg.ChannelTimeout,
...@@ -154,24 +97,36 @@ func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerF ...@@ -154,24 +97,36 @@ func NewBatchSubmitterWithSigner(cfg Config, addr common.Address, signer SignerF
TargetNumFrames: cfg.TargetNumFrames, TargetNumFrames: cfg.TargetNumFrames,
ApproxComprRatio: cfg.ApproxComprRatio, ApproxComprRatio: cfg.ApproxComprRatio,
}, },
ChainID: chainID,
PollInterval: cfg.PollInterval,
} }
return NewBatchSubmitter(batcherCfg, l)
}
// NewBatchSubmitter initializes the BatchSubmitter, gathering any resources
// that will be needed during operation.
func NewBatchSubmitter(cfg Config, l log.Logger) (*BatchSubmitter, error) {
ctx, cancel := context.WithCancel(context.Background()) ctx, cancel := context.WithCancel(context.Background())
balance, err := cfg.L1Client.BalanceAt(ctx, cfg.From, nil)
if err != nil {
cancel()
return nil, err
}
cfg.log = l
cfg.log.Info("creating batch submitter", "submitter_addr", cfg.From, "submitter_bal", balance)
return &BatchSubmitter{ return &BatchSubmitter{
cfg: batcherCfg, Config: cfg,
addr: addr, txMgr: NewTransactionManager(l, cfg.TxManagerConfig, cfg.BatchInboxAddress, cfg.ChainID, cfg.From, cfg.L1Client, cfg.SignerFnFactory(cfg.ChainID)),
txMgr: NewTransactionManager(l, txManagerConfig, batchInboxAddress, chainID, addr, l1Client, signer(chainID)), done: make(chan struct{}),
done: make(chan struct{}),
log: l,
state: NewChannelManager(l, batcherCfg.Channel),
// TODO: this context only exists because the event loop doesn't reach done // TODO: this context only exists because the event loop doesn't reach done
// if the tx manager is blocking forever due to e.g. insufficient balance. // if the tx manager is blocking forever due to e.g. insufficient balance.
ctx: ctx, ctx: ctx,
cancel: cancel, cancel: cancel,
state: NewChannelManager(l, cfg.Channel),
}, nil }, nil
} }
func (l *BatchSubmitter) Start() error { func (l *BatchSubmitter) Start() error {
...@@ -218,7 +173,7 @@ func (l *BatchSubmitter) loadBlocksIntoState(ctx context.Context) { ...@@ -218,7 +173,7 @@ func (l *BatchSubmitter) loadBlocksIntoState(ctx context.Context) {
// loadBlockIntoState fetches & stores a single block into `state`. It returns the block it loaded. // loadBlockIntoState fetches & stores a single block into `state`. It returns the block it loaded.
func (l *BatchSubmitter) loadBlockIntoState(ctx context.Context, blockNumber uint64) (eth.BlockID, error) { func (l *BatchSubmitter) loadBlockIntoState(ctx context.Context, blockNumber uint64) (eth.BlockID, error) {
ctx, cancel := context.WithTimeout(ctx, networkTimeout) ctx, cancel := context.WithTimeout(ctx, networkTimeout)
block, err := l.cfg.L2Client.BlockByNumber(ctx, new(big.Int).SetUint64(blockNumber)) block, err := l.L2Client.BlockByNumber(ctx, new(big.Int).SetUint64(blockNumber))
cancel() cancel()
if err != nil { if err != nil {
return eth.BlockID{}, err return eth.BlockID{}, err
...@@ -236,7 +191,7 @@ func (l *BatchSubmitter) loadBlockIntoState(ctx context.Context, blockNumber uin ...@@ -236,7 +191,7 @@ func (l *BatchSubmitter) loadBlockIntoState(ctx context.Context, blockNumber uin
func (l *BatchSubmitter) calculateL2BlockRangeToStore(ctx context.Context) (eth.BlockID, eth.BlockID, error) { func (l *BatchSubmitter) calculateL2BlockRangeToStore(ctx context.Context) (eth.BlockID, eth.BlockID, error) {
childCtx, cancel := context.WithTimeout(ctx, networkTimeout) childCtx, cancel := context.WithTimeout(ctx, networkTimeout)
defer cancel() defer cancel()
syncStatus, err := l.cfg.RollupNode.SyncStatus(childCtx) syncStatus, err := l.RollupNode.SyncStatus(childCtx)
// Ensure that we have the sync status // Ensure that we have the sync status
if err != nil { if err != nil {
return eth.BlockID{}, eth.BlockID{}, fmt.Errorf("failed to get sync status: %w", err) return eth.BlockID{}, eth.BlockID{}, fmt.Errorf("failed to get sync status: %w", err)
...@@ -277,7 +232,7 @@ func (l *BatchSubmitter) calculateL2BlockRangeToStore(ctx context.Context) (eth. ...@@ -277,7 +232,7 @@ func (l *BatchSubmitter) calculateL2BlockRangeToStore(ctx context.Context) (eth.
func (l *BatchSubmitter) loop() { func (l *BatchSubmitter) loop() {
defer l.wg.Done() defer l.wg.Done()
ticker := time.NewTicker(l.cfg.PollInterval) ticker := time.NewTicker(l.PollInterval)
defer ticker.Stop() defer ticker.Stop()
for { for {
select { select {
......
package batcher
import (
"math/big"
"time"
"github.com/ethereum-optimism/optimism/op-node/sources"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/ethclient"
"github.com/ethereum/go-ethereum/log"
)
type DriverConfig struct {
Log log.Logger
Name string
// API to submit txs to
L1Client *ethclient.Client
// API to hit for batch data
L2Client *ethclient.Client
RollupNode *sources.RollupClient
// Where to send the batch txs to.
BatchInboxAddress common.Address
// Channel creation parameters
Channel ChannelConfig
// Chain ID of the L1 chain to submit txs to.
ChainID *big.Int
PollInterval time.Duration
}
...@@ -13,12 +13,12 @@ import ( ...@@ -13,12 +13,12 @@ import (
"github.com/ethereum/go-ethereum/ethclient" "github.com/ethereum/go-ethereum/ethclient"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
opcrypto "github.com/ethereum-optimism/optimism/op-service/crypto"
) )
const networkTimeout = 2 * time.Second // How long a single network request can take. TODO: put in a config somewhere const networkTimeout = 2 * time.Second // How long a single network request can take. TODO: put in a config somewhere
type SignerFn func(ctx context.Context, rawTx types.TxData) (*types.Transaction, error)
// TransactionManager wraps the simple txmgr package to make it easy to send & wait for transactions // TransactionManager wraps the simple txmgr package to make it easy to send & wait for transactions
type TransactionManager struct { type TransactionManager struct {
// Config // Config
...@@ -28,11 +28,11 @@ type TransactionManager struct { ...@@ -28,11 +28,11 @@ type TransactionManager struct {
// Outside world // Outside world
txMgr txmgr.TxManager txMgr txmgr.TxManager
l1Client *ethclient.Client l1Client *ethclient.Client
signerFn SignerFn signerFn opcrypto.SignerFn
log log.Logger log log.Logger
} }
func NewTransactionManager(log log.Logger, txMgrConfg txmgr.Config, batchInboxAddress common.Address, chainID *big.Int, senderAddress common.Address, l1Client *ethclient.Client, signerFn SignerFn) *TransactionManager { func NewTransactionManager(log log.Logger, txMgrConfg txmgr.Config, batchInboxAddress common.Address, chainID *big.Int, senderAddress common.Address, l1Client *ethclient.Client, signerFn opcrypto.SignerFn) *TransactionManager {
t := &TransactionManager{ t := &TransactionManager{
batchInboxAddress: batchInboxAddress, batchInboxAddress: batchInboxAddress,
senderAddress: senderAddress, senderAddress: senderAddress,
...@@ -132,7 +132,8 @@ func (t *TransactionManager) CraftTx(ctx context.Context, data []byte) (*types.T ...@@ -132,7 +132,8 @@ func (t *TransactionManager) CraftTx(ctx context.Context, data []byte) (*types.T
ctx, cancel = context.WithTimeout(ctx, networkTimeout) ctx, cancel = context.WithTimeout(ctx, networkTimeout)
defer cancel() defer cancel()
return t.signerFn(ctx, rawTx) tx := types.NewTx(rawTx)
return t.signerFn(ctx, t.senderAddress, tx)
} }
// UpdateGasPrice signs an otherwise identical txn to the one provided but with // UpdateGasPrice signs an otherwise identical txn to the one provided but with
...@@ -157,5 +158,6 @@ func (t *TransactionManager) UpdateGasPrice(ctx context.Context, tx *types.Trans ...@@ -157,5 +158,6 @@ func (t *TransactionManager) UpdateGasPrice(ctx context.Context, tx *types.Trans
// Only log the new tip/fee cap because the updateGasPrice closure reuses the same initial transaction // Only log the new tip/fee cap because the updateGasPrice closure reuses the same initial transaction
t.log.Trace("updating gas price", "tip_cap", gasTipCap, "fee_cap", gasFeeCap) t.log.Trace("updating gas price", "tip_cap", gasTipCap, "fee_cap", gasFeeCap)
return t.signerFn(ctx, rawTx) finalTx := types.NewTx(rawTx)
return t.signerFn(ctx, t.senderAddress, finalTx)
} }
...@@ -13,7 +13,7 @@ import ( ...@@ -13,7 +13,7 @@ import (
) )
var ( var (
Version = "v0.10.11" Version = "v0.10.12"
GitCommit = "" GitCommit = ""
GitDate = "" GitDate = ""
) )
...@@ -29,9 +29,17 @@ func main() { ...@@ -29,9 +29,17 @@ func main() {
app.Description = "Service for generating and submitting L2 tx batches " + app.Description = "Service for generating and submitting L2 tx batches " +
"to L1" "to L1"
app.Action = batcher.Main(Version) app.Action = curryMain(Version)
err := app.Run(os.Args) err := app.Run(os.Args)
if err != nil { if err != nil {
log.Crit("Application failed", "message", err) log.Crit("Application failed", "message", err)
} }
} }
// curryMain transforms the batcher.Main function into an app.Action
// This is done to capture the Version of the batcher.
func curryMain(version string) func(ctx *cli.Context) error {
return func(ctx *cli.Context) error {
return batcher.Main(version, ctx)
}
}
...@@ -3,9 +3,8 @@ module github.com/ethereum-optimism/optimism/op-batcher ...@@ -3,9 +3,8 @@ module github.com/ethereum-optimism/optimism/op-batcher
go 1.18 go 1.18
require ( require (
github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 github.com/ethereum-optimism/optimism/op-node v0.10.12
github.com/ethereum-optimism/optimism/op-node v0.10.11 github.com/ethereum-optimism/optimism/op-service v0.10.12
github.com/ethereum-optimism/optimism/op-service v0.10.11
github.com/ethereum-optimism/optimism/op-signer v0.1.0 github.com/ethereum-optimism/optimism/op-signer v0.1.0
github.com/ethereum/go-ethereum v1.10.26 github.com/ethereum/go-ethereum v1.10.26
github.com/urfave/cli v1.22.9 github.com/urfave/cli v1.22.9
...@@ -24,7 +23,8 @@ require ( ...@@ -24,7 +23,8 @@ require (
github.com/deckarep/golang-set v1.8.0 // indirect github.com/deckarep/golang-set v1.8.0 // indirect
github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 // indirect github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 // indirect
github.com/dyson/certman v0.3.0 // indirect github.com/dyson/certman v0.3.0 // indirect
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 // indirect github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 // indirect
github.com/ethereum-optimism/optimism/op-bindings v0.10.12 // indirect
github.com/fjl/memsize v0.0.1 // indirect github.com/fjl/memsize v0.0.1 // indirect
github.com/fsnotify/fsnotify v1.6.0 // indirect github.com/fsnotify/fsnotify v1.6.0 // indirect
github.com/go-ole/go-ole v1.2.6 // indirect github.com/go-ole/go-ole v1.2.6 // indirect
......
...@@ -109,12 +109,12 @@ github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 h1:RWHKLhCrQThMfch+QJ1Z ...@@ -109,12 +109,12 @@ github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 h1:RWHKLhCrQThMfch+QJ1Z
github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3/go.mod h1:QziizLAiF0KqyLdNJYD7O5cpDlaFMNZzlxYNcWsJUxs= github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3/go.mod h1:QziizLAiF0KqyLdNJYD7O5cpDlaFMNZzlxYNcWsJUxs=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 h1:RDiRyHo0G/UuxHZQdMJyqIuHtWvpionuFNfczNaWCcM= github.com/ethereum-optimism/optimism/op-bindings v0.10.12 h1:/B1gaCLwZYy9Rja3MiceV3R642bygp937kZjnYwRxA0=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c= github.com/ethereum-optimism/optimism/op-bindings v0.10.12/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c=
github.com/ethereum-optimism/optimism/op-node v0.10.11 h1:ED72b68ainzcXr5/cLOYRwv+LdE4hRDnkq3SmNRY1+Q= github.com/ethereum-optimism/optimism/op-node v0.10.12 h1:yOxMThwwz1rEDDM0xTjS+6jqJwgKRtrYM6h4Pdf0zno=
github.com/ethereum-optimism/optimism/op-node v0.10.11/go.mod h1:/CDpkMxc3mDklZ1nqz2lmxfeUyAUz7yC/OLmX8egAUw= github.com/ethereum-optimism/optimism/op-node v0.10.12/go.mod h1:z+DiFb82Vnn5zM3VEwc2OXK2V/JBg6MLg7ejTbsxye8=
github.com/ethereum-optimism/optimism/op-service v0.10.11 h1:o+SazhFXlE3EM9Re5KIPEQklZ9uTI8rNkjl0h5OwRtU= github.com/ethereum-optimism/optimism/op-service v0.10.12 h1:Y7pR3/b8eeHYkmo2V5z7sj8jaraYqm2Azyph5lbiIxo=
github.com/ethereum-optimism/optimism/op-service v0.10.11/go.mod h1:wbtHqi1fv00B3agj7a2zdP3OFanEfGZ23zPgGgFCF/c= github.com/ethereum-optimism/optimism/op-service v0.10.12/go.mod h1:Ibbun+aic0rjQBV8yBf9kohqIj6mQ8nSTWbZjHv+Q7Q=
github.com/ethereum-optimism/optimism/op-signer v0.1.0 h1:wH44Deai43YQWO0pEd44pDm3BahdAtSmrOHKiPvTB8Y= github.com/ethereum-optimism/optimism/op-signer v0.1.0 h1:wH44Deai43YQWO0pEd44pDm3BahdAtSmrOHKiPvTB8Y=
github.com/ethereum-optimism/optimism/op-signer v0.1.0/go.mod h1:u8sN6X/c20pP9F1Ey7jH3fi19D08Y+T9ep3PGJfdyi8= github.com/ethereum-optimism/optimism/op-signer v0.1.0/go.mod h1:u8sN6X/c20pP9F1Ey7jH3fi19D08Y+T9ep3PGJfdyi8=
github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ= github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ=
...@@ -391,7 +391,7 @@ github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572/go.mod h1:w ...@@ -391,7 +391,7 @@ github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572/go.mod h1:w
github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI= github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI=
github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/status-im/keycard-go v0.0.0-20190316090335-8537d3370df4 h1:Gb2Tyox57NRNuZ2d3rmvB3pcmbu7O1RS3m8WRx7ilrg= github.com/status-im/keycard-go v0.0.0-20211109104530-b0e0482ba91d h1:vmirMegf1vqPJ+lDBxLQ0MAt3tz+JL57UPxu44JBOjA=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/objx v0.5.0 h1:1zr/of2m5FGMsad5YfcqgdqdWrIhu+EBEJRhR1U7z/c= github.com/stretchr/objx v0.5.0 h1:1zr/of2m5FGMsad5YfcqgdqdWrIhu+EBEJRhR1U7z/c=
......
...@@ -3,7 +3,7 @@ module github.com/ethereum-optimism/optimism/op-chain-ops ...@@ -3,7 +3,7 @@ module github.com/ethereum-optimism/optimism/op-chain-ops
go 1.18 go 1.18
require ( require (
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 github.com/ethereum-optimism/optimism/op-bindings v0.10.12
github.com/ethereum-optimism/optimism/op-node v0.10.1 github.com/ethereum-optimism/optimism/op-node v0.10.1
github.com/ethereum/go-ethereum v1.10.26 github.com/ethereum/go-ethereum v1.10.26
github.com/holiman/uint256 v1.2.0 github.com/holiman/uint256 v1.2.0
...@@ -23,7 +23,7 @@ require ( ...@@ -23,7 +23,7 @@ require (
github.com/deckarep/golang-set v1.8.0 // indirect github.com/deckarep/golang-set v1.8.0 // indirect
github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 // indirect github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 // indirect
github.com/edsrzf/mmap-go v1.1.0 // indirect github.com/edsrzf/mmap-go v1.1.0 // indirect
github.com/ethereum-optimism/optimism/op-service v0.10.11 // indirect github.com/ethereum-optimism/optimism/op-service v0.10.12 // indirect
github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 // indirect github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 // indirect
github.com/go-kit/kit v0.10.0 // indirect github.com/go-kit/kit v0.10.0 // indirect
github.com/go-ole/go-ole v1.2.6 // indirect github.com/go-ole/go-ole v1.2.6 // indirect
...@@ -49,7 +49,7 @@ require ( ...@@ -49,7 +49,7 @@ require (
github.com/rogpeppe/go-internal v1.8.1 // indirect github.com/rogpeppe/go-internal v1.8.1 // indirect
github.com/russross/blackfriday/v2 v2.1.0 // indirect github.com/russross/blackfriday/v2 v2.1.0 // indirect
github.com/shirou/gopsutil v3.21.11+incompatible // indirect github.com/shirou/gopsutil v3.21.11+incompatible // indirect
github.com/status-im/keycard-go v0.0.0-20190316090335-8537d3370df4 // indirect github.com/status-im/keycard-go v0.0.0-20211109104530-b0e0482ba91d // indirect
github.com/syndtr/goleveldb v1.0.1-0.20220614013038-64ee5596c38a // indirect github.com/syndtr/goleveldb v1.0.1-0.20220614013038-64ee5596c38a // indirect
github.com/tklauser/go-sysconf v0.3.10 // indirect github.com/tklauser/go-sysconf v0.3.10 // indirect
github.com/tklauser/numcpus v0.5.0 // indirect github.com/tklauser/numcpus v0.5.0 // indirect
......
...@@ -79,20 +79,20 @@ github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.m ...@@ -79,20 +79,20 @@ github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.m
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 h1:RDiRyHo0G/UuxHZQdMJyqIuHtWvpionuFNfczNaWCcM= github.com/ethereum-optimism/optimism/op-bindings v0.10.12 h1:/B1gaCLwZYy9Rja3MiceV3R642bygp937kZjnYwRxA0=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c= github.com/ethereum-optimism/optimism/op-bindings v0.10.12/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c=
github.com/ethereum-optimism/optimism/op-node v0.10.1 h1:kVBaOEOYLV22XEHRhB7dfdmoXepO0kx/RsZQK+Bpk1Y= github.com/ethereum-optimism/optimism/op-node v0.10.1 h1:kVBaOEOYLV22XEHRhB7dfdmoXepO0kx/RsZQK+Bpk1Y=
github.com/ethereum-optimism/optimism/op-node v0.10.1/go.mod h1:pup7wiiUs9g8cZKwXeB5tEGCqwUUwFVmej9MmSIm6S8= github.com/ethereum-optimism/optimism/op-node v0.10.1/go.mod h1:pup7wiiUs9g8cZKwXeB5tEGCqwUUwFVmej9MmSIm6S8=
github.com/ethereum-optimism/optimism/op-service v0.10.11 h1:o+SazhFXlE3EM9Re5KIPEQklZ9uTI8rNkjl0h5OwRtU= github.com/ethereum-optimism/optimism/op-service v0.10.12 h1:Y7pR3/b8eeHYkmo2V5z7sj8jaraYqm2Azyph5lbiIxo=
github.com/ethereum-optimism/optimism/op-service v0.10.11/go.mod h1:wbtHqi1fv00B3agj7a2zdP3OFanEfGZ23zPgGgFCF/c= github.com/ethereum-optimism/optimism/op-service v0.10.12/go.mod h1:Ibbun+aic0rjQBV8yBf9kohqIj6mQ8nSTWbZjHv+Q7Q=
github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4=
github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ= github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ=
github.com/franela/goblin v0.0.0-20200105215937-c9ffbefa60db/go.mod h1:7dvUGVsVBjqR7JHJk0brhHOZYGmfBYOrK0ZhYMEtBr4= github.com/franela/goblin v0.0.0-20200105215937-c9ffbefa60db/go.mod h1:7dvUGVsVBjqR7JHJk0brhHOZYGmfBYOrK0ZhYMEtBr4=
github.com/franela/goreq v0.0.0-20171204163338-bcd34c9993f8/go.mod h1:ZhphrRTfi2rbfLwlschooIH4+wKKDR4Pdxhh+TRoA20= github.com/franela/goreq v0.0.0-20171204163338-bcd34c9993f8/go.mod h1:ZhphrRTfi2rbfLwlschooIH4+wKKDR4Pdxhh+TRoA20=
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ=
github.com/fsnotify/fsnotify v1.5.4 h1:jRbGcIw6P2Meqdwuo0H1p6JVLbL5DHKAKlYndzMwVZI=
github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmVXmkdnm1bU= github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmVXmkdnm1bU=
github.com/fsnotify/fsnotify v1.6.0 h1:n+5WquG0fcWoWp6xPWfHdbskMCQaFnG6PfBrh1Ky4HY=
github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 h1:f6D9Hr8xV8uYKlyuj8XIruxlh9WjVjdh1gIicAS7ays= github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 h1:f6D9Hr8xV8uYKlyuj8XIruxlh9WjVjdh1gIicAS7ays=
github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08/go.mod h1:x7DCsMOv1taUwEWCzT4cmDeAkigA5/QCwUodaVOe8Ww= github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08/go.mod h1:x7DCsMOv1taUwEWCzT4cmDeAkigA5/QCwUodaVOe8Ww=
github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
...@@ -377,8 +377,8 @@ github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasO ...@@ -377,8 +377,8 @@ github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasO
github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI= github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI=
github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ= github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ=
github.com/spf13/pflag v1.0.1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/pflag v1.0.1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
github.com/status-im/keycard-go v0.0.0-20190316090335-8537d3370df4 h1:Gb2Tyox57NRNuZ2d3rmvB3pcmbu7O1RS3m8WRx7ilrg= github.com/status-im/keycard-go v0.0.0-20211109104530-b0e0482ba91d h1:vmirMegf1vqPJ+lDBxLQ0MAt3tz+JL57UPxu44JBOjA=
github.com/status-im/keycard-go v0.0.0-20190316090335-8537d3370df4/go.mod h1:RZLeN1LMWmRsyYjvAu+I6Dm9QmlDaIIt+Y+4Kd7Tp+Q= github.com/status-im/keycard-go v0.0.0-20211109104530-b0e0482ba91d/go.mod h1:97vT0Rym0wCnK4B++hNA3nCetr0Mh1KXaVxzSt1arjg=
github.com/streadway/amqp v0.0.0-20190404075320-75d898a42a94/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= github.com/streadway/amqp v0.0.0-20190404075320-75d898a42a94/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw=
github.com/streadway/amqp v0.0.0-20190827072141-edfb9018d271/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw= github.com/streadway/amqp v0.0.0-20190827072141-edfb9018d271/go.mod h1:AZpEONHx3DKn8O/DFsRAY58/XVQiIPMTMB1SddzLXVw=
github.com/streadway/handy v0.0.0-20190108123426-d5acb3125c2a/go.mod h1:qNTQ5P5JnDBl6z3cMAg/SywNDC5ABu5ApDIw6lUbRmI= github.com/streadway/handy v0.0.0-20190108123426-d5acb3125c2a/go.mod h1:qNTQ5P5JnDBl6z3cMAg/SywNDC5ABu5ApDIw6lUbRmI=
......
...@@ -18,11 +18,11 @@ type MockL1OriginSelector struct { ...@@ -18,11 +18,11 @@ type MockL1OriginSelector struct {
originOverride eth.L1BlockRef // override which origin gets picked originOverride eth.L1BlockRef // override which origin gets picked
} }
func (m *MockL1OriginSelector) FindL1Origin(ctx context.Context, l1Head eth.L1BlockRef, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) { func (m *MockL1OriginSelector) FindL1Origin(ctx context.Context, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) {
if m.originOverride != (eth.L1BlockRef{}) { if m.originOverride != (eth.L1BlockRef{}) {
return m.originOverride, nil return m.originOverride, nil
} }
return m.actual.FindL1Origin(ctx, l1Head, l2Head) return m.actual.FindL1Origin(ctx, l2Head)
} }
// L2Sequencer is an actor that functions like a rollup node, // L2Sequencer is an actor that functions like a rollup node,
...@@ -40,8 +40,9 @@ type L2Sequencer struct { ...@@ -40,8 +40,9 @@ type L2Sequencer struct {
func NewL2Sequencer(t Testing, log log.Logger, l1 derive.L1Fetcher, eng L2API, cfg *rollup.Config, seqConfDepth uint64) *L2Sequencer { func NewL2Sequencer(t Testing, log log.Logger, l1 derive.L1Fetcher, eng L2API, cfg *rollup.Config, seqConfDepth uint64) *L2Sequencer {
ver := NewL2Verifier(t, log, l1, eng, cfg) ver := NewL2Verifier(t, log, l1, eng, cfg)
attrBuilder := derive.NewFetchingAttributesBuilder(cfg, l1, eng) attrBuilder := derive.NewFetchingAttributesBuilder(cfg, l1, eng)
seqConfDepthL1 := driver.NewConfDepth(seqConfDepth, ver.l1State.L1Head, l1)
l1OriginSelector := &MockL1OriginSelector{ l1OriginSelector := &MockL1OriginSelector{
actual: driver.NewL1OriginSelector(log, cfg, l1, seqConfDepth), actual: driver.NewL1OriginSelector(log, cfg, seqConfDepthL1),
} }
return &L2Sequencer{ return &L2Sequencer{
L2Verifier: *ver, L2Verifier: *ver,
...@@ -62,7 +63,7 @@ func (s *L2Sequencer) ActL2StartBlock(t Testing) { ...@@ -62,7 +63,7 @@ func (s *L2Sequencer) ActL2StartBlock(t Testing) {
return return
} }
err := s.sequencer.StartBuildingBlock(t.Ctx(), s.l1State.L1Head()) err := s.sequencer.StartBuildingBlock(t.Ctx())
require.NoError(t, err, "failed to start block building") require.NoError(t, err, "failed to start block building")
s.l2Building = true s.l2Building = true
...@@ -106,7 +107,7 @@ func (s *L2Sequencer) ActBuildToL1Head(t Testing) { ...@@ -106,7 +107,7 @@ func (s *L2Sequencer) ActBuildToL1Head(t Testing) {
func (s *L2Sequencer) ActBuildToL1HeadExcl(t Testing) { func (s *L2Sequencer) ActBuildToL1HeadExcl(t Testing) {
for { for {
s.ActL2PipelineFull(t) s.ActL2PipelineFull(t)
nextOrigin, err := s.mockL1OriginSelector.FindL1Origin(t.Ctx(), s.l1State.L1Head(), s.derivation.UnsafeL2Head()) nextOrigin, err := s.mockL1OriginSelector.FindL1Origin(t.Ctx(), s.derivation.UnsafeL2Head())
require.NoError(t, err) require.NoError(t, err)
if nextOrigin.Number >= s.l1State.L1Head().Number { if nextOrigin.Number >= s.l1State.L1Head().Number {
break break
......
...@@ -10,12 +10,12 @@ require ( ...@@ -10,12 +10,12 @@ require (
github.com/docker/docker v20.10.21+incompatible github.com/docker/docker v20.10.21+incompatible
github.com/docker/go-connections v0.4.0 github.com/docker/go-connections v0.4.0
github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3
github.com/ethereum-optimism/optimism/op-batcher v0.10.11 github.com/ethereum-optimism/optimism/op-batcher v0.10.12
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 github.com/ethereum-optimism/optimism/op-bindings v0.10.12
github.com/ethereum-optimism/optimism/op-chain-ops v0.10.11 github.com/ethereum-optimism/optimism/op-chain-ops v0.10.12
github.com/ethereum-optimism/optimism/op-node v0.10.11 github.com/ethereum-optimism/optimism/op-node v0.10.12
github.com/ethereum-optimism/optimism/op-proposer v0.10.11 github.com/ethereum-optimism/optimism/op-proposer v0.10.12
github.com/ethereum-optimism/optimism/op-service v0.10.11 github.com/ethereum-optimism/optimism/op-service v0.10.12
github.com/ethereum/go-ethereum v1.10.26 github.com/ethereum/go-ethereum v1.10.26
github.com/google/gofuzz v1.2.1-0.20220503160820-4a35382e8fc8 github.com/google/gofuzz v1.2.1-0.20220503160820-4a35382e8fc8
github.com/libp2p/go-libp2p v0.23.3 github.com/libp2p/go-libp2p v0.23.3
......
...@@ -161,18 +161,18 @@ github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 h1:RWHKLhCrQThMfch+QJ1Z ...@@ -161,18 +161,18 @@ github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 h1:RWHKLhCrQThMfch+QJ1Z
github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3/go.mod h1:QziizLAiF0KqyLdNJYD7O5cpDlaFMNZzlxYNcWsJUxs= github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3/go.mod h1:QziizLAiF0KqyLdNJYD7O5cpDlaFMNZzlxYNcWsJUxs=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY=
github.com/ethereum-optimism/optimism/op-batcher v0.10.11 h1:aqTOE3UnTrX/rngXruT815CyRhcKi9kvZ4xJllW9l6I= github.com/ethereum-optimism/optimism/op-batcher v0.10.12 h1:Vyb2oEujqokXiybaC64l+T5e0NpEMOC6rhXqIFIN8Oo=
github.com/ethereum-optimism/optimism/op-batcher v0.10.11/go.mod h1:HIsxM0YihXGGImsUuPdI0T+L1LuS8UXgZnaZweXUGug= github.com/ethereum-optimism/optimism/op-batcher v0.10.12/go.mod h1:ai4nZjD0aOOHWhLZj7R8KFttG9+EFsdxiELDuqwzrO4=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 h1:RDiRyHo0G/UuxHZQdMJyqIuHtWvpionuFNfczNaWCcM= github.com/ethereum-optimism/optimism/op-bindings v0.10.12 h1:/B1gaCLwZYy9Rja3MiceV3R642bygp937kZjnYwRxA0=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c= github.com/ethereum-optimism/optimism/op-bindings v0.10.12/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c=
github.com/ethereum-optimism/optimism/op-chain-ops v0.10.11 h1:6ihrVPJYN1HvD4KG0Fk1zIJCM4ZB109kCu9fq81jznQ= github.com/ethereum-optimism/optimism/op-chain-ops v0.10.12 h1:gRX5oIk0hboTOZ65y5MpEdM5+nmaad87QZP1donrHXo=
github.com/ethereum-optimism/optimism/op-chain-ops v0.10.11/go.mod h1:6mub7Tx1cC4gDrfX9o9n+kA4R2qLlYvfWkG8es21EQI= github.com/ethereum-optimism/optimism/op-chain-ops v0.10.12/go.mod h1:x98mGAxXIhyYM4WsnbgziJCAk+qA4JX0wvaE+azBg48=
github.com/ethereum-optimism/optimism/op-node v0.10.11 h1:ED72b68ainzcXr5/cLOYRwv+LdE4hRDnkq3SmNRY1+Q= github.com/ethereum-optimism/optimism/op-node v0.10.12 h1:yOxMThwwz1rEDDM0xTjS+6jqJwgKRtrYM6h4Pdf0zno=
github.com/ethereum-optimism/optimism/op-node v0.10.11/go.mod h1:/CDpkMxc3mDklZ1nqz2lmxfeUyAUz7yC/OLmX8egAUw= github.com/ethereum-optimism/optimism/op-node v0.10.12/go.mod h1:z+DiFb82Vnn5zM3VEwc2OXK2V/JBg6MLg7ejTbsxye8=
github.com/ethereum-optimism/optimism/op-proposer v0.10.11 h1:uG+CXcac1LVRAnivv+3q7qJZDTgdKLv0D3mbu2o7nKI= github.com/ethereum-optimism/optimism/op-proposer v0.10.12 h1:4K61QLg1mF38zwsaTQKOJnDqc65DKKsO33X20cLrhmk=
github.com/ethereum-optimism/optimism/op-proposer v0.10.11/go.mod h1:O/BolDMRNanlblBQKwq2UGwnl7hTdKrnVlmXfijG7vw= github.com/ethereum-optimism/optimism/op-proposer v0.10.12/go.mod h1:JBB9oVfhx9VjrBgcE5KIxCdQPnr7ma/xLBLYg2EFo9I=
github.com/ethereum-optimism/optimism/op-service v0.10.11 h1:o+SazhFXlE3EM9Re5KIPEQklZ9uTI8rNkjl0h5OwRtU= github.com/ethereum-optimism/optimism/op-service v0.10.12 h1:Y7pR3/b8eeHYkmo2V5z7sj8jaraYqm2Azyph5lbiIxo=
github.com/ethereum-optimism/optimism/op-service v0.10.11/go.mod h1:wbtHqi1fv00B3agj7a2zdP3OFanEfGZ23zPgGgFCF/c= github.com/ethereum-optimism/optimism/op-service v0.10.12/go.mod h1:Ibbun+aic0rjQBV8yBf9kohqIj6mQ8nSTWbZjHv+Q7Q=
github.com/ethereum-optimism/optimism/op-signer v0.1.0 h1:wH44Deai43YQWO0pEd44pDm3BahdAtSmrOHKiPvTB8Y= github.com/ethereum-optimism/optimism/op-signer v0.1.0 h1:wH44Deai43YQWO0pEd44pDm3BahdAtSmrOHKiPvTB8Y=
github.com/ethereum-optimism/optimism/op-signer v0.1.0/go.mod h1:u8sN6X/c20pP9F1Ey7jH3fi19D08Y+T9ep3PGJfdyi8= github.com/ethereum-optimism/optimism/op-signer v0.1.0/go.mod h1:u8sN6X/c20pP9F1Ey7jH3fi19D08Y+T9ep3PGJfdyi8=
github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ= github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ=
......
...@@ -319,7 +319,7 @@ func TestMigration(t *testing.T) { ...@@ -319,7 +319,7 @@ func TestMigration(t *testing.T) {
require.NoError(t, rollupNode.Close()) require.NoError(t, rollupNode.Close())
}) })
batcher, err := bss.NewBatchSubmitter(bss.Config{ batcher, err := bss.NewBatchSubmitterFromCLIConfig(bss.CLIConfig{
L1EthRpc: forkedL1URL, L1EthRpc: forkedL1URL,
L2EthRpc: gethNode.WSEndpoint(), L2EthRpc: gethNode.WSEndpoint(),
RollupRpc: rollupNode.HTTPEndpoint(), RollupRpc: rollupNode.HTTPEndpoint(),
......
...@@ -522,7 +522,7 @@ func (cfg SystemConfig) Start() (*System, error) { ...@@ -522,7 +522,7 @@ func (cfg SystemConfig) Start() (*System, error) {
} }
// Batch Submitter // Batch Submitter
sys.BatchSubmitter, err = bss.NewBatchSubmitter(bss.Config{ sys.BatchSubmitter, err = bss.NewBatchSubmitterFromCLIConfig(bss.CLIConfig{
L1EthRpc: sys.Nodes["l1"].WSEndpoint(), L1EthRpc: sys.Nodes["l1"].WSEndpoint(),
L2EthRpc: sys.Nodes["sequencer"].WSEndpoint(), L2EthRpc: sys.Nodes["sequencer"].WSEndpoint(),
RollupRpc: sys.RollupNodes["sequencer"].HTTPEndpoint(), RollupRpc: sys.RollupNodes["sequencer"].HTTPEndpoint(),
......
...@@ -6,9 +6,9 @@ require ( ...@@ -6,9 +6,9 @@ require (
github.com/btcsuite/btcd v0.23.3 github.com/btcsuite/btcd v0.23.3
github.com/btcsuite/btcd/chaincfg/chainhash v1.0.1 github.com/btcsuite/btcd/chaincfg/chainhash v1.0.1
github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 github.com/ethereum-optimism/optimism/op-bindings v0.10.12
github.com/ethereum-optimism/optimism/op-chain-ops v0.10.11 github.com/ethereum-optimism/optimism/op-chain-ops v0.10.12
github.com/ethereum-optimism/optimism/op-service v0.10.11 github.com/ethereum-optimism/optimism/op-service v0.10.12
github.com/ethereum/go-ethereum v1.10.26 github.com/ethereum/go-ethereum v1.10.26
github.com/golang/snappy v0.0.4 github.com/golang/snappy v0.0.4
github.com/google/go-cmp v0.5.8 github.com/google/go-cmp v0.5.8
...@@ -52,8 +52,7 @@ require ( ...@@ -52,8 +52,7 @@ require (
github.com/fjl/memsize v0.0.1 // indirect github.com/fjl/memsize v0.0.1 // indirect
github.com/flynn/noise v1.0.0 // indirect github.com/flynn/noise v1.0.0 // indirect
github.com/francoispqt/gojay v1.2.13 // indirect github.com/francoispqt/gojay v1.2.13 // indirect
github.com/fsnotify/fsnotify v1.5.4 // indirect github.com/fsnotify/fsnotify v1.6.0 // indirect
github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 // indirect
github.com/go-ole/go-ole v1.2.6 // indirect github.com/go-ole/go-ole v1.2.6 // indirect
github.com/go-stack/stack v1.8.1 // indirect github.com/go-stack/stack v1.8.1 // indirect
github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0 // indirect github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0 // indirect
...@@ -137,7 +136,6 @@ require ( ...@@ -137,7 +136,6 @@ require (
github.com/syndtr/goleveldb v1.0.1-0.20220614013038-64ee5596c38a // indirect github.com/syndtr/goleveldb v1.0.1-0.20220614013038-64ee5596c38a // indirect
github.com/tklauser/go-sysconf v0.3.10 // indirect github.com/tklauser/go-sysconf v0.3.10 // indirect
github.com/tklauser/numcpus v0.5.0 // indirect github.com/tklauser/numcpus v0.5.0 // indirect
github.com/tyler-smith/go-bip39 v1.1.0 // indirect
github.com/urfave/cli/v2 v2.17.2-0.20221006022127-8f469abc00aa // indirect github.com/urfave/cli/v2 v2.17.2-0.20221006022127-8f469abc00aa // indirect
github.com/whyrusleeping/timecache v0.0.0-20160911033111-cfcb2f1abfee // indirect github.com/whyrusleeping/timecache v0.0.0-20160911033111-cfcb2f1abfee // indirect
github.com/xrash/smetrics v0.0.0-20201216005158-039620a65673 // indirect github.com/xrash/smetrics v0.0.0-20201216005158-039620a65673 // indirect
...@@ -151,7 +149,6 @@ require ( ...@@ -151,7 +149,6 @@ require (
golang.org/x/net v0.0.0-20220920183852-bf014ff85ad5 // indirect golang.org/x/net v0.0.0-20220920183852-bf014ff85ad5 // indirect
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4 // indirect golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4 // indirect
golang.org/x/sys v0.0.0-20221013171732-95e765b1cc43 // indirect golang.org/x/sys v0.0.0-20221013171732-95e765b1cc43 // indirect
golang.org/x/time v0.0.0-20220224211638-0e9765cccd65 // indirect
golang.org/x/tools v0.1.12 // indirect golang.org/x/tools v0.1.12 // indirect
google.golang.org/protobuf v1.28.1 // indirect google.golang.org/protobuf v1.28.1 // indirect
gopkg.in/natefinch/npipe.v2 v2.0.0-20160621034901-c1b8fa8bdcce // indirect gopkg.in/natefinch/npipe.v2 v2.0.0-20160621034901-c1b8fa8bdcce // indirect
......
...@@ -145,12 +145,12 @@ github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1m ...@@ -145,12 +145,12 @@ github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1m
github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468 h1:7KgjBYDji5AKi42eRYI+n8Gs+ZJVilSASL3WBu82c3M=
github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY= github.com/ethereum-optimism/op-geth v0.0.0-20221216190603-60b51d600468/go.mod h1:p0Yox74PhYlq1HvijrCBCD9A3cI7rXco7hT6KrQr+rY=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 h1:RDiRyHo0G/UuxHZQdMJyqIuHtWvpionuFNfczNaWCcM= github.com/ethereum-optimism/optimism/op-bindings v0.10.12 h1:/B1gaCLwZYy9Rja3MiceV3R642bygp937kZjnYwRxA0=
github.com/ethereum-optimism/optimism/op-bindings v0.10.11/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c= github.com/ethereum-optimism/optimism/op-bindings v0.10.12/go.mod h1:9ZSUq/rjlzp3uYyBN4sZmhTc3oZgDVqJ4wrUja7vj6c=
github.com/ethereum-optimism/optimism/op-chain-ops v0.10.11 h1:6ihrVPJYN1HvD4KG0Fk1zIJCM4ZB109kCu9fq81jznQ= github.com/ethereum-optimism/optimism/op-chain-ops v0.10.12 h1:gRX5oIk0hboTOZ65y5MpEdM5+nmaad87QZP1donrHXo=
github.com/ethereum-optimism/optimism/op-chain-ops v0.10.11/go.mod h1:6mub7Tx1cC4gDrfX9o9n+kA4R2qLlYvfWkG8es21EQI= github.com/ethereum-optimism/optimism/op-chain-ops v0.10.12/go.mod h1:x98mGAxXIhyYM4WsnbgziJCAk+qA4JX0wvaE+azBg48=
github.com/ethereum-optimism/optimism/op-service v0.10.11 h1:o+SazhFXlE3EM9Re5KIPEQklZ9uTI8rNkjl0h5OwRtU= github.com/ethereum-optimism/optimism/op-service v0.10.12 h1:Y7pR3/b8eeHYkmo2V5z7sj8jaraYqm2Azyph5lbiIxo=
github.com/ethereum-optimism/optimism/op-service v0.10.11/go.mod h1:wbtHqi1fv00B3agj7a2zdP3OFanEfGZ23zPgGgFCF/c= github.com/ethereum-optimism/optimism/op-service v0.10.12/go.mod h1:Ibbun+aic0rjQBV8yBf9kohqIj6mQ8nSTWbZjHv+Q7Q=
github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ= github.com/fjl/memsize v0.0.1 h1:+zhkb+dhUgx0/e+M8sF0QqiouvMQUiKR+QYvdxIOKcQ=
github.com/fjl/memsize v0.0.1/go.mod h1:VvhXpOYNQvB+uIk2RvXzuaQtkQJzzIx6lSBe1xv7hi0= github.com/fjl/memsize v0.0.1/go.mod h1:VvhXpOYNQvB+uIk2RvXzuaQtkQJzzIx6lSBe1xv7hi0=
github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc=
...@@ -160,10 +160,10 @@ github.com/francoispqt/gojay v1.2.13 h1:d2m3sFjloqoIUQU3TsHBgj6qg/BVGlTBeHDUmyJn ...@@ -160,10 +160,10 @@ github.com/francoispqt/gojay v1.2.13 h1:d2m3sFjloqoIUQU3TsHBgj6qg/BVGlTBeHDUmyJn
github.com/francoispqt/gojay v1.2.13/go.mod h1:ehT5mTG4ua4581f1++1WLG0vPdaA9HaiDsoyrBGkyDY= github.com/francoispqt/gojay v1.2.13/go.mod h1:ehT5mTG4ua4581f1++1WLG0vPdaA9HaiDsoyrBGkyDY=
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ=
github.com/fsnotify/fsnotify v1.5.4 h1:jRbGcIw6P2Meqdwuo0H1p6JVLbL5DHKAKlYndzMwVZI=
github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmVXmkdnm1bU= github.com/fsnotify/fsnotify v1.5.4/go.mod h1:OVB6XrOHzAwXMpEM7uPOzcehqUV2UqJxmVXmkdnm1bU=
github.com/fsnotify/fsnotify v1.6.0 h1:n+5WquG0fcWoWp6xPWfHdbskMCQaFnG6PfBrh1Ky4HY=
github.com/fsnotify/fsnotify v1.6.0/go.mod h1:sl3t1tCWJFWoRz9R8WJCbQihKKwmorjAbSClcnxKAGw=
github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 h1:f6D9Hr8xV8uYKlyuj8XIruxlh9WjVjdh1gIicAS7ays= github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08 h1:f6D9Hr8xV8uYKlyuj8XIruxlh9WjVjdh1gIicAS7ays=
github.com/gballet/go-libpcsclite v0.0.0-20191108122812-4678299bea08/go.mod h1:x7DCsMOv1taUwEWCzT4cmDeAkigA5/QCwUodaVOe8Ww=
github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
github.com/gliderlabs/ssh v0.1.1/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0= github.com/gliderlabs/ssh v0.1.1/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0=
github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q= github.com/go-errors/errors v1.0.1/go.mod h1:f4zRHt4oKfwPJE5k8C9vpYG+aDHdBFUsgrm6/TyX73Q=
...@@ -587,7 +587,7 @@ github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572/go.mod h1:w ...@@ -587,7 +587,7 @@ github.com/spacemonkeygo/spacelog v0.0.0-20180420211403-2296661a0572/go.mod h1:w
github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI= github.com/spaolacci/murmur3 v1.1.0 h1:7c1g84S4BPRrfL5Xrdp6fOJ206sU9y293DDHaoy0bLI=
github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spaolacci/murmur3 v1.1.0/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA=
github.com/status-im/keycard-go v0.0.0-20190316090335-8537d3370df4 h1:Gb2Tyox57NRNuZ2d3rmvB3pcmbu7O1RS3m8WRx7ilrg= github.com/status-im/keycard-go v0.0.0-20211109104530-b0e0482ba91d h1:vmirMegf1vqPJ+lDBxLQ0MAt3tz+JL57UPxu44JBOjA=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw=
...@@ -613,7 +613,6 @@ github.com/tklauser/numcpus v0.4.0/go.mod h1:1+UI3pD8NW14VMwdgJNJ1ESk2UnwhAnz5hM ...@@ -613,7 +613,6 @@ github.com/tklauser/numcpus v0.4.0/go.mod h1:1+UI3pD8NW14VMwdgJNJ1ESk2UnwhAnz5hM
github.com/tklauser/numcpus v0.5.0 h1:ooe7gN0fg6myJ0EKoTAf5hebTZrH52px3New/D9iJ+A= github.com/tklauser/numcpus v0.5.0 h1:ooe7gN0fg6myJ0EKoTAf5hebTZrH52px3New/D9iJ+A=
github.com/tklauser/numcpus v0.5.0/go.mod h1:OGzpTxpcIMNGYQdit2BYL1pvk/dSOaJWjKoflh+RQjo= github.com/tklauser/numcpus v0.5.0/go.mod h1:OGzpTxpcIMNGYQdit2BYL1pvk/dSOaJWjKoflh+RQjo=
github.com/tyler-smith/go-bip39 v1.1.0 h1:5eUemwrMargf3BSLRRCalXT93Ns6pQJIjYQN2nyfOP8= github.com/tyler-smith/go-bip39 v1.1.0 h1:5eUemwrMargf3BSLRRCalXT93Ns6pQJIjYQN2nyfOP8=
github.com/tyler-smith/go-bip39 v1.1.0/go.mod h1:gUYDtqQw1JS3ZJ8UWVcGTGqqr6YIN3CWg+kkNaLt55U=
github.com/urfave/cli v1.22.2/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= github.com/urfave/cli v1.22.2/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0=
github.com/urfave/cli v1.22.9 h1:cv3/KhXGBGjEXLC4bH0sLuJ9BewaAbpk5oyMOveu4pw= github.com/urfave/cli v1.22.9 h1:cv3/KhXGBGjEXLC4bH0sLuJ9BewaAbpk5oyMOveu4pw=
github.com/urfave/cli v1.22.9/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0= github.com/urfave/cli v1.22.9/go.mod h1:Gos4lmkARVdJ6EkW0WaNv/tZAAMe9V7XWyB60NtXRu0=
...@@ -846,6 +845,7 @@ golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBc ...@@ -846,6 +845,7 @@ golang.org/x/sys v0.0.0-20220503163025-988cb79eb6c6/go.mod h1:oPkhp1MJrh7nUepCBc
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220704084225-05e143d24a9e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220704084225-05e143d24a9e/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220908164124-27713097b956/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20221013171732-95e765b1cc43 h1:OK7RB6t2WQX54srQQYSXMW8dF5C6/8+oA/s5QBmmto4= golang.org/x/sys v0.0.0-20221013171732-95e765b1cc43 h1:OK7RB6t2WQX54srQQYSXMW8dF5C6/8+oA/s5QBmmto4=
golang.org/x/sys v0.0.0-20221013171732-95e765b1cc43/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20221013171732-95e765b1cc43/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
...@@ -865,7 +865,6 @@ golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxb ...@@ -865,7 +865,6 @@ golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxb
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/time v0.0.0-20220224211638-0e9765cccd65 h1:M73Iuj3xbbb9Uk1DYhzydthsj6oOd6l9bpuFcNoUvTs= golang.org/x/time v0.0.0-20220224211638-0e9765cccd65 h1:M73Iuj3xbbb9Uk1DYhzydthsj6oOd6l9bpuFcNoUvTs=
golang.org/x/time v0.0.0-20220224211638-0e9765cccd65/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
golang.org/x/tools v0.0.0-20181030000716-a0a13e073c7b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20181030000716-a0a13e073c7b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
......
...@@ -66,10 +66,10 @@ type L1StateIface interface { ...@@ -66,10 +66,10 @@ type L1StateIface interface {
} }
type SequencerIface interface { type SequencerIface interface {
StartBuildingBlock(ctx context.Context, l1Head eth.L1BlockRef) error StartBuildingBlock(ctx context.Context) error
CompleteBuildingBlock(ctx context.Context) (*eth.ExecutionPayload, error) CompleteBuildingBlock(ctx context.Context) (*eth.ExecutionPayload, error)
PlanNextSequencerAction() time.Duration PlanNextSequencerAction() time.Duration
RunNextSequencerAction(ctx context.Context, l1Head eth.L1BlockRef) *eth.ExecutionPayload RunNextSequencerAction(ctx context.Context) *eth.ExecutionPayload
BuildingOnto() eth.L2BlockRef BuildingOnto() eth.L2BlockRef
} }
...@@ -81,7 +81,8 @@ type Network interface { ...@@ -81,7 +81,8 @@ type Network interface {
// NewDriver composes an events handler that tracks L1 state, triggers L2 derivation, and optionally sequences new L2 blocks. // NewDriver composes an events handler that tracks L1 state, triggers L2 derivation, and optionally sequences new L2 blocks.
func NewDriver(driverCfg *Config, cfg *rollup.Config, l2 L2Chain, l1 L1Chain, network Network, log log.Logger, snapshotLog log.Logger, metrics Metrics) *Driver { func NewDriver(driverCfg *Config, cfg *rollup.Config, l2 L2Chain, l1 L1Chain, network Network, log log.Logger, snapshotLog log.Logger, metrics Metrics) *Driver {
l1State := NewL1State(log, metrics) l1State := NewL1State(log, metrics)
findL1Origin := NewL1OriginSelector(log, cfg, l1, driverCfg.SequencerConfDepth) sequencerConfDepth := NewConfDepth(driverCfg.SequencerConfDepth, l1State.L1Head, l1)
findL1Origin := NewL1OriginSelector(log, cfg, sequencerConfDepth)
verifConfDepth := NewConfDepth(driverCfg.VerifierConfDepth, l1State.L1Head, l1) verifConfDepth := NewConfDepth(driverCfg.VerifierConfDepth, l1State.L1Head, l1)
derivationPipeline := derive.NewDerivationPipeline(log, cfg, verifConfDepth, l2, metrics) derivationPipeline := derive.NewDerivationPipeline(log, cfg, verifConfDepth, l2, metrics)
attrBuilder := derive.NewFetchingAttributesBuilder(cfg, l1, l2) attrBuilder := derive.NewFetchingAttributesBuilder(cfg, l1, l2)
......
...@@ -2,7 +2,10 @@ package driver ...@@ -2,7 +2,10 @@ package driver
import ( import (
"context" "context"
"errors"
"fmt"
"github.com/ethereum/go-ethereum"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
"github.com/ethereum-optimism/optimism/op-node/eth" "github.com/ethereum-optimism/optimism/op-node/eth"
...@@ -19,63 +22,49 @@ type L1OriginSelector struct { ...@@ -19,63 +22,49 @@ type L1OriginSelector struct {
log log.Logger log log.Logger
cfg *rollup.Config cfg *rollup.Config
l1 L1Blocks l1 L1Blocks
sequencingConfDepth uint64
} }
func NewL1OriginSelector(log log.Logger, cfg *rollup.Config, l1 L1Blocks, sequencingConfDepth uint64) *L1OriginSelector { func NewL1OriginSelector(log log.Logger, cfg *rollup.Config, l1 L1Blocks) *L1OriginSelector {
return &L1OriginSelector{ return &L1OriginSelector{
log: log, log: log,
cfg: cfg, cfg: cfg,
l1: l1, l1: l1,
sequencingConfDepth: sequencingConfDepth,
} }
} }
// FindL1Origin determines what the next L1 Origin should be. // FindL1Origin determines what the next L1 Origin should be.
// The L1 Origin is either the L2 Head's Origin, or the following L1 block // The L1 Origin is either the L2 Head's Origin, or the following L1 block
// if the next L2 block's time is greater than or equal to the L2 Head's Origin. // if the next L2 block's time is greater than or equal to the L2 Head's Origin.
func (los *L1OriginSelector) FindL1Origin(ctx context.Context, l1Head eth.L1BlockRef, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) { func (los *L1OriginSelector) FindL1Origin(ctx context.Context, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) {
// If we are at the head block, don't do a lookup. // Grab a reference to the current L1 origin block. This call is by hash and thus easily cached.
if l2Head.L1Origin.Hash == l1Head.Hash {
return l1Head, nil
}
// Grab a reference to the current L1 origin block.
currentOrigin, err := los.l1.L1BlockRefByHash(ctx, l2Head.L1Origin.Hash) currentOrigin, err := los.l1.L1BlockRefByHash(ctx, l2Head.L1Origin.Hash)
if err != nil { if err != nil {
return eth.L1BlockRef{}, err return eth.L1BlockRef{}, err
} }
log := los.log.New("current", currentOrigin, "current_time", currentOrigin.Time,
"l2_head", l2Head, "l2_head_time", l2Head.Time)
// If we are past the sequencer depth, we may want to advance the origin, but need to still // If we are past the sequencer depth, we may want to advance the origin, but need to still
// check the time of the next origin. // check the time of the next origin.
pastSeqDrift := l2Head.Time+los.cfg.BlockTime > currentOrigin.Time+los.cfg.MaxSequencerDrift pastSeqDrift := l2Head.Time+los.cfg.BlockTime > currentOrigin.Time+los.cfg.MaxSequencerDrift
if pastSeqDrift { if pastSeqDrift {
log.Info("Next L2 block time is past the sequencer drift + current origin time", log.Warn("Next L2 block time is past the sequencer drift + current origin time")
"current", currentOrigin, "current_time", currentOrigin.Time,
"l1_head", l1Head, "l1_head_time", l1Head.Time,
"l2_head", l2Head, "l2_head_time", l2Head.Time,
"depth", los.sequencingConfDepth)
}
if !pastSeqDrift && currentOrigin.Number+1+los.sequencingConfDepth > l1Head.Number {
// TODO: we can decide to ignore confirmation depth if we would be forced
// to make an empty block (only deposits) by staying on the current origin.
log.Info("sequencing with old origin to preserve conf depth",
"current", currentOrigin, "current_time", currentOrigin.Time,
"l1_head", l1Head, "l1_head_time", l1Head.Time,
"l2_head", l2Head, "l2_head_time", l2Head.Time,
"depth", los.sequencingConfDepth)
return currentOrigin, nil
} }
// Attempt to find the next L1 origin block, where the next origin is the immediate child of // Attempt to find the next L1 origin block, where the next origin is the immediate child of
// the current origin block. // the current origin block.
// The L1 source can be shimmed to hide new L1 blocks and enforce a sequencer confirmation distance.
nextOrigin, err := los.l1.L1BlockRefByNumber(ctx, currentOrigin.Number+1) nextOrigin, err := los.l1.L1BlockRefByNumber(ctx, currentOrigin.Number+1)
if err != nil { if err != nil {
// TODO: this could result in a bad origin being selected if we are past the seq if pastSeqDrift {
// drift & should instead advance to the next origin. return eth.L1BlockRef{}, fmt.Errorf("cannot build next L2 block past current L1 origin %s by more than sequencer time drift, and failed to find next L1 origin: %w", currentOrigin, err)
log.Error("Failed to get next origin. Falling back to current origin", "err", err) }
if errors.Is(err, ethereum.NotFound) {
log.Debug("No next L1 block found, repeating current origin")
} else {
log.Error("Failed to get next origin. Falling back to current origin", "err", err)
}
return currentOrigin, nil return currentOrigin, nil
} }
......
...@@ -27,6 +27,7 @@ func TestOriginSelectorAdvances(t *testing.T) { ...@@ -27,6 +27,7 @@ func TestOriginSelectorAdvances(t *testing.T) {
BlockTime: 2, BlockTime: 2,
} }
l1 := &testutils.MockL1Source{} l1 := &testutils.MockL1Source{}
defer l1.AssertExpectations(t)
a := eth.L1BlockRef{ a := eth.L1BlockRef{
Hash: common.Hash{'a'}, Hash: common.Hash{'a'},
Number: 10, Number: 10,
...@@ -46,9 +47,8 @@ func TestOriginSelectorAdvances(t *testing.T) { ...@@ -46,9 +47,8 @@ func TestOriginSelectorAdvances(t *testing.T) {
l1.ExpectL1BlockRefByHash(a.Hash, a, nil) l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByNumber(b.Number, b, nil) l1.ExpectL1BlockRefByNumber(b.Number, b, nil)
s := NewL1OriginSelector(log, cfg, l1, 0) s := NewL1OriginSelector(log, cfg, l1)
next, err := s.FindL1Origin(context.Background(), l2Head)
next, err := s.FindL1Origin(context.Background(), b, l2Head)
require.Nil(t, err) require.Nil(t, err)
require.Equal(t, b, next) require.Equal(t, b, next)
} }
...@@ -68,6 +68,7 @@ func TestOriginSelectorRespectsOriginTiming(t *testing.T) { ...@@ -68,6 +68,7 @@ func TestOriginSelectorRespectsOriginTiming(t *testing.T) {
BlockTime: 2, BlockTime: 2,
} }
l1 := &testutils.MockL1Source{} l1 := &testutils.MockL1Source{}
defer l1.AssertExpectations(t)
a := eth.L1BlockRef{ a := eth.L1BlockRef{
Hash: common.Hash{'a'}, Hash: common.Hash{'a'},
Number: 10, Number: 10,
...@@ -87,15 +88,14 @@ func TestOriginSelectorRespectsOriginTiming(t *testing.T) { ...@@ -87,15 +88,14 @@ func TestOriginSelectorRespectsOriginTiming(t *testing.T) {
l1.ExpectL1BlockRefByHash(a.Hash, a, nil) l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByNumber(b.Number, b, nil) l1.ExpectL1BlockRefByNumber(b.Number, b, nil)
s := NewL1OriginSelector(log, cfg, l1, 0) s := NewL1OriginSelector(log, cfg, l1)
next, err := s.FindL1Origin(context.Background(), l2Head)
next, err := s.FindL1Origin(context.Background(), b, l2Head)
require.Nil(t, err) require.Nil(t, err)
require.Equal(t, a, next) require.Equal(t, a, next)
} }
// TestOriginSelectorRespectsConfDepth ensures that the origin selector // TestOriginSelectorRespectsConfDepth ensures that the origin selector
// will respects the confirmation depth requirement // will respect the confirmation depth requirement
// //
// There are 2 L1 blocks at time 20 & 25. The L2 Head is at time 27. // There are 2 L1 blocks at time 20 & 25. The L2 Head is at time 27.
// The next L2 time is 29 which enough to normally select block `b` // The next L2 time is 29 which enough to normally select block `b`
...@@ -108,6 +108,7 @@ func TestOriginSelectorRespectsConfDepth(t *testing.T) { ...@@ -108,6 +108,7 @@ func TestOriginSelectorRespectsConfDepth(t *testing.T) {
BlockTime: 2, BlockTime: 2,
} }
l1 := &testutils.MockL1Source{} l1 := &testutils.MockL1Source{}
defer l1.AssertExpectations(t)
a := eth.L1BlockRef{ a := eth.L1BlockRef{
Hash: common.Hash{'a'}, Hash: common.Hash{'a'},
Number: 10, Number: 10,
...@@ -125,33 +126,32 @@ func TestOriginSelectorRespectsConfDepth(t *testing.T) { ...@@ -125,33 +126,32 @@ func TestOriginSelectorRespectsConfDepth(t *testing.T) {
} }
l1.ExpectL1BlockRefByHash(a.Hash, a, nil) l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByNumber(b.Number, b, nil) confDepthL1 := NewConfDepth(10, func() eth.L1BlockRef { return b }, l1)
s := NewL1OriginSelector(log, cfg, confDepthL1)
s := NewL1OriginSelector(log, cfg, l1, 10)
next, err := s.FindL1Origin(context.Background(), b, l2Head) next, err := s.FindL1Origin(context.Background(), l2Head)
require.Nil(t, err) require.Nil(t, err)
require.Equal(t, a, next) require.Equal(t, a, next)
} }
// TestOriginSelectorRespectsMaxSeqDrift ensures that the origin selector // TestOriginSelectorStrictConfDepth ensures that the origin selector will maintain the sequencer conf depth,
// will advance if the time delta between the current L1 origin and the next // even while the time delta between the current L1 origin and the next
// L2 block is greater than the sequencer drift. This needs to occur even // L2 block is greater than the sequencer drift.
// if conf depth needs to be ignored // It's more important to maintain safety with an empty block than to maintain liveness with poor conf depth.
// //
// There are 2 L1 blocks at time 20 & 25. The L2 Head is at time 27. // There are 2 L1 blocks at time 20 & 25. The L2 Head is at time 27.
// The next L2 time is 29. The sequencer drift is 8 so the L2 head is // The next L2 time is 29. The sequencer drift is 8 so the L2 head is
// valid with origin `a`, but the next L2 block is not valid with origin `b.` // valid with origin `a`, but the next L2 block is not valid with origin `b.`
// This is because 29 (next L2 time) > 20 (origin) + 8 (seq drift) => invalid block. // This is because 29 (next L2 time) > 20 (origin) + 8 (seq drift) => invalid block.
// Even though the LOS would normally refuse to advance because block `b` does not // We maintain confirmation distance, even though we would shift to the next origin if we could.
// have enough confirmations, it should in this instance. func TestOriginSelectorStrictConfDepth(t *testing.T) {
func TestOriginSelectorRespectsMaxSeqDrift(t *testing.T) {
log := testlog.Logger(t, log.LvlCrit) log := testlog.Logger(t, log.LvlCrit)
cfg := &rollup.Config{ cfg := &rollup.Config{
MaxSequencerDrift: 8, MaxSequencerDrift: 8,
BlockTime: 2, BlockTime: 2,
} }
l1 := &testutils.MockL1Source{} l1 := &testutils.MockL1Source{}
defer l1.AssertExpectations(t)
a := eth.L1BlockRef{ a := eth.L1BlockRef{
Hash: common.Hash{'a'}, Hash: common.Hash{'a'},
Number: 10, Number: 10,
...@@ -169,13 +169,11 @@ func TestOriginSelectorRespectsMaxSeqDrift(t *testing.T) { ...@@ -169,13 +169,11 @@ func TestOriginSelectorRespectsMaxSeqDrift(t *testing.T) {
} }
l1.ExpectL1BlockRefByHash(a.Hash, a, nil) l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByNumber(b.Number, b, nil) confDepthL1 := NewConfDepth(10, func() eth.L1BlockRef { return b }, l1)
s := NewL1OriginSelector(log, cfg, confDepthL1)
s := NewL1OriginSelector(log, cfg, l1, 10)
next, err := s.FindL1Origin(context.Background(), b, l2Head) _, err := s.FindL1Origin(context.Background(), l2Head)
require.Nil(t, err) require.ErrorContains(t, err, "sequencer time drift")
require.Equal(t, b, next)
} }
// TestOriginSelectorSeqDriftRespectsNextOriginTime // TestOriginSelectorSeqDriftRespectsNextOriginTime
...@@ -191,6 +189,7 @@ func TestOriginSelectorSeqDriftRespectsNextOriginTime(t *testing.T) { ...@@ -191,6 +189,7 @@ func TestOriginSelectorSeqDriftRespectsNextOriginTime(t *testing.T) {
BlockTime: 2, BlockTime: 2,
} }
l1 := &testutils.MockL1Source{} l1 := &testutils.MockL1Source{}
defer l1.AssertExpectations(t)
a := eth.L1BlockRef{ a := eth.L1BlockRef{
Hash: common.Hash{'a'}, Hash: common.Hash{'a'},
Number: 10, Number: 10,
...@@ -210,9 +209,76 @@ func TestOriginSelectorSeqDriftRespectsNextOriginTime(t *testing.T) { ...@@ -210,9 +209,76 @@ func TestOriginSelectorSeqDriftRespectsNextOriginTime(t *testing.T) {
l1.ExpectL1BlockRefByHash(a.Hash, a, nil) l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByNumber(b.Number, b, nil) l1.ExpectL1BlockRefByNumber(b.Number, b, nil)
s := NewL1OriginSelector(log, cfg, l1, 10) s := NewL1OriginSelector(log, cfg, l1)
next, err := s.FindL1Origin(context.Background(), l2Head)
next, err := s.FindL1Origin(context.Background(), b, l2Head)
require.Nil(t, err) require.Nil(t, err)
require.Equal(t, a, next) require.Equal(t, a, next)
} }
// TestOriginSelectorHandlesLateL1Blocks tests the forced repeat of the previous origin,
// but with a conf depth that first prevents it from learning about the need to repeat.
//
// There are 2 L1 blocks at time 20 & 100. The L2 Head is at time 27.
// The next L2 time is 29. Even though the next L2 time is past the seq
// drift, the origin should remain on block `a` because the next origin's
// time is greater than the next L2 time.
// Due to a conf depth of 2, block `b` is not immediately visible,
// and the origin selection should fail until it is visible, by waiting for block `c`.
func TestOriginSelectorHandlesLateL1Blocks(t *testing.T) {
log := testlog.Logger(t, log.LvlCrit)
cfg := &rollup.Config{
MaxSequencerDrift: 8,
BlockTime: 2,
}
l1 := &testutils.MockL1Source{}
defer l1.AssertExpectations(t)
a := eth.L1BlockRef{
Hash: common.Hash{'a'},
Number: 10,
Time: 20,
}
b := eth.L1BlockRef{
Hash: common.Hash{'b'},
Number: 11,
Time: 100,
ParentHash: a.Hash,
}
c := eth.L1BlockRef{
Hash: common.Hash{'c'},
Number: 12,
Time: 150,
ParentHash: b.Hash,
}
d := eth.L1BlockRef{
Hash: common.Hash{'d'},
Number: 13,
Time: 200,
ParentHash: c.Hash,
}
l2Head := eth.L2BlockRef{
L1Origin: a.ID(),
Time: 27,
}
// l2 head does not change, so we start at the same origin again and again until we meet the conf depth
l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByHash(a.Hash, a, nil)
l1.ExpectL1BlockRefByNumber(b.Number, b, nil)
l1Head := b
confDepthL1 := NewConfDepth(2, func() eth.L1BlockRef { return l1Head }, l1)
s := NewL1OriginSelector(log, cfg, confDepthL1)
_, err := s.FindL1Origin(context.Background(), l2Head)
require.ErrorContains(t, err, "sequencer time drift")
l1Head = c
_, err = s.FindL1Origin(context.Background(), l2Head)
require.ErrorContains(t, err, "sequencer time drift")
l1Head = d
next, err := s.FindL1Origin(context.Background(), l2Head)
require.Nil(t, err)
require.Equal(t, a, next, "must stay on a because the L1 time may not be higher than the L2 time")
}
...@@ -20,7 +20,7 @@ type Downloader interface { ...@@ -20,7 +20,7 @@ type Downloader interface {
} }
type L1OriginSelectorIface interface { type L1OriginSelectorIface interface {
FindL1Origin(ctx context.Context, l1Head eth.L1BlockRef, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) FindL1Origin(ctx context.Context, l2Head eth.L2BlockRef) (eth.L1BlockRef, error)
} }
// Sequencer implements the sequencing interface of the driver: it starts and completes block building jobs. // Sequencer implements the sequencing interface of the driver: it starts and completes block building jobs.
...@@ -51,11 +51,11 @@ func NewSequencer(log log.Logger, cfg *rollup.Config, engine derive.EngineContro ...@@ -51,11 +51,11 @@ func NewSequencer(log log.Logger, cfg *rollup.Config, engine derive.EngineContro
} }
// StartBuildingBlock initiates a block building job on top of the given L2 head, safe and finalized blocks, and using the provided l1Origin. // StartBuildingBlock initiates a block building job on top of the given L2 head, safe and finalized blocks, and using the provided l1Origin.
func (d *Sequencer) StartBuildingBlock(ctx context.Context, l1Head eth.L1BlockRef) error { func (d *Sequencer) StartBuildingBlock(ctx context.Context) error {
l2Head := d.engine.UnsafeL2Head() l2Head := d.engine.UnsafeL2Head()
// Figure out which L1 origin block we're going to be building on top of. // Figure out which L1 origin block we're going to be building on top of.
l1Origin, err := d.l1OriginSelector.FindL1Origin(ctx, l1Head, l2Head) l1Origin, err := d.l1OriginSelector.FindL1Origin(ctx, l2Head)
if err != nil { if err != nil {
d.log.Error("Error finding next L1 Origin", "err", err) d.log.Error("Error finding next L1 Origin", "err", err)
return err return err
...@@ -159,7 +159,7 @@ func (d *Sequencer) BuildingOnto() eth.L2BlockRef { ...@@ -159,7 +159,7 @@ func (d *Sequencer) BuildingOnto() eth.L2BlockRef {
// RunNextSequencerAction starts new block building work, or seals existing work, // RunNextSequencerAction starts new block building work, or seals existing work,
// and is best timed by first awaiting the delay returned by PlanNextSequencerAction. // and is best timed by first awaiting the delay returned by PlanNextSequencerAction.
// If a new block is successfully sealed, it will be returned for publishing, nil otherwise. // If a new block is successfully sealed, it will be returned for publishing, nil otherwise.
func (d *Sequencer) RunNextSequencerAction(ctx context.Context, l1Head eth.L1BlockRef) *eth.ExecutionPayload { func (d *Sequencer) RunNextSequencerAction(ctx context.Context) *eth.ExecutionPayload {
if _, buildingID, _ := d.engine.BuildingPayload(); buildingID != (eth.PayloadID{}) { if _, buildingID, _ := d.engine.BuildingPayload(); buildingID != (eth.PayloadID{}) {
payload, err := d.CompleteBuildingBlock(ctx) payload, err := d.CompleteBuildingBlock(ctx)
if err != nil { if err != nil {
...@@ -174,7 +174,7 @@ func (d *Sequencer) RunNextSequencerAction(ctx context.Context, l1Head eth.L1Blo ...@@ -174,7 +174,7 @@ func (d *Sequencer) RunNextSequencerAction(ctx context.Context, l1Head eth.L1Blo
return payload return payload
} }
} else { } else {
err := d.StartBuildingBlock(ctx, l1Head) err := d.StartBuildingBlock(ctx)
if err != nil { if err != nil {
d.log.Error("sequencer failed to start building new block", "err", err) d.log.Error("sequencer failed to start building new block", "err", err)
d.nextAction = d.timeNow().Add(time.Second) d.nextAction = d.timeNow().Add(time.Second)
......
...@@ -132,10 +132,10 @@ func (fn testAttrBuilderFn) PreparePayloadAttributes(ctx context.Context, l2Pare ...@@ -132,10 +132,10 @@ func (fn testAttrBuilderFn) PreparePayloadAttributes(ctx context.Context, l2Pare
var _ derive.AttributesBuilder = (testAttrBuilderFn)(nil) var _ derive.AttributesBuilder = (testAttrBuilderFn)(nil)
type testOriginSelectorFn func(ctx context.Context, l1Head eth.L1BlockRef, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) type testOriginSelectorFn func(ctx context.Context, l2Head eth.L2BlockRef) (eth.L1BlockRef, error)
func (fn testOriginSelectorFn) FindL1Origin(ctx context.Context, l1Head eth.L1BlockRef, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) { func (fn testOriginSelectorFn) FindL1Origin(ctx context.Context, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) {
return fn(ctx, l1Head, l2Head) return fn(ctx, l2Head)
} }
var _ L1OriginSelectorIface = (testOriginSelectorFn)(nil) var _ L1OriginSelectorIface = (testOriginSelectorFn)(nil)
...@@ -262,7 +262,7 @@ func TestSequencerChaosMonkey(t *testing.T) { ...@@ -262,7 +262,7 @@ func TestSequencerChaosMonkey(t *testing.T) {
maxL1BlockTimeGap := uint64(100) maxL1BlockTimeGap := uint64(100)
// The origin selector just generates random L1 blocks based on RNG // The origin selector just generates random L1 blocks based on RNG
var originErr error var originErr error
originSelector := testOriginSelectorFn(func(ctx context.Context, l1Head eth.L1BlockRef, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) { originSelector := testOriginSelectorFn(func(ctx context.Context, l2Head eth.L2BlockRef) (eth.L1BlockRef, error) {
if originErr != nil { if originErr != nil {
return eth.L1BlockRef{}, originErr return eth.L1BlockRef{}, originErr
} }
...@@ -298,8 +298,6 @@ func TestSequencerChaosMonkey(t *testing.T) { ...@@ -298,8 +298,6 @@ func TestSequencerChaosMonkey(t *testing.T) {
seq := NewSequencer(log, cfg, engControl, attrBuilder, originSelector) seq := NewSequencer(log, cfg, engControl, attrBuilder, originSelector)
seq.timeNow = clockFn seq.timeNow = clockFn
l1Head := eth.L1BlockRef{} // TODO this is getting removed
// try to build 1000 blocks, with 5x as many planning attempts, to handle errors and clock problems // try to build 1000 blocks, with 5x as many planning attempts, to handle errors and clock problems
desiredBlocks := 1000 desiredBlocks := 1000
for i := 0; i < 5*desiredBlocks && engControl.totalBuiltBlocks < desiredBlocks; i++ { for i := 0; i < 5*desiredBlocks && engControl.totalBuiltBlocks < desiredBlocks; i++ {
...@@ -339,7 +337,7 @@ func TestSequencerChaosMonkey(t *testing.T) { ...@@ -339,7 +337,7 @@ func TestSequencerChaosMonkey(t *testing.T) {
default: default:
// no error // no error
} }
payload := seq.RunNextSequencerAction(context.Background(), l1Head) payload := seq.RunNextSequencerAction(context.Background())
if payload != nil { if payload != nil {
require.Equal(t, engControl.UnsafeL2Head().ID(), payload.ID(), "head must stay in sync with emitted payloads") require.Equal(t, engControl.UnsafeL2Head().ID(), payload.ID(), "head must stay in sync with emitted payloads")
var tx types.Transaction var tx types.Transaction
......
...@@ -212,7 +212,7 @@ func (s *Driver) eventLoop() { ...@@ -212,7 +212,7 @@ func (s *Driver) eventLoop() {
select { select {
case <-sequencerCh: case <-sequencerCh:
payload := s.sequencer.RunNextSequencerAction(ctx, s.l1State.L1Head()) payload := s.sequencer.RunNextSequencerAction(ctx)
if s.network != nil && payload != nil { if s.network != nil && payload != nil {
// Publishing of unsafe data via p2p is optional. // Publishing of unsafe data via p2p is optional.
// Errors are not severe enough to change/halt sequencing but should be logged and metered. // Errors are not severe enough to change/halt sequencing but should be logged and metered.
......
package version package version
var ( var (
Version = "v0.10.11" Version = "v0.10.12"
Meta = "dev" Meta = "dev"
) )
...@@ -13,7 +13,7 @@ import ( ...@@ -13,7 +13,7 @@ import (
) )
var ( var (
Version = "v0.10.11" Version = "v0.10.12"
GitCommit = "" GitCommit = ""
GitDate = "" GitDate = ""
) )
......
...@@ -3,9 +3,9 @@ module github.com/ethereum-optimism/optimism/op-proposer ...@@ -3,9 +3,9 @@ module github.com/ethereum-optimism/optimism/op-proposer
go 1.18 go 1.18
require ( require (
github.com/ethereum-optimism/optimism/op-bindings v0.10.11 github.com/ethereum-optimism/optimism/op-bindings v0.10.12
github.com/ethereum-optimism/optimism/op-node v0.10.11 github.com/ethereum-optimism/optimism/op-node v0.10.12
github.com/ethereum-optimism/optimism/op-service v0.10.11 github.com/ethereum-optimism/optimism/op-service v0.10.12
github.com/ethereum-optimism/optimism/op-signer v0.1.0 github.com/ethereum-optimism/optimism/op-signer v0.1.0
github.com/ethereum/go-ethereum v1.10.26 github.com/ethereum/go-ethereum v1.10.26
github.com/urfave/cli v1.22.9 github.com/urfave/cli v1.22.9
...@@ -15,12 +15,16 @@ require ( ...@@ -15,12 +15,16 @@ require (
github.com/VictoriaMetrics/fastcache v1.10.0 // indirect github.com/VictoriaMetrics/fastcache v1.10.0 // indirect
github.com/benbjohnson/clock v1.3.0 // indirect github.com/benbjohnson/clock v1.3.0 // indirect
github.com/beorn7/perks v1.0.1 // indirect github.com/beorn7/perks v1.0.1 // indirect
github.com/btcsuite/btcd v0.23.3 // indirect
github.com/btcsuite/btcd/btcec/v2 v2.2.0 // indirect github.com/btcsuite/btcd/btcec/v2 v2.2.0 // indirect
github.com/btcsuite/btcd/btcutil v1.1.0 // indirect
github.com/btcsuite/btcd/chaincfg/chainhash v1.0.1 // indirect
github.com/cespare/xxhash/v2 v2.1.2 // indirect github.com/cespare/xxhash/v2 v2.1.2 // indirect
github.com/cpuguy83/go-md2man/v2 v2.0.2 // indirect github.com/cpuguy83/go-md2man/v2 v2.0.2 // indirect
github.com/deckarep/golang-set v1.8.0 // indirect github.com/deckarep/golang-set v1.8.0 // indirect
github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 // indirect github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0 // indirect
github.com/dyson/certman v0.3.0 // indirect github.com/dyson/certman v0.3.0 // indirect
github.com/ethereum-optimism/go-ethereum-hdwallet v0.1.3 // indirect
github.com/fjl/memsize v0.0.1 // indirect github.com/fjl/memsize v0.0.1 // indirect
github.com/fsnotify/fsnotify v1.6.0 // indirect github.com/fsnotify/fsnotify v1.6.0 // indirect
github.com/go-ole/go-ole v1.2.6 // indirect github.com/go-ole/go-ole v1.2.6 // indirect
...@@ -80,6 +84,7 @@ require ( ...@@ -80,6 +84,7 @@ require (
github.com/syndtr/goleveldb v1.0.1-0.20220614013038-64ee5596c38a // indirect github.com/syndtr/goleveldb v1.0.1-0.20220614013038-64ee5596c38a // indirect
github.com/tklauser/go-sysconf v0.3.10 // indirect github.com/tklauser/go-sysconf v0.3.10 // indirect
github.com/tklauser/numcpus v0.5.0 // indirect github.com/tklauser/numcpus v0.5.0 // indirect
github.com/tyler-smith/go-bip39 v1.1.0 // indirect
github.com/urfave/cli/v2 v2.17.2-0.20221006022127-8f469abc00aa // indirect github.com/urfave/cli/v2 v2.17.2-0.20221006022127-8f469abc00aa // indirect
github.com/xrash/smetrics v0.0.0-20201216005158-039620a65673 // indirect github.com/xrash/smetrics v0.0.0-20201216005158-039620a65673 // indirect
github.com/yusufpapurcu/wmi v1.2.2 // indirect github.com/yusufpapurcu/wmi v1.2.2 // indirect
......
This diff is collapsed.
...@@ -124,6 +124,7 @@ export abstract class BaseServiceV2< ...@@ -124,6 +124,7 @@ export abstract class BaseServiceV2<
metricsSpec: MetricsSpec<TMetrics> metricsSpec: MetricsSpec<TMetrics>
options?: Partial<TOptions & StandardOptions> options?: Partial<TOptions & StandardOptions>
loop?: boolean loop?: boolean
bodyParserParams?: bodyParser.OptionsJson
} }
) { ) {
this.loop = params.loop !== undefined ? params.loop : true this.loop = params.loop !== undefined ? params.loop : true
...@@ -330,6 +331,7 @@ export abstract class BaseServiceV2< ...@@ -330,6 +331,7 @@ export abstract class BaseServiceV2<
verify: (req, res, buf, encoding) => { verify: (req, res, buf, encoding) => {
;(req as any).rawBody = buf?.toString(encoding || 'utf8') || '' ;(req as any).rawBody = buf?.toString(encoding || 'utf8') || ''
}, },
...(this.params.bodyParserParams ?? {}),
}) })
) )
......
...@@ -9,13 +9,13 @@ GasBenchMark_L2OutputOracle:test_proposeL2Output_benchmark() (gas: 88513) ...@@ -9,13 +9,13 @@ GasBenchMark_L2OutputOracle:test_proposeL2Output_benchmark() (gas: 88513)
GasBenchMark_OptimismPortal:test_depositTransaction_benchmark() (gas: 74998) GasBenchMark_OptimismPortal:test_depositTransaction_benchmark() (gas: 74998)
GasBenchMark_OptimismPortal:test_depositTransaction_benchmark_1() (gas: 36156) GasBenchMark_OptimismPortal:test_depositTransaction_benchmark_1() (gas: 36156)
GasBenchMark_OptimismPortal:test_proveWithdrawalTransaction_benchmark() (gas: 167187) GasBenchMark_OptimismPortal:test_proveWithdrawalTransaction_benchmark() (gas: 167187)
Bytes_Test:test_slice_acrossMultipleWords_works() (gas: 9391) Bytes_slice_Test:test_slice_acrossMultipleWords_works() (gas: 9357)
Bytes_Test:test_slice_acrossWords_works() (gas: 1397) Bytes_slice_Test:test_slice_acrossWords_works() (gas: 1396)
Bytes_Test:test_slice_fromNonZeroIdx_works() (gas: 17218) Bytes_slice_Test:test_slice_fromNonZeroIdx_works() (gas: 17154)
Bytes_Test:test_slice_fromZeroIdx_works() (gas: 20826) Bytes_slice_Test:test_slice_fromZeroIdx_works() (gas: 20671)
Bytes_Test:test_toNibbles_expectedResult128Bytes_works() (gas: 129885) Bytes_toNibbles_Test:test_toNibbles_expectedResult128Bytes_works() (gas: 129830)
Bytes_Test:test_toNibbles_expectedResult5Bytes_works() (gas: 6132) Bytes_toNibbles_Test:test_toNibbles_expectedResult5Bytes_works() (gas: 6088)
Bytes_Test:test_toNibbles_zeroLengthInput_works() (gas: 966) Bytes_toNibbles_Test:test_toNibbles_zeroLengthInput_works() (gas: 944)
CrossDomainMessenger_BaseGas_Test:test_baseGas_succeeds() (gas: 20120) CrossDomainMessenger_BaseGas_Test:test_baseGas_succeeds() (gas: 20120)
CrossDomainOwnableThroughPortal_Test:test_depositTransaction_crossDomainOwner_succeeds() (gas: 61882) CrossDomainOwnableThroughPortal_Test:test_depositTransaction_crossDomainOwner_succeeds() (gas: 61882)
CrossDomainOwnable_Test:test_onlyOwner_notOwner_reverts() (gas: 10530) CrossDomainOwnable_Test:test_onlyOwner_notOwner_reverts() (gas: 10530)
...@@ -46,7 +46,7 @@ GovernanceToken_Test:test_mint_fromNotOwner_reverts() (gas: 17052) ...@@ -46,7 +46,7 @@ GovernanceToken_Test:test_mint_fromNotOwner_reverts() (gas: 17052)
GovernanceToken_Test:test_mint_fromOwner_succeeds() (gas: 108547) GovernanceToken_Test:test_mint_fromOwner_succeeds() (gas: 108547)
GovernanceToken_Test:test_transferFrom_succeeds() (gas: 146295) GovernanceToken_Test:test_transferFrom_succeeds() (gas: 146295)
GovernanceToken_Test:test_transfer_succeeds() (gas: 138085) GovernanceToken_Test:test_transfer_succeeds() (gas: 138085)
Hashing_Test:test_hashDepositSource_succeeds() (gas: 650) Hashing_hashDepositSource_Test:test_hashDepositSource_succeeds() (gas: 566)
L1BlockTest:test_basefee_succeeds() (gas: 7553) L1BlockTest:test_basefee_succeeds() (gas: 7553)
L1BlockTest:test_hash_succeeds() (gas: 7510) L1BlockTest:test_hash_succeeds() (gas: 7510)
L1BlockTest:test_number_succeeds() (gas: 7584) L1BlockTest:test_number_succeeds() (gas: 7584)
......
...@@ -4,7 +4,10 @@ pragma solidity 0.8.15; ...@@ -4,7 +4,10 @@ pragma solidity 0.8.15;
import { Test } from "forge-std/Test.sol"; import { Test } from "forge-std/Test.sol";
import { AddressAliasHelper } from "../vendor/AddressAliasHelper.sol"; import { AddressAliasHelper } from "../vendor/AddressAliasHelper.sol";
contract AddressAliasHelper_Test is Test { contract AddressAliasHelper_applyAndUndo_Test is Test {
/**
* @notice Tests that applying and then undoing an alias results in the original address.
*/
function testFuzz_applyAndUndo_succeeds(address _address) external { function testFuzz_applyAndUndo_succeeds(address _address) external {
address aliased = AddressAliasHelper.applyL1ToL2Alias(_address); address aliased = AddressAliasHelper.applyL1ToL2Alias(_address);
address unaliased = AddressAliasHelper.undoL1ToL2Alias(aliased); address unaliased = AddressAliasHelper.undoL1ToL2Alias(aliased);
......
...@@ -6,20 +6,33 @@ import { Types } from "../libraries/Types.sol"; ...@@ -6,20 +6,33 @@ import { Types } from "../libraries/Types.sol";
import { Hashing } from "../libraries/Hashing.sol"; import { Hashing } from "../libraries/Hashing.sol";
import { Encoding } from "../libraries/Encoding.sol"; import { Encoding } from "../libraries/Encoding.sol";
contract Hashing_Test is CommonTest { contract Hashing_hashDepositSource_Test is CommonTest {
function setUp() external { function setUp() external {
_setUp(); _setUp();
} }
/**
* @notice Tests that hashDepositSource returns the correct hash in a simple case.
*/
function test_hashDepositSource_succeeds() external { function test_hashDepositSource_succeeds() external {
bytes32 sourceHash = Hashing.hashDepositSource( assertEq(
0xd25df7858efc1778118fb133ac561b138845361626dfb976699c5287ed0f4959, Hashing.hashDepositSource(
0x1 0xd25df7858efc1778118fb133ac561b138845361626dfb976699c5287ed0f4959,
0x1
),
0xf923fb07134d7d287cb52c770cc619e17e82606c21a875c92f4c63b65280a5cc
); );
}
}
assertEq(sourceHash, 0xf923fb07134d7d287cb52c770cc619e17e82606c21a875c92f4c63b65280a5cc); contract Hashing_hashCrossDomainMessage_Test is CommonTest {
function setUp() external {
_setUp();
} }
/**
* @notice Tests that hashCrossDomainMessage returns the correct hash in a simple case.
*/
function testDiff_hashCrossDomainMessage_succeeds( function testDiff_hashCrossDomainMessage_succeeds(
uint240 _nonce, uint240 _nonce,
uint16 _version, uint16 _version,
...@@ -29,31 +42,25 @@ contract Hashing_Test is CommonTest { ...@@ -29,31 +42,25 @@ contract Hashing_Test is CommonTest {
uint256 _gasLimit, uint256 _gasLimit,
bytes memory _data bytes memory _data
) external { ) external {
// Ensure the version is valid // Ensure the version is valid.
uint16 version = uint16(bound(uint256(_version), 0, 1)); uint16 version = uint16(bound(uint256(_version), 0, 1));
uint256 nonce = Encoding.encodeVersionedNonce(_nonce, version); uint256 nonce = Encoding.encodeVersionedNonce(_nonce, version);
bytes32 _hash = ffi.hashCrossDomainMessage( assertEq(
nonce, Hashing.hashCrossDomainMessage(nonce, _sender, _target, _value, _gasLimit, _data),
_sender, ffi.hashCrossDomainMessage(nonce, _sender, _target, _value, _gasLimit, _data)
_target,
_value,
_gasLimit,
_data
);
bytes32 hash = Hashing.hashCrossDomainMessage(
nonce,
_sender,
_target,
_value,
_gasLimit,
_data
); );
}
}
assertEq(hash, _hash); contract Hashing_hashWithdrawal_Test is CommonTest {
function setUp() external {
_setUp();
} }
/**
* @notice Tests that hashWithdrawal returns the correct hash in a simple case.
*/
function testDiff_hashWithdrawal_succeeds( function testDiff_hashWithdrawal_succeeds(
uint256 _nonce, uint256 _nonce,
address _sender, address _sender,
...@@ -62,42 +69,56 @@ contract Hashing_Test is CommonTest { ...@@ -62,42 +69,56 @@ contract Hashing_Test is CommonTest {
uint256 _gasLimit, uint256 _gasLimit,
bytes memory _data bytes memory _data
) external { ) external {
bytes32 hash = Hashing.hashWithdrawal( assertEq(
Types.WithdrawalTransaction(_nonce, _sender, _target, _value, _gasLimit, _data) Hashing.hashWithdrawal(
Types.WithdrawalTransaction(_nonce, _sender, _target, _value, _gasLimit, _data)
),
ffi.hashWithdrawal(_nonce, _sender, _target, _value, _gasLimit, _data)
); );
}
}
bytes32 _hash = ffi.hashWithdrawal(_nonce, _sender, _target, _value, _gasLimit, _data); contract Hashing_hashOutputRootProof_Test is CommonTest {
function setUp() external {
assertEq(hash, _hash); _setUp();
} }
/**
* @notice Tests that hashOutputRootProof returns the correct hash in a simple case.
*/
function testDiff_hashOutputRootProof_succeeds( function testDiff_hashOutputRootProof_succeeds(
bytes32 _version, bytes32 _version,
bytes32 _stateRoot, bytes32 _stateRoot,
bytes32 _messagePasserStorageRoot, bytes32 _messagePasserStorageRoot,
bytes32 _latestBlockhash bytes32 _latestBlockhash
) external { ) external {
Types.OutputRootProof memory proof = Types.OutputRootProof({ assertEq(
version: _version, Hashing.hashOutputRootProof(
stateRoot: _stateRoot, Types.OutputRootProof({
messagePasserStorageRoot: _messagePasserStorageRoot, version: _version,
latestBlockhash: _latestBlockhash stateRoot: _stateRoot,
}); messagePasserStorageRoot: _messagePasserStorageRoot,
latestBlockhash: _latestBlockhash
bytes32 hash = Hashing.hashOutputRootProof(proof); })
),
bytes32 _hash = ffi.hashOutputRootProof( ffi.hashOutputRootProof(
_version, _version,
_stateRoot, _stateRoot,
_messagePasserStorageRoot, _messagePasserStorageRoot,
_latestBlockhash _latestBlockhash
)
); );
}
}
assertEq(hash, _hash); contract Hashing_hashDepositTransaction_Test is CommonTest {
function setUp() external {
_setUp();
} }
// TODO(tynes): foundry bug cannot serialize /**
// bytes32 as strings with vm.toString * @notice Tests that hashDepositTransaction returns the correct hash in a simple case.
*/
function testDiff_hashDepositTransaction_succeeds( function testDiff_hashDepositTransaction_succeeds(
address _from, address _from,
address _to, address _to,
...@@ -107,30 +128,21 @@ contract Hashing_Test is CommonTest { ...@@ -107,30 +128,21 @@ contract Hashing_Test is CommonTest {
bytes memory _data, bytes memory _data,
uint256 _logIndex uint256 _logIndex
) external { ) external {
bytes32 hash = Hashing.hashDepositTransaction( assertEq(
Types.UserDepositTransaction( Hashing.hashDepositTransaction(
_from, Types.UserDepositTransaction(
_to, _from,
false, // isCreate _to,
_value, false, // isCreate
_mint, _value,
_gas, _mint,
_data, _gas,
bytes32(uint256(0)), _data,
_logIndex bytes32(uint256(0)),
) _logIndex
)
),
ffi.hashDepositTransaction(_from, _to, _mint, _value, _gas, _data, _logIndex)
); );
bytes32 _hash = ffi.hashDepositTransaction(
_from,
_to,
_mint,
_value,
_gas,
_data,
_logIndex
);
assertEq(hash, _hash);
} }
} }
...@@ -13,6 +13,34 @@ AssetReceiverTest:test_withdrawETHwithAmount() (gas: 26108) ...@@ -13,6 +13,34 @@ AssetReceiverTest:test_withdrawETHwithAmount() (gas: 26108)
AssetReceiverTest:test_attest_bulk() (gas: 611440) AssetReceiverTest:test_attest_bulk() (gas: 611440)
AssetReceiverTest:test_attest_individual() (gas: 538514) AssetReceiverTest:test_attest_individual() (gas: 538514)
AssetReceiverTest:test_attest_single() (gas: 558962) AssetReceiverTest:test_attest_single() (gas: 558962)
CheckBalanceHighTest:testFuzz_check_fails(address,uint256) (runs: 256, μ: 12352, ~: 12382)
CheckBalanceHighTest:testFuzz_check_succeeds(address,uint256) (runs: 256, μ: 10284, ~: 10284)
CheckBalanceLowTest:testFuzz_check_fails(address,uint256) (runs: 256, μ: 10262, ~: 10262)
CheckBalanceLowTest:testFuzz_check_succeeds(address,uint256) (runs: 256, μ: 12374, ~: 12404)
CheckGelatoLowTest:testFuzz_check_fails(uint256,address) (runs: 256, μ: 34938, ~: 35871)
CheckGelatoLowTest:testFuzz_check_succeeds(uint256,address) (runs: 256, μ: 18800, ~: 18800)
CheckTrueTest:testFuzz_always_true_succeeds(bytes) (runs: 256, μ: 6539, ~: 6486)
Drippie_Test:testFuzz_fails_unauthorized(address) (runs: 256, μ: 17073, ~: 17073)
Drippie_Test:test_create_fails_twice() (gas: 169499)
Drippie_Test:test_create_success() (gas: 184013)
Drippie_Test:test_drip_amount() (gas: 286156)
Drippie_Test:test_drip_not_exist_fails() (gas: 15136)
Drippie_Test:test_name_not_exist_fails() (gas: 16157)
Drippie_Test:test_non_reentrant_zero_interval_fails() (gas: 19090)
Drippie_Test:test_not_active_fails() (gas: 171861)
Drippie_Test:test_reentrant_fails() (gas: 19129)
Drippie_Test:test_reentrant_succeeds() (gas: 180769)
Drippie_Test:test_set_status_none_fails() (gas: 169439)
Drippie_Test:test_set_status_same_fails() (gas: 169939)
Drippie_Test:test_set_status_success() (gas: 199270)
Drippie_Test:test_should_archive_if_paused_success() (gas: 177922)
Drippie_Test:test_should_not_allow_active_if_archived_fails() (gas: 175362)
Drippie_Test:test_should_not_allow_paused_if_archived_fails() (gas: 175383)
Drippie_Test:test_should_not_archive_if_active_fails() (gas: 176512)
Drippie_Test:test_status_unauthorized_fails() (gas: 167971)
Drippie_Test:test_trigger_one_function() (gas: 339137)
Drippie_Test:test_trigger_two_functions() (gas: 493184)
Drippie_Test:test_twice_in_one_interval_fails() (gas: 305202)
OptimistTest:test_optimist_baseURI() (gas: 116809) OptimistTest:test_optimist_baseURI() (gas: 116809)
OptimistTest:test_optimist_burn() (gas: 77526) OptimistTest:test_optimist_burn() (gas: 77526)
OptimistTest:test_optimist_initialize() (gas: 23095) OptimistTest:test_optimist_initialize() (gas: 23095)
......
import { DeployConfig } from '../../src'
const config: DeployConfig = {
ddd: '0x9C6373dE60c2D3297b18A8f964618ac46E011B58',
l2ProxyOwnerAddress: '0x60c5C9c98bcBd0b0F2fD89B24c16e533BaA8CdA3',
optimistName: 'Optimist',
optimistSymbol: 'OPTIMIST',
attestorAddress: '0x60c5C9c98bcBd0b0F2fD89B24c16e533BaA8CdA3',
}
export default config
import { ethers } from 'ethers'
import { DrippieConfig, Time } from '../../src'
const config: DrippieConfig = {
BatcherBalance: {
interval: 1 * Time.DAY,
dripcheck: 'CheckBalanceLow',
checkparams: {
target: '0x6887246668a3b87f54deb3b94ba47a6f63f32985',
threshold: ethers.utils.parseEther('75'),
},
actions: [
{
target: '0x6887246668a3b87f54deb3b94ba47a6f63f32985',
value: ethers.utils.parseEther('125'),
},
],
},
ProposerBalance: {
interval: 1 * Time.DAY,
dripcheck: 'CheckBalanceLow',
checkparams: {
target: '0x473300df21d047806a082244b417f96b32f13a33',
threshold: ethers.utils.parseEther('50'),
},
actions: [
{
target: '0x473300df21d047806a082244b417f96b32f13a33',
value: ethers.utils.parseEther('100'),
},
],
},
GelatoBalance: {
interval: 1 * Time.DAY,
dripcheck: 'CheckGelatoLow',
checkparams: {
treasury: '0x2807B4aE232b624023f87d0e237A3B1bf200Fd99',
recipient: '0xc37f6a6c4AB335E20d10F034B90386E2fb70bbF5',
threshold: ethers.utils.parseEther('0.1'),
},
actions: [
{
target: '0x2807B4aE232b624023f87d0e237A3B1bf200Fd99',
value: ethers.utils.parseEther('1'),
data: {
fn: 'depositFunds',
args: [
// receiver
'0xc37f6a6c4AB335E20d10F034B90386E2fb70bbF5',
// token
'0xeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee',
// amount
ethers.utils.parseEther('1'),
],
},
},
],
},
}
export default config
//SPDX-License-Identifier: MIT
pragma solidity 0.8.16;
import { Test } from "forge-std/Test.sol";
import { CheckBalanceHigh } from "../universal/drippie/dripchecks/CheckBalanceHigh.sol";
/**
* @title CheckBalanceHighTest
* @notice Tests the CheckBalanceHigh contract via fuzzing both the success case
* and the failure case.
*/
contract CheckBalanceHighTest is Test {
/**
* @notice An instance of the CheckBalanceHigh contract.
*/
CheckBalanceHigh c;
/**
* @notice Deploy the `CheckTrue` contract.
*/
function setUp() external {
c = new CheckBalanceHigh();
}
/**
* @notice Fuzz the `check` function and assert that it always returns true
* when the target's balance is larger than the threshold.
*/
function testFuzz_check_succeeds(address _target, uint256 _threshold) external {
CheckBalanceHigh.Params memory p = CheckBalanceHigh.Params({
target: _target,
threshold: _threshold
});
// prevent overflows
vm.assume(_threshold != type(uint256).max);
vm.deal(_target, _threshold + 1);
assertEq(c.check(abi.encode(p)), true);
}
/**
* @notice Fuzz the `check` function and assert that it always returns false
* when the target's balance is smaller than the threshold.
*/
function testFuzz_check_fails(address _target, uint256 _threshold) external {
CheckBalanceHigh.Params memory p = CheckBalanceHigh.Params({
target: _target,
threshold: _threshold
});
vm.assume(_target.balance < _threshold);
assertEq(c.check(abi.encode(p)), false);
}
}
//SPDX-License-Identifier: MIT
pragma solidity 0.8.16;
import { Test } from "forge-std/Test.sol";
import { CheckBalanceLow } from "../universal/drippie/dripchecks/CheckBalanceLow.sol";
/**
* @title CheckBalanceLowTest
* @notice Tests the CheckBalanceLow contract via fuzzing both the success case
* and the failure case.
*/
contract CheckBalanceLowTest is Test {
/**
* @notice An instance of the CheckBalanceLow contract.
*/
CheckBalanceLow c;
/**
* @notice Deploy the `CheckBalanceLow` contract.
*/
function setUp() external {
c = new CheckBalanceLow();
}
/**
* @notice Fuzz the `check` function and assert that it always returns true
* when the target's balance is smaller than the threshold.
*/
function testFuzz_check_succeeds(address _target, uint256 _threshold) external {
CheckBalanceLow.Params memory p = CheckBalanceLow.Params({
target: _target,
threshold: _threshold
});
vm.assume(_target.balance < _threshold);
assertEq(c.check(abi.encode(p)), true);
}
/**
* @notice Fuzz the `check` function and assert that it always returns false
* when the target's balance is larger than the threshold.
*/
function testFuzz_check_fails(address _target, uint256 _threshold) external {
CheckBalanceLow.Params memory p = CheckBalanceLow.Params({
target: _target,
threshold: _threshold
});
// prevent overflows
vm.assume(_threshold != type(uint256).max);
vm.deal(_target, _threshold + 1);
assertEq(c.check(abi.encode(p)), false);
}
}
//SPDX-License-Identifier: MIT
pragma solidity 0.8.16;
import { Test } from "forge-std/Test.sol";
import {
CheckGelatoLow,
IGelatoTreasury
} from "../universal/drippie/dripchecks/CheckGelatoLow.sol";
/**
* @title MockGelatoTreasury
* @notice Mocks the Gelato treasury for testing purposes. Allows arbitrary
* setting of user balances.
*/
contract MockGelatoTreasury is IGelatoTreasury {
mapping(address => mapping(address => uint256)) private tokenBalances;
function setTokenBalance(
address _user,
address _token,
uint256 _balance
) external {
tokenBalances[_token][_user] = _balance;
}
function userTokenBalance(address _user, address _token) external view returns (uint256) {
return tokenBalances[_token][_user];
}
}
/**
* @title CheckGelatoLowTest
* @notice Tests the CheckBalanceHigh contract via fuzzing both the success case
* and the failure case.
*/
contract CheckGelatoLowTest is Test {
/**
* @notice An instance of the CheckGelatoLow contract.
*/
CheckGelatoLow c;
/**
* @notice An instance of the MockGelatoTreasury contract.
*/
MockGelatoTreasury gelato;
/**
* @notice The account Gelato uses to represent ether
*/
address internal constant eth = 0xEeeeeEeeeEeEeeEeEeEeeEEEeeeeEeeeeeeeEEeE;
/**
* @notice Deploy the `CheckGelatoLow` and `MockGelatoTreasury` contracts.
*/
function setUp() external {
c = new CheckGelatoLow();
gelato = new MockGelatoTreasury();
}
/**
* @notice Fuzz the `check` function and assert that it always returns true
* when the user's balance in the treasury is less than the threshold.
*/
function testFuzz_check_succeeds(uint256 _threshold, address _recipient) external {
CheckGelatoLow.Params memory p = CheckGelatoLow.Params({
treasury: address(gelato),
threshold: _threshold,
recipient: _recipient
});
vm.assume(gelato.userTokenBalance(_recipient, eth) < _threshold);
assertEq(c.check(abi.encode(p)), true);
}
/**
* @notice Fuzz the `check` function and assert that it always returns false
* when the user's balance in the treasury is greater than or equal
* to the threshold.
*/
function testFuzz_check_fails(uint256 _threshold, address _recipient) external {
CheckGelatoLow.Params memory p = CheckGelatoLow.Params({
treasury: address(gelato),
threshold: _threshold,
recipient: _recipient
});
gelato.setTokenBalance(_recipient, eth, _threshold);
assertEq(c.check(abi.encode(p)), false);
}
}
//SPDX-License-Identifier: MIT
pragma solidity 0.8.16;
import { Test } from "forge-std/Test.sol";
import { CheckTrue } from "../universal/drippie/dripchecks/CheckTrue.sol";
/**
* @title CheckTrueTest
* @notice Ensures that the CheckTrue DripCheck contract always returns true.
*/
contract CheckTrueTest is Test {
/**
* @notice An instance of the CheckTrue contract.
*/
CheckTrue c;
/**
* @notice Deploy the `CheckTrue` contract.
*/
function setUp() external {
c = new CheckTrue();
}
/**
* @notice Fuzz the `check` function and assert that it always returns true.
*/
function testFuzz_always_true_succeeds(bytes memory input) external {
assertEq(c.check(input), true);
}
}
This source diff could not be displayed because it is too large. You can view the blob instead.
...@@ -54,7 +54,6 @@ ...@@ -54,7 +54,6 @@
"url": "https://github.com/ethereum-optimism/optimism.git" "url": "https://github.com/ethereum-optimism/optimism.git"
}, },
"devDependencies": { "devDependencies": {
"@defi-wonderland/smock": "^2.0.7",
"@eth-optimism/contracts-bedrock": "0.11.3", "@eth-optimism/contracts-bedrock": "0.11.3",
"@eth-optimism/core-utils": "^0.12.0", "@eth-optimism/core-utils": "^0.12.0",
"@eth-optimism/hardhat-deploy-config": "^0.2.5", "@eth-optimism/hardhat-deploy-config": "^0.2.5",
......
import hre from 'hardhat'
import { SignerWithAddress } from '@nomiclabs/hardhat-ethers/signers'
import { Contract } from 'ethers'
import { toRpcHexString } from '@eth-optimism/core-utils'
import { expect } from '../../../setup'
import { deploy } from '../../../helpers'
describe('Drippie', () => {
const DEFAULT_DRIP_NAME = 'drippity drip drip'
const DEFAULT_DRIP_CONFIG = {
interval: hre.ethers.BigNumber.from(100),
dripcheck: '', // Gets added in setup
checkparams: '0x',
actions: [
{
target: '0x' + '11'.repeat(20),
data: '0x',
value: hre.ethers.BigNumber.from(1),
},
],
}
let signer1: SignerWithAddress
let signer2: SignerWithAddress
before('signer setup', async () => {
;[signer1, signer2] = await hre.ethers.getSigners()
})
before('deploy default dripcheck', async () => {
DEFAULT_DRIP_CONFIG.dripcheck = (await deploy('CheckTrue')).address
})
let SimpleStorage: Contract
let Drippie: Contract
beforeEach('deploy contracts', async () => {
SimpleStorage = await deploy('SimpleStorage')
Drippie = await deploy('Drippie', {
signer: signer1,
args: [signer1.address],
})
})
beforeEach('balance setup', async () => {
await hre.ethers.provider.send('hardhat_setBalance', [
Drippie.address,
toRpcHexString(DEFAULT_DRIP_CONFIG.actions[0].value.mul(100000)),
])
await hre.ethers.provider.send('hardhat_setBalance', [
DEFAULT_DRIP_CONFIG.actions[0].target,
'0x0',
])
})
describe('create', () => {
describe('when called by authorized address', () => {
it('should create a drip with the given name', async () => {
await expect(
Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
).to.emit(Drippie, 'DripCreated')
const drip = await Drippie.drips(DEFAULT_DRIP_NAME)
expect(drip.status).to.equal(1) // PAUSED
expect(drip.last).to.deep.equal(hre.ethers.BigNumber.from(0))
expect(drip.config.interval).to.deep.equal(DEFAULT_DRIP_CONFIG.interval)
expect(drip.config.dripcheck).to.deep.equal(
DEFAULT_DRIP_CONFIG.dripcheck
)
expect(drip.config.checkparams).to.deep.equal(
DEFAULT_DRIP_CONFIG.checkparams
)
expect(drip.config.actions[0][0]).to.deep.equal(
DEFAULT_DRIP_CONFIG.actions[0].target
)
expect(drip.config.actions[0][1]).to.deep.equal(
DEFAULT_DRIP_CONFIG.actions[0].data
)
expect(drip.config.actions[0][2]).to.deep.equal(
DEFAULT_DRIP_CONFIG.actions[0].value
)
})
it('should not be able to create the same drip twice', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await expect(
Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
).to.be.revertedWith('Drippie: drip with that name already exists')
})
})
describe('when called by not authorized address', () => {
it('should revert', async () => {
await expect(
Drippie.connect(signer2).create(
DEFAULT_DRIP_NAME,
DEFAULT_DRIP_CONFIG
)
).to.be.revertedWith('UNAUTHORIZED')
})
})
})
describe('status', () => {
describe('when called by authorized address', () => {
it('should allow setting between PAUSED and ACTIVE', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
expect((await Drippie.drips(DEFAULT_DRIP_NAME)).status).to.equal(1) // PAUSED
await Drippie.status(DEFAULT_DRIP_NAME, 2) // ACTIVE
expect((await Drippie.drips(DEFAULT_DRIP_NAME)).status).to.equal(2) // ACTIVE
await Drippie.status(DEFAULT_DRIP_NAME, 1) // PAUSED
expect((await Drippie.drips(DEFAULT_DRIP_NAME)).status).to.equal(1) // PAUSED
})
it('should not allow setting status to NONE', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await expect(Drippie.status(DEFAULT_DRIP_NAME, 0)).to.be.revertedWith(
'Drippie: drip status can never be set back to NONE after creation'
)
})
it('should not allow setting status to same status as before', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await expect(Drippie.status(DEFAULT_DRIP_NAME, 1)).to.be.revertedWith(
'Drippie: cannot set drip status to the same status as its current status'
)
})
it('should allow setting status to ARCHIVED if PAUSED', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await Drippie.status(DEFAULT_DRIP_NAME, 3) // ARCHIVED
expect((await Drippie.drips(DEFAULT_DRIP_NAME)).status).to.equal(3) // ARCHIVED
})
it('should not allow setting status to ARCHIVED if ACTIVE', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await Drippie.status(DEFAULT_DRIP_NAME, 2) // ACTIVE
await expect(Drippie.status(DEFAULT_DRIP_NAME, 3)).to.be.revertedWith(
'Drippie: drip must first be paused before being archived'
)
})
it('should not allow setting status to PAUSED if ARCHIVED', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await Drippie.status(DEFAULT_DRIP_NAME, 3) // ARCHIVED
await expect(Drippie.status(DEFAULT_DRIP_NAME, 2)).to.be.revertedWith(
'Drippie: drip with that name has been archived'
)
})
it('should not allow setting status to ACTIVE if ARCHIVED', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await Drippie.status(DEFAULT_DRIP_NAME, 3) // ARCHIVED
await expect(Drippie.status(DEFAULT_DRIP_NAME, 1)).to.be.revertedWith(
'Drippie: drip with that name has been archived'
)
})
it('should revert if the drip does not exist yet', async () => {
await expect(Drippie.status(DEFAULT_DRIP_NAME, 1)).to.be.revertedWith(
'Drippie: drip with that name does not exist'
)
})
})
describe('when called by not authorized address', () => {
it('should revert', async () => {
await expect(
Drippie.connect(signer2).status(DEFAULT_DRIP_NAME, 1)
).to.be.revertedWith('UNAUTHORIZED')
})
})
})
describe('drip', () => {
it('should drip the amount', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await Drippie.status(DEFAULT_DRIP_NAME, 2) // ACTIVE
await expect(Drippie.drip(DEFAULT_DRIP_NAME)).to.emit(
Drippie,
'DripExecuted'
)
expect(
await signer1.provider.getBalance(DEFAULT_DRIP_CONFIG.actions[0].target)
).to.equal(DEFAULT_DRIP_CONFIG.actions[0].value)
})
it('should be able to trigger one function', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, {
...DEFAULT_DRIP_CONFIG,
actions: [
{
target: SimpleStorage.address,
data: SimpleStorage.interface.encodeFunctionData('set', [
'0x' + '33'.repeat(32),
'0x' + '44'.repeat(32),
]),
value: hre.ethers.BigNumber.from(0),
},
],
})
await Drippie.status(DEFAULT_DRIP_NAME, 2) // ACTIVE
await Drippie.drip(DEFAULT_DRIP_NAME)
expect(await SimpleStorage.get('0x' + '33'.repeat(32))).to.equal(
'0x' + '44'.repeat(32)
)
})
it('should be able to trigger two functions', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, {
...DEFAULT_DRIP_CONFIG,
actions: [
{
target: SimpleStorage.address,
data: SimpleStorage.interface.encodeFunctionData('set', [
'0x' + '33'.repeat(32),
'0x' + '44'.repeat(32),
]),
value: hre.ethers.BigNumber.from(0),
},
{
target: SimpleStorage.address,
data: SimpleStorage.interface.encodeFunctionData('set', [
'0x' + '44'.repeat(32),
'0x' + '55'.repeat(32),
]),
value: hre.ethers.BigNumber.from(0),
},
],
})
await Drippie.status(DEFAULT_DRIP_NAME, 2) // ACTIVE
await Drippie.drip(DEFAULT_DRIP_NAME)
expect(await SimpleStorage.get('0x' + '33'.repeat(32))).to.equal(
'0x' + '44'.repeat(32)
)
expect(await SimpleStorage.get('0x' + '44'.repeat(32))).to.equal(
'0x' + '55'.repeat(32)
)
})
it('should revert if dripping twice in one interval', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await Drippie.status(DEFAULT_DRIP_NAME, 2) // ACTIVE
await Drippie.drip(DEFAULT_DRIP_NAME)
await expect(Drippie.drip(DEFAULT_DRIP_NAME)).to.be.revertedWith(
'Drippie: drip interval has not elapsed'
)
await hre.ethers.provider.send('evm_increaseTime', [
DEFAULT_DRIP_CONFIG.interval.add(1).toHexString(),
])
await expect(Drippie.drip(DEFAULT_DRIP_NAME)).to.not.be.reverted
})
it('should revert when the drip does not exist', async () => {
await expect(Drippie.drip(DEFAULT_DRIP_NAME)).to.be.revertedWith(
'Drippie: selected drip does not exist or is not currently active'
)
})
it('should revert when the drip is not active', async () => {
await Drippie.create(DEFAULT_DRIP_NAME, DEFAULT_DRIP_CONFIG)
await expect(Drippie.drip(DEFAULT_DRIP_NAME)).to.be.revertedWith(
'Drippie: selected drip does not exist or is not currently active'
)
})
})
})
import hre from 'hardhat'
import { Contract } from 'ethers'
import { toRpcHexString } from '@eth-optimism/core-utils'
import { expect } from '../../../../setup'
import { deploy } from '../../../../helpers'
import { encodeDripCheckParams } from '../../../../../src'
describe('CheckBalanceHigh', () => {
const RECIPIENT = '0x' + '11'.repeat(20)
const THRESHOLD = 100
let CheckBalanceHigh: Contract
before(async () => {
CheckBalanceHigh = await deploy('CheckBalanceHigh')
})
describe('check', () => {
it('should return true when balance is above threshold', async () => {
await hre.ethers.provider.send('hardhat_setBalance', [
RECIPIENT,
toRpcHexString(THRESHOLD + 1),
])
expect(
await CheckBalanceHigh.check(
encodeDripCheckParams(CheckBalanceHigh.interface, {
target: RECIPIENT,
threshold: THRESHOLD,
})
)
).to.equal(true)
})
it('should return false when balance is below threshold', async () => {
await hre.ethers.provider.send('hardhat_setBalance', [
RECIPIENT,
toRpcHexString(THRESHOLD - 1),
])
expect(
await CheckBalanceHigh.check(
encodeDripCheckParams(CheckBalanceHigh.interface, {
target: RECIPIENT,
threshold: THRESHOLD,
})
)
).to.equal(false)
})
})
})
import hre from 'hardhat'
import { Contract } from 'ethers'
import { toRpcHexString } from '@eth-optimism/core-utils'
import { expect } from '../../../../setup'
import { deploy } from '../../../../helpers'
import { encodeDripCheckParams } from '../../../../../src'
describe('CheckBalanceLow', () => {
const RECIPIENT = '0x' + '11'.repeat(20)
const THRESHOLD = 100
let CheckBalanceLow: Contract
before(async () => {
CheckBalanceLow = await deploy('CheckBalanceLow')
})
describe('check', () => {
it('should return true when balance is below threshold', async () => {
await hre.ethers.provider.send('hardhat_setBalance', [
RECIPIENT,
toRpcHexString(THRESHOLD - 1),
])
expect(
await CheckBalanceLow.check(
encodeDripCheckParams(CheckBalanceLow.interface, {
target: RECIPIENT,
threshold: THRESHOLD,
})
)
).to.equal(true)
})
it('should return false when balance is above threshold', async () => {
await hre.ethers.provider.send('hardhat_setBalance', [
RECIPIENT,
toRpcHexString(THRESHOLD + 1),
])
expect(
await CheckBalanceLow.check(
encodeDripCheckParams(CheckBalanceLow.interface, {
target: RECIPIENT,
threshold: THRESHOLD,
})
)
).to.equal(false)
})
})
})
import { Contract } from 'ethers'
import { smock, FakeContract } from '@defi-wonderland/smock'
import { expect } from '../../../../setup'
import { deploy } from '../../../../helpers'
import { encodeDripCheckParams } from '../../../../../src'
describe('CheckGelatoLow', () => {
const RECIPIENT = '0x' + '11'.repeat(20)
const THRESHOLD = 100
let CheckGelatoLow: Contract
let FakeGelatoTresury: FakeContract<Contract>
before(async () => {
CheckGelatoLow = await deploy('CheckGelatoLow')
FakeGelatoTresury = await smock.fake('IGelatoTreasury')
})
describe('check', () => {
it('should return true when balance is below threshold', async () => {
FakeGelatoTresury.userTokenBalance.returns(THRESHOLD - 1)
expect(
await CheckGelatoLow.check(
encodeDripCheckParams(CheckGelatoLow.interface, {
treasury: FakeGelatoTresury.address,
threshold: THRESHOLD,
recipient: RECIPIENT,
})
)
).to.equal(true)
})
it('should return false when balance is above threshold', async () => {
FakeGelatoTresury.userTokenBalance.returns(THRESHOLD + 1)
expect(
await CheckGelatoLow.check(
encodeDripCheckParams(CheckGelatoLow.interface, {
treasury: FakeGelatoTresury.address,
threshold: THRESHOLD,
recipient: RECIPIENT,
})
)
).to.equal(false)
})
})
})
import { Contract } from 'ethers'
import { expect } from '../../../../setup'
import { deploy } from '../../../../helpers'
describe('CheckTrue', () => {
let CheckTrue: Contract
before(async () => {
CheckTrue = await deploy('CheckTrue')
})
describe('check', () => {
it('should return true', async () => {
expect(await CheckTrue.check('0x')).to.equal(true)
})
})
})
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