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
6 changes: 3 additions & 3 deletions runtime/v2/module.go
Original file line number Diff line number Diff line change
Expand Up @@ -241,9 +241,9 @@ func DefaultServiceBindings() depinject.Config {
stf.NewKVStoreService(actor),
)
}
headerService header.Service = services.NewGenesisHeaderService(stf.HeaderService{})
cometService comet.Service = &services.ContextAwareCometInfoService{}
eventService = stf.NewEventService()
cometService comet.Service = &services.ContextAwareCometInfoService{}
headerService = services.NewGenesisHeaderService(stf.HeaderService{})
eventService = services.NewGenesisEventService(stf.NewEventService())
)
return depinject.Supply(
kvServiceFactory,
Expand Down
55 changes: 48 additions & 7 deletions runtime/v2/services/genesis.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,13 @@ package services

import (
"context"
"errors"
"fmt"

"cosmossdk.io/core/event"
"cosmossdk.io/core/header"
"cosmossdk.io/core/store"
"cosmossdk.io/core/transaction"
)

var (
Expand Down Expand Up @@ -105,6 +108,18 @@ func (g *GenesisKVStoreService) OpenKVStore(ctx context.Context) store.KVStore {
return readonlyKVStore{state}
}

type readonlyKVStore struct {
store.Reader
}
Comment on lines +111 to +113
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🛠️ Refactor suggestion

Consider using an explicit field instead of embedding the interface

Embedding the store.Reader interface directly in the readonlyKVStore struct can lead to unintended method implementations. It's generally better to use an explicit field for better control and clarity.

Consider modifying the struct as follows:

type readonlyKVStore struct {
    reader store.Reader
}

This change would require updating the methods to use r.reader instead of directly calling the methods.


func (r readonlyKVStore) Set(key, value []byte) error {
return errors.New("tried to call Set on a readonly store")
}

func (r readonlyKVStore) Delete(key []byte) error {
return errors.New("tried to call Delete on a readonly store")
}

// GenesisHeaderService is a header.Service implementation that is used during
// genesis initialization. It wraps an inner execution context header.Service.
type GenesisHeaderService struct {
Expand All @@ -123,20 +138,46 @@ func (g *GenesisHeaderService) HeaderInfo(ctx context.Context) header.Info {

// NewGenesisHeaderService creates a new GenesisHeaderService.
// - executionService is the header.Service to use when the genesis context is not active.
func NewGenesisHeaderService(executionService header.Service) *GenesisHeaderService {
func NewGenesisHeaderService(executionService header.Service) header.Service {
return &GenesisHeaderService{
executionService: executionService,
}
}

type readonlyKVStore struct {
store.Reader
// GenesisEventService is an event.Service implementation that is used during
// genesis initialization. It wraps an inner execution context event.Service.
// During genesis initialization, it returns a blackHoleEventManager into which
// events enter and disappear completely.
type GenesisEventService struct {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

go doc on why it exists please

executionService event.Service
}

func (r readonlyKVStore) Set(key, value []byte) error {
panic("tried to call Set on a readonly store")
// NewGenesisEventService creates a new GenesisEventService.
// - executionService is the event.Service to use when the genesis context is not active.
func NewGenesisEventService(executionService event.Service) event.Service {
return &GenesisEventService{
executionService: executionService,
}
}

func (r readonlyKVStore) Delete(key []byte) error {
panic("tried to call Delete on a readonly store")
func (g *GenesisEventService) EventManager(ctx context.Context) event.Manager {
v := ctx.Value(genesisContextKey)
if v == nil {
return g.executionService.EventManager(ctx)
}
return &blackHoleEventManager{}
}

var _ event.Manager = (*blackHoleEventManager)(nil)

// blackHoleEventManager is an event.Manager that does nothing.
// It is used during genesis initialization, genesis events are not emitted.
type blackHoleEventManager struct{}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

great name haha.


func (b *blackHoleEventManager) Emit(_ transaction.Msg) error {
return nil
}

func (b *blackHoleEventManager) EmitKV(_ string, _ ...event.Attribute) error {
return nil
}