Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor events #586

Merged
merged 5 commits into from
Aug 11, 2021
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
11 changes: 11 additions & 0 deletions EVENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -402,6 +402,17 @@ If the original contract execution example above was actually the result of a me
and it registered a ReplyOn clause, the `reply` function on that contract would receive the entire 11 events in the example
above, and would need to use the `message` markers to locate the segment of interest.

## Governance Events
alpe marked this conversation as resolved.
Show resolved Hide resolved
The governance process is handled by the cosmos-sdk `gov` module. We do not emit any events of type "message" anymore in v0.18+.
Context-specific events are emitted as described above. `Execution` and `Migration` return some contract result though that are
emitted as:
```go
sdk.NewEvent(
"gov_contract_result",
sdk.NewAttribute("result", hex.EncodeToString(data)),
)
```

## IBC Events

TODO: define what the default SDK messages are here and what we add to our custom keeper events.
14 changes: 0 additions & 14 deletions x/wasm/keeper/events.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,20 +21,6 @@ func newWasmModuleEvent(customAttributes []wasmvmtypes.EventAttribute, contractA
return sdk.Events{sdk.NewEvent(types.WasmModuleEventType, attrs...)}, nil
}

// returns true when a wasm module event was emitted for this contract already
func hasWasmModuleEvent(ctx sdk.Context, contractAddr sdk.AccAddress) bool {
for _, e := range ctx.EventManager().Events() {
if e.Type == types.WasmModuleEventType {
for _, a := range e.Attributes {
if string(a.Key) == types.AttributeKeyContractAddr && string(a.Value) == contractAddr.String() {
return true
}
}
}
}
return false
}

const eventTypeMinLength = 2

// newCustomEvents converts wasmvm events from a contract response to sdk type events
Expand Down
14 changes: 14 additions & 0 deletions x/wasm/keeper/events_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -251,3 +251,17 @@ func TestNewWasmModuleEvent(t *testing.T) {
})
}
}

// returns true when a wasm module event was emitted for this contract already
func hasWasmModuleEvent(ctx sdk.Context, contractAddr sdk.AccAddress) bool {
for _, e := range ctx.EventManager().Events() {
if e.Type == types.WasmModuleEventType {
for _, a := range e.Attributes {
if string(a.Key) == types.AttributeKeyContractAddr && string(a.Value) == contractAddr.String() {
return true
}
}
}
}
return false
}
79 changes: 71 additions & 8 deletions x/wasm/keeper/keeper.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ import (
"github.com/tendermint/tendermint/libs/log"
"math"
"path/filepath"
"strconv"
"strings"
"time"
)

Expand Down Expand Up @@ -178,6 +180,16 @@ func (k Keeper) create(ctx sdk.Context, creator sdk.AccAddress, wasmCode []byte,
}
codeInfo := types.NewCodeInfo(checksum, creator, *instantiateAccess)
k.storeCodeInfo(ctx, codeID, codeInfo)

evt := sdk.NewEvent(
alpe marked this conversation as resolved.
Show resolved Hide resolved
types.EventTypeStoreCode,
sdk.NewAttribute(types.AttributeKeyCodeID, strconv.FormatUint(codeID, 10)),
)
for _, f := range strings.Split(report.RequiredFeatures, ",") {
evt.AppendAttributes(sdk.NewAttribute(types.AttributeKeyFeature, strings.TrimSpace(f)))
}
ctx.EventManager().EmitEvent(evt)

return codeID, nil
}

