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

feat:sweep axelarcork module acct balances in end blocker #270

Merged
merged 13 commits into from
Jan 30, 2024
50 changes: 50 additions & 0 deletions integration_tests/axelarcork_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,9 @@ import (
"cosmossdk.io/math"
"github.com/cosmos/cosmos-sdk/client"
sdk "github.com/cosmos/cosmos-sdk/types"
authtypes "github.com/cosmos/cosmos-sdk/x/auth/types"
banktypes "github.com/cosmos/cosmos-sdk/x/bank/types"
distributiontypes "github.com/cosmos/cosmos-sdk/x/distribution/types"
govtypesv1beta1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1beta1"
"github.com/ethereum/go-ethereum/common"
"github.com/golang/protobuf/proto" //nolint:staticcheck
Expand Down Expand Up @@ -456,6 +459,53 @@ func (s *IntegrationTestSuite) TestAxelarCork() {
chainConfigurationsResponse, err = axelarcorkQueryClient.QueryChainConfigurations(context.Background(), &types.QueryChainConfigurationsRequest{})
s.Require().NoError(err)
s.Require().Empty(chainConfigurationsResponse.Configurations)

//////////////////////////////////////////
// Test module account balance sweeping //
//////////////////////////////////////////

// Get the baseline balance of the distribution community pool, send funds to the axelarcork module account,
// verify they are received, and that the balance is zero on the next block.
s.T().Log("Querying distribution community pool balance")
distributionQueryClient := distributiontypes.NewQueryClient(orch0ClientCtx)
distributionCommunityPoolResponse, err := distributionQueryClient.CommunityPool(context.Background(), &distributiontypes.QueryCommunityPoolRequest{})
s.Require().NoError(err)
initialPool := distributionCommunityPoolResponse.Pool

// Send all of orchestrator's sweep denom and some usomm
s.T().Log("Querying orchestrator account balances")
bankQueryClient := banktypes.NewQueryClient(orch0ClientCtx)
orch0AccountResponse, err := bankQueryClient.AllBalances(context.Background(), &banktypes.QueryAllBalancesRequest{Address: orch0.address().String()})
s.Require().NoError(err)
orch0Balances := orch0AccountResponse.Balances
usommToSend := sdk.NewCoin(testDenom, math.NewInt(1000))
found, sweepDenomToSend := orch0Balances.Find(axelarSweepDenom)
s.Require().True(found, "orch0 doesn't have any sweep test denom funds")
orch0SweepFunds := sdk.Coins{
sweepDenomToSend,
usommToSend,
}

s.T().Log("Sending funds to axelarcork module account")
axelarcorkModuleAddress := authtypes.NewModuleAddress(types.ModuleName)
sendFundsToAxelarcorkMsg := banktypes.NewMsgSend(
orch0.address(),
axelarcorkModuleAddress,
orch0SweepFunds,
)
sendResponse, err := s.chain.sendMsgs(*orch0ClientCtx, sendFundsToAxelarcorkMsg)
s.Require().NoError(err)
s.Require().Zero(sendResponse.Code, "raw log: %s", sendResponse.RawLog)
s.T().Log("Verifying distribution community pool balances includes the swept funds")

// Short delay to ensure a new block is queried
time.Sleep(10 * time.Second)

// Verify fund appear in the community pool
distributionCommunityPoolResponse, err = distributionQueryClient.CommunityPool(context.Background(), &distributiontypes.QueryCommunityPoolRequest{})
s.Require().NoError(err)
poolAfterSweep := initialPool.Add(sdk.NewDecCoinsFromCoins(usommToSend)...).Add(sdk.NewDecCoinsFromCoins(sweepDenomToSend)...)
s.Require().Equal(poolAfterSweep, distributionCommunityPoolResponse.Pool)
})
}

Expand Down
20 changes: 19 additions & 1 deletion integration_tests/setup_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@ HOqHGS8ApZcunRauDAIwRtgceZpkS92KuP3QOUotAH/nnCzp7X1lVzGOSTBRTVYJ
pohf4PJrfacqpi7PoXBk
-----END CERTIFICATE-----
`
axelarSweepDenom = "sweep"
)

var (
Expand Down Expand Up @@ -319,7 +320,19 @@ func (s *IntegrationTestSuite) initGenesis() {
Exponent: 0,
},
},
})
},
banktypes.Metadata{
Description: "Test token for sweeping",
Display: axelarSweepDenom,
Base: axelarSweepDenom,
Name: axelarSweepDenom,
DenomUnits: []*banktypes.DenomUnit{
{
Denom: axelarSweepDenom,
Exponent: 0,
},
},
})

// Set up auction module with some coins to auction off
balance := banktypes.Balance{
Expand All @@ -330,8 +343,13 @@ func (s *IntegrationTestSuite) initGenesis() {
Address: authtypes.NewModuleAddress(disttypes.ModuleName).String(),
Coins: sdk.NewCoins(sdk.NewCoin(params.BaseCoinUnit, sdk.NewInt(1000000000))),
}
orchSweepBalance := banktypes.Balance{
Address: s.chain.orchestrators[0].address().String(),
Coins: sdk.NewCoins(sdk.NewCoin(axelarSweepDenom, sdk.NewInt(2000000000))),
}
bankGenState.Balances = append(bankGenState.Balances, balance)
bankGenState.Balances = append(bankGenState.Balances, distBalance)
bankGenState.Balances = append(bankGenState.Balances, orchSweepBalance)

bz, err := cdc.MarshalJSON(&bankGenState)
s.Require().NoError(err)
Expand Down
27 changes: 27 additions & 0 deletions x/axelarcork/keeper/abci.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (

"github.com/ethereum/go-ethereum/common"

distributionTypes "github.com/cosmos/cosmos-sdk/x/distribution/types"
"github.com/peggyjv/sommelier/v7/x/axelarcork/types"

sdk "github.com/cosmos/cosmos-sdk/types"
Expand Down Expand Up @@ -54,4 +55,30 @@ func (k Keeper) EndBlocker(ctx sdk.Context) {

return false
})

// Sweep all axelarcork sender module account balances to the community pool. Because this account is the
// sender for transfers created by RelayCork calls, funds will not be returned to the caller if the IBC
// transfer fails or gas is refunded.
moduleAcct := k.GetSenderAccount(ctx)
balances := k.bankKeeper.GetAllBalances(ctx, moduleAcct.GetAddress())
balancesForPool := sdk.Coins{}

for _, b := range balances {
if b.Amount.IsPositive() {
balancesForPool.Add(b)
}
}

if balancesForPool.Len() == 0 {
return
}

if err := k.bankKeeper.SendCoinsFromModuleToModule(ctx, types.ModuleName, distributionTypes.ModuleName, balancesForPool); err != nil {
panic(err)
}

feePool := k.distributionKeeper.GetFeePool(ctx)
feePool.CommunityPool = feePool.CommunityPool.Add(sdk.NewDecCoinsFromCoins(balancesForPool...)...)

k.distributionKeeper.SetFeePool(ctx, feePool)
}
Loading