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

fix: ensure we dont attempt to send funds from deposit to delegate after we refund user #1764

Merged
merged 2 commits into from
Dec 2, 2024
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
36 changes: 20 additions & 16 deletions x/interchainstaking/keeper/receipt.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,21 +122,25 @@
k.Logger(ctx).Error("unable to update intent. Ignoring.", "senderAddress", senderAddress, "zone", zone.ChainId, "err", err.Error())
return fmt.Errorf("unable to update intent. Ignoring. senderAddress=%q zone=%q err: %w", senderAddress, zone.ChainId, err)
}
if err := k.MintAndSendQAsset(ctx, senderAccAddress, senderAddress, &zone, assets, memoRTS, mappedAddress); err != nil {

success, err := k.MintAndSendQAsset(ctx, senderAccAddress, senderAddress, &zone, assets, memoRTS, mappedAddress)
if err != nil {
joe-bowman marked this conversation as resolved.
Show resolved Hide resolved
k.Logger(ctx).Error("unable to mint QAsset. Ignoring.", "senderAddress", senderAddress, "zone", zone.ChainId, "err", err)
return fmt.Errorf("unable to mint QAsset. Ignoring. senderAddress=%q zone=%q err: %w", senderAddress, zone.ChainId, err)
}
if err := k.TransferToDelegate(ctx, &zone, assets, hash); err != nil {
k.Logger(ctx).Error("unable to transfer to delegate. Ignoring.", "senderAddress", senderAddress, "zone", zone.ChainId, "err", err)
return fmt.Errorf("unable to transfer to delegate. Ignoring. senderAddress=%q zone=%q err: %w", senderAddress, zone.ChainId, err)
}
if memoAutoClaim {
if err := k.HandleAutoClaim(ctx, senderAccAddress); err != nil {
k.Logger(ctx).Error("unable to handle auto claim. Ignoring.", "senderAddress", senderAddress, "zone", zone.ChainId, "err", err)
return fmt.Errorf("unable to handle auto claim. Ignoring. senderAddress=%q zone=%q err: %w", senderAddress, zone.ChainId, err)

if success {
if err := k.TransferToDelegate(ctx, &zone, assets, hash); err != nil {
k.Logger(ctx).Error("unable to transfer to delegate. Ignoring.", "senderAddress", senderAddress, "zone", zone.ChainId, "err", err)
return fmt.Errorf("unable to transfer to delegate. Ignoring. senderAddress=%q zone=%q err: %w", senderAddress, zone.ChainId, err)
}

Check warning on line 136 in x/interchainstaking/keeper/receipt.go

View check run for this annotation

Codecov / codecov/patch

x/interchainstaking/keeper/receipt.go#L134-L136

Added lines #L134 - L136 were not covered by tests
if memoAutoClaim {
if err := k.HandleAutoClaim(ctx, senderAccAddress); err != nil {
k.Logger(ctx).Error("unable to handle auto claim. Ignoring.", "senderAddress", senderAddress, "zone", zone.ChainId, "err", err)
return fmt.Errorf("unable to handle auto claim. Ignoring. senderAddress=%q zone=%q err: %w", senderAddress, zone.ChainId, err)
}

Check warning on line 141 in x/interchainstaking/keeper/receipt.go

View check run for this annotation

Codecov / codecov/patch

x/interchainstaking/keeper/receipt.go#L138-L141

Added lines #L138 - L141 were not covered by tests
}
}

// create receipt
receipt := k.NewReceipt(ctx, &zone, senderAddress, hash, assets)
k.SetReceipt(ctx, *receipt)
Expand Down Expand Up @@ -206,9 +210,9 @@
// - Mint QAssets, set new mapping for the mapped account in the keeper, and send to corresponding mapped account.
// 5. If the zone is 118 and no other flags are set:
// - Mint QAssets and transfer to send to msg creator.
func (k *Keeper) MintAndSendQAsset(ctx sdk.Context, sender sdk.AccAddress, senderAddress string, zone *types.Zone, assets sdk.Coins, memoRTS bool, mappedAddress sdk.AccAddress) error {
func (k *Keeper) MintAndSendQAsset(ctx sdk.Context, sender sdk.AccAddress, senderAddress string, zone *types.Zone, assets sdk.Coins, memoRTS bool, mappedAddress sdk.AccAddress) (bool, error) {
if zone.RedemptionRate.IsZero() {
return errors.New("zero redemption rate")
return false, errors.New("zero redemption rate")

Check warning on line 215 in x/interchainstaking/keeper/receipt.go

View check run for this annotation

Codecov / codecov/patch

x/interchainstaking/keeper/receipt.go#L215

Added line #L215 was not covered by tests
}

qAssets := sdk.Coins{}
Expand All @@ -225,7 +229,7 @@
if !found {
// if not found, skip minting and refund assets
msg := &banktypes.MsgSend{FromAddress: zone.DepositAddress.GetAddress(), ToAddress: senderAddress, Amount: assets}
return k.SubmitTx(ctx, []sdk.Msg{msg}, zone.DepositAddress, "refund", zone.MessagesPerTx)
return false, k.SubmitTx(ctx, []sdk.Msg{msg}, zone.DepositAddress, "refund", zone.MessagesPerTx)
joe-bowman marked this conversation as resolved.
Show resolved Hide resolved
}
// do not set, since mapped address already exists
setMappedAddress = false
Expand All @@ -234,7 +238,7 @@
k.Logger(ctx).Info("Minting qAssets for receipt", "assets", qAssets)
err := k.BankKeeper.MintCoins(ctx, types.ModuleName, qAssets)
if err != nil {
return err
return false, err

Check warning on line 241 in x/interchainstaking/keeper/receipt.go

View check run for this annotation

Codecov / codecov/patch

x/interchainstaking/keeper/receipt.go#L241

Added line #L241 was not covered by tests
}

switch {
Expand All @@ -258,7 +262,7 @@
}

if err != nil {
return fmt.Errorf("unable to transfer coins: %w", err)
return false, fmt.Errorf("unable to transfer coins: %w", err)

Check warning on line 265 in x/interchainstaking/keeper/receipt.go

View check run for this annotation

Codecov / codecov/patch

x/interchainstaking/keeper/receipt.go#L265

Added line #L265 was not covered by tests
}

ctx.EventManager().EmitEvent(
Expand All @@ -267,7 +271,7 @@
sdk.NewAttribute(sdk.AttributeKeyAmount, qAssets.String()),
),
)
return nil
return true, nil
}

// TransferToDelegate transfers tokens from the zone deposit account address to the zone delegate account address.
Expand Down
39 changes: 34 additions & 5 deletions x/interchainstaking/keeper/receipt_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -397,8 +397,9 @@ func (suite *KeeperTestSuite) TestMintAndSendQAsset1RR() {
amount := sdk.NewCoins(sdk.NewCoin(zone.BaseDenom, sdk.NewInt(5000)))

// Test sending QAsset
err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
success, err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
suite.NoError(err)
suite.True(success)

// Verify balance of receiver
receiverBalance := quicksilver.BankKeeper.GetBalance(ctx, sender, zone.LocalDenom)
Expand All @@ -422,8 +423,9 @@ func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RR() {
amount := sdk.NewCoins(sdk.NewCoin(zone.BaseDenom, sdk.NewInt(5000)))

// Test sending QAsset
err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
success, err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
suite.NoError(err)
suite.True(success)

// Verify balance of receiver
receiverBalance := quicksilver.BankKeeper.GetBalance(ctx, sender, zone.LocalDenom)
Expand All @@ -447,8 +449,9 @@ func (suite *KeeperTestSuite) TestMintAndSendQAssetSub1RR() {
amount := sdk.NewCoins(sdk.NewCoin(zone.BaseDenom, sdk.NewInt(5000)))

// Test sending QAsset
err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
success, err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
suite.NoError(err)
suite.True(success)

// Verify balance of receiver
receiverBalance := quicksilver.BankKeeper.GetBalance(ctx, sender, zone.LocalDenom)
Expand All @@ -464,6 +467,7 @@ func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RRMappedAccount() {

zone, found := quicksilver.InterchainstakingKeeper.GetZone(ctx, suite.chainB.ChainID)
zone.RedemptionRate = sdk.NewDecWithPrec(110, 2)
zone.Is_118 = false
suite.True(found)

senderAddress := addressutils.GenerateAddressForTestWithPrefix("cosmos")
Expand All @@ -473,8 +477,9 @@ func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RRMappedAccount() {
amount := sdk.NewCoins(sdk.NewCoin(zone.BaseDenom, sdk.NewInt(5000)))

// Test sending QAsset
err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, mappedAccount)
success, err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, mappedAccount)
suite.NoError(err)
suite.True(success)

// Verify balance of receiver
receiverBalance := quicksilver.BankKeeper.GetBalance(ctx, sender, zone.LocalDenom)
Expand All @@ -492,6 +497,29 @@ func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RRMappedAccount() {
suite.Equal(mappedAccount, localAddress)
}

func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RRNon118NoMappedAccount() {
suite.SetupTest()
suite.setupTestZones()

quicksilver := suite.GetQuicksilverApp(suite.chainA)
ctx := suite.chainA.GetContext()

zone, found := quicksilver.InterchainstakingKeeper.GetZone(ctx, suite.chainB.ChainID)
zone.RedemptionRate = sdk.NewDecWithPrec(110, 2)
zone.Is_118 = false
suite.True(found)

senderAddress := addressutils.GenerateAddressForTestWithPrefix("cosmos")
sender := addressutils.MustAccAddressFromBech32(senderAddress, "")

amount := sdk.NewCoins(sdk.NewCoin(zone.BaseDenom, sdk.NewInt(5000)))

// Test sending QAsset
success, err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, false, nil)
suite.NoError(err)
suite.False(success)
}

func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RTS() {
suite.SetupTest()
// this is required because the ibc-go test suite CreateTransferChannels defaults to a value that causes executing a message to error.
Expand All @@ -514,8 +542,9 @@ func (suite *KeeperTestSuite) TestMintAndSendQAssetNon1RTS() {
amount := sdk.NewCoins(sdk.NewCoin(zone.BaseDenom, sdk.NewInt(5000)))

// Test sending QAsset
err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, true, nil)
success, err := quicksilver.InterchainstakingKeeper.MintAndSendQAsset(ctx, sender, senderAddress, &zone, amount, true, nil)
suite.NoError(err)
suite.True(success)

// Verify balance of receiver
receiverBalance := quicksilver.BankKeeper.GetBalance(ctx, sender, zone.LocalDenom)
Expand Down
Loading