Commit 59ba5f37 authored by protolambda's avatar protolambda Committed by GitHub

op-supervisor: dependency-set config (#12450)

* op-supervisor: cleanup, refactor to take local-safe info from op-node

* op-supervisor: dependency-set config

---------
Co-authored-by: default avataraxelKingsley <axel.kingsley@gmail.com>
parent 745b251d
...@@ -10,10 +10,6 @@ import ( ...@@ -10,10 +10,6 @@ import (
"testing" "testing"
"time" "time"
emit "github.com/ethereum-optimism/optimism/op-e2e/interop/contracts"
"github.com/ethereum-optimism/optimism/op-e2e/system/helpers"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
"github.com/ethereum/go-ethereum/accounts/abi/bind" "github.com/ethereum/go-ethereum/accounts/abi/bind"
...@@ -30,11 +26,14 @@ import ( ...@@ -30,11 +26,14 @@ import (
"github.com/ethereum-optimism/optimism/op-chain-ops/devkeys" "github.com/ethereum-optimism/optimism/op-chain-ops/devkeys"
"github.com/ethereum-optimism/optimism/op-chain-ops/foundry" "github.com/ethereum-optimism/optimism/op-chain-ops/foundry"
"github.com/ethereum-optimism/optimism/op-chain-ops/interopgen" "github.com/ethereum-optimism/optimism/op-chain-ops/interopgen"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils/fakebeacon" "github.com/ethereum-optimism/optimism/op-e2e/e2eutils/fakebeacon"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils/geth" "github.com/ethereum-optimism/optimism/op-e2e/e2eutils/geth"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils/opnode" "github.com/ethereum-optimism/optimism/op-e2e/e2eutils/opnode"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils/services" "github.com/ethereum-optimism/optimism/op-e2e/e2eutils/services"
"github.com/ethereum-optimism/optimism/op-e2e/e2eutils/setuputils" "github.com/ethereum-optimism/optimism/op-e2e/e2eutils/setuputils"
emit "github.com/ethereum-optimism/optimism/op-e2e/interop/contracts"
"github.com/ethereum-optimism/optimism/op-e2e/system/helpers"
"github.com/ethereum-optimism/optimism/op-node/node" "github.com/ethereum-optimism/optimism/op-node/node"
"github.com/ethereum-optimism/optimism/op-node/p2p" "github.com/ethereum-optimism/optimism/op-node/p2p"
"github.com/ethereum-optimism/optimism/op-node/rollup/derive" "github.com/ethereum-optimism/optimism/op-node/rollup/derive"
...@@ -53,6 +52,8 @@ import ( ...@@ -53,6 +52,8 @@ import (
"github.com/ethereum-optimism/optimism/op-service/testlog" "github.com/ethereum-optimism/optimism/op-service/testlog"
supervisorConfig "github.com/ethereum-optimism/optimism/op-supervisor/config" supervisorConfig "github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
supervisortypes "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
) )
// SuperSystem is an interface for the system (collection of connected resources) // SuperSystem is an interface for the system (collection of connected resources)
...@@ -437,9 +438,18 @@ func (s *interopE2ESystem) prepareSupervisor() *supervisor.SupervisorService { ...@@ -437,9 +438,18 @@ func (s *interopE2ESystem) prepareSupervisor() *supervisor.SupervisorService {
L2RPCs: []string{}, L2RPCs: []string{},
Datadir: path.Join(s.t.TempDir(), "supervisor"), Datadir: path.Join(s.t.TempDir(), "supervisor"),
} }
depSet := &depset.StaticConfigDependencySet{
Dependencies: make(map[supervisortypes.ChainID]*depset.StaticConfigDependency),
}
for id := range s.l2s { for id := range s.l2s {
cfg.L2RPCs = append(cfg.L2RPCs, s.l2s[id].l2Geth.UserRPC().RPC()) cfg.L2RPCs = append(cfg.L2RPCs, s.l2s[id].l2Geth.UserRPC().RPC())
chainID := supervisortypes.ChainIDFromBig(s.l2s[id].chainID)
depSet.Dependencies[chainID] = &depset.StaticConfigDependency{
ActivationTime: 0,
HistoryMinTime: 0,
}
} }
cfg.DependencySetSource = depSet
// Create the supervisor with the configuration // Create the supervisor with the configuration
super, err := supervisor.SupervisorFromConfig(context.Background(), &cfg, logger) super, err := supervisor.SupervisorFromConfig(context.Background(), &cfg, logger)
require.NoError(s.t, err) require.NoError(s.t, err)
......
...@@ -6,12 +6,13 @@ import ( ...@@ -6,12 +6,13 @@ import (
"fmt" "fmt"
"testing" "testing"
"github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/stretchr/testify/require" "github.com/stretchr/testify/require"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
"github.com/ethereum-optimism/optimism/op-service/cliapp" "github.com/ethereum-optimism/optimism/op-service/cliapp"
"github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
) )
var ( var (
...@@ -36,7 +37,8 @@ func TestLogLevel(t *testing.T) { ...@@ -36,7 +37,8 @@ func TestLogLevel(t *testing.T) {
func TestDefaultCLIOptionsMatchDefaultConfig(t *testing.T) { func TestDefaultCLIOptionsMatchDefaultConfig(t *testing.T) {
cfg := configForArgs(t, addRequiredArgs()) cfg := configForArgs(t, addRequiredArgs())
defaultCfgTempl := config.NewConfig(ValidL2RPCs, ValidDatadir) depSet := &depset.JsonDependencySetLoader{Path: "test"}
defaultCfgTempl := config.NewConfig(ValidL2RPCs, depSet, ValidDatadir)
defaultCfg := *defaultCfgTempl defaultCfg := *defaultCfgTempl
defaultCfg.Version = Version defaultCfg.Version = Version
require.Equal(t, defaultCfg, *cfg) require.Equal(t, defaultCfg, *cfg)
...@@ -123,8 +125,9 @@ func toArgList(req map[string]string) []string { ...@@ -123,8 +125,9 @@ func toArgList(req map[string]string) []string {
func requiredArgs() map[string]string { func requiredArgs() map[string]string {
args := map[string]string{ args := map[string]string{
"--l2-rpcs": ValidL2RPCs[0], "--l2-rpcs": ValidL2RPCs[0],
"--datadir": ValidDatadir, "--dependency-set": "test",
"--datadir": ValidDatadir,
} }
return args return args
} }
...@@ -7,11 +7,13 @@ import ( ...@@ -7,11 +7,13 @@ import (
opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics" opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics"
"github.com/ethereum-optimism/optimism/op-service/oppprof" "github.com/ethereum-optimism/optimism/op-service/oppprof"
oprpc "github.com/ethereum-optimism/optimism/op-service/rpc" oprpc "github.com/ethereum-optimism/optimism/op-service/rpc"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
) )
var ( var (
ErrMissingL2RPC = errors.New("must specify at least one L2 RPC") ErrMissingL2RPC = errors.New("must specify at least one L2 RPC")
ErrMissingDatadir = errors.New("must specify datadir") ErrMissingDependencySet = errors.New("must specify a dependency set source")
ErrMissingDatadir = errors.New("must specify datadir")
) )
type Config struct { type Config struct {
...@@ -22,6 +24,8 @@ type Config struct { ...@@ -22,6 +24,8 @@ type Config struct {
PprofConfig oppprof.CLIConfig PprofConfig oppprof.CLIConfig
RPC oprpc.CLIConfig RPC oprpc.CLIConfig
DependencySetSource depset.DependencySetSource
// MockRun runs the service with a mock backend // MockRun runs the service with a mock backend
MockRun bool MockRun bool
...@@ -37,6 +41,9 @@ func (c *Config) Check() error { ...@@ -37,6 +41,9 @@ func (c *Config) Check() error {
if len(c.L2RPCs) == 0 { if len(c.L2RPCs) == 0 {
result = errors.Join(result, ErrMissingL2RPC) result = errors.Join(result, ErrMissingL2RPC)
} }
if c.DependencySetSource == nil {
result = errors.Join(result, ErrMissingDependencySet)
}
if c.Datadir == "" { if c.Datadir == "" {
result = errors.Join(result, ErrMissingDatadir) result = errors.Join(result, ErrMissingDatadir)
} }
...@@ -45,14 +52,15 @@ func (c *Config) Check() error { ...@@ -45,14 +52,15 @@ func (c *Config) Check() error {
// NewConfig creates a new config using default values whenever possible. // NewConfig creates a new config using default values whenever possible.
// Required options with no suitable default are passed as parameters. // Required options with no suitable default are passed as parameters.
func NewConfig(l2RPCs []string, datadir string) *Config { func NewConfig(l2RPCs []string, depSet depset.DependencySetSource, datadir string) *Config {
return &Config{ return &Config{
LogConfig: oplog.DefaultCLIConfig(), LogConfig: oplog.DefaultCLIConfig(),
MetricsConfig: opmetrics.DefaultCLIConfig(), MetricsConfig: opmetrics.DefaultCLIConfig(),
PprofConfig: oppprof.DefaultCLIConfig(), PprofConfig: oppprof.DefaultCLIConfig(),
RPC: oprpc.DefaultCLIConfig(), RPC: oprpc.DefaultCLIConfig(),
MockRun: false, DependencySetSource: depSet,
L2RPCs: l2RPCs, MockRun: false,
Datadir: datadir, L2RPCs: l2RPCs,
Datadir: datadir,
} }
} }
...@@ -3,10 +3,13 @@ package config ...@@ -3,10 +3,13 @@ package config
import ( import (
"testing" "testing"
"github.com/stretchr/testify/require"
"github.com/ethereum-optimism/optimism/op-service/metrics" "github.com/ethereum-optimism/optimism/op-service/metrics"
"github.com/ethereum-optimism/optimism/op-service/oppprof" "github.com/ethereum-optimism/optimism/op-service/oppprof"
"github.com/ethereum-optimism/optimism/op-service/rpc" "github.com/ethereum-optimism/optimism/op-service/rpc"
"github.com/stretchr/testify/require" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
) )
func TestDefaultConfigIsValid(t *testing.T) { func TestDefaultConfigIsValid(t *testing.T) {
...@@ -20,6 +23,12 @@ func TestRequireL2RPC(t *testing.T) { ...@@ -20,6 +23,12 @@ func TestRequireL2RPC(t *testing.T) {
require.ErrorIs(t, cfg.Check(), ErrMissingL2RPC) require.ErrorIs(t, cfg.Check(), ErrMissingL2RPC)
} }
func TestRequireDependencySet(t *testing.T) {
cfg := validConfig()
cfg.DependencySetSource = nil
require.ErrorIs(t, cfg.Check(), ErrMissingDependencySet)
}
func TestRequireDatadir(t *testing.T) { func TestRequireDatadir(t *testing.T) {
cfg := validConfig() cfg := validConfig()
cfg.Datadir = "" cfg.Datadir = ""
...@@ -47,6 +56,14 @@ func TestValidateRPCConfig(t *testing.T) { ...@@ -47,6 +56,14 @@ func TestValidateRPCConfig(t *testing.T) {
} }
func validConfig() *Config { func validConfig() *Config {
depSet := &depset.StaticConfigDependencySet{
Dependencies: map[types.ChainID]*depset.StaticConfigDependency{
types.ChainIDFromUInt64(900): &depset.StaticConfigDependency{
ActivationTime: 0,
HistoryMinTime: 0,
},
},
}
// Should be valid using only the required arguments passed in via the constructor. // Should be valid using only the required arguments passed in via the constructor.
return NewConfig([]string{"http://localhost:8545"}, "./supervisor_config_testdir") return NewConfig([]string{"http://localhost:8545"}, depSet, "./supervisor_testdir")
} }
...@@ -3,7 +3,6 @@ package flags ...@@ -3,7 +3,6 @@ package flags
import ( import (
"fmt" "fmt"
"github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/urfave/cli/v2" "github.com/urfave/cli/v2"
opservice "github.com/ethereum-optimism/optimism/op-service" opservice "github.com/ethereum-optimism/optimism/op-service"
...@@ -11,6 +10,8 @@ import ( ...@@ -11,6 +10,8 @@ import (
opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics" opmetrics "github.com/ethereum-optimism/optimism/op-service/metrics"
"github.com/ethereum-optimism/optimism/op-service/oppprof" "github.com/ethereum-optimism/optimism/op-service/oppprof"
oprpc "github.com/ethereum-optimism/optimism/op-service/rpc" oprpc "github.com/ethereum-optimism/optimism/op-service/rpc"
"github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
) )
const EnvVarPrefix = "OP_SUPERVISOR" const EnvVarPrefix = "OP_SUPERVISOR"
...@@ -30,6 +31,12 @@ var ( ...@@ -30,6 +31,12 @@ var (
Usage: "Directory to store data generated as part of responding to games", Usage: "Directory to store data generated as part of responding to games",
EnvVars: prefixEnvVars("DATADIR"), EnvVars: prefixEnvVars("DATADIR"),
} }
DependencySetFlag = &cli.PathFlag{
Name: "dependency-set",
Usage: "Dependency-set configuration, point at JSON file.",
EnvVars: prefixEnvVars("DEPENDENCY_SET"),
TakesFile: true,
}
MockRunFlag = &cli.BoolFlag{ MockRunFlag = &cli.BoolFlag{
Name: "mock-run", Name: "mock-run",
Usage: "Mock run, no actual backend used, just presenting the service", Usage: "Mock run, no actual backend used, just presenting the service",
...@@ -41,6 +48,7 @@ var ( ...@@ -41,6 +48,7 @@ var (
var requiredFlags = []cli.Flag{ var requiredFlags = []cli.Flag{
L2RPCsFlag, L2RPCsFlag,
DataDirFlag, DataDirFlag,
DependencySetFlag,
} }
var optionalFlags = []cli.Flag{ var optionalFlags = []cli.Flag{
...@@ -71,13 +79,14 @@ func CheckRequired(ctx *cli.Context) error { ...@@ -71,13 +79,14 @@ func CheckRequired(ctx *cli.Context) error {
func ConfigFromCLI(ctx *cli.Context, version string) *config.Config { func ConfigFromCLI(ctx *cli.Context, version string) *config.Config {
return &config.Config{ return &config.Config{
Version: version, Version: version,
LogConfig: oplog.ReadCLIConfig(ctx), LogConfig: oplog.ReadCLIConfig(ctx),
MetricsConfig: opmetrics.ReadCLIConfig(ctx), MetricsConfig: opmetrics.ReadCLIConfig(ctx),
PprofConfig: oppprof.ReadCLIConfig(ctx), PprofConfig: oppprof.ReadCLIConfig(ctx),
RPC: oprpc.ReadCLIConfig(ctx), RPC: oprpc.ReadCLIConfig(ctx),
MockRun: ctx.Bool(MockRunFlag.Name), DependencySetSource: &depset.JsonDependencySetLoader{Path: ctx.Path(DependencySetFlag.Name)},
L2RPCs: ctx.StringSlice(L2RPCsFlag.Name), MockRun: ctx.Bool(MockRunFlag.Name),
Datadir: ctx.Path(DataDirFlag.Name), L2RPCs: ctx.StringSlice(L2RPCsFlag.Name),
Datadir: ctx.Path(DataDirFlag.Name),
} }
} }
...@@ -19,6 +19,7 @@ import ( ...@@ -19,6 +19,7 @@ import (
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/db" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/db"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/db/entrydb" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/db/entrydb"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/db/logs" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/db/logs"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/processors" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/processors"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/frontend" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/frontend"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
...@@ -35,6 +36,8 @@ type SupervisorBackend struct { ...@@ -35,6 +36,8 @@ type SupervisorBackend struct {
// Write = set of chains is changing. // Write = set of chains is changing.
mu sync.RWMutex mu sync.RWMutex
depSet depset.DependencySet
// db holds on to the DB indices for each chain // db holds on to the DB indices for each chain
db *db.ChainsDB db *db.ChainsDB
...@@ -52,6 +55,12 @@ func NewSupervisorBackend(ctx context.Context, logger log.Logger, m Metrics, cfg ...@@ -52,6 +55,12 @@ func NewSupervisorBackend(ctx context.Context, logger log.Logger, m Metrics, cfg
return nil, err return nil, err
} }
// Load the dependency set
depSet, err := cfg.DependencySetSource.LoadDependencySet(ctx)
if err != nil {
return nil, fmt.Errorf("failed to load dependency set: %w", err)
}
// create the chains db // create the chains db
chainsDB := db.NewChainsDB(logger) chainsDB := db.NewChainsDB(logger)
...@@ -63,6 +72,7 @@ func NewSupervisorBackend(ctx context.Context, logger log.Logger, m Metrics, cfg ...@@ -63,6 +72,7 @@ func NewSupervisorBackend(ctx context.Context, logger log.Logger, m Metrics, cfg
logger: logger, logger: logger,
m: m, m: m,
dataDir: cfg.Datadir, dataDir: cfg.Datadir,
depSet: depSet,
chainProcessors: chainProcessors, chainProcessors: chainProcessors,
db: chainsDB, db: chainsDB,
} }
......
package depset
import (
"context"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
)
type DependencySetSource interface {
LoadDependencySet(ctx context.Context) (DependencySet, error)
}
// DependencySet is an initialized dependency set, ready to answer queries
// of what is and what is not part of the dependency set.
type DependencySet interface {
// CanExecuteAt determines if an executing message is valid at all.
// I.e. if the chain may be executing messages at the given timestamp.
// This may return an error if the query temporarily cannot be answered.
// E.g. if the DependencySet is syncing new changes.
CanExecuteAt(chainID types.ChainID, execTimestamp uint64) (bool, error)
// CanInitiateAt determines if an initiating message is valid to pull in.
// I.e. if the message of the given chain is readable or not.
// This may return an error if the query temporarily cannot be answered.
// E.g. if the DependencySet is syncing new changes.
CanInitiateAt(chainID types.ChainID, initTimestamp uint64) (bool, error)
}
package depset
import (
"context"
"encoding/json"
"os"
"path"
"testing"
"github.com/stretchr/testify/require"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
)
func TestDependencySet(t *testing.T) {
d := path.Join(t.TempDir(), "tmp_dep_set.json")
depSet := &StaticConfigDependencySet{
Dependencies: map[types.ChainID]*StaticConfigDependency{
types.ChainIDFromUInt64(900): {
ActivationTime: 42,
HistoryMinTime: 100,
},
types.ChainIDFromUInt64(901): {
ActivationTime: 30,
HistoryMinTime: 20,
},
},
}
data, err := json.Marshal(depSet)
require.NoError(t, err)
require.NoError(t, os.WriteFile(d, data, 0644))
loader := &JsonDependencySetLoader{Path: d}
result, err := loader.LoadDependencySet(context.Background())
require.NoError(t, err)
v, err := result.CanExecuteAt(types.ChainIDFromUInt64(900), 42)
require.NoError(t, err)
require.True(t, v)
v, err = result.CanExecuteAt(types.ChainIDFromUInt64(900), 41)
require.NoError(t, err)
require.False(t, v)
v, err = result.CanInitiateAt(types.ChainIDFromUInt64(900), 100)
require.NoError(t, err)
require.True(t, v)
v, err = result.CanInitiateAt(types.ChainIDFromUInt64(900), 99)
require.NoError(t, err)
require.False(t, v)
v, err = result.CanExecuteAt(types.ChainIDFromUInt64(901), 30)
require.NoError(t, err)
require.True(t, v)
v, err = result.CanExecuteAt(types.ChainIDFromUInt64(901), 29)
require.NoError(t, err)
require.False(t, v)
v, err = result.CanInitiateAt(types.ChainIDFromUInt64(901), 20)
require.NoError(t, err)
require.True(t, v)
v, err = result.CanInitiateAt(types.ChainIDFromUInt64(901), 19)
require.NoError(t, err)
require.False(t, v)
v, err = result.CanExecuteAt(types.ChainIDFromUInt64(902), 100000)
require.NoError(t, err)
require.False(t, v, "902 not a dependency")
v, err = result.CanInitiateAt(types.ChainIDFromUInt64(902), 100000)
require.NoError(t, err)
require.False(t, v, "902 not a dependency")
}
package depset
import (
"context"
"encoding/json"
"fmt"
"os"
)
// JsonDependencySetLoader loads a dependency set from a file-path.
type JsonDependencySetLoader struct {
Path string
}
func (j *JsonDependencySetLoader) LoadDependencySet(ctx context.Context) (DependencySet, error) {
f, err := os.Open(j.Path)
if err != nil {
return nil, fmt.Errorf("failed to open dependency set: %w", err)
}
defer f.Close()
dec := json.NewDecoder(f)
var out StaticConfigDependencySet
if err := dec.Decode(&out); err != nil {
return nil, fmt.Errorf("failed to decode dependency set: %w", err)
}
return &out, nil
}
var _ DependencySetSource = (*JsonDependencySetLoader)(nil)
package depset
import (
"context"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
)
type StaticConfigDependency struct {
// ActivationTime is when the chain becomes part of the dependency set.
// This is the minimum timestamp of the inclusion of an executing message.
ActivationTime uint64 `json:"activationTime"`
// HistoryMinTime is what the lower bound of data is to store.
// This is the minimum timestamp of an initiating message to be accessible to others.
// This is set to 0 when all data since genesis is executable.
HistoryMinTime uint64 `json:"historyMinTime"`
}
// StaticConfigDependencySet statically declares a DependencySet.
// It can be used as a DependencySetSource itself, by simply returning the itself when loading the set.
type StaticConfigDependencySet struct {
Dependencies map[types.ChainID]*StaticConfigDependency `json:"dependencies"`
}
var _ DependencySetSource = (*StaticConfigDependencySet)(nil)
var _ DependencySet = (*StaticConfigDependencySet)(nil)
func (ds *StaticConfigDependencySet) LoadDependencySet(ctx context.Context) (DependencySet, error) {
return ds, nil
}
func (ds *StaticConfigDependencySet) CanExecuteAt(chainID types.ChainID, execTimestamp uint64) (bool, error) {
dep, ok := ds.Dependencies[chainID]
if !ok {
return false, nil
}
return execTimestamp >= dep.ActivationTime, nil
}
func (ds *StaticConfigDependencySet) CanInitiateAt(chainID types.ChainID, initTimestamp uint64) (bool, error) {
dep, ok := ds.Dependencies[chainID]
if !ok {
return false, nil
}
return initTimestamp >= dep.HistoryMinTime, nil
}
...@@ -4,7 +4,6 @@ import ( ...@@ -4,7 +4,6 @@ import (
"context" "context"
"fmt" "fmt"
"github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/urfave/cli/v2" "github.com/urfave/cli/v2"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
...@@ -12,6 +11,7 @@ import ( ...@@ -12,6 +11,7 @@ import (
opservice "github.com/ethereum-optimism/optimism/op-service" opservice "github.com/ethereum-optimism/optimism/op-service"
"github.com/ethereum-optimism/optimism/op-service/cliapp" "github.com/ethereum-optimism/optimism/op-service/cliapp"
oplog "github.com/ethereum-optimism/optimism/op-service/log" oplog "github.com/ethereum-optimism/optimism/op-service/log"
"github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/ethereum-optimism/optimism/op-supervisor/flags" "github.com/ethereum-optimism/optimism/op-supervisor/flags"
) )
......
...@@ -17,6 +17,7 @@ import ( ...@@ -17,6 +17,7 @@ import (
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/testlog" "github.com/ethereum-optimism/optimism/op-service/testlog"
"github.com/ethereum-optimism/optimism/op-supervisor/config" "github.com/ethereum-optimism/optimism/op-supervisor/config"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/backend/depset"
"github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types" "github.com/ethereum-optimism/optimism/op-supervisor/supervisor/types"
) )
...@@ -46,6 +47,9 @@ func TestSupervisorService(t *testing.T) { ...@@ -46,6 +47,9 @@ func TestSupervisorService(t *testing.T) {
ListenPort: 0, // pick a port automatically ListenPort: 0, // pick a port automatically
EnableAdmin: true, EnableAdmin: true,
}, },
DependencySetSource: &depset.StaticConfigDependencySet{
Dependencies: make(map[types.ChainID]*depset.StaticConfigDependency),
},
MockRun: true, MockRun: true,
} }
logger := testlog.Logger(t, log.LevelError) logger := testlog.Logger(t, log.LevelError)
......
...@@ -168,6 +168,20 @@ func (id ChainID) ToUInt32() (uint32, error) { ...@@ -168,6 +168,20 @@ func (id ChainID) ToUInt32() (uint32, error) {
return uint32(v64), nil return uint32(v64), nil
} }
func (id ChainID) MarshalText() ([]byte, error) {
return []byte(id.String()), nil
}
func (id *ChainID) UnmarshalText(data []byte) error {
var x uint256.Int
err := x.UnmarshalText(data)
if err != nil {
return err
}
*id = ChainID(x)
return nil
}
type ReferenceView struct { type ReferenceView struct {
Local eth.BlockID `json:"local"` Local eth.BlockID `json:"local"`
Cross eth.BlockID `json:"cross"` Cross eth.BlockID `json:"cross"`
......
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