package keeper_test import ( "go.uber.org/mock/gomock" "cosmossdk.io/math" "git.cw.tr/mukan-network/mukan-sdk/codec/address" sdk "git.cw.tr/mukan-network/mukan-sdk/types" "git.cw.tr/mukan-network/mukan-sdk/x/protocolpool/types" ) func (suite *KeeperTestSuite) TestParams() { expectedParams := types.DefaultGenesisState().Params err := suite.poolKeeper.Params.Set(suite.ctx, expectedParams) suite.Require().NoError(err) testCases := []struct { name string preRun func() req *types.QueryParamsRequest expErr bool expErrMsg string resp *types.QueryParamsResponse }{ { name: "nil request - error", req: nil, expErr: true, expErrMsg: "rpc error: code = InvalidArgument desc = empty request", }, { name: "valid", req: &types.QueryParamsRequest{}, expErr: false, expErrMsg: "empty address string is not allowed", resp: &types.QueryParamsResponse{ Params: expectedParams, }, }, } for _, tc := range testCases { suite.Run(tc.name, func() { if tc.preRun != nil { tc.preRun() } resp, err := suite.queryServer.Params(suite.ctx, tc.req) if tc.expErr { suite.Require().Error(err) suite.Require().Contains(err.Error(), tc.expErrMsg) } else { suite.Require().NoError(err) suite.Require().Equal(tc.resp, resp) } }) } } func (suite *KeeperTestSuite) TestCommunityPool() { testCases := []struct { name string preRun func() req *types.QueryCommunityPoolRequest expErr bool expErrMsg string resp *types.QueryCommunityPoolResponse }{ { name: "nil request - error", req: nil, expErr: true, expErrMsg: "rpc error: code = InvalidArgument desc = empty request", }, { name: "valid", preRun: func() { suite.authKeeper.EXPECT().GetModuleAccount(gomock.Any(), types.ModuleName).Return(poolAcc).Times(1) suite.bankKeeper.EXPECT().GetAllBalances(gomock.Any(), poolAcc.GetAddress()).Return(sdk.NewCoins(fooCoin)).Times(1) }, req: &types.QueryCommunityPoolRequest{}, resp: &types.QueryCommunityPoolResponse{ Pool: sdk.NewCoins(fooCoin), }, expErr: false, expErrMsg: "", }, } for _, tc := range testCases { suite.Run(tc.name, func() { if tc.preRun != nil { tc.preRun() } resp, err := suite.queryServer.CommunityPool(suite.ctx, tc.req) if tc.expErr { suite.Require().Error(err) suite.Require().Contains(err.Error(), tc.expErrMsg) } else { suite.Require().NoError(err) suite.Require().Equal(tc.resp, resp) } }) } } func (suite *KeeperTestSuite) TestContinuousFund() { testCases := []struct { name string preRun func() req *types.QueryContinuousFundRequest expErr bool expErrMsg string resp *types.QueryContinuousFundResponse }{ { name: "nil request - error", req: nil, expErr: true, expErrMsg: "empty request", }, { name: "invalid address", req: &types.QueryContinuousFundRequest{ Recipient: "invalid", // not a valid Bech32 address }, preRun: func() { // Return a real codec; its StringToBytes will fail for an invalid address. suite.authKeeper.EXPECT().AddressCodec(). Return(address.NewBech32Codec("cosmos")).AnyTimes() }, expErr: true, expErrMsg: "invalid address:", }, { name: "fund not found", req: &types.QueryContinuousFundRequest{ Recipient: recipientAddr.String(), // valid format but not set in store }, preRun: func() { suite.authKeeper.EXPECT().AddressCodec(). Return(address.NewBech32Codec("cosmos")).AnyTimes() }, expErr: true, expErrMsg: "not found", }, { name: "valid continuous fund", req: &types.QueryContinuousFundRequest{ Recipient: recipientAddr.String(), }, preRun: func() { // Use the real codec to convert the address. suite.authKeeper.EXPECT().AddressCodec(). Return(address.NewBech32Codec("cosmos")).AnyTimes() // Insert a continuous fund directly into the pool keeper. fund := types.ContinuousFund{ Recipient: recipientAddr.String(), Percentage: math.LegacyMustNewDecFromStr("0.5"), Expiry: nil, } err := suite.poolKeeper.ContinuousFunds.Set(suite.ctx, recipientAddr, fund) suite.Require().NoError(err) }, expErr: false, resp: &types.QueryContinuousFundResponse{ ContinuousFund: types.ContinuousFund{ Recipient: recipientAddr.String(), Percentage: math.LegacyMustNewDecFromStr("0.5"), Expiry: nil, }, }, }, } for _, tc := range testCases { suite.Run(tc.name, func() { if tc.preRun != nil { tc.preRun() } resp, err := suite.queryServer.ContinuousFund(suite.ctx, tc.req) if tc.expErr { suite.Require().Error(err) suite.Require().Contains(err.Error(), tc.expErrMsg) } else { suite.Require().NoError(err) suite.Require().Equal(tc.resp.ContinuousFund.Recipient, resp.ContinuousFund.Recipient) suite.Require().Equal(tc.resp.ContinuousFund.Percentage, resp.ContinuousFund.Percentage) suite.Require().Equal(tc.resp.ContinuousFund.Expiry, resp.ContinuousFund.Expiry) } }) } } func (suite *KeeperTestSuite) TestContinuousFunds() { testCases := []struct { name string preRun func() req *types.QueryContinuousFundsRequest expErr bool expErrMsg string resp *types.QueryContinuousFundsResponse }{ { name: "nil request - error", req: nil, expErr: true, expErrMsg: "empty request", }, { name: "no continuous funds", req: &types.QueryContinuousFundsRequest{}, preRun: nil, expErr: false, resp: &types.QueryContinuousFundsResponse{ ContinuousFunds: []types.ContinuousFund{}, }, }, { name: "valid continuous funds", req: &types.QueryContinuousFundsRequest{}, preRun: func() { // Insert two continuous funds directly into the keeper. fund1 := types.ContinuousFund{ Recipient: recipientAddr.String(), Percentage: math.LegacyMustNewDecFromStr("0.3"), Expiry: nil, } err := suite.poolKeeper.ContinuousFunds.Set(suite.ctx, recipientAddr, fund1) suite.Require().NoError(err) fund2 := types.ContinuousFund{ Recipient: recipientAddr2.String(), Percentage: math.LegacyMustNewDecFromStr("0.7"), Expiry: nil, } err = suite.poolKeeper.ContinuousFunds.Set(suite.ctx, recipientAddr2, fund2) suite.Require().NoError(err) }, expErr: false, resp: &types.QueryContinuousFundsResponse{ ContinuousFunds: []types.ContinuousFund{ { Recipient: recipientAddr.String(), Percentage: math.LegacyMustNewDecFromStr("0.3"), Expiry: nil, }, { Recipient: recipientAddr2.String(), Percentage: math.LegacyMustNewDecFromStr("0.7"), Expiry: nil, }, }, }, }, } for _, tc := range testCases { suite.Run(tc.name, func() { if tc.preRun != nil { tc.preRun() } resp, err := suite.queryServer.ContinuousFunds(suite.ctx, tc.req) if tc.expErr { suite.Require().Error(err) suite.Require().Contains(err.Error(), tc.expErrMsg) } else { suite.Require().NoError(err) suite.Require().ElementsMatch(tc.resp.ContinuousFunds, resp.ContinuousFunds) } }) } }