Skip to content

Commit

Permalink
Merge pull request #22 from multiversx/chain-simulator-custom-configs…
Browse files Browse the repository at this point in the history
…-remade

Chain simulator custom configs
  • Loading branch information
iulianpascalau authored Mar 27, 2024
2 parents 09fd222 + 66b9e75 commit b9c3cd8
Show file tree
Hide file tree
Showing 16 changed files with 364 additions and 40 deletions.
73 changes: 72 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,31 @@ This endpoint initiates the generation of a specified number of blocks for each
- **Status Codes:**
- `200 OK`: Blocks generated successfully.
- `400 Bad Request`: Invalid request parameters.
-

#### Response Body
```json
{
"data": {},
"error": "",
"code": "successful"
}
```

### `POST /simulator/generate-blocks-until-epoch-reached/:epoch`

This endpoint initiates the generation of blocks for each shard until the target epoch is reached.

##### Request
- **Method:** POST
- **Path:** `/simulator/generate-blocks-until-epoch-reached/:epoch`
- **Parameters:**
- `epoch` (path parameter): The target epoch to be reached.

##### Response
- **Status Codes:**
- `200 OK`: Blocks generated successfully, target epoch reached.
- `400 Bad Request`: Invalid request parameters.

#### Response Body
```json
{
Expand Down Expand Up @@ -211,6 +235,28 @@ Example:
}
```

### `POST /simulator/force-reset-validator-statistics`

This endpoint resets (clears) an internal cache used by the `/validator/statistics` API endpoint route.

##### Request
- **Method:** POST
- **Path:** `/simulator/force-reset-validator-statistics`

##### Response
- **Status Codes:**
- `200 OK`: Cache cleared successfully.
- `400 Bad Request`: Internal error while clearing the cache.

#### Response Body
```json
{
"data": {},
"error": "",
"code": "successful"
}
```


---

