Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions cli/smartcontract/permission.go
Original file line number Diff line number Diff line change
Expand Up @@ -51,9 +51,9 @@ func (p permission) MarshalYAML() (any, error) {
return m, nil
}

func (p *permission) UnmarshalYAML(unmarshal func(any) error) error {
func (p *permission) UnmarshalYAML(node *yaml.Node) error {
var m map[string]any
if err := unmarshal(&m); err != nil {
if err := node.Decode(&m); err != nil {
return err
}

Expand Down
4 changes: 2 additions & 2 deletions docs/node-configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -33,13 +33,13 @@ node-related settings described in the table below.
| Prometheus | [Metrics Services Configuration](#Metrics-Services-Configuration) | | Configuration for Prometheus (monitoring system). See the [Metrics Services Configuration](#Metrics-Services-Configuration) section for details |
| Relay | `bool` | `true` | Determines whether the server is forwarding its inventory. |
| Consensus | [Consensus Configuration](#Consensus-Configuration) | | Describes consensus (dBFT) configuration. See the [Consensus Configuration](#Consensus-Configuration) for details. |
| RemoveUntraceableBlocks | `bool`| `false` | Denotes whether old blocks should be removed from cache and database. If enabled, then only the last `MaxTraceableBlocks` are stored and accessible to smart contracts. Old MPT data is also deleted in accordance with `GarbageCollectionPeriod` setting. If enabled along with `P2PStateExchangeExtensions` protocol extension, then old blocks and MPT states will be removed up to the second latest state synchronisation point (see `StateSyncInterval`). |
| RemoveUntraceableHeaders | `bool`| `false` | Used only with RemoveUntraceableBlocks and makes node delete untraceable block headers as well. Notice that this is an experimental option, not recommended for production use. |
| RemoveUntraceableBlocks | `bool`| `false` | Denotes whether old blocks, headers, transactions, execution results and transfer logs should be removed from cache and database. If enabled, then only the last `MaxTraceableBlocks` are stored and accessible to smart contracts. Old MPT data is also deleted in accordance with `GarbageCollectionPeriod` setting. If enabled along with `P2PStateExchangeExtensions` protocol extension, then old blocks and MPT states will be removed up to the second latest state synchronisation point (see `StateSyncInterval`). |
| RPC | [RPC Configuration](#RPC-Configuration) | | Describes [RPC subsystem](rpc.md) configuration. See the [RPC Configuration](#RPC-Configuration) for details. |
| SaveStorageBatch | `bool` | `false` | Enables storage batch saving before every persist. It is similar to StorageDump plugin for C# node. |
| SkipBlockVerification | `bool` | `false` | Allows to disable verification of received/processed blocks (including cryptographic checks). |
| StateRoot | [State Root Configuration](#State-Root-Configuration) | | State root module configuration. See the [State Root Configuration](#State-Root-Configuration) section for details. |
| SaveInvocations | `bool` | `false` | Determines if additional smart contract invocation details are stored. If enabled, the `getapplicationlog` RPC method will return a new field with invocation details for the transaction. See the [RPC](rpc.md#applicationlog-invocations) documentation for more information. |
| TrustedHeader | `map[uint32]Hash256` | `nil` | Determines header (height and hash in the LE form) to start light node synchronization from. Headers below trusted height won't be fetched and processed at all. Requires `RemoveUntraceableBlocks` to be enabled along with one of `P2PStateExchangeExtensions` or `NeoFSStateSyncExtensions`. |

### P2P Configuration

Expand Down
3 changes: 3 additions & 0 deletions pkg/config/application_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -166,5 +166,8 @@ func (a *ApplicationConfiguration) Validate() error {
if err := a.Logger.Validate(); err != nil {
return fmt.Errorf("invalid logger config: %w", err)
}
if err := a.Ledger.Validate(); err != nil {
return fmt.Errorf("invalid ledger config: %w", err)
}
return nil
}
16 changes: 14 additions & 2 deletions pkg/config/application_config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"testing"
"time"

"github.com/nspcc-dev/neo-go/pkg/util"
"github.com/stretchr/testify/require"
)

Expand Down Expand Up @@ -233,13 +234,24 @@ func TestApplicationConfiguration_Validate(t *testing.T) {
shouldFail: true,
errMsg: "invalid logger config: invalid LogEncoding: unknown",
},
{
cfg: ApplicationConfiguration{
Ledger: Ledger{
TrustedHeader: HashIndex{
Hash: util.Uint256{1, 2, 3},
Index: 4,
},
},
},
shouldFail: true,
errMsg: "TrustedHeader is set, but RemoveUntraceableBlocks is disabled",
},
}

for _, c := range cases {
err := c.cfg.Validate()
if c.shouldFail {
require.Error(t, err)
require.Contains(t, err.Error(), c.errMsg)
require.ErrorContains(t, err, c.errMsg)
} else {
require.NoError(t, err)
}
Expand Down
5 changes: 3 additions & 2 deletions pkg/config/genesis_extensions.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (

"github.com/nspcc-dev/neo-go/pkg/core/native/noderoles"
"github.com/nspcc-dev/neo-go/pkg/crypto/keys"
"gopkg.in/yaml.v3"
)

// Genesis represents a set of genesis block settings including the extensions
Expand Down Expand Up @@ -85,9 +86,9 @@ func (e Genesis) MarshalYAML() (any, error) {
}

// UnmarshalYAML implements the YAML unmarshaler interface.
func (e *Genesis) UnmarshalYAML(unmarshal func(any) error) error {
func (e *Genesis) UnmarshalYAML(node *yaml.Node) error {
var aux genesisAux
if err := unmarshal(&aux); err != nil {
if err := node.Decode(&aux); err != nil {
return err
}

Expand Down
68 changes: 64 additions & 4 deletions pkg/config/ledger_config.go
Original file line number Diff line number Diff line change
@@ -1,5 +1,13 @@
package config

import (
"errors"
"fmt"

"github.com/nspcc-dev/neo-go/pkg/util"
"gopkg.in/yaml.v3"
)

// Ledger contains core node-specific settings that are not
// a part of the ProtocolConfiguration (which is common for every node on the
// network).
Expand All @@ -12,18 +20,28 @@
// If true, DB size will be smaller, but older roots won't be accessible.
// This value should remain the same for the same database.
KeepOnlyLatestState bool `yaml:"KeepOnlyLatestState"`
// RemoveUntraceableBlocks specifies if old data should be removed.
// RemoveUntraceableBlocks specifies if old data (blocks, headers,
// transactions, execution results, transfer logs and MPT data) should be
// removed.
RemoveUntraceableBlocks bool `yaml:"RemoveUntraceableBlocks"`
// RemoveUntraceableHeaders is used in addition to RemoveUntraceableBlocks
// when headers need to be removed as well.
RemoveUntraceableHeaders bool `yaml:"RemoveUntraceableHeaders"`
// SaveStorageBatch enables storage batch saving before every persist.
SaveStorageBatch bool `yaml:"SaveStorageBatch"`
// SkipBlockVerification allows to disable verification of received
// blocks (including cryptographic checks).
SkipBlockVerification bool `yaml:"SkipBlockVerification"`
// SaveInvocations enables smart contract invocation data saving.
SaveInvocations bool `yaml:"SaveInvocations"`
// TrustedHeader is an index/hash of header that can be used to start
// light node headers synchronisation from (without additional verification).
// It's valid iff RemoveUntraceableBlocks is enabled along with one of
// P2PStateExchangeExtensions or NeoFSStateSyncExtensions.
TrustedHeader HashIndex `yaml:"TrustedHeader"`
}

// HashIndex is a structure representing hash and index of block/header.
type HashIndex struct {
Hash util.Uint256
Index uint32
}

// Blockchain is a set of settings for core.Blockchain to use, it includes protocol
Expand All @@ -34,3 +52,45 @@
NeoFSBlockFetcher
NeoFSStateFetcher
}

// Validate checks Ledger for internal consistency and returns an error if any
// invalid settings are found.
func (l Ledger) Validate() error {
if l.TrustedHeader.Index != 0 && !l.RemoveUntraceableBlocks {
return errors.New("TrustedHeader is set, but RemoveUntraceableBlocks is disabled")
}
return nil
}

// MarshalYAML implements the YAML marshaller interface.
func (h HashIndex) MarshalYAML() (any, error) {
var startSyncFrom = make(map[uint32]util.Uint256)
if h.Index != 0 {
startSyncFrom[h.Index] = h.Hash
}
return startSyncFrom, nil
}

// UnmarshalYAML implements the YAML Unmarshaler interface.
func (h *HashIndex) UnmarshalYAML(node *yaml.Node) error {
var aux map[uint32]util.Uint256

err := node.Decode(&aux)
if err != nil {
return err
}

Check warning on line 81 in pkg/config/ledger_config.go

View check run for this annotation

Codecov / codecov/patch

pkg/config/ledger_config.go#L80-L81

Added lines #L80 - L81 were not covered by tests
if len(aux) > 1 {
return fmt.Errorf("only one trusted height is supported, got %d entries", len(aux))
}

if len(aux) > 0 {
for i, hh := range aux {
*h = HashIndex{
Hash: hh,
Index: i,
}
}
}

return nil
}
27 changes: 27 additions & 0 deletions pkg/config/ledger_config_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package config

import (
"testing"

"github.com/nspcc-dev/neo-go/internal/testserdes"
"github.com/nspcc-dev/neo-go/pkg/util"
"github.com/stretchr/testify/require"
"gopkg.in/yaml.v3"
)

func TestHashIndex_MarshalUnmarshalYAML(t *testing.T) {
t.Run("good", func(t *testing.T) {
testserdes.MarshalUnmarshalYAML(t, &HashIndex{
Hash: util.Uint256{1, 2, 3},
Index: 1,
}, new(HashIndex))
})
t.Run("empty", func(t *testing.T) {
testserdes.MarshalUnmarshalYAML(t, &HashIndex{}, new(HashIndex))
})
t.Run("multiple heights", func(t *testing.T) {
require.ErrorContains(t, yaml.Unmarshal([]byte(`
1: `+util.Uint256{1, 2, 3}.String()+`
2: `+util.Uint256{1, 2, 3}.String()), new(HashIndex)), "only one trusted height is supported")
})
}
Loading
Loading