Skip to content

Commit

Permalink
refactor: testnode utilities (#3785)
Browse files Browse the repository at this point in the history
## Motivation

I was looking through testnode code while working on a separate PR and
these minor renames + moves made the code a little easier to read and
understand.
  • Loading branch information
rootulp authored Aug 21, 2024
1 parent 5a06415 commit 0113f49
Show file tree
Hide file tree
Showing 10 changed files with 179 additions and 169 deletions.
28 changes: 14 additions & 14 deletions test/util/genesis/files.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,50 +11,50 @@ import (
"github.com/tendermint/tendermint/privval"
)

// InitFiles initializes the files for a new tendermint node with the provided
// InitFiles initializes the files for a new Comet node with the provided
// genesis. It will use the validatorIndex to save the validator's consensus
// key.
func InitFiles(
dir string,
tmCfg *config.Config,
g *Genesis,
rootDir string,
tmConfig *config.Config,
genesis *Genesis,
validatorIndex int,
) (string, error) {
val, has := g.Validator(validatorIndex)
) (basePath string, err error) {
val, has := genesis.Validator(validatorIndex)
if !has {
return "", fmt.Errorf("validator %d not found", validatorIndex)
}

basePath := filepath.Join(dir, ".celestia-app")
tmCfg.SetRoot(basePath)
basePath = filepath.Join(rootDir, ".celestia-app")
tmConfig.SetRoot(basePath)

// save the genesis file
configPath := filepath.Join(basePath, "config")
err := os.MkdirAll(configPath, os.ModePerm)
err = os.MkdirAll(configPath, os.ModePerm)
if err != nil {
return "", err
}
gDoc, err := g.Export()
genesisDoc, err := genesis.Export()
if err != nil {
return "", fmt.Errorf("exporting genesis: %w", err)
}
err = gDoc.SaveAs(tmCfg.GenesisFile())
err = genesisDoc.SaveAs(tmConfig.GenesisFile())
if err != nil {
return "", err
}

pvStateFile := tmCfg.PrivValidatorStateFile()
pvStateFile := tmConfig.PrivValidatorStateFile()
if err := tmos.EnsureDir(filepath.Dir(pvStateFile), 0o777); err != nil {
return "", err
}
pvKeyFile := tmCfg.PrivValidatorKeyFile()
pvKeyFile := tmConfig.PrivValidatorKeyFile()
if err := tmos.EnsureDir(filepath.Dir(pvKeyFile), 0o777); err != nil {
return "", err
}
filePV := privval.NewFilePV(val.ConsensusKey, pvKeyFile, pvStateFile)
filePV.Save()

nodeKeyFile := tmCfg.NodeKeyFile()
nodeKeyFile := tmConfig.NodeKeyFile()
if err := tmos.EnsureDir(filepath.Dir(nodeKeyFile), 0o777); err != nil {
return "", err
}
Expand Down
47 changes: 47 additions & 0 deletions test/util/testnode/comet_node.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
package testnode

import (
"path/filepath"

"github.com/cosmos/cosmos-sdk/client/flags"
servertypes "github.com/cosmos/cosmos-sdk/server/types"
"github.com/tendermint/tendermint/node"
"github.com/tendermint/tendermint/p2p"
"github.com/tendermint/tendermint/privval"
"github.com/tendermint/tendermint/proxy"
tmdb "github.com/tendermint/tm-db"
)

// NewCometNode creates a ready to use comet node that operates a single
// validator celestia-app network. It expects that all configuration files are
// already initialized and saved to the baseDir.
func NewCometNode(baseDir string, config *UniversalTestingConfig) (*node.Node, servertypes.Application, error) {
logger := NewLogger(config)
dbPath := filepath.Join(config.TmConfig.RootDir, "data")
db, err := tmdb.NewGoLevelDB("application", dbPath)
if err != nil {
return nil, nil, err
}

config.AppOptions.Set(flags.FlagHome, baseDir)

app := config.AppCreator(logger, db, nil, config.AppOptions)

nodeKey, err := p2p.LoadOrGenNodeKey(config.TmConfig.NodeKeyFile())
if err != nil {
return nil, nil, err
}

cometNode, err := node.NewNode(
config.TmConfig,
privval.LoadOrGenFilePV(config.TmConfig.PrivValidatorKeyFile(), config.TmConfig.PrivValidatorStateFile()),
nodeKey,
proxy.NewLocalClientCreator(app),
node.DefaultGenesisDocProviderFunc(config.TmConfig),
node.DefaultDBProvider,
node.DefaultMetricsProvider(config.TmConfig.Instrumentation),
logger,
)

return cometNode, app, err
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import (
"github.com/celestiaorg/celestia-app/v3/pkg/appconsts"
"github.com/celestiaorg/celestia-app/v3/test/util/genesis"
blobtypes "github.com/celestiaorg/celestia-app/v3/x/blob/types"
appns "github.com/celestiaorg/go-square/v2/share"
"github.com/celestiaorg/go-square/v2/share"
"github.com/cosmos/cosmos-sdk/client/flags"
"github.com/stretchr/testify/require"
"github.com/stretchr/testify/suite"
Expand Down Expand Up @@ -72,7 +72,7 @@ func (s *IntegrationTestSuite) Test_verifyTimeIotaMs() {

func (s *IntegrationTestSuite) TestPostData() {
require := s.Require()
_, err := s.cctx.PostData(s.accounts[0], flags.BroadcastBlock, appns.RandomBlobNamespace(), tmrand.Bytes(kibibyte))
_, err := s.cctx.PostData(s.accounts[0], flags.BroadcastBlock, share.RandomBlobNamespace(), tmrand.Bytes(kibibyte))
require.NoError(err)
}

Expand Down
9 changes: 9 additions & 0 deletions test/util/testnode/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -202,3 +202,12 @@ func CustomAppCreator(minGasPrice string) srvtypes.AppCreator {
)
}
}

// DefaultAppConfig wraps the default config described in the server
func DefaultAppConfig() *srvconfig.Config {
appCfg := srvconfig.DefaultConfig()
appCfg.GRPC.Address = fmt.Sprintf("127.0.0.1:%d", mustGetFreePort())
appCfg.API.Address = fmt.Sprintf("tcp://127.0.0.1:%d", mustGetFreePort())
appCfg.MinGasPrices = fmt.Sprintf("%v%s", appconsts.DefaultMinGasPrice, appconsts.BondDenom)
return appCfg
}
58 changes: 0 additions & 58 deletions test/util/testnode/full_node.go

This file was deleted.

24 changes: 24 additions & 0 deletions test/util/testnode/logger.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package testnode

import (
"os"

"github.com/tendermint/tendermint/libs/log"
)

func NewLogger(config *UniversalTestingConfig) log.Logger {
if config.SuppressLogs {
return log.NewNopLogger()
}
logger := log.NewTMLogger(log.NewSyncWriter(os.Stdout))
switch config.TmConfig.LogLevel {
case "error":
return log.NewFilter(logger, log.AllowError())
case "info":
return log.NewFilter(logger, log.AllowInfo())
case "debug":
return log.NewFilter(logger, log.AllowDebug())
default:
return logger
}
}
40 changes: 7 additions & 33 deletions test/util/testnode/network.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ package testnode

import (
"context"
"net"
"testing"

"github.com/celestiaorg/celestia-app/v3/test/util/genesis"
Expand All @@ -16,30 +15,30 @@ import (
// accessed via the returned client.Context or via the returned rpc and grpc
// addresses. Configured genesis options will be applied after all accounts have
// been initialized.
func NewNetwork(t testing.TB, cfg *Config) (cctx Context, rpcAddr, grpcAddr string) {
func NewNetwork(t testing.TB, config *Config) (cctx Context, rpcAddr, grpcAddr string) {
t.Helper()

// initialize the genesis file and validator files for the first validator.
baseDir, err := genesis.InitFiles(t.TempDir(), cfg.TmConfig, cfg.Genesis, 0)
baseDir, err := genesis.InitFiles(t.TempDir(), config.TmConfig, config.Genesis, 0)
require.NoError(t, err)

tmNode, app, err := NewCometNode(baseDir, &cfg.UniversalTestingConfig)
tmNode, app, err := NewCometNode(baseDir, &config.UniversalTestingConfig)
require.NoError(t, err)

ctx, cancel := context.WithCancel(context.Background())
t.Cleanup(func() {
cancel()
})

cctx = NewContext(ctx, cfg.Genesis.Keyring(), cfg.TmConfig, cfg.Genesis.ChainID, cfg.AppConfig.API.Address)
cctx = NewContext(ctx, config.Genesis.Keyring(), config.TmConfig, config.Genesis.ChainID, config.AppConfig.API.Address)

cctx, stopNode, err := StartNode(tmNode, cctx)
require.NoError(t, err)

cctx, cleanupGRPC, err := StartGRPCServer(app, cfg.AppConfig, cctx)
cctx, cleanupGRPC, err := StartGRPCServer(app, config.AppConfig, cctx)
require.NoError(t, err)

apiServer, err := StartAPIServer(app, *cfg.AppConfig, cctx)
apiServer, err := StartAPIServer(app, *config.AppConfig, cctx)
require.NoError(t, err)

t.Cleanup(func() {
Expand All @@ -64,30 +63,5 @@ func NewNetwork(t testing.TB, cfg *Config) (cctx Context, rpcAddr, grpcAddr stri
}
})

return cctx, cfg.TmConfig.RPC.ListenAddress, cfg.AppConfig.GRPC.Address
}

// getFreePort returns a free port and optionally an error.
func getFreePort() (int, error) {
a, err := net.ResolveTCPAddr("tcp", "localhost:0")
if err != nil {
return 0, err
}

l, err := net.ListenTCP("tcp", a)
if err != nil {
return 0, err
}
defer l.Close()
return l.Addr().(*net.TCPAddr).Port, nil
}

// mustGetFreePort returns a free port. Panics if no free ports are available or
// an error is encountered.
func mustGetFreePort() int {
port, err := getFreePort()
if err != nil {
panic(err)
}
return port
return cctx, config.TmConfig.RPC.ListenAddress, config.AppConfig.GRPC.Address
}
34 changes: 17 additions & 17 deletions test/util/testnode/node_interaction_api.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,28 +30,28 @@ const (
)

type Context struct {
rootCtx context.Context
goContext context.Context
client.Context
apiAddress string
}

func NewContext(goCtx context.Context, kr keyring.Keyring, tmCfg *tmconfig.Config, chainID, apiAddress string) Context {
ecfg := encoding.MakeConfig(app.ModuleEncodingRegisters...)
cctx := client.Context{}.
WithKeyring(kr).
WithHomeDir(tmCfg.RootDir).
func NewContext(goContext context.Context, keyring keyring.Keyring, tmConfig *tmconfig.Config, chainID, apiAddress string) Context {
config := encoding.MakeConfig(app.ModuleEncodingRegisters...)
clientContext := client.Context{}.
WithKeyring(keyring).
WithHomeDir(tmConfig.RootDir).
WithChainID(chainID).
WithInterfaceRegistry(ecfg.InterfaceRegistry).
WithCodec(ecfg.Codec).
WithLegacyAmino(ecfg.Amino).
WithTxConfig(ecfg.TxConfig).
WithInterfaceRegistry(config.InterfaceRegistry).
WithCodec(config.Codec).
WithLegacyAmino(config.Amino).
WithTxConfig(config.TxConfig).
WithAccountRetriever(authtypes.AccountRetriever{})

return Context{rootCtx: goCtx, Context: cctx, apiAddress: apiAddress}
return Context{goContext: goContext, Context: clientContext, apiAddress: apiAddress}
}

func (c *Context) GoContext() context.Context {
return c.rootCtx
return c.goContext
}

// GenesisTime returns the genesis block time.
Expand Down Expand Up @@ -92,7 +92,7 @@ func (c *Context) WaitForHeightWithTimeout(h int64, t time.Duration) (int64, err
ticker := time.NewTicker(time.Second)
defer ticker.Stop()

ctx, cancel := context.WithTimeout(c.rootCtx, t)
ctx, cancel := context.WithTimeout(c.goContext, t)
defer cancel()

var (
Expand All @@ -102,8 +102,8 @@ func (c *Context) WaitForHeightWithTimeout(h int64, t time.Duration) (int64, err
for {
select {
case <-ctx.Done():
if c.rootCtx.Err() != nil {
return latestHeight, c.rootCtx.Err()
if c.goContext.Err() != nil {
return latestHeight, c.goContext.Err()
}
return latestHeight, fmt.Errorf("timeout (%v) exceeded waiting for network to reach height %d. Got to height %d", t, h, latestHeight)
case <-ticker.C:
Expand All @@ -123,7 +123,7 @@ func (c *Context) WaitForTimestampWithTimeout(t time.Time, d time.Duration) (tim
ticker := time.NewTicker(time.Second)
defer ticker.Stop()

ctx, cancel := context.WithTimeout(c.rootCtx, d)
ctx, cancel := context.WithTimeout(c.goContext, d)
defer cancel()

var latestTimestamp time.Time
Expand Down Expand Up @@ -193,7 +193,7 @@ func (c *Context) WaitForTx(hashHexStr string, blocks int) (*rpctypes.ResultTx,
return nil, err
}

ctx, cancel := context.WithTimeout(c.rootCtx, DefaultTimeout)
ctx, cancel := context.WithTimeout(c.goContext, DefaultTimeout)
defer cancel()

for {
Expand Down
Loading

0 comments on commit 0113f49

Please sign in to comment.