Expand Down Expand Up @@ -293,7 +305,12 @@ func (k Keeper) instantiate(ctx sdk.Context, codeID uint64, creator, admin sdk.A
k.appendToContractHistory(ctx, contractAddress, historyEntry)
k.storeContractInfo(ctx, contractAddress, &contractInfo)

// dispatch submessages then messages
ctx.EventManager().EmitEvent(sdk.NewEvent(
types.EventTypeInstantiate,
sdk.NewAttribute(types.AttributeKeyContractAddr, contractAddress.String()),
sdk.NewAttribute(types.AttributeKeyCodeID, strconv.FormatUint(codeID, 10)),
))

data, err := k.handleContractResponse(ctx, contractAddress, contractInfo.IBCPortID, res.Messages, res.Attributes, res.Data, res.Events)
if err != nil {
return nil, nil, sdkerrors.Wrap(err, "dispatch")
Expand Down Expand Up @@ -332,11 +349,16 @@ func (k Keeper) execute(ctx sdk.Context, contractAddress sdk.AccAddress, caller
return nil, sdkerrors.Wrap(types.ErrExecuteFailed, execErr.Error())
}

// dispatch submessages then messages
ctx.EventManager().EmitEvent(sdk.NewEvent(
types.EventTypeExecute,
sdk.NewAttribute(types.AttributeKeyContractAddr, contractAddress.String()),
))

data, err := k.handleContractResponse(ctx, contractAddress, contractInfo.IBCPortID, res.Messages, res.Attributes, res.Data, res.Events)
if err != nil {
return nil, sdkerrors.Wrap(err, "dispatch")
}

return data, nil
}

Expand Down Expand Up @@ -396,11 +418,17 @@ func (k Keeper) migrate(ctx sdk.Context, contractAddress sdk.AccAddress, caller
k.addToContractCodeSecondaryIndex(ctx, contractAddress, historyEntry)
k.storeContractInfo(ctx, contractAddress, contractInfo)

// dispatch submessages then messages
ctx.EventManager().EmitEvent(sdk.NewEvent(
alpe marked this conversation as resolved.
Show resolved Hide resolved
types.EventTypeMigrate,
sdk.NewAttribute(types.AttributeKeyCodeID, strconv.FormatUint(newCodeID, 10)),
sdk.NewAttribute(types.AttributeKeyContractAddr, contractAddress.String()),
))

data, err := k.handleContractResponse(ctx, contractAddress, contractInfo.IBCPortID, res.Messages, res.Attributes, res.Data, res.Events)
if err != nil {
return nil, sdkerrors.Wrap(err, "dispatch")
}

return data, nil
}

Expand Down Expand Up @@ -428,11 +456,16 @@ func (k Keeper) Sudo(ctx sdk.Context, contractAddress sdk.AccAddress, msg []byte
return nil, sdkerrors.Wrap(types.ErrExecuteFailed, execErr.Error())
}

// dispatch submessages then messages
ctx.EventManager().EmitEvent(sdk.NewEvent(
types.EventTypeSudo,
sdk.NewAttribute(types.AttributeKeyContractAddr, contractAddress.String()),
))

data, err := k.handleContractResponse(ctx, contractAddress, contractInfo.IBCPortID, res.Messages, res.Attributes, res.Data, res.Events)
if err != nil {
return nil, sdkerrors.Wrap(err, "dispatch")
}

return data, nil
}

Expand Down Expand Up @@ -461,11 +494,16 @@ func (k Keeper) reply(ctx sdk.Context, contractAddress sdk.AccAddress, reply was
return nil, sdkerrors.Wrap(types.ErrExecuteFailed, execErr.Error())
}

// dispatch submessages then messages
ctx.EventManager().EmitEvent(sdk.NewEvent(
types.EventTypeReply,
sdk.NewAttribute(types.AttributeKeyContractAddr, contractAddress.String()),
))

data, err := k.handleContractResponse(ctx, contractAddress, contractInfo.IBCPortID, res.Messages, res.Attributes, res.Data, res.Events)
if err != nil {
return nil, sdkerrors.Wrap(err, "dispatch")
}

return data, nil
}

Expand Down Expand Up @@ -709,6 +747,11 @@ func (k Keeper) pinCode(ctx sdk.Context, codeID uint64) error {
store := ctx.KVStore(k.storeKey)
// store 1 byte to not run into `nil` debugging issues
store.Set(types.GetPinnedCodeIndexPrefix(codeID), []byte{1})

ctx.EventManager().EmitEvent(sdk.NewEvent(
types.EventTypePinCode,
sdk.NewAttribute(types.AttributeKeyCodeID, strconv.FormatUint(codeID, 10)),
))
return nil
}

