diff --git a/docs/core/proto-docs.md b/docs/core/proto-docs.md index 957b35f919c5..d40a50889e7c 100644 --- a/docs/core/proto-docs.md +++ b/docs/core/proto-docs.md @@ -5111,6 +5111,7 @@ DepositParams defines the params for deposits on governance proposals. | ----- | ---- | ----- | ----------- | | `min_deposit` | [cosmos.base.v1beta1.Coin](#cosmos.base.v1beta1.Coin) | repeated | Minimum deposit for a proposal to enter voting period. | | `max_deposit_period` | [google.protobuf.Duration](#google.protobuf.Duration) | | Maximum period for Atom holders to deposit on a proposal. Initial value: 2 months. | +| `min_expedited_deposit` | [cosmos.base.v1beta1.Coin](#cosmos.base.v1beta1.Coin) | repeated | Minimum expedited deposit for a proposal to enter voting period. | diff --git a/proto/cosmos/gov/v1beta1/gov.proto b/proto/cosmos/gov/v1beta1/gov.proto index 6b67adb1e8e2..f6f2165b755a 100644 --- a/proto/cosmos/gov/v1beta1/gov.proto +++ b/proto/cosmos/gov/v1beta1/gov.proto @@ -160,6 +160,14 @@ message DepositParams { (gogoproto.jsontag) = "max_deposit_period,omitempty", (gogoproto.moretags) = "yaml:\"max_deposit_period\"" ]; + + // Minimum expedited deposit for a proposal to enter voting period. + repeated cosmos.base.v1beta1.Coin min_expedited_deposit = 3 [ + (gogoproto.nullable) = false, + (gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins", + (gogoproto.moretags) = "yaml:\"min_expedited_deposit\"", + (gogoproto.jsontag) = "min_expedited_deposit,omitempty" + ]; } // VotingParams defines the params for voting on governance proposals. diff --git a/x/gov/abci.go b/x/gov/abci.go index 4883b25cae72..8749fc7f685e 100644 --- a/x/gov/abci.go +++ b/x/gov/abci.go @@ -35,8 +35,9 @@ func EndBlocker(ctx sdk.Context, keeper keeper.Keeper) { logger.Info( "proposal did not meet minimum deposit; deleted", "proposal", proposal.ProposalId, + "is_expedited", proposal.IsExpedited, "title", proposal.GetTitle(), - "min_deposit", keeper.GetDepositParams(ctx).MinDeposit.String(), + "min_deposit", proposal.GetMinDepositFromParams(keeper.GetDepositParams(ctx)).String(), "total_deposit", proposal.TotalDeposit.String(), ) diff --git a/x/gov/abci_test.go b/x/gov/abci_test.go index 2d2086e815d4..c78759a5a595 100644 --- a/x/gov/abci_test.go +++ b/x/gov/abci_test.go @@ -224,6 +224,8 @@ func TestTickPassedVotingPeriod(t *testing.T) { t.Run(tc.name, func(t *testing.T) { testProposal := TestProposal + depositMultiplier := getDepositMultiplier(tc.isExpedited) + app := simapp.Setup(false) ctx := app.BaseApp.NewContext(false, tmproto.Header{}) addrs := simapp.AddTestAddrs(app, ctx, 10, valTokens) @@ -242,7 +244,7 @@ func TestTickPassedVotingPeriod(t *testing.T) { require.False(t, activeQueue.Valid()) activeQueue.Close() - proposalCoins := sdk.Coins{sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 5))} + proposalCoins := sdk.Coins{sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 5*depositMultiplier))} newProposalMsg, err := types.NewMsgSubmitProposal(testProposal, proposalCoins, addrs[0], tc.isExpedited) require.NoError(t, err) @@ -319,15 +321,15 @@ func TestTickPassedVotingPeriod(t *testing.T) { func TestProposalPassedEndblocker(t *testing.T) { testcases := []struct { name string - IsExpedited bool + isExpedited bool }{ { name: "regular text", - IsExpedited: false, + isExpedited: false, }, { name: "text expedited", - IsExpedited: true, + isExpedited: true, }, } @@ -335,9 +337,11 @@ func TestProposalPassedEndblocker(t *testing.T) { t.Run(tc.name, func(t *testing.T) { testProposal := TestProposal + depositMultiplier := getDepositMultiplier(tc.isExpedited) + app := simapp.Setup(false) ctx := app.BaseApp.NewContext(false, tmproto.Header{}) - addrs := simapp.AddTestAddrs(app, ctx, 10, valTokens) + addrs := simapp.AddTestAddrs(app, ctx, 10, valTokens.Mul(sdk.NewInt(depositMultiplier))) SortAddresses(addrs) @@ -356,10 +360,10 @@ func TestProposalPassedEndblocker(t *testing.T) { require.NotNil(t, macc) initialModuleAccCoins := app.BankKeeper.GetAllBalances(ctx, macc.GetAddress()) - proposal, err := app.GovKeeper.SubmitProposal(ctx, testProposal, tc.IsExpedited) + proposal, err := app.GovKeeper.SubmitProposal(ctx, testProposal, tc.isExpedited) require.NoError(t, err) - proposalCoins := sdk.Coins{sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 10))} + proposalCoins := sdk.Coins{sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 10*depositMultiplier))} newDepositMsg := types.NewMsgDeposit(addrs[0], proposal.ProposalId, proposalCoins) handleAndCheck(t, handler, ctx, newDepositMsg) @@ -415,9 +419,11 @@ func TestExpeditedProposal_PassAndConversionToRegular(t *testing.T) { t.Run(tc.name, func(t *testing.T) { testProposal := TestProposal + depositMultiplier := getDepositMultiplier(true) + app := simapp.Setup(false) ctx := app.BaseApp.NewContext(false, tmproto.Header{}) - addrs := simapp.AddTestAddrs(app, ctx, 10, valTokens) + addrs := simapp.AddTestAddrs(app, ctx, 10, valTokens.Mul(sdk.NewInt(depositMultiplier))) SortAddresses(addrs) @@ -447,7 +453,7 @@ func TestExpeditedProposal_PassAndConversionToRegular(t *testing.T) { submitterInitialBalance := app.BankKeeper.GetAllBalances(ctx, addrs[0]) depositorInitialBalance := app.BankKeeper.GetAllBalances(ctx, addrs[1]) - proposalCoins := sdk.Coins{sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 5))} + proposalCoins := sdk.Coins{sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 5*depositMultiplier))} newProposalMsg, err := types.NewMsgSubmitProposal(testProposal, proposalCoins, addrs[0], true) require.NoError(t, err) @@ -639,3 +645,13 @@ func TestEndBlockerProposalHandlerFailed(t *testing.T) { // validate that the proposal fails/has been rejected gov.EndBlocker(ctx, app.GovKeeper) } + +// With expedited proposal's minimum deposit set higher than the default deposit, we must +// initialize and deposit an amount depositMultiplier times larger +// than the regular min deposit amount. +func getDepositMultiplier(isExpedited bool) int64 { + if !isExpedited { + return 1 + } + return types.DefaultMinExpeditedDepositTokens.Quo(types.DefaultMinDepositTokens).Int64() +} diff --git a/x/gov/client/testutil/cli_test.go b/x/gov/client/testutil/cli_test.go index 60e0b7ce8d61..46252a20dafb 100644 --- a/x/gov/client/testutil/cli_test.go +++ b/x/gov/client/testutil/cli_test.go @@ -21,7 +21,7 @@ func TestIntegrationTestSuite(t *testing.T) { suite.Run(t, NewIntegrationTestSuite(cfg)) genesisState := types.DefaultGenesisState() - genesisState.DepositParams = types.NewDepositParams(sdk.NewCoins(sdk.NewCoin(cfg.BondDenom, types.DefaultMinDepositTokens)), time.Duration(15)*time.Second) + genesisState.DepositParams = types.NewDepositParams(sdk.NewCoins(sdk.NewCoin(cfg.BondDenom, types.DefaultMinDepositTokens)), time.Duration(15)*time.Second, sdk.NewCoins(sdk.NewCoin(cfg.BondDenom, types.DefaultMinExpeditedDepositTokens))) genesisState.VotingParams = types.NewVotingParams(time.Duration(5)*time.Second, time.Duration(2)*time.Second, []types.ProposalVotingPeriod{}) bz, err := cfg.Codec.MarshalJSON(genesisState) require.NoError(t, err) diff --git a/x/gov/client/testutil/suite.go b/x/gov/client/testutil/suite.go index ef3e4b38912e..2b7fe39f95d7 100644 --- a/x/gov/client/testutil/suite.go +++ b/x/gov/client/testutil/suite.go @@ -88,7 +88,7 @@ func (s *IntegrationTestSuite) TestCmdParams() { { "json output", []string{fmt.Sprintf("--%s=json", tmcli.OutputFlag)}, - `{"voting_params":{"voting_period":"172800000000000","proposal_voting_periods":null,"expedited_voting_period":"86400000000000"},"tally_params":{"quorum":"0.334000000000000000","threshold":"0.500000000000000000","veto_threshold":"0.334000000000000000","expedited_threshold":"0.667000000000000000"},"deposit_params":{"min_deposit":[{"denom":"stake","amount":"10000000"}],"max_deposit_period":"172800000000000"}}`, + `{"voting_params":{"voting_period":"172800000000000","proposal_voting_periods":null,"expedited_voting_period":"86400000000000"},"tally_params":{"quorum":"0.334000000000000000","threshold":"0.500000000000000000","veto_threshold":"0.334000000000000000","expedited_threshold":"0.667000000000000000"},"deposit_params":{"min_deposit":[{"denom":"stake","amount":"10000000"}],"max_deposit_period":"172800000000000","min_expedited_deposit":[{"denom":"stake","amount":"50000000"}]}}`, }, { "text output", @@ -99,6 +99,9 @@ deposit_params: min_deposit: - amount: "10000000" denom: stake + min_expedited_deposit: + - amount: "50000000" + denom: stake tally_params: expedited_threshold: "0.667000000000000000" quorum: "0.334000000000000000" @@ -156,7 +159,7 @@ func (s *IntegrationTestSuite) TestCmdParam() { "deposit", fmt.Sprintf("--%s=json", tmcli.OutputFlag), }, - `{"min_deposit":[{"denom":"stake","amount":"10000000"}],"max_deposit_period":"172800000000000"}`, + `{"min_deposit":[{"denom":"stake","amount":"10000000"}],"max_deposit_period":"172800000000000","min_expedited_deposit":[{"denom":"stake","amount":"50000000"}]}`, }, } diff --git a/x/gov/keeper/deposit.go b/x/gov/keeper/deposit.go index 9275fbff40dc..8f02e2dd0194 100644 --- a/x/gov/keeper/deposit.go +++ b/x/gov/keeper/deposit.go @@ -135,7 +135,8 @@ func (keeper Keeper) AddDeposit(ctx sdk.Context, proposalID uint64, depositorAdd // Check if deposit has provided sufficient total funds to transition the proposal into the voting period activatedVotingPeriod := false - if proposal.Status == types.StatusDepositPeriod && proposal.TotalDeposit.IsAllGTE(keeper.GetDepositParams(ctx).MinDeposit) { + minDepositAmount := proposal.GetMinDepositFromParams(keeper.GetDepositParams(ctx)) + if proposal.Status == types.StatusDepositPeriod && proposal.TotalDeposit.IsAllGTE(minDepositAmount) { keeper.ActivateVotingPeriod(ctx, proposal) activatedVotingPeriod = true diff --git a/x/gov/keeper/deposit_test.go b/x/gov/keeper/deposit_test.go index 9f2e5b92407e..fd5c7dc43afc 100644 --- a/x/gov/keeper/deposit_test.go +++ b/x/gov/keeper/deposit_test.go @@ -9,102 +9,124 @@ import ( "github.com/cosmos/cosmos-sdk/simapp" sdk "github.com/cosmos/cosmos-sdk/types" + "github.com/cosmos/cosmos-sdk/x/gov/types" ) func TestDeposits(t *testing.T) { - app := simapp.Setup(false) - ctx := app.BaseApp.NewContext(false, tmproto.Header{}) - - TestAddrs := simapp.AddTestAddrsIncremental(app, ctx, 2, sdk.NewInt(10000000)) - - tp := TestProposal - proposal, err := app.GovKeeper.SubmitProposal(ctx, tp, false) - require.NoError(t, err) - proposalID := proposal.ProposalId - - fourStake := sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 4))) - fiveStake := sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 5))) - - addr0Initial := app.BankKeeper.GetAllBalances(ctx, TestAddrs[0]) - addr1Initial := app.BankKeeper.GetAllBalances(ctx, TestAddrs[1]) - - require.True(t, proposal.TotalDeposit.IsEqual(sdk.NewCoins())) - - // Check no deposits at beginning - deposit, found := app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) - require.False(t, found) - proposal, ok := app.GovKeeper.GetProposal(ctx, proposalID) - require.True(t, ok) - require.True(t, proposal.VotingStartTime.Equal(time.Time{})) - - // Check first deposit - votingStarted, err := app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[0], fourStake) - require.NoError(t, err) - require.False(t, votingStarted) - deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[0]) - require.True(t, found) - require.Equal(t, fourStake, deposit.Amount) - require.Equal(t, TestAddrs[0].String(), deposit.Depositor) - proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) - require.True(t, ok) - require.Equal(t, fourStake, proposal.TotalDeposit) - require.Equal(t, addr0Initial.Sub(fourStake), app.BankKeeper.GetAllBalances(ctx, TestAddrs[0])) - - // Check a second deposit from same address - votingStarted, err = app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[0], fiveStake) - require.NoError(t, err) - require.False(t, votingStarted) - deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[0]) - require.True(t, found) - require.Equal(t, fourStake.Add(fiveStake...), deposit.Amount) - require.Equal(t, TestAddrs[0].String(), deposit.Depositor) - proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) - require.True(t, ok) - require.Equal(t, fourStake.Add(fiveStake...), proposal.TotalDeposit) - require.Equal(t, addr0Initial.Sub(fourStake).Sub(fiveStake), app.BankKeeper.GetAllBalances(ctx, TestAddrs[0])) - - // Check third deposit from a new address - votingStarted, err = app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[1], fourStake) - require.NoError(t, err) - require.True(t, votingStarted) - deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) - require.True(t, found) - require.Equal(t, TestAddrs[1].String(), deposit.Depositor) - require.Equal(t, fourStake, deposit.Amount) - proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) - require.True(t, ok) - require.Equal(t, fourStake.Add(fiveStake...).Add(fourStake...), proposal.TotalDeposit) - require.Equal(t, addr1Initial.Sub(fourStake), app.BankKeeper.GetAllBalances(ctx, TestAddrs[1])) - - // Check that proposal moved to voting period - proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) - require.True(t, ok) - require.True(t, proposal.VotingStartTime.Equal(ctx.BlockHeader().Time)) - - // Test deposit iterator - // NOTE order of deposits is determined by the addresses - deposits := app.GovKeeper.GetAllDeposits(ctx) - require.Len(t, deposits, 2) - require.Equal(t, deposits, app.GovKeeper.GetDeposits(ctx, proposalID)) - require.Equal(t, TestAddrs[0].String(), deposits[0].Depositor) - require.Equal(t, fourStake.Add(fiveStake...), deposits[0].Amount) - require.Equal(t, TestAddrs[1].String(), deposits[1].Depositor) - require.Equal(t, fourStake, deposits[1].Amount) - - // Test Refund Deposits - deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) - require.True(t, found) - require.Equal(t, fourStake, deposit.Amount) - app.GovKeeper.RefundDeposits(ctx, proposalID) - deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) - require.False(t, found) - require.Equal(t, addr0Initial, app.BankKeeper.GetAllBalances(ctx, TestAddrs[0])) - require.Equal(t, addr1Initial, app.BankKeeper.GetAllBalances(ctx, TestAddrs[1])) - - // Test delete deposits - _, err = app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[0], fourStake) - require.NoError(t, err) - app.GovKeeper.DeleteDeposits(ctx, proposalID) - deposits = app.GovKeeper.GetDeposits(ctx, proposalID) - require.Len(t, deposits, 0) + testcases := map[string]struct { + isExpedited bool + }{ + "regular": { + isExpedited: false, + }, + "expedited": { + isExpedited: true, + }, + } + + for _, tc := range testcases { + app := simapp.Setup(false) + ctx := app.BaseApp.NewContext(false, tmproto.Header{}) + + // With expedited proposals the minimum deposit is higer, so we must + // initialize and deposit an amount depositMultiplier times larger + // than the regular min deposit amount. + depositMultiplier := int64(1) + if tc.isExpedited { + depositMultiplier = types.DefaultMinExpeditedDepositTokens.Quo(types.DefaultMinDepositTokens).Int64() + } + + TestAddrs := simapp.AddTestAddrsIncremental(app, ctx, 2, sdk.NewInt(10000000*depositMultiplier)) + + tp := TestProposal + proposal, err := app.GovKeeper.SubmitProposal(ctx, tp, tc.isExpedited) + require.NoError(t, err) + proposalID := proposal.ProposalId + + firstDepositValue := sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 4*depositMultiplier))) + secondDepositValue := sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, app.StakingKeeper.TokensFromConsensusPower(ctx, 5*depositMultiplier))) + + addr0Initial := app.BankKeeper.GetAllBalances(ctx, TestAddrs[0]) + addr1Initial := app.BankKeeper.GetAllBalances(ctx, TestAddrs[1]) + + require.True(t, proposal.TotalDeposit.IsEqual(sdk.NewCoins())) + + // Check no deposits at beginning + deposit, found := app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) + require.False(t, found) + proposal, ok := app.GovKeeper.GetProposal(ctx, proposalID) + require.True(t, ok) + require.True(t, proposal.VotingStartTime.Equal(time.Time{})) + + // Check first deposit + votingStarted, err := app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[0], firstDepositValue) + require.NoError(t, err) + require.False(t, votingStarted) + deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[0]) + require.True(t, found) + require.Equal(t, firstDepositValue, deposit.Amount) + require.Equal(t, TestAddrs[0].String(), deposit.Depositor) + proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) + require.True(t, ok) + require.Equal(t, firstDepositValue, proposal.TotalDeposit) + require.Equal(t, addr0Initial.Sub(firstDepositValue), app.BankKeeper.GetAllBalances(ctx, TestAddrs[0])) + + // Check a second deposit from same address + votingStarted, err = app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[0], secondDepositValue) + require.NoError(t, err) + require.False(t, votingStarted) + deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[0]) + require.True(t, found) + require.Equal(t, firstDepositValue.Add(secondDepositValue...), deposit.Amount) + require.Equal(t, TestAddrs[0].String(), deposit.Depositor) + proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) + require.True(t, ok) + require.Equal(t, firstDepositValue.Add(secondDepositValue...), proposal.TotalDeposit) + require.Equal(t, addr0Initial.Sub(firstDepositValue).Sub(secondDepositValue), app.BankKeeper.GetAllBalances(ctx, TestAddrs[0])) + + // Check third deposit from a new address + votingStarted, err = app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[1], firstDepositValue) + require.NoError(t, err) + require.True(t, votingStarted) + deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) + require.True(t, found) + require.Equal(t, TestAddrs[1].String(), deposit.Depositor) + require.Equal(t, firstDepositValue, deposit.Amount) + proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) + require.True(t, ok) + require.Equal(t, firstDepositValue.Add(secondDepositValue...).Add(firstDepositValue...), proposal.TotalDeposit) + require.Equal(t, addr1Initial.Sub(firstDepositValue), app.BankKeeper.GetAllBalances(ctx, TestAddrs[1])) + + // Check that proposal moved to voting period + proposal, ok = app.GovKeeper.GetProposal(ctx, proposalID) + require.True(t, ok) + require.True(t, proposal.VotingStartTime.Equal(ctx.BlockHeader().Time)) + + // Test deposit iterator + // NOTE order of deposits is determined by the addresses + deposits := app.GovKeeper.GetAllDeposits(ctx) + require.Len(t, deposits, 2) + require.Equal(t, deposits, app.GovKeeper.GetDeposits(ctx, proposalID)) + require.Equal(t, TestAddrs[0].String(), deposits[0].Depositor) + require.Equal(t, firstDepositValue.Add(secondDepositValue...), deposits[0].Amount) + require.Equal(t, TestAddrs[1].String(), deposits[1].Depositor) + require.Equal(t, firstDepositValue, deposits[1].Amount) + + // Test Refund Deposits + deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) + require.True(t, found) + require.Equal(t, firstDepositValue, deposit.Amount) + app.GovKeeper.RefundDeposits(ctx, proposalID) + deposit, found = app.GovKeeper.GetDeposit(ctx, proposalID, TestAddrs[1]) + require.False(t, found) + require.Equal(t, addr0Initial, app.BankKeeper.GetAllBalances(ctx, TestAddrs[0])) + require.Equal(t, addr1Initial, app.BankKeeper.GetAllBalances(ctx, TestAddrs[1])) + + // Test delete deposits + _, err = app.GovKeeper.AddDeposit(ctx, proposalID, TestAddrs[0], firstDepositValue) + require.NoError(t, err) + app.GovKeeper.DeleteDeposits(ctx, proposalID) + deposits = app.GovKeeper.GetDeposits(ctx, proposalID) + require.Len(t, deposits, 0) + } } diff --git a/x/gov/legacy/v040/migrate_test.go b/x/gov/legacy/v040/migrate_test.go index 1ac128b133e8..9d9fb3263399 100644 --- a/x/gov/legacy/v040/migrate_test.go +++ b/x/gov/legacy/v040/migrate_test.go @@ -97,7 +97,8 @@ func TestMigrate(t *testing.T) { expected := `{ "deposit_params": { "max_deposit_period": "0s", - "min_deposit": [] + "min_deposit": [], + "min_expedited_deposit": [] }, "deposits": [], "proposals": [ diff --git a/x/gov/legacy/v043/json_test.go b/x/gov/legacy/v043/json_test.go index 6cdcb5b0e602..3e24b31aa2c1 100644 --- a/x/gov/legacy/v043/json_test.go +++ b/x/gov/legacy/v043/json_test.go @@ -50,7 +50,8 @@ func TestMigrateJSON(t *testing.T) { expected := `{ "deposit_params": { "max_deposit_period": "0s", - "min_deposit": [] + "min_deposit": [], + "min_expedited_deposit": [] }, "deposits": [], "proposals": [], diff --git a/x/gov/simulation/genesis.go b/x/gov/simulation/genesis.go index 7045f62b874b..b088376af2ad 100644 --- a/x/gov/simulation/genesis.go +++ b/x/gov/simulation/genesis.go @@ -17,6 +17,7 @@ import ( // Simulation parameter constants const ( DepositParamsMinDeposit = "deposit_params_min_deposit" + DepositParamsMinExpeditedDeposit = "deposit_params_min_expedited_deposit" DepositParamsDepositPeriod = "deposit_params_deposit_period" VotingParamsVotingPeriod = "voting_params_voting_period" ExpeditedVotingParamsVotingPeriod = "expedited_voting_params_voting_period" @@ -41,7 +42,12 @@ func GenDepositParamsDepositPeriod(r *rand.Rand) time.Duration { // GenDepositParamsMinDeposit randomized DepositParamsMinDeposit func GenDepositParamsMinDeposit(r *rand.Rand) sdk.Coins { - return sdk.NewCoins(sdk.NewInt64Coin(sdk.DefaultBondDenom, int64(simulation.RandIntBetween(r, 1, 1e3)))) + return sdk.NewCoins(sdk.NewInt64Coin(sdk.DefaultBondDenom, int64(simulation.RandIntBetween(r, 1, 1e3/2)))) +} + +// GenDepositParamsMinExpeditedDeposit randomized DepositParamsMinExpeditedDeposit +func GenDepositParamsMinExpeditedDeposit(r *rand.Rand) sdk.Coins { + return sdk.NewCoins(sdk.NewInt64Coin(sdk.DefaultBondDenom, int64(simulation.RandIntBetween(r, 1e3/2, 1e3)))) } // GenVotingParamsVotingPeriod randomized VotingParamsVotingPeriod @@ -84,6 +90,12 @@ func RandomizedGenState(simState *module.SimulationState) { func(r *rand.Rand) { minDeposit = GenDepositParamsMinDeposit(r) }, ) + var minExpeditedDeposit sdk.Coins + simState.AppParams.GetOrGenerate( + simState.Cdc, DepositParamsMinExpeditedDeposit, &minExpeditedDeposit, simState.Rand, + func(r *rand.Rand) { minExpeditedDeposit = GenDepositParamsMinExpeditedDeposit(r) }, + ) + var depositPeriod time.Duration simState.AppParams.GetOrGenerate( simState.Cdc, DepositParamsDepositPeriod, &depositPeriod, simState.Rand, @@ -143,7 +155,7 @@ func RandomizedGenState(simState *module.SimulationState) { govGenesis := types.NewGenesisState( startingProposalID, - types.NewDepositParams(minDeposit, depositPeriod), + types.NewDepositParams(minDeposit, depositPeriod, minExpeditedDeposit), types.NewVotingParams(votingPeriod, expeditedVotingPeriod, proposalVotingPeriods), types.NewTallyParams(quorum, threshold, expeditedThreshold, veto), ) diff --git a/x/gov/simulation/genesis_test.go b/x/gov/simulation/genesis_test.go index 0d41fde63be3..98897defb45f 100644 --- a/x/gov/simulation/genesis_test.go +++ b/x/gov/simulation/genesis_test.go @@ -40,15 +40,16 @@ func TestRandomizedGenState(t *testing.T) { var govGenesis types.GenesisState simState.Cdc.MustUnmarshalJSON(simState.GenState[types.ModuleName], &govGenesis) - dec1, _ := sdk.NewDecFromStr("0.400000000000000000") - dec2, _ := sdk.NewDecFromStr("0.458000000000000000") - dec3, _ := sdk.NewDecFromStr("0.528000000000000000") - dec4, _ := sdk.NewDecFromStr("0.324000000000000000") + dec1, _ := sdk.NewDecFromStr("0.375000000000000000") + dec2, _ := sdk.NewDecFromStr("0.487000000000000000") + dec3, _ := sdk.NewDecFromStr("0.524000000000000000") + dec4, _ := sdk.NewDecFromStr("0.313000000000000000") - require.Equal(t, "905stake", govGenesis.DepositParams.MinDeposit.String()) - require.Equal(t, "77h26m10s", govGenesis.DepositParams.MaxDepositPeriod.String()) - require.Equal(t, float64(317894), govGenesis.VotingParams.VotingPeriod.Seconds()) - require.Equal(t, float64(107823), govGenesis.VotingParams.ExpeditedVotingPeriod.Seconds()) + require.Equal(t, "272stake", govGenesis.DepositParams.MinDeposit.String()) + require.Equal(t, "41h11m36s", govGenesis.DepositParams.MaxDepositPeriod.String()) + require.Equal(t, "800stake", govGenesis.DepositParams.MinExpeditedDeposit.String()) + require.Equal(t, float64(270511), govGenesis.VotingParams.VotingPeriod.Seconds()) + require.Equal(t, float64(137225), govGenesis.VotingParams.ExpeditedVotingPeriod.Seconds()) require.Equal(t, dec1, govGenesis.TallyParams.Quorum) require.Equal(t, dec2, govGenesis.TallyParams.Threshold) require.Equal(t, dec3, govGenesis.TallyParams.ExpeditedThreshold) diff --git a/x/gov/types/genesis.go b/x/gov/types/genesis.go index 84fed2e13f87..f703863736c8 100644 --- a/x/gov/types/genesis.go +++ b/x/gov/types/genesis.go @@ -68,9 +68,22 @@ func ValidateGenesis(data *GenesisState) error { veto.String()) } - if !data.DepositParams.MinDeposit.IsValid() { + minDeposit := data.DepositParams.MinDeposit + if !minDeposit.IsValid() { return fmt.Errorf("governance deposit amount must be a valid sdk.Coins amount, is %s", - data.DepositParams.MinDeposit.String()) + minDeposit.String()) + } + + minExpeditedDeposit := data.DepositParams.MinExpeditedDeposit + if !minExpeditedDeposit.IsValid() { + return fmt.Errorf("governance expedited deposit amount must be a valid sdk.Coins amount, is %s", + minExpeditedDeposit.String()) + } + + if minExpeditedDeposit.IsAllLTE(minDeposit) { + return fmt.Errorf("governance min expedited deposit amount %s must be greater than regular min deposit %s", + minExpeditedDeposit.String(), + minDeposit.String()) } return nil diff --git a/x/gov/types/gov.pb.go b/x/gov/types/gov.pb.go index 5e32466a4acb..15af097a9c2b 100644 --- a/x/gov/types/gov.pb.go +++ b/x/gov/types/gov.pb.go @@ -378,6 +378,8 @@ type DepositParams struct { // Maximum period for Atom holders to deposit on a proposal. Initial value: 2 // months. MaxDepositPeriod time.Duration `protobuf:"bytes,2,opt,name=max_deposit_period,json=maxDepositPeriod,proto3,stdduration" json:"max_deposit_period,omitempty" yaml:"max_deposit_period"` + // Minimum expedited deposit for a proposal to enter voting period. + MinExpeditedDeposit github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,3,rep,name=min_expedited_deposit,json=minExpeditedDeposit,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"min_expedited_deposit,omitempty" yaml:"min_expedited_deposit"` } func (m *DepositParams) Reset() { *m = DepositParams{} } @@ -418,7 +420,7 @@ type VotingParams struct { VotingPeriod time.Duration `protobuf:"bytes,1,opt,name=voting_period,json=votingPeriod,proto3,stdduration" json:"voting_period,omitempty" yaml:"voting_period"` // proposal_voting_periods defines custom voting periods for proposal types. ProposalVotingPeriods []ProposalVotingPeriod `protobuf:"bytes,2,rep,name=proposal_voting_periods,json=proposalVotingPeriods,proto3" json:"proposal_voting_periods"` - // Length of the expedited voting period. + // Length of the expedited voting period. ExpeditedVotingPeriod time.Duration `protobuf:"bytes,3,opt,name=expedited_voting_period,json=expeditedVotingPeriod,proto3,stdduration" json:"expedited_voting_period,omitempty" yaml:"expedited_voting_period"` } @@ -557,107 +559,110 @@ func init() { func init() { proto.RegisterFile("cosmos/gov/v1beta1/gov.proto", fileDescriptor_6e82113c1a9a4b7c) } var fileDescriptor_6e82113c1a9a4b7c = []byte{ - // 1597 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x58, 0xcd, 0x6f, 0x1a, 0xd7, - 0x16, 0x67, 0x00, 0x7f, 0x70, 0x01, 0x9b, 0x5c, 0x63, 0x1b, 0xf3, 0x92, 0x19, 0x32, 0x79, 0x8a, - 0xac, 0x28, 0xc1, 0x89, 0xdf, 0xd3, 0x7b, 0x7a, 0x8e, 0xf4, 0xde, 0x03, 0x33, 0x7e, 0xe1, 0x29, - 0x02, 0x34, 0x10, 0xac, 0xe4, 0x2d, 0x46, 0x63, 0xb8, 0xc6, 0xf3, 0x0a, 0x73, 0x29, 0x73, 0x71, - 0x8c, 0xba, 0xc9, 0x32, 0x62, 0x51, 0x65, 0x99, 0xaa, 0x42, 0x8a, 0x5a, 0x75, 0xd3, 0x75, 0x17, - 0x5d, 0x75, 0x6d, 0x55, 0x95, 0x1a, 0x75, 0x15, 0x75, 0x41, 0x1a, 0x5b, 0xaa, 0x22, 0x2f, 0xfd, - 0x17, 0x54, 0x33, 0xf7, 0x0e, 0xcc, 0x00, 0x89, 0x43, 0x17, 0x5d, 0x79, 0xe6, 0x9c, 0xf3, 0xfb, - 0x9d, 0x8f, 0x7b, 0xce, 0xb9, 0x63, 0xc0, 0xe5, 0x0a, 0x36, 0x1a, 0xd8, 0xd8, 0xa8, 0xe1, 0xc3, - 0x8d, 0xc3, 0x3b, 0x7b, 0x88, 0xa8, 0x77, 0xcc, 0xe7, 0x64, 0xb3, 0x85, 0x09, 0x86, 0x90, 0x6a, - 0x93, 0xa6, 0x84, 0x69, 0xe3, 0x3c, 0x43, 0xec, 0xa9, 0x06, 0x1a, 0x40, 0x2a, 0x58, 0xd3, 0x29, - 0x26, 0x1e, 0xad, 0xe1, 0x1a, 0xb6, 0x1e, 0x37, 0xcc, 0x27, 0x26, 0x5d, 0xa3, 0x28, 0x85, 0x2a, - 0x18, 0x2d, 0x55, 0x09, 0x35, 0x8c, 0x6b, 0x75, 0xb4, 0x61, 0xbd, 0xed, 0xb5, 0xf7, 0x37, 0x88, - 0xd6, 0x40, 0x06, 0x51, 0x1b, 0x4d, 0x1b, 0x3b, 0x6a, 0xa0, 0xea, 0x1d, 0xa6, 0xe2, 0x47, 0x55, - 0xd5, 0x76, 0x4b, 0x25, 0x1a, 0x66, 0xc1, 0x88, 0x5f, 0x71, 0x00, 0xee, 0x22, 0xad, 0x76, 0x40, - 0x50, 0xb5, 0x8c, 0x09, 0xca, 0x37, 0x4d, 0x25, 0xfc, 0x1b, 0x98, 0xc5, 0xd6, 0x53, 0x8c, 0x4b, - 0x70, 0xeb, 0x0b, 0x9b, 0x7c, 0x72, 0x3c, 0xd1, 0xe4, 0xd0, 0x5e, 0x66, 0xd6, 0x70, 0x17, 0xcc, - 0x3e, 0xb6, 0xd8, 0x62, 0xde, 0x04, 0xb7, 0x1e, 0x48, 0xff, 0xeb, 0xb8, 0x2f, 0x78, 0x7e, 0xee, - 0x0b, 0xd7, 0x6b, 0x1a, 0x39, 0x68, 0xef, 0x25, 0x2b, 0xb8, 0xc1, 0x72, 0x63, 0x7f, 0x6e, 0x19, - 0xd5, 0x8f, 0x36, 0x48, 0xa7, 0x89, 0x8c, 0x64, 0x06, 0x55, 0xce, 0xfb, 0x42, 0xb8, 0xa3, 0x36, - 0xea, 0x5b, 0x22, 0x65, 0x11, 0x65, 0x46, 0x27, 0xee, 0x82, 0x50, 0x09, 0x1d, 0x91, 0x42, 0x0b, - 0x37, 0xb1, 0xa1, 0xd6, 0x61, 0x14, 0xcc, 0x10, 0x8d, 0xd4, 0x91, 0x15, 0x5f, 0x40, 0xa6, 0x2f, - 0x30, 0x01, 0x82, 0x55, 0x64, 0x54, 0x5a, 0x1a, 0x8d, 0xdd, 0x8a, 0x41, 0x76, 0x8a, 0xb6, 0x16, - 0xdf, 0xbe, 0x10, 0xb8, 0x9f, 0xbe, 0xb9, 0x35, 0xb7, 0x8d, 0x75, 0x82, 0x74, 0x22, 0xfe, 0xc8, - 0x81, 0xb9, 0x0c, 0x6a, 0x62, 0x43, 0x23, 0xf0, 0xef, 0x20, 0xd8, 0x64, 0x0e, 0x14, 0xad, 0x6a, - 0x51, 0xfb, 0xd3, 0x2b, 0xe7, 0x7d, 0x01, 0xd2, 0xa0, 0x1c, 0x4a, 0x51, 0x06, 0xf6, 0x5b, 0xb6, - 0x0a, 0x2f, 0x83, 0x40, 0x95, 0x72, 0xe0, 0x16, 0xf3, 0x3a, 0x14, 0xc0, 0x0a, 0x98, 0x55, 0x1b, - 0xb8, 0xad, 0x93, 0x98, 0x2f, 0xe1, 0x5b, 0x0f, 0x6e, 0xae, 0xd9, 0xc5, 0x34, 0x3b, 0x64, 0x50, - 0xcd, 0x6d, 0xac, 0xe9, 0xe9, 0xdb, 0x66, 0xbd, 0xbe, 0x7e, 0x2d, 0xac, 0x7f, 0x40, 0xbd, 0x4c, - 0x80, 0x21, 0x33, 0xea, 0xad, 0xf9, 0xa7, 0x2f, 0x04, 0xcf, 0xdb, 0x17, 0x82, 0x47, 0xfc, 0x6c, - 0x0e, 0xcc, 0x0f, 0xea, 0xf4, 0xd7, 0x49, 0x29, 0x2d, 0x9d, 0xf5, 0x05, 0xaf, 0x56, 0x3d, 0xef, - 0x0b, 0x01, 0x9a, 0xd8, 0x68, 0x3e, 0x77, 0xc1, 0x5c, 0x85, 0xd6, 0xc7, 0xca, 0x26, 0xb8, 0x19, - 0x4d, 0xd2, 0x3e, 0x4a, 0xda, 0x7d, 0x94, 0x4c, 0xe9, 0x9d, 0x74, 0xf0, 0xfb, 0x61, 0x21, 0x65, - 0x1b, 0x01, 0xcb, 0x60, 0xd6, 0x20, 0x2a, 0x69, 0x1b, 0x31, 0x9f, 0xd5, 0x3b, 0xe2, 0xa4, 0xde, - 0xb1, 0x03, 0x2c, 0x5a, 0x96, 0xe9, 0xf8, 0x79, 0x5f, 0x58, 0x19, 0x29, 0x32, 0x25, 0x11, 0x65, - 0xc6, 0x06, 0x9b, 0x00, 0xee, 0x6b, 0xba, 0x5a, 0x57, 0x88, 0x5a, 0xaf, 0x77, 0x94, 0x16, 0x32, - 0xda, 0x75, 0x12, 0xf3, 0x5b, 0xf1, 0x09, 0x93, 0x7c, 0x94, 0x4c, 0x3b, 0xd9, 0x32, 0x4b, 0x5f, - 0x35, 0x0b, 0x7b, 0xde, 0x17, 0xd6, 0xa8, 0x93, 0x71, 0x22, 0x51, 0x8e, 0x58, 0x42, 0x07, 0x08, - 0xfe, 0x0f, 0x04, 0x8d, 0xf6, 0x5e, 0x43, 0x23, 0x8a, 0x39, 0x71, 0xb1, 0x19, 0xcb, 0x55, 0x7c, - 0xac, 0x14, 0x25, 0x7b, 0x1c, 0xd3, 0x3c, 0xf3, 0xc2, 0xfa, 0xc5, 0x01, 0x16, 0x9f, 0xbd, 0x16, - 0x38, 0x19, 0x50, 0x89, 0x09, 0x80, 0x1a, 0x88, 0xb0, 0x16, 0x51, 0x90, 0x5e, 0xa5, 0x1e, 0x66, - 0x2f, 0xf4, 0x70, 0x8d, 0x79, 0x58, 0xa5, 0x1e, 0x46, 0x19, 0xa8, 0x9b, 0x05, 0x26, 0x96, 0xf4, - 0xaa, 0xe5, 0xea, 0x29, 0x07, 0xc2, 0x04, 0x13, 0xb5, 0xae, 0x30, 0x45, 0x6c, 0xee, 0xa2, 0x46, - 0xbc, 0xc7, 0xfc, 0x44, 0xa9, 0x1f, 0x17, 0x5a, 0x9c, 0xaa, 0x41, 0x43, 0x16, 0xd6, 0x1e, 0xb1, - 0x3a, 0xb8, 0x74, 0x88, 0x89, 0xa6, 0xd7, 0xcc, 0xe3, 0x6d, 0xb1, 0xc2, 0xce, 0x5f, 0x98, 0xf6, - 0x9f, 0x59, 0x38, 0x31, 0x1a, 0xce, 0x18, 0x05, 0xcd, 0x7b, 0x91, 0xca, 0x8b, 0xa6, 0xd8, 0x4a, - 0x7c, 0x1f, 0x30, 0xd1, 0xb0, 0xc4, 0x81, 0x0b, 0x7d, 0x89, 0xcc, 0xd7, 0x8a, 0xcb, 0x97, 0xbb, - 0xc2, 0x61, 0x2a, 0xb5, 0x0b, 0x7c, 0x15, 0x84, 0x34, 0x43, 0x41, 0x47, 0x4d, 0x54, 0xd5, 0x08, - 0xaa, 0xc6, 0x40, 0x82, 0x5b, 0x9f, 0x97, 0x83, 0x9a, 0x21, 0xd9, 0xa2, 0x2d, 0xbf, 0xb9, 0x78, - 0xc4, 0x63, 0x2f, 0x08, 0x3a, 0x3b, 0xec, 0xdf, 0xc0, 0xd7, 0x41, 0x06, 0x5d, 0x62, 0xe9, 0xe4, - 0x14, 0xcb, 0x32, 0xab, 0x13, 0xd9, 0x84, 0xc2, 0x7b, 0x60, 0x4e, 0xdd, 0x33, 0x88, 0xaa, 0xb1, - 0x75, 0x37, 0x35, 0x8b, 0x0d, 0x87, 0xff, 0x04, 0x5e, 0x1d, 0x5b, 0x33, 0x3b, 0x3d, 0x89, 0x57, - 0xc7, 0xb0, 0x06, 0x42, 0x3a, 0x56, 0x1e, 0x6b, 0xe4, 0x40, 0x39, 0x44, 0x04, 0x5b, 0x93, 0x19, - 0x48, 0x4b, 0xd3, 0x31, 0x9d, 0xf7, 0x85, 0x25, 0x5a, 0x77, 0x27, 0x97, 0x28, 0x03, 0x1d, 0xef, - 0x6a, 0xe4, 0xa0, 0x8c, 0x08, 0x66, 0xa5, 0x3c, 0xe5, 0x80, 0xdf, 0xbc, 0x81, 0x7e, 0xff, 0xd6, - 0x8e, 0x82, 0x99, 0x43, 0x4c, 0x90, 0xbd, 0xb1, 0xe9, 0x0b, 0xdc, 0x1a, 0x5c, 0x7d, 0xbe, 0x0f, - 0xb9, 0xfa, 0xd2, 0xde, 0x18, 0x37, 0xb8, 0xfe, 0x76, 0xc0, 0x1c, 0x7d, 0x32, 0x62, 0x7e, 0x6b, - 0xc2, 0xae, 0x4f, 0x02, 0x8f, 0xdf, 0xb7, 0x69, 0xbf, 0x59, 0x25, 0xd9, 0x06, 0x6f, 0xcd, 0x3f, - 0xb7, 0x97, 0xf9, 0x77, 0x5e, 0x10, 0x66, 0xb3, 0x53, 0x50, 0x5b, 0x6a, 0xc3, 0x80, 0x9f, 0x73, - 0x20, 0xd8, 0xd0, 0xf4, 0xc1, 0x28, 0x73, 0x17, 0x8d, 0xb2, 0x62, 0x72, 0x9f, 0xf5, 0x85, 0x65, - 0x07, 0xea, 0x26, 0x6e, 0x68, 0x04, 0x35, 0x9a, 0xa4, 0x33, 0xac, 0x93, 0x43, 0x3d, 0xdd, 0x84, - 0x83, 0x86, 0xa6, 0xdb, 0xf3, 0xfd, 0x29, 0x07, 0x60, 0x43, 0x3d, 0xb2, 0x89, 0x94, 0x26, 0x6a, - 0x69, 0xb8, 0xca, 0x6e, 0x91, 0xb5, 0xb1, 0xa9, 0xcb, 0xb0, 0xaf, 0x11, 0xda, 0x26, 0x67, 0x7d, - 0xe1, 0xf2, 0x38, 0xd8, 0x15, 0x2b, 0xdb, 0xdf, 0xe3, 0x56, 0xe2, 0x73, 0x73, 0x2e, 0x23, 0x0d, - 0xf5, 0xc8, 0x2e, 0x17, 0x13, 0xfb, 0x40, 0xa8, 0x6c, 0x0d, 0x2b, 0xab, 0xdf, 0x27, 0x80, 0x0d, - 0xaf, 0x1d, 0x1b, 0x77, 0x51, 0x6c, 0x77, 0x59, 0x6c, 0xab, 0x2e, 0x9c, 0x2b, 0xac, 0xa8, 0x6b, - 0x57, 0x38, 0x23, 0x0a, 0x51, 0x19, 0x8d, 0x06, 0xee, 0x83, 0xd5, 0x41, 0x3b, 0xba, 0x8c, 0x8d, - 0x98, 0xd7, 0x3a, 0xc7, 0xf5, 0xf7, 0x5d, 0x96, 0x65, 0x07, 0x15, 0x6b, 0x99, 0xe5, 0xe6, 0x04, - 0x9d, 0x01, 0xbf, 0xe0, 0xc0, 0xea, 0x60, 0x1d, 0xb9, 0x3d, 0x59, 0x6d, 0xfd, 0xde, 0x7c, 0xf3, - 0x2c, 0xdf, 0xab, 0xef, 0x60, 0x70, 0x65, 0xce, 0xd3, 0xcc, 0xdf, 0x61, 0x4a, 0x6b, 0xb0, 0x3c, - 0xd0, 0x3a, 0xa3, 0x14, 0xfb, 0x3e, 0xb6, 0x0c, 0xd9, 0xc9, 0x3c, 0x02, 0xb3, 0x1f, 0xb7, 0x71, - 0xab, 0xdd, 0xb0, 0x8e, 0x24, 0x94, 0x4e, 0x4f, 0xf7, 0xf1, 0x78, 0xd6, 0x17, 0x22, 0x14, 0x3f, - 0x0c, 0x50, 0x66, 0x8c, 0xb0, 0x02, 0x02, 0xe4, 0xa0, 0x85, 0x8c, 0x03, 0x5c, 0xa7, 0xdd, 0x18, - 0x9a, 0x6a, 0x33, 0x51, 0xfa, 0xa5, 0x01, 0x85, 0xc3, 0xc3, 0x90, 0x17, 0x76, 0x39, 0xb0, 0x60, - 0xae, 0x2b, 0x65, 0xe8, 0xca, 0x67, 0xb9, 0xaa, 0x4c, 0xed, 0x2a, 0xe6, 0xe6, 0x71, 0x95, 0x7c, - 0x99, 0x35, 0x9b, 0xcb, 0x42, 0x94, 0xc3, 0xa6, 0xa0, 0x34, 0x08, 0xe6, 0x09, 0x07, 0x96, 0x86, - 0xa7, 0x32, 0x8c, 0xc8, 0x6f, 0x45, 0x94, 0x9f, 0x3a, 0xa2, 0x2b, 0x13, 0xc8, 0x1c, 0x65, 0x80, - 0x03, 0xf5, 0x20, 0x04, 0xf1, 0x5b, 0x0e, 0x44, 0x27, 0xf5, 0x2e, 0xbc, 0x06, 0xc2, 0x83, 0x31, - 0x30, 0x7d, 0xb0, 0xaf, 0xf8, 0x90, 0x2d, 0x2c, 0x75, 0x9a, 0x68, 0x7c, 0x50, 0xbd, 0x7f, 0xdc, - 0xa0, 0xde, 0xf8, 0x95, 0x03, 0xc0, 0xf1, 0xff, 0xd0, 0x4d, 0xb0, 0x5a, 0xce, 0x97, 0x24, 0x25, - 0x5f, 0x28, 0x65, 0xf3, 0x39, 0xe5, 0x41, 0xae, 0x58, 0x90, 0xb6, 0xb3, 0x3b, 0x59, 0x29, 0x13, - 0xf1, 0xc4, 0x17, 0xbb, 0xbd, 0x44, 0x90, 0x1a, 0x4a, 0xa6, 0x1b, 0x28, 0x82, 0x45, 0xa7, 0xf5, - 0x43, 0xa9, 0x18, 0xe1, 0xe2, 0xe1, 0x6e, 0x2f, 0x11, 0xa0, 0x56, 0x0f, 0x91, 0x01, 0x6f, 0x80, - 0x25, 0xa7, 0x4d, 0x2a, 0x5d, 0x2c, 0xa5, 0xb2, 0xb9, 0x88, 0x37, 0x7e, 0xa9, 0xdb, 0x4b, 0x84, - 0xa9, 0x5d, 0x8a, 0xdd, 0xcc, 0x09, 0xb0, 0xe0, 0xb4, 0xcd, 0xe5, 0x23, 0xbe, 0x78, 0xa8, 0xdb, - 0x4b, 0xcc, 0x53, 0xb3, 0x1c, 0x86, 0x9b, 0x20, 0xe6, 0xb6, 0x50, 0x76, 0xb3, 0xa5, 0x7b, 0x4a, - 0x59, 0x2a, 0xe5, 0x23, 0xfe, 0x78, 0xb4, 0xdb, 0x4b, 0x44, 0x6c, 0x5b, 0xfb, 0x1a, 0x8d, 0xfb, - 0x9f, 0x7e, 0xc9, 0x7b, 0x6e, 0xfc, 0xe0, 0x05, 0x0b, 0xee, 0x8f, 0x71, 0x98, 0x04, 0x7f, 0x2a, - 0xc8, 0xf9, 0x42, 0xbe, 0x98, 0xba, 0xaf, 0x14, 0x4b, 0xa9, 0xd2, 0x83, 0xe2, 0x48, 0xc2, 0x56, - 0x2a, 0xd4, 0x38, 0xa7, 0xd5, 0xe1, 0x5d, 0xc0, 0x8f, 0xda, 0x67, 0xa4, 0x42, 0xbe, 0x98, 0x2d, - 0x29, 0x05, 0x49, 0xce, 0xe6, 0x33, 0x11, 0x2e, 0xbe, 0xda, 0xed, 0x25, 0x96, 0x28, 0xc4, 0xb5, - 0x9f, 0xe1, 0x3f, 0xc0, 0x95, 0x51, 0x70, 0x39, 0x5f, 0xca, 0xe6, 0xfe, 0x63, 0x63, 0xbd, 0xf1, - 0x95, 0x6e, 0x2f, 0x01, 0x29, 0xd6, 0xd5, 0x45, 0x37, 0xc1, 0xca, 0x28, 0xb4, 0x90, 0x2a, 0x16, - 0xa5, 0x4c, 0xc4, 0x17, 0x8f, 0x74, 0x7b, 0x89, 0x10, 0xc5, 0x14, 0x54, 0xc3, 0x40, 0x55, 0x78, - 0x1b, 0xc4, 0x46, 0xad, 0x65, 0xe9, 0xbf, 0xd2, 0x76, 0x49, 0xca, 0x44, 0xfc, 0x71, 0xd8, 0xed, - 0x25, 0x16, 0xa8, 0xbd, 0x8c, 0xfe, 0x8f, 0x2a, 0x04, 0x4d, 0xe4, 0xdf, 0x49, 0x65, 0xef, 0x4b, - 0x99, 0xc8, 0x8c, 0x93, 0x7f, 0x47, 0xd5, 0xea, 0xa8, 0x4a, 0xcb, 0x99, 0xce, 0x1d, 0xbf, 0xe1, - 0x3d, 0xaf, 0xde, 0xf0, 0x9e, 0x27, 0x27, 0xbc, 0xe7, 0xf8, 0x84, 0xe7, 0x5e, 0x9e, 0xf0, 0xdc, - 0x2f, 0x27, 0x3c, 0xf7, 0xec, 0x94, 0xf7, 0xbc, 0x3c, 0xe5, 0x3d, 0xaf, 0x4e, 0x79, 0xcf, 0xa3, - 0xf7, 0xdf, 0xad, 0x47, 0xd6, 0x8f, 0x0d, 0xd6, 0xec, 0xed, 0xcd, 0x5a, 0x5d, 0xfe, 0x97, 0xdf, - 0x02, 0x00, 0x00, 0xff, 0xff, 0x88, 0x57, 0xc4, 0xb1, 0x87, 0x10, 0x00, 0x00, + // 1634 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x58, 0xcf, 0x6f, 0xe2, 0xda, + 0x15, 0xc6, 0x40, 0x7e, 0x70, 0x81, 0x84, 0x77, 0x43, 0x12, 0x42, 0xf3, 0x6c, 0xc6, 0xaf, 0x7a, + 0x8a, 0x46, 0xf3, 0xc8, 0x7b, 0x69, 0xd5, 0xaa, 0x19, 0xa9, 0x2d, 0x04, 0xa7, 0x43, 0xf5, 0x04, + 0xc8, 0xf0, 0x88, 0xde, 0xeb, 0xc2, 0x72, 0xe0, 0x86, 0xb8, 0xc5, 0xbe, 0x14, 0x5f, 0x32, 0x41, + 0xdd, 0x8c, 0xd4, 0xcd, 0x88, 0x45, 0x35, 0xcb, 0xa9, 0x2a, 0xa4, 0x51, 0xab, 0x6e, 0xba, 0xee, + 0xa2, 0xeb, 0xae, 0xa2, 0xaa, 0x52, 0x47, 0x5d, 0x8d, 0xba, 0x60, 0x3a, 0x89, 0x54, 0x8d, 0xb2, + 0xcc, 0x5f, 0x50, 0xd9, 0xf7, 0xda, 0xd8, 0xc0, 0x0c, 0x43, 0x17, 0x5d, 0xc5, 0x9c, 0x7b, 0xbe, + 0xef, 0x9c, 0xf3, 0x71, 0xce, 0xb9, 0x26, 0x60, 0xb7, 0x81, 0x4d, 0x1d, 0x9b, 0xfb, 0x2d, 0x7c, + 0xb1, 0x7f, 0xf1, 0xc5, 0x29, 0x22, 0xea, 0x17, 0xd6, 0x73, 0xb6, 0xd3, 0xc5, 0x04, 0x43, 0x48, + 0x4f, 0xb3, 0x96, 0x85, 0x9d, 0xa6, 0x79, 0x86, 0x38, 0x55, 0x4d, 0xe4, 0x42, 0x1a, 0x58, 0x33, + 0x28, 0x26, 0x9d, 0x6c, 0xe1, 0x16, 0xb6, 0x1f, 0xf7, 0xad, 0x27, 0x66, 0xdd, 0xa1, 0x28, 0x85, + 0x1e, 0x30, 0x5a, 0x7a, 0x24, 0xb4, 0x30, 0x6e, 0xb5, 0xd1, 0xbe, 0xfd, 0xe9, 0xb4, 0x77, 0xb6, + 0x4f, 0x34, 0x1d, 0x99, 0x44, 0xd5, 0x3b, 0x0e, 0x76, 0xd2, 0x41, 0x35, 0xfa, 0xec, 0x88, 0x9f, + 0x3c, 0x6a, 0xf6, 0xba, 0x2a, 0xd1, 0x30, 0x4b, 0x46, 0xfc, 0x23, 0x07, 0xe0, 0x09, 0xd2, 0x5a, + 0xe7, 0x04, 0x35, 0xeb, 0x98, 0xa0, 0x72, 0xc7, 0x3a, 0x84, 0xdf, 0x03, 0xcb, 0xd8, 0x7e, 0x4a, + 0x71, 0x19, 0x6e, 0x6f, 0xed, 0x80, 0xcf, 0x4e, 0x17, 0x9a, 0x1d, 0xfb, 0xcb, 0xcc, 0x1b, 0x9e, + 0x80, 0xe5, 0xc7, 0x36, 0x5b, 0x2a, 0x98, 0xe1, 0xf6, 0x22, 0xf9, 0x1f, 0x5d, 0x8d, 0x84, 0xc0, + 0xbf, 0x46, 0xc2, 0xa7, 0x2d, 0x8d, 0x9c, 0xf7, 0x4e, 0xb3, 0x0d, 0xac, 0xb3, 0xda, 0xd8, 0x9f, + 0xcf, 0xcc, 0xe6, 0x2f, 0xf6, 0x49, 0xbf, 0x83, 0xcc, 0x6c, 0x01, 0x35, 0xee, 0x46, 0x42, 0xbc, + 0xaf, 0xea, 0xed, 0x43, 0x91, 0xb2, 0x88, 0x32, 0xa3, 0x13, 0x4f, 0x40, 0xac, 0x86, 0x2e, 0x49, + 0xa5, 0x8b, 0x3b, 0xd8, 0x54, 0xdb, 0x30, 0x09, 0x96, 0x88, 0x46, 0xda, 0xc8, 0xce, 0x2f, 0x22, + 0xd3, 0x0f, 0x30, 0x03, 0xa2, 0x4d, 0x64, 0x36, 0xba, 0x1a, 0xcd, 0xdd, 0xce, 0x41, 0xf6, 0x9a, + 0x0e, 0xd7, 0xdf, 0xbe, 0x10, 0xb8, 0x7f, 0xfe, 0xf9, 0xb3, 0x95, 0x23, 0x6c, 0x10, 0x64, 0x10, + 0xf1, 0x1f, 0x1c, 0x58, 0x29, 0xa0, 0x0e, 0x36, 0x35, 0x02, 0xbf, 0x0f, 0xa2, 0x1d, 0x16, 0x40, + 0xd1, 0x9a, 0x36, 0x75, 0x38, 0xbf, 0x75, 0x37, 0x12, 0x20, 0x4d, 0xca, 0x73, 0x28, 0xca, 0xc0, + 0xf9, 0x54, 0x6c, 0xc2, 0x5d, 0x10, 0x69, 0x52, 0x0e, 0xdc, 0x65, 0x51, 0xc7, 0x06, 0xd8, 0x00, + 0xcb, 0xaa, 0x8e, 0x7b, 0x06, 0x49, 0x85, 0x32, 0xa1, 0xbd, 0xe8, 0xc1, 0x8e, 0x23, 0xa6, 0xd5, + 0x21, 0xae, 0x9a, 0x47, 0x58, 0x33, 0xf2, 0x9f, 0x5b, 0x7a, 0xfd, 0xe9, 0xb5, 0xb0, 0xf7, 0x01, + 0x7a, 0x59, 0x00, 0x53, 0x66, 0xd4, 0x87, 0xab, 0x4f, 0x5f, 0x08, 0x81, 0xb7, 0x2f, 0x84, 0x80, + 0xf8, 0xdb, 0x15, 0xb0, 0xea, 0xea, 0xf4, 0xdd, 0x59, 0x25, 0x6d, 0xdc, 0x8e, 0x84, 0xa0, 0xd6, + 0xbc, 0x1b, 0x09, 0x11, 0x5a, 0xd8, 0x64, 0x3d, 0x0f, 0xc1, 0x4a, 0x83, 0xea, 0x63, 0x57, 0x13, + 0x3d, 0x48, 0x66, 0x69, 0x1f, 0x65, 0x9d, 0x3e, 0xca, 0xe6, 0x8c, 0x7e, 0x3e, 0xfa, 0xb7, 0xb1, + 0x90, 0xb2, 0x83, 0x80, 0x75, 0xb0, 0x6c, 0x12, 0x95, 0xf4, 0xcc, 0x54, 0xc8, 0xee, 0x1d, 0x71, + 0x56, 0xef, 0x38, 0x09, 0x56, 0x6d, 0xcf, 0x7c, 0xfa, 0x6e, 0x24, 0x6c, 0x4d, 0x88, 0x4c, 0x49, + 0x44, 0x99, 0xb1, 0xc1, 0x0e, 0x80, 0x67, 0x9a, 0xa1, 0xb6, 0x15, 0xa2, 0xb6, 0xdb, 0x7d, 0xa5, + 0x8b, 0xcc, 0x5e, 0x9b, 0xa4, 0xc2, 0x76, 0x7e, 0xc2, 0xac, 0x18, 0x35, 0xcb, 0x4f, 0xb6, 0xdd, + 0xf2, 0xf7, 0x2c, 0x61, 0xef, 0x46, 0xc2, 0x0e, 0x0d, 0x32, 0x4d, 0x24, 0xca, 0x09, 0xdb, 0xe8, + 0x01, 0xc1, 0x9f, 0x81, 0xa8, 0xd9, 0x3b, 0xd5, 0x35, 0xa2, 0x58, 0x13, 0x97, 0x5a, 0xb2, 0x43, + 0xa5, 0xa7, 0xa4, 0xa8, 0x39, 0xe3, 0x98, 0xe7, 0x59, 0x14, 0xd6, 0x2f, 0x1e, 0xb0, 0xf8, 0xec, + 0xb5, 0xc0, 0xc9, 0x80, 0x5a, 0x2c, 0x00, 0xd4, 0x40, 0x82, 0xb5, 0x88, 0x82, 0x8c, 0x26, 0x8d, + 0xb0, 0x3c, 0x37, 0xc2, 0x27, 0x2c, 0xc2, 0x36, 0x8d, 0x30, 0xc9, 0x40, 0xc3, 0xac, 0x31, 0xb3, + 0x64, 0x34, 0xed, 0x50, 0x4f, 0x39, 0x10, 0x27, 0x98, 0xa8, 0x6d, 0x85, 0x1d, 0xa4, 0x56, 0xe6, + 0x35, 0xe2, 0x23, 0x16, 0x27, 0x49, 0xe3, 0xf8, 0xd0, 0xe2, 0x42, 0x0d, 0x1a, 0xb3, 0xb1, 0xce, + 0x88, 0xb5, 0xc1, 0x47, 0x17, 0x98, 0x68, 0x46, 0xcb, 0xfa, 0x7a, 0xbb, 0x4c, 0xd8, 0xd5, 0xb9, + 0x65, 0x7f, 0x9b, 0xa5, 0x93, 0xa2, 0xe9, 0x4c, 0x51, 0xd0, 0xba, 0xd7, 0xa9, 0xbd, 0x6a, 0x99, + 0xed, 0xc2, 0xcf, 0x00, 0x33, 0x8d, 0x25, 0x8e, 0xcc, 0x8d, 0x25, 0xb2, 0x58, 0x5b, 0xbe, 0x58, + 0x7e, 0x85, 0xe3, 0xd4, 0xea, 0x08, 0x7c, 0x0f, 0xc4, 0x34, 0x53, 0x41, 0x97, 0x1d, 0xd4, 0xd4, + 0x08, 0x6a, 0xa6, 0x40, 0x86, 0xdb, 0x5b, 0x95, 0xa3, 0x9a, 0x29, 0x39, 0xa6, 0xc3, 0xb0, 0xb5, + 0x78, 0xc4, 0xab, 0x20, 0x88, 0x7a, 0x3b, 0xec, 0xc7, 0x20, 0xd4, 0x47, 0x26, 0x5d, 0x62, 0xf9, + 0xec, 0x02, 0xcb, 0xb2, 0x68, 0x10, 0xd9, 0x82, 0xc2, 0x47, 0x60, 0x45, 0x3d, 0x35, 0x89, 0xaa, + 0xb1, 0x75, 0xb7, 0x30, 0x8b, 0x03, 0x87, 0x3f, 0x04, 0x41, 0x03, 0xdb, 0x33, 0xbb, 0x38, 0x49, + 0xd0, 0xc0, 0xb0, 0x05, 0x62, 0x06, 0x56, 0x1e, 0x6b, 0xe4, 0x5c, 0xb9, 0x40, 0x04, 0xdb, 0x93, + 0x19, 0xc9, 0x4b, 0x8b, 0x31, 0xdd, 0x8d, 0x84, 0x0d, 0xaa, 0xbb, 0x97, 0x4b, 0x94, 0x81, 0x81, + 0x4f, 0x34, 0x72, 0x5e, 0x47, 0x04, 0x33, 0x29, 0x6f, 0x38, 0x10, 0xb6, 0x6e, 0xa0, 0xff, 0x7d, + 0x6b, 0x27, 0xc1, 0xd2, 0x05, 0x26, 0xc8, 0xd9, 0xd8, 0xf4, 0x03, 0x3c, 0x74, 0xaf, 0xbe, 0xd0, + 0x87, 0x5c, 0x7d, 0xf9, 0x60, 0x8a, 0x73, 0xaf, 0xbf, 0x63, 0xb0, 0x42, 0x9f, 0xcc, 0x54, 0xd8, + 0x9e, 0xb0, 0x4f, 0x67, 0x81, 0xa7, 0xef, 0xdb, 0x7c, 0xd8, 0x52, 0x49, 0x76, 0xc0, 0x87, 0xab, + 0xcf, 0x9d, 0x65, 0xfe, 0xeb, 0x30, 0x88, 0xb3, 0xd9, 0xa9, 0xa8, 0x5d, 0x55, 0x37, 0xe1, 0xef, + 0x38, 0x10, 0xd5, 0x35, 0xc3, 0x1d, 0x65, 0x6e, 0xde, 0x28, 0x2b, 0x16, 0xf7, 0xed, 0x48, 0xd8, + 0xf4, 0xa0, 0x1e, 0x60, 0x5d, 0x23, 0x48, 0xef, 0x90, 0xfe, 0x58, 0x27, 0xcf, 0xf1, 0x62, 0x13, + 0x0e, 0x74, 0xcd, 0x70, 0xe6, 0xfb, 0x37, 0x1c, 0x80, 0xba, 0x7a, 0xe9, 0x10, 0x29, 0x1d, 0xd4, + 0xd5, 0x70, 0x93, 0xdd, 0x22, 0x3b, 0x53, 0x53, 0x57, 0x60, 0x6f, 0x23, 0xb4, 0x4d, 0x6e, 0x47, + 0xc2, 0xee, 0x34, 0xd8, 0x97, 0x2b, 0xdb, 0xdf, 0xd3, 0x5e, 0xe2, 0x73, 0x6b, 0x2e, 0x13, 0xba, + 0x7a, 0xe9, 0xc8, 0x65, 0x9b, 0xe1, 0x5f, 0x39, 0x60, 0x17, 0xee, 0x0e, 0xa7, 0x2b, 0xdc, 0xdc, + 0xcb, 0xd8, 0x64, 0x39, 0x09, 0x33, 0xf1, 0xbe, 0xb4, 0x76, 0xc7, 0x12, 0x4e, 0x39, 0x2e, 0x26, + 0xe6, 0x86, 0xae, 0x19, 0xee, 0xd6, 0x60, 0xa5, 0x88, 0xcf, 0x43, 0x20, 0x56, 0xb7, 0x37, 0x0e, + 0x6b, 0x82, 0x5f, 0x01, 0xb6, 0x81, 0x1c, 0x81, 0xb9, 0x79, 0x02, 0x3f, 0x64, 0xc5, 0x6c, 0xfb, + 0x70, 0xbe, 0x22, 0x92, 0xbe, 0x85, 0xe7, 0x95, 0x35, 0x46, 0x6d, 0x4c, 0xd2, 0x33, 0xb0, 0xed, + 0xce, 0x94, 0xcf, 0xd9, 0x4c, 0x05, 0x6d, 0x4d, 0xf7, 0xde, 0x77, 0xe3, 0xd7, 0x3d, 0x54, 0xac, + 0xef, 0x37, 0x3b, 0x33, 0xce, 0x4c, 0xf8, 0x7b, 0x0e, 0x6c, 0x8f, 0xd5, 0xf4, 0xd7, 0x1b, 0x9a, + 0x57, 0x6f, 0x99, 0xd5, 0x7b, 0xef, 0x1d, 0x0c, 0xbe, 0xca, 0x79, 0x5a, 0xf9, 0x3b, 0x5c, 0xa9, + 0x06, 0x9b, 0xee, 0xa9, 0x37, 0x4b, 0x71, 0x14, 0x62, 0x1b, 0x9d, 0x7d, 0x33, 0xdf, 0x80, 0xe5, + 0x5f, 0xf6, 0x70, 0xb7, 0xa7, 0xdb, 0x5f, 0x49, 0x2c, 0x9f, 0x5f, 0xec, 0x0d, 0xf8, 0x76, 0x24, + 0x24, 0x28, 0x7e, 0x9c, 0xa0, 0xcc, 0x18, 0x61, 0x03, 0x44, 0xc8, 0x79, 0x17, 0x99, 0xe7, 0xb8, + 0x4d, 0x47, 0x2a, 0xb6, 0xd0, 0x7a, 0xa5, 0xf4, 0x1b, 0x2e, 0x85, 0x27, 0xc2, 0x98, 0x17, 0x0e, + 0x38, 0xb0, 0x66, 0xed, 0x5c, 0x65, 0x1c, 0x2a, 0x64, 0x87, 0x6a, 0x2c, 0x1c, 0x2a, 0xe5, 0xe7, + 0xf1, 0x49, 0xbe, 0xc9, 0x9a, 0xcd, 0xe7, 0x21, 0xca, 0x71, 0xcb, 0x50, 0x73, 0x93, 0x79, 0xc2, + 0x81, 0x8d, 0xf1, 0xb7, 0x32, 0xce, 0x28, 0x6c, 0x67, 0x54, 0x5e, 0x38, 0xa3, 0x8f, 0x67, 0x90, + 0x79, 0x64, 0x80, 0xee, 0xb1, 0x9b, 0x82, 0xf8, 0x17, 0x0e, 0x24, 0x67, 0xf5, 0x2e, 0xfc, 0x04, + 0xc4, 0xdd, 0x31, 0xb0, 0x62, 0xb0, 0x9f, 0x22, 0x31, 0xc7, 0x58, 0xeb, 0x77, 0xd0, 0xf4, 0xa0, + 0x06, 0xff, 0x7f, 0x83, 0x7a, 0xff, 0x3f, 0x1c, 0x00, 0x9e, 0x1f, 0x75, 0x0f, 0xc0, 0x76, 0xbd, + 0x5c, 0x93, 0x94, 0x72, 0xa5, 0x56, 0x2c, 0x97, 0x94, 0xaf, 0x4a, 0xd5, 0x8a, 0x74, 0x54, 0x3c, + 0x2e, 0x4a, 0x85, 0x44, 0x20, 0xbd, 0x3e, 0x18, 0x66, 0xa2, 0xd4, 0x51, 0xb2, 0xc2, 0x40, 0x11, + 0xac, 0x7b, 0xbd, 0xbf, 0x96, 0xaa, 0x09, 0x2e, 0x1d, 0x1f, 0x0c, 0x33, 0x11, 0xea, 0xf5, 0x35, + 0x32, 0xe1, 0x7d, 0xb0, 0xe1, 0xf5, 0xc9, 0xe5, 0xab, 0xb5, 0x5c, 0xb1, 0x94, 0x08, 0xa6, 0x3f, + 0x1a, 0x0c, 0x33, 0x71, 0xea, 0x97, 0x63, 0xaf, 0x17, 0x19, 0xb0, 0xe6, 0xf5, 0x2d, 0x95, 0x13, + 0xa1, 0x74, 0x6c, 0x30, 0xcc, 0xac, 0x52, 0xb7, 0x12, 0x86, 0x07, 0x20, 0xe5, 0xf7, 0x50, 0x4e, + 0x8a, 0xb5, 0x47, 0x4a, 0x5d, 0xaa, 0x95, 0x13, 0xe1, 0x74, 0x72, 0x30, 0xcc, 0x24, 0x1c, 0x5f, + 0xe7, 0x5d, 0x20, 0x1d, 0x7e, 0xfa, 0x07, 0x3e, 0x70, 0xff, 0xef, 0x41, 0xb0, 0xe6, 0xff, 0x45, + 0x01, 0xb3, 0xe0, 0x5b, 0x15, 0xb9, 0x5c, 0x29, 0x57, 0x73, 0x5f, 0x2a, 0xd5, 0x5a, 0xae, 0xf6, + 0x55, 0x75, 0xa2, 0x60, 0xbb, 0x14, 0xea, 0x5c, 0xd2, 0xda, 0xf0, 0x21, 0xe0, 0x27, 0xfd, 0x0b, + 0x52, 0xa5, 0x5c, 0x2d, 0xd6, 0x94, 0x8a, 0x24, 0x17, 0xcb, 0x85, 0x04, 0x97, 0xde, 0x1e, 0x0c, + 0x33, 0x1b, 0x14, 0xe2, 0xbf, 0x64, 0x7e, 0x00, 0x3e, 0x9e, 0x04, 0xd7, 0xcb, 0xb5, 0x62, 0xe9, + 0x27, 0x0e, 0x36, 0x98, 0xde, 0x1a, 0x0c, 0x33, 0x90, 0x62, 0x7d, 0x5d, 0xf4, 0x00, 0x6c, 0x4d, + 0x42, 0x2b, 0xb9, 0x6a, 0x55, 0x2a, 0x24, 0x42, 0xe9, 0xc4, 0x60, 0x98, 0x89, 0x51, 0x4c, 0x45, + 0x35, 0x4d, 0xd4, 0x84, 0x9f, 0x83, 0xd4, 0xa4, 0xb7, 0x2c, 0xfd, 0x54, 0x3a, 0xaa, 0x49, 0x85, + 0x44, 0x38, 0x0d, 0x07, 0xc3, 0xcc, 0x1a, 0xf5, 0x97, 0xd1, 0xcf, 0x51, 0x83, 0xa0, 0x99, 0xfc, + 0xc7, 0xb9, 0xe2, 0x97, 0x52, 0x21, 0xb1, 0xe4, 0xe5, 0x3f, 0x56, 0xb5, 0x36, 0x6a, 0x52, 0x39, + 0xf3, 0xa5, 0xab, 0x37, 0x7c, 0xe0, 0xd5, 0x1b, 0x3e, 0xf0, 0xe4, 0x9a, 0x0f, 0x5c, 0x5d, 0xf3, + 0xdc, 0xcb, 0x6b, 0x9e, 0xfb, 0xf7, 0x35, 0xcf, 0x3d, 0xbb, 0xe1, 0x03, 0x2f, 0x6f, 0xf8, 0xc0, + 0xab, 0x1b, 0x3e, 0xf0, 0xcd, 0xfb, 0xef, 0xb4, 0x4b, 0xfb, 0x3f, 0x26, 0xf6, 0xec, 0x9d, 0x2e, + 0xdb, 0x5d, 0xfe, 0x9d, 0xff, 0x06, 0x00, 0x00, 0xff, 0xff, 0xba, 0x25, 0x63, 0x35, 0x4c, 0x11, + 0x00, 0x00, } func (this *TextProposal) Equal(that interface{}) bool { @@ -1148,6 +1153,20 @@ func (m *DepositParams) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l + if len(m.MinExpeditedDeposit) > 0 { + for iNdEx := len(m.MinExpeditedDeposit) - 1; iNdEx >= 0; iNdEx-- { + { + size, err := m.MinExpeditedDeposit[iNdEx].MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGov(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x1a + } + } n7, err7 := github_com_gogo_protobuf_types.StdDurationMarshalTo(m.MaxDepositPeriod, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdDuration(m.MaxDepositPeriod):]) if err7 != nil { return 0, err7 @@ -1485,6 +1504,12 @@ func (m *DepositParams) Size() (n int) { } l = github_com_gogo_protobuf_types.SizeOfStdDuration(m.MaxDepositPeriod) n += 1 + l + sovGov(uint64(l)) + if len(m.MinExpeditedDeposit) > 0 { + for _, e := range m.MinExpeditedDeposit { + l = e.Size() + n += 1 + l + sovGov(uint64(l)) + } + } return n } @@ -2676,6 +2701,40 @@ func (m *DepositParams) Unmarshal(dAtA []byte) error { return err } iNdEx = postIndex + case 3: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field MinExpeditedDeposit", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGov + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGov + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGov + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.MinExpeditedDeposit = append(m.MinExpeditedDeposit, types.Coin{}) + if err := m.MinExpeditedDeposit[len(m.MinExpeditedDeposit)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex default: iNdEx = preIndex skippy, err := skipGov(dAtA[iNdEx:]) diff --git a/x/gov/types/params.go b/x/gov/types/params.go index c1a94f6b90f2..56003987d80b 100644 --- a/x/gov/types/params.go +++ b/x/gov/types/params.go @@ -21,11 +21,12 @@ const ( // Default governance params var ( - DefaultMinDepositTokens = sdk.NewInt(10000000) - DefaultQuorum = sdk.NewDecWithPrec(334, 3) - DefaultThreshold = sdk.NewDecWithPrec(5, 1) - DefaultExpeditedThreshold = sdk.NewDecWithPrec(667, 3) - DefaultVetoThreshold = sdk.NewDecWithPrec(334, 3) + DefaultMinDepositTokens = sdk.NewInt(10000000) + DefaultMinExpeditedDepositTokens = sdk.NewInt(10000000 * 5) + DefaultQuorum = sdk.NewDecWithPrec(334, 3) + DefaultThreshold = sdk.NewDecWithPrec(5, 1) + DefaultExpeditedThreshold = sdk.NewDecWithPrec(667, 3) + DefaultVetoThreshold = sdk.NewDecWithPrec(334, 3) DefaultProposalVotingPeriods []ProposalVotingPeriod = []ProposalVotingPeriod{} ) @@ -73,10 +74,11 @@ func ParamKeyTable() paramtypes.KeyTable { } // NewDepositParams creates a new DepositParams object -func NewDepositParams(minDeposit sdk.Coins, maxDepositPeriod time.Duration) DepositParams { +func NewDepositParams(minDeposit sdk.Coins, maxDepositPeriod time.Duration, minExpeditedDeposit sdk.Coins) DepositParams { return DepositParams{ - MinDeposit: minDeposit, - MaxDepositPeriod: maxDepositPeriod, + MinDeposit: minDeposit, + MaxDepositPeriod: maxDepositPeriod, + MinExpeditedDeposit: minExpeditedDeposit, } } @@ -85,6 +87,7 @@ func DefaultDepositParams() DepositParams { return NewDepositParams( sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, DefaultMinDepositTokens)), DefaultPeriod, + sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, DefaultMinExpeditedDepositTokens)), ) } @@ -105,12 +108,20 @@ func validateDepositParams(i interface{}) error { return fmt.Errorf("invalid parameter type: %T", i) } - if !v.MinDeposit.IsValid() { - return fmt.Errorf("invalid minimum deposit: %s", v.MinDeposit) + minDeposit := v.MinDeposit + if !minDeposit.IsValid() { + return fmt.Errorf("invalid minimum deposit: %s", minDeposit) } if v.MaxDepositPeriod <= 0 { return fmt.Errorf("maximum deposit period must be positive: %d", v.MaxDepositPeriod) } + minExpeditedDeposit := v.MinExpeditedDeposit + if !minExpeditedDeposit.IsValid() { + return fmt.Errorf("invalid minimum expedited deposit: %s", minExpeditedDeposit) + } + if minExpeditedDeposit.IsAllLTE(minDeposit) { + return fmt.Errorf("minimum expedited deposit %s must be greater than expedited deposit %s", minExpeditedDeposit, minDeposit) + } return nil } diff --git a/x/gov/types/proposal.go b/x/gov/types/proposal.go index 08c7f0ee2e93..ab2b7e1c6025 100644 --- a/x/gov/types/proposal.go +++ b/x/gov/types/proposal.go @@ -85,6 +85,16 @@ func (p Proposal) GetTitle() string { return content.GetTitle() } +// GetMinDepositFromParams returns min expedited deposit from depositParams if +// the proposal is expedited. Otherwise, returns the regular min deposit from +// depositParams. +func (p Proposal) GetMinDepositFromParams(depositParams DepositParams) sdk.Coins { + if p.IsExpedited { + return depositParams.MinExpeditedDeposit + } + return depositParams.MinDeposit +} + // UnpackInterfaces implements UnpackInterfacesMessage.UnpackInterfaces func (p Proposal) UnpackInterfaces(unpacker types.AnyUnpacker) error { var content Content diff --git a/x/gov/types/proposals_test.go b/x/gov/types/proposals_test.go index 83c4074c9737..63d9f702b348 100644 --- a/x/gov/types/proposals_test.go +++ b/x/gov/types/proposals_test.go @@ -5,6 +5,7 @@ import ( "testing" "time" + sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/x/gov/types" "github.com/stretchr/testify/require" ) @@ -36,3 +37,32 @@ func TestProposalSetIsExpedited(t *testing.T) { proposal, err = types.NewProposal(testProposal, 1, time.Now(), time.Now(), !startIsExpedited) require.Equal(t, !startIsExpedited, proposal.IsExpedited) } + +func TestProposalGetMinDepositFromParams(t *testing.T) { + testcases := []struct { + isExpedited bool + expectedMinDeposit sdk.Int + }{ + { + isExpedited: true, + expectedMinDeposit: types.DefaultMinExpeditedDepositTokens, + }, + { + isExpedited: false, + expectedMinDeposit: types.DefaultMinDepositTokens, + }, + } + + for _, tc := range testcases { + testProposal := types.NewTextProposal("test", "description") + + proposal, err := types.NewProposal(testProposal, 1, time.Now(), time.Now(), tc.isExpedited) + require.NoError(t, err) + + actualMinDeposit := proposal.GetMinDepositFromParams(types.DefaultDepositParams()) + + require.Equal(t, 1, len(actualMinDeposit)) + require.Equal(t, sdk.DefaultBondDenom, actualMinDeposit[0].Denom) + require.Equal(t, tc.expectedMinDeposit, actualMinDeposit[0].Amount) + } +} diff --git a/x/params/proposal_handler_test.go b/x/params/proposal_handler_test.go index f48b6ca3a3d5..3005418d7b80 100644 --- a/x/params/proposal_handler_test.go +++ b/x/params/proposal_handler_test.go @@ -64,17 +64,29 @@ func (suite *HandlerTestSuite) TestProposalHandler() { testProposal(proposal.ParamChange{ Subspace: govtypes.ModuleName, Key: string(govtypes.ParamStoreKeyDepositParams), - Value: `{"min_deposit": [{"denom": "uatom","amount": "64000000"}]}`, + Value: `{"min_deposit": [{"denom": "uatom","amount": "64000000"}],"min_expedited_deposit": [{"denom": "uatom","amount": "64000001"}]}`, }), func() { depositParams := suite.app.GovKeeper.GetDepositParams(suite.ctx) suite.Require().Equal(govtypes.DepositParams{ - MinDeposit: sdk.NewCoins(sdk.NewCoin("uatom", sdk.NewInt(64000000))), - MaxDepositPeriod: govtypes.DefaultPeriod, + MinDeposit: sdk.NewCoins(sdk.NewCoin("uatom", sdk.NewInt(64000000))), + MaxDepositPeriod: govtypes.DefaultPeriod, + MinExpeditedDeposit: sdk.NewCoins(sdk.NewCoin("uatom", sdk.NewInt(64000001))), }, depositParams) }, false, }, + { + "min_deposit equals to min_expedited_deposit", + testProposal(proposal.ParamChange{ + Subspace: govtypes.ModuleName, + Key: string(govtypes.ParamStoreKeyDepositParams), + Value: `{"min_deposit": [{"denom": "uatom","amount": "64000000"}],"min_expedited_deposit": [{"denom": "uatom","amount": "64000000"}]}`, + }), + func() { + }, + true, + }, } for _, tc := range testCases {