Expand Down Expand Up @@ -278,6 +324,31 @@ The **_[config.toml](./cmd/chainsimulator/config/config.toml)_** file:
block-time-in-milliseconds = 6000
```

There is also an optional configuration file called `nodeOverride.toml` that can be used to alter specific configuration options
for the nodes that assemble the chain simulator. The override mechanism is the same as the one found on the mx-chain-go, prefs.toml file.

The **_[nodeOverride.toml](./cmd/chainsimulator/config/config.toml)_** file:

```toml
# OverridableConfigTomlValues represents an array of items to be overloaded inside other configuration files, which can be helpful
# so that certain config values need to remain the same during upgrades.
# (for example, an Elasticsearch user wants external.toml->ElasticSearchConnector.Enabled to remain true all the time during upgrades, while the default
# configuration of the node has the false value)
# The Path indicates what value to change, while Value represents the new value in string format. The node operator must make sure
# to follow the same type of the original value (ex: uint32: "37", float32: "37.0", bool: "true")
# File represents the file name that holds the configuration. Currently, the supported files are:
# api.toml, config.toml, economics.toml, enableEpochs.toml, enableRounds.toml, external.toml, fullArchiveP2P.toml, p2p.toml, ratings.toml, systemSmartContractsConfig.toml
# -------------------------------
# Un-comment and update the following section in order to enable config values overloading
# -------------------------------
# OverridableConfigTomlValues = [
# { File = "config.toml", Path = "StoragePruning.NumEpochsToKeep", Value = "4" },
# { File = "config.toml", Path = "MiniBlocksStorage.Cache.Name", Value = "MiniBlocksStorage" },
# { File = "external.toml", Path = "ElasticSearchConnector.Enabled", Value = "true" }
#]
```


### Build docker image
```
DOCKER_BUILDKIT=1 docker build -t chainsimulator:latest .
Expand Down
16 changes: 16 additions & 0 deletions cmd/chainsimulator/config/nodeOverride.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# OverridableConfigTomlValues represents an array of items to be overloaded inside other configuration files, which can be helpful
# so that certain config values need to remain the same during upgrades.
# (for example, an Elasticsearch user wants external.toml->ElasticSearchConnector.Enabled to remain true all the time during upgrades, while the default
# configuration of the node has the false value)
# The Path indicates what value to change, while Value represents the new value in string format. The node operator must make sure
# to follow the same type of the original value (ex: uint32: "37", float32: "37.0", bool: "true")
# File represents the file name that holds the configuration. Currently, the supported files are:
# api.toml, config.toml, economics.toml, enableEpochs.toml, enableRounds.toml, external.toml, fullArchiveP2P.toml, p2p.toml, ratings.toml, systemSmartContractsConfig.toml
# -------------------------------
# Un-comment and update the following section in order to enable config values overloading
# -------------------------------
# OverridableConfigTomlValues = [
# { File = "config.toml", Path = "StoragePruning.NumEpochsToKeep", Value = "4" },
# { File = "config.toml", Path = "MiniBlocksStorage.Cache.Name", Value = "MiniBlocksStorage" },
# { File = "external.toml", Path = "ElasticSearchConnector.Enabled", Value = "true" }
#]
15 changes: 15 additions & 0 deletions cmd/chainsimulator/flags.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,11 @@ var (
Usage: "The main configuration file to load",
Value: "./config/config.toml",
}
nodeOverrideConfigurationFile = cli.StringFlag{
Name: "node-override-config",
Usage: "The node's override configuration file to load",
Value: "./config/nodeOverride.toml",
}
logLevel = cli.StringFlag{
Name: "log-level",
Usage: "This flag specifies the logger `level(s)`. It can contain multiple comma-separated value. For example" +
Expand Down Expand Up @@ -76,11 +81,21 @@ var (
Usage: "This flag is used to specify the number of validators per shard",
Value: 1,
}
numWaitingValidatorsPerShard = cli.IntFlag{
Name: "num-waiting-validators-per-shard",
Usage: "This flag is used to specify the number of waiting validators per shard",
Value: 0,
}
numValidatorsMeta = cli.IntFlag{
Name: "num-validators-meta",
Usage: "This flag is used to specify the number of validators on metachain",
Value: 1,
}
numWaitingValidatorsMeta = cli.IntFlag{
Name: "num-waiting-validators-meta",
Usage: "This flag is used to specify the number of waiting validators on metachain",
Value: 0,
}
initialRound = cli.Uint64Flag{
Name: "initial-round",
Usage: "This flag is used to specify the initial round when chain simulator will start",
Expand Down
62 changes: 49 additions & 13 deletions cmd/chainsimulator/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ import (
"github.com/multiversx/mx-chain-core-go/core"
"github.com/multiversx/mx-chain-core-go/core/check"
"github.com/multiversx/mx-chain-core-go/core/closing"
nodeConfig "github.com/multiversx/mx-chain-go/config"
"github.com/multiversx/mx-chain-go/config/overridableConfig"
"github.com/multiversx/mx-chain-go/node/chainSimulator"
"github.com/multiversx/mx-chain-go/node/chainSimulator/components/api"
logger "github.com/multiversx/mx-chain-logger-go"
Expand Down Expand Up @@ -52,6 +54,7 @@ func main() {
app.Usage = ""
app.Flags = []cli.Flag{
configurationFile,
nodeOverrideConfigurationFile,
logLevel,
logSaveFile,
disableAnsiColor,
Expand All @@ -64,7 +67,9 @@ func main() {
roundDurationInMs,
bypassTransactionsSignature,
numValidatorsPerShard,
numWaitingValidatorsPerShard,
numValidatorsMeta,
numWaitingValidatorsMeta,
initialRound,
initialNonce,
initialEpoch,
Expand Down Expand Up @@ -99,6 +104,11 @@ func startChainSimulator(ctx *cli.Context) error {
return fmt.Errorf("%w while loading the config file", err)
}

overrideCfg, err := loadOverrideConfig(ctx.GlobalString(nodeOverrideConfigurationFile.Name))
if err != nil {
return fmt.Errorf("%w while loading the node override config file", err)
}

applyFlags(ctx, &cfg)

fileLogging, err := initializeLogger(ctx, cfg)
Expand Down Expand Up @@ -136,10 +146,19 @@ func startChainSimulator(ctx *cli.Context) error {
if numValidatorsShard < 1 {
return errors.New("invalid value for the number of validators per shard")
}
numWaitingValidatorsShard := ctx.GlobalInt(numWaitingValidatorsPerShard.Name)
if numWaitingValidatorsShard < 0 {
return errors.New("invalid value for the number of waiting validators per shard")
}

numValidatorsMetaShard := ctx.GlobalInt(numValidatorsMeta.Name)
if numValidatorsMetaShard < 1 {
return errors.New("invalid value for the number of validators for metachain")
}
numWaitingValidatorsMetaShard := ctx.GlobalInt(numWaitingValidatorsMeta.Name)
if numWaitingValidatorsMetaShard < 0 {
return errors.New("invalid value for the number of waiting validators for metachain")
}

startTimeUnix := ctx.GlobalInt64(startTime.Name)
apiConfigurator := api.NewFreePortAPIConfigurator("localhost")
Expand All @@ -149,26 +168,36 @@ func startChainSimulator(ctx *cli.Context) error {
return err
}

var alterConfigsError error
argsChainSimulator := chainSimulator.ArgsChainSimulator{
BypassTxSignatureCheck: bypassTxsSignature,
TempDir: tempDir,
PathToInitialConfig: nodeConfigs,
NumOfShards: uint32(cfg.Config.Simulator.NumOfShards),
GenesisTimestamp: startTimeUnix,
RoundDurationInMillis: roundDurationInMillis,
RoundsPerEpoch: rounds,
ApiInterface: apiConfigurator,
MinNodesPerShard: uint32(numValidatorsShard),
MetaChainMinNodes: uint32(numValidatorsMetaShard),
InitialRound: cfg.Config.Simulator.InitialRound,
InitialNonce: cfg.Config.Simulator.InitialNonce,
InitialEpoch: cfg.Config.Simulator.InitialEpoch,
BypassTxSignatureCheck: bypassTxsSignature,
TempDir: tempDir,
PathToInitialConfig: nodeConfigs,
NumOfShards: uint32(cfg.Config.Simulator.NumOfShards),
GenesisTimestamp: startTimeUnix,
RoundDurationInMillis: roundDurationInMillis,
RoundsPerEpoch: rounds,
ApiInterface: apiConfigurator,
MinNodesPerShard: uint32(numValidatorsShard),
NumNodesWaitingListShard: uint32(numWaitingValidatorsShard),
MetaChainMinNodes: uint32(numValidatorsMetaShard),
NumNodesWaitingListMeta: uint32(numWaitingValidatorsMetaShard),
InitialRound: cfg.Config.Simulator.InitialRound,
InitialNonce: cfg.Config.Simulator.InitialNonce,
InitialEpoch: cfg.Config.Simulator.InitialEpoch,
AlterConfigsFunction: func(cfg *nodeConfig.Configs) {
alterConfigsError = overridableConfig.OverrideConfigValues(overrideCfg.OverridableConfigTomlValues, cfg)
},
}
simulator, err := chainSimulator.NewChainSimulator(argsChainSimulator)
if err != nil {
return err
}

if alterConfigsError != nil {
return alterConfigsError
}

log.Info("simulators were initialized")

err = simulator.GenerateBlocks(1)
Expand Down Expand Up @@ -293,6 +322,13 @@ func loadMainConfig(filepath string) (config.Config, error) {
return cfg, err
}

func loadOverrideConfig(filepath string) (config.OverrideConfigs, error) {
cfg := config.OverrideConfigs{}
err := core.LoadTomlFile(&cfg, filepath)

return cfg, err
}

func removeANSIColorsForLoggerIfNeeded(disableAnsi bool) error {
if !disableAnsi {
return nil
Expand Down
7 changes: 7 additions & 0 deletions config/config.go
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package config

import "github.com/multiversx/mx-chain-go/config"

// Config will hold the whole config file's data
type Config struct {
Config struct {
Expand Down Expand Up @@ -29,3 +31,8 @@ type BlocksGeneratorConfig struct {
AutoGenerateBlocks bool `toml:"auto-generate-blocks"`
BlockTimeInMs uint64 `toml:"block-time-in-milliseconds"`
}

// OverrideConfigs defines the struct used for the overridable configs
type OverrideConfigs struct {
OverridableConfigTomlValues []config.OverridableConfig
}
42 changes: 42 additions & 0 deletions config/tomlConfig_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
package config

import (
"testing"

"github.com/multiversx/mx-chain-go/config"
"github.com/pelletier/go-toml"
"github.com/stretchr/testify/assert"
)

func TestLoadNodeOverrideConfigs(t *testing.T) {
t.Parallel()

testString := `
# Test comment
OverridableConfigTomlValues = [
{ File = "config.toml", Path = "A", Value = "B" },
{ File = "external.toml", Path = "C", Value = "D" }
]
`

expectedConfig := OverrideConfigs{
OverridableConfigTomlValues: []config.OverridableConfig{
{
File: "config.toml",
Path: "A",
Value: "B",
},
{
File: "external.toml",
Path: "C",
Value: "D",
},
},
}

cfg := OverrideConfigs{}

err := toml.Unmarshal([]byte(testString), &cfg)
assert.Nil(t, err)
assert.Equal(t, expectedConfig, cfg)
}
27 changes: 27 additions & 0 deletions examples/generateBlocks/epoch-reached.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import sys

from multiversx_sdk_network_providers import ProxyNetworkProvider

SIMULATOR_URL = "http://localhost:8085"
GENERATE_BLOCKS_UNTIL_EPOCH_REACHED_URL = f"{SIMULATOR_URL}/simulator/generate-blocks-until-epoch-reached"
NETWORK_STATUS_URL = f"{SIMULATOR_URL}/network/status/4294967295"


def main():
# create a network provider
provider = ProxyNetworkProvider(SIMULATOR_URL)

targetEpoch = 10
# generate blocks until we reach the target epoch
provider.do_post(f"{GENERATE_BLOCKS_UNTIL_EPOCH_REACHED_URL}/{targetEpoch}", {})

network_status = provider.get_network_status() # will default to metachain

if network_status.epoch_number < targetEpoch:
sys.exit(f"epoch {targetEpoch} not reached")

print(f"successfully created blocks and epoch {targetEpoch} was reached")


if __name__ == "__main__":
main()
12 changes: 6 additions & 6 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,10 @@ go 1.20
require (
github.com/gin-gonic/gin v1.9.1
github.com/multiversx/mx-chain-core-go v1.2.19-0.20240222081523-011c96ab2548
github.com/multiversx/mx-chain-go v1.7.6
github.com/multiversx/mx-chain-go v1.7.7-0.20240322123517-e7dac66bf179
github.com/multiversx/mx-chain-logger-go v1.0.14-0.20240129144507-d00e967c890c
github.com/multiversx/mx-chain-proxy-go v1.1.44-0.20240212150040-5f7a82b10b0e
github.com/pelletier/go-toml v1.9.3
github.com/stretchr/testify v1.8.4
github.com/urfave/cli v1.22.10
)
Expand Down Expand Up @@ -121,17 +122,16 @@ require (
github.com/multiversx/mx-chain-scenario-go v1.4.3-0.20240212160120-cc32d1580157 // indirect
github.com/multiversx/mx-chain-storage-go v1.0.15-0.20240129144933-b1c0d642d7f8 // indirect
github.com/multiversx/mx-chain-vm-common-go v1.5.12-0.20240305123516-2231c71162a2 // indirect
github.com/multiversx/mx-chain-vm-go v1.5.28-0.20240216171908-e2a4c8ed9823 // indirect
github.com/multiversx/mx-chain-vm-v1_2-go v1.2.66-0.20240129145751-f814f5525edb // indirect
github.com/multiversx/mx-chain-vm-v1_3-go v1.3.67-0.20240129150004-536a22d9c618 // indirect
github.com/multiversx/mx-chain-vm-v1_4-go v1.4.96-0.20240216071525-f7d1b8ce8662 // indirect
github.com/multiversx/mx-chain-vm-go v1.5.28-0.20240307121727-b8d371971d9a // indirect
github.com/multiversx/mx-chain-vm-v1_2-go v1.2.66-0.20240308085208-3b5a4ab4dd34 // indirect
github.com/multiversx/mx-chain-vm-v1_3-go v1.3.67-0.20240308082903-132f9002736b // indirect
github.com/multiversx/mx-chain-vm-v1_4-go v1.4.96-0.20240308082831-f05004a05b35 // indirect
github.com/multiversx/mx-components-big-int v1.0.0 // indirect
github.com/onsi/ginkgo/v2 v2.11.0 // indirect
github.com/onsi/gomega v1.27.10 // indirect
github.com/opencontainers/runtime-spec v1.0.2 // indirect
github.com/opentracing/opentracing-go v1.2.0 // indirect
github.com/pbnjay/memory v0.0.0-20210728143218-7b4eea64cf58 // indirect
github.com/pelletier/go-toml v1.9.3 // indirect
github.com/pelletier/go-toml/v2 v2.0.8 // indirect
github.com/pkg/errors v0.9.1 // indirect
github.com/pmezard/go-difflib v1.0.0 // indirect
Expand Down
Loading

0 comments on commit b9c3cd8

Please sign in to comment.