Skip to content

Commit

Permalink
feat x/bridge: using MsgServer to access tokenfactory (#7748)
Browse files Browse the repository at this point in the history
* using MsgServer to access tokenfactory

* clarified errors

* fixed tokenfactory denom creation
  • Loading branch information
keruch authored Mar 15, 2024
1 parent 16f0156 commit ea86019
Show file tree
Hide file tree
Showing 6 changed files with 85 additions and 40 deletions.
22 changes: 18 additions & 4 deletions x/bridge/keeper/assets.go
Original file line number Diff line number Diff line change
@@ -1,12 +1,11 @@
package keeper

import (
"fmt"

errorsmod "cosmossdk.io/errors"
sdk "github.com/cosmos/cosmos-sdk/types"

"github.com/osmosis-labs/osmosis/v23/x/bridge/types"
tokenfactorytypes "github.com/osmosis-labs/osmosis/v23/x/tokenfactory/types"
)

type ChangeAssetStatusResult struct {
Expand Down Expand Up @@ -52,10 +51,25 @@ func (k Keeper) ChangeAssetStatus(
func (k Keeper) createAssets(ctx sdk.Context, assets []types.AssetWithStatus) error {
bridgeModuleAddr := k.accountKeeper.GetModuleAddress(types.ModuleName)

handler := k.router.Handler(new(tokenfactorytypes.MsgCreateDenom))
if handler == nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't route a create denom message")
}

for _, asset := range assets {
_, err := k.tokenFactoryKeeper.CreateDenom(ctx, bridgeModuleAddr.String(), asset.Asset.Name())
msgCreateDenom := &tokenfactorytypes.MsgCreateDenom{
Sender: bridgeModuleAddr.String(),
Subdenom: asset.Asset.Name(),
}

// ignore resp since it is not needed in this method
// TODO: double-check if we need to handle the response
_, err := handler(ctx, msgCreateDenom)
if err != nil {
return fmt.Errorf("can't create a new denom %s: %s", asset.Asset.Name(), err)
return errorsmod.Wrapf(
types.ErrTokenfactory,
"Can't execute a create denom message for %s: %s", asset.Asset.Name(), err,
)
}
}

Expand Down
26 changes: 13 additions & 13 deletions x/bridge/keeper/keeper.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,29 +4,30 @@ import (
"fmt"

"github.com/cometbft/cometbft/libs/log"
storetypes "github.com/cosmos/cosmos-sdk/store/types"
"github.com/cosmos/cosmos-sdk/baseapp"
sdk "github.com/cosmos/cosmos-sdk/types"
paramtypes "github.com/cosmos/cosmos-sdk/x/params/types"

"github.com/osmosis-labs/osmosis/v23/x/bridge/types"
)

type Keeper struct {
storeKey storetypes.StoreKey
// paramSpace stores module's params
paramSpace paramtypes.Subspace

accountKeeper types.AccountKeeper
tokenFactoryKeeper types.TokenFactoryKeeper

// router is used to access tokenfactory methods
router *baseapp.MsgServiceRouter
// accountKeeper helps get the module's address
accountKeeper types.AccountKeeper
// govModuleAddr is used in UpdateParams method since it is
// the only addr that can update bridge module params
govModuleAddr string
}

// NewKeeper returns a new instance of the x/bridge keeper.
func NewKeeper(
storeKey storetypes.StoreKey,
paramSpace paramtypes.Subspace,
router *baseapp.MsgServiceRouter,
accountKeeper types.AccountKeeper,
tokenFactoryKeeper types.TokenFactoryKeeper,
govModuleAddr string,
) Keeper {
// ensure bridge module account is set
Expand All @@ -39,11 +40,10 @@ func NewKeeper(
}

return Keeper{
storeKey: storeKey,
paramSpace: paramSpace,
accountKeeper: accountKeeper,
tokenFactoryKeeper: tokenFactoryKeeper,
govModuleAddr: govModuleAddr,
paramSpace: paramSpace,
router: router,
accountKeeper: accountKeeper,
govModuleAddr: govModuleAddr,
}
}

Expand Down
5 changes: 3 additions & 2 deletions x/bridge/keeper/params.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,15 +28,16 @@ func (k Keeper) UpdateParams(ctx sdk.Context, newParams types.Params) (UpdatePar
// create denoms for all new assets
err := k.createAssets(ctx, assetsToCreate)
if err != nil {
return UpdateParamsResult{}, err
return UpdateParamsResult{},
errorsmod.Wrapf(types.ErrCantCreateAsset, "Can't create new assets: %s", err)
}

// disable deleted assets
for _, asset := range assetsToDelete {
_, err = k.ChangeAssetStatus(ctx, asset.Asset, types.AssetStatus_ASSET_STATUS_BLOCKED_BOTH)
if err != nil {
return UpdateParamsResult{},
errorsmod.Wrapf(types.ErrCantChangeAssetStatus, "Can't disable asset %v: %s", asset.Asset, err)
errorsmod.Wrapf(types.ErrCantChangeAssetStatus, "Can't disable asset %s: %s", asset.Asset.Name(), err)
}
}

Expand Down
61 changes: 49 additions & 12 deletions x/bridge/keeper/transfers.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import (
sdk "github.com/cosmos/cosmos-sdk/types"

"github.com/osmosis-labs/osmosis/v23/x/bridge/types"
tokenfactorytypes "github.com/osmosis-labs/osmosis/v23/x/tokenfactory/types"
)

func (k Keeper) InboundTransfer(
Expand All @@ -27,12 +28,30 @@ func (k Keeper) InboundTransfer(

moduleAddr := k.accountKeeper.GetModuleAddress(types.ModuleName)

return k.tokenFactoryKeeper.Mint(
ctx,
moduleAddr.String(),
sdk.NewCoin(asset.Name(), amount),
destAddr,
)
denom, err := tokenfactorytypes.GetTokenDenom(moduleAddr.String(), asset.Name())
if err != nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't create a tokenfacroty denom for %s", asset.Name())
}

msgMint := &tokenfactorytypes.MsgMint{
Sender: moduleAddr.String(),
Amount: sdk.NewCoin(denom, amount),
MintToAddress: destAddr,
}

handler := k.router.Handler(msgMint)
if handler == nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't route a mint message")
}

// ignore resp since it is empty in this method
// TODO: double-check if we need to handle the response
_, err = handler(ctx, msgMint)
if err != nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't execute a mint message: %s", err)
}

return nil
}

func (k Keeper) OutboundTransfer(
Expand All @@ -54,10 +73,28 @@ func (k Keeper) OutboundTransfer(

moduleAddr := k.accountKeeper.GetModuleAddress(types.ModuleName)

return k.tokenFactoryKeeper.Burn(
ctx,
moduleAddr.String(),
sdk.NewCoin(asset.Name(), amount),
sourceAddr,
)
denom, err := tokenfactorytypes.GetTokenDenom(moduleAddr.String(), asset.Name())
if err != nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't create a tokenfacroty denom for %s", asset.Name())
}

msgBurn := &tokenfactorytypes.MsgBurn{
Sender: moduleAddr.String(),
Amount: sdk.NewCoin(denom, amount),
BurnFromAddress: sourceAddr,
}

handler := k.router.Handler(msgBurn)
if handler == nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't route a burn message")
}

// ignore resp since it is empty in this method
// TODO: double-check if we need to handle the response
_, err = handler(ctx, msgBurn)
if err != nil {
return errorsmod.Wrapf(types.ErrTokenfactory, "Can't execute a burn message: %s", err)
}

return nil
}
2 changes: 2 additions & 0 deletions x/bridge/types/errors.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,6 @@ var (
ErrInvalidSourceChain = errorsmod.Register(ModuleName, 7, "invalid source chain")
ErrInvalidSigners = errorsmod.Register(ModuleName, 8, "invalid signers")
ErrCantChangeAssetStatus = errorsmod.Register(ModuleName, 9, "can't change asset status")
ErrCantCreateAsset = errorsmod.Register(ModuleName, 10, "can't create asset")
ErrTokenfactory = errorsmod.Register(ModuleName, 11, "tokenfactory error")
)
9 changes: 0 additions & 9 deletions x/bridge/types/expected_keepers.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,19 +2,10 @@ package types

import (
sdk "github.com/cosmos/cosmos-sdk/types"
authtypes "github.com/cosmos/cosmos-sdk/x/auth/types"
)

type AccountKeeper interface {
// GetModuleAccount is used to create x/bridge module account
GetModuleAccount(ctx sdk.Context, moduleName string) authtypes.ModuleAccountI
// GetModuleAddress is used to get the module account
// to use it as the admin for denoms in x/tokenfactory.
GetModuleAddress(name string) sdk.AccAddress
}

type TokenFactoryKeeper interface {
CreateDenom(ctx sdk.Context, creatorAddr string, subdenom string) (newTokenDenom string, err error)
Mint(ctx sdk.Context, sender string, amount sdk.Coin, mintTo string) error
Burn(ctx sdk.Context, sender string, amount sdk.Coin, burnFrom string) error
}

0 comments on commit ea86019

Please sign in to comment.