Expand All @@ -724,6 +767,11 @@ func (k Keeper) unpinCode(ctx sdk.Context, codeID uint64) error {

store := ctx.KVStore(k.storeKey)
store.Delete(types.GetPinnedCodeIndexPrefix(codeID))

ctx.EventManager().EmitEvent(sdk.NewEvent(
types.EventTypeUnpinCode,
sdk.NewAttribute(types.AttributeKeyCodeID, strconv.FormatUint(codeID, 10)),
))
return nil
}

Expand Down Expand Up @@ -775,7 +823,7 @@ func (k *Keeper) handleContractResponse(
attributeGasCost := k.gasRegister.EventCosts(attrs, evts)
ctx.GasMeter().ConsumeGas(attributeGasCost, "Custom contract event attributes")
// emit all events from this contract itself
if len(attrs) != 0 || !hasWasmModuleEvent(ctx, contractAddr) {
if len(attrs) != 0 {
alpe marked this conversation as resolved.
Show resolved Hide resolved
wasmEvents, err := newWasmModuleEvent(attrs, contractAddr)
if err != nil {
return nil, err
Expand Down Expand Up @@ -985,7 +1033,9 @@ func NewBankCoinTransferrer(keeper types.BankKeeper) BankCoinTransferrer {

// TransferCoins transfers coins from source to destination account when coin send was enabled for them and the recipient
// is not in the blocked address list.
func (c BankCoinTransferrer) TransferCoins(ctx sdk.Context, fromAddr sdk.AccAddress, toAddr sdk.AccAddress, amt sdk.Coins) error {
func (c BankCoinTransferrer) TransferCoins(parentCtx sdk.Context, fromAddr sdk.AccAddress, toAddr sdk.AccAddress, amt sdk.Coins) error {
em := sdk.NewEventManager()
ctx := parentCtx.WithEventManager(em)
if err := c.keeper.SendEnabledCoins(ctx, amt...); err != nil {
return err
}
Expand All @@ -996,6 +1046,12 @@ func (c BankCoinTransferrer) TransferCoins(ctx sdk.Context, fromAddr sdk.AccAddr
if sdkerr != nil {
return sdkerr
}
for _, e := range em.Events() {
alpe marked this conversation as resolved.
Show resolved Hide resolved
if e.Type == sdk.EventTypeMessage { // skip messages as we talk to the keeper directly
continue
}
parentCtx.EventManager().EmitEvent(e)
}
return nil
}

Expand All @@ -1016,12 +1072,19 @@ func NewDefaultWasmVMContractResponseHandler(md msgDispatcher) *DefaultWasmVMCon

// Handle processes the data returned by a contract invocation.
func (h DefaultWasmVMContractResponseHandler) Handle(ctx sdk.Context, contractAddr sdk.AccAddress, ibcPort string, messages []wasmvmtypes.SubMsg, origRspData []byte) ([]byte, error) {
em := sdk.NewEventManager()
result := origRspData
switch rsp, err := h.md.DispatchSubmessages(ctx, contractAddr, ibcPort, messages); {
switch rsp, err := h.md.DispatchSubmessages(ctx.WithEventManager(em), contractAddr, ibcPort, messages); {
case err != nil:
return nil, sdkerrors.Wrap(err, "submessages")
case rsp != nil:
result = rsp
}
// emit non message type events only
Copy link
Member

Choose a reason for hiding this comment

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

This is good to clear, but in the spec, we need to clear the messages before we possibly place them inside reply.

I believe you need to do that inside DispatchSubmessages

Copy link
Member

Choose a reason for hiding this comment

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

TODO: I will raise this as a new issue (and to add tests if it works or not)

Copy link
Member

Choose a reason for hiding this comment

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

See #587

for _, e := range em.Events() {
if e.Type != sdk.EventTypeMessage {
ctx.EventManager().EmitEvent(e)
}
}
return result, nil
}
Loading