diff --git a/.changelog/unreleased/api-breaking/3149-bump-ics.md b/.changelog/unreleased/api-breaking/3149-bump-ics.md new file mode 100644 index 00000000000..a71b63ffb73 --- /dev/null +++ b/.changelog/unreleased/api-breaking/3149-bump-ics.md @@ -0,0 +1,3 @@ +- Bump [interchain-security](https://github.com/cosmos/interchain-security) to + [v4.3.0-lsm](https://github.com/cosmos/interchain-security/releases/tag/v4.3.0-lsm). + ([\#3149](https://github.com/cosmos/gaia/pull/3149)) \ No newline at end of file diff --git a/.changelog/unreleased/dependencies/3051-add-cosmwasm.md b/.changelog/unreleased/dependencies/3051-add-cosmwasm.md new file mode 100644 index 00000000000..3898012f02c --- /dev/null +++ b/.changelog/unreleased/dependencies/3051-add-cosmwasm.md @@ -0,0 +1,2 @@ +- Add the wasmd module. + ([\#3051](https://github.com/cosmos/gaia/pull/3051)) \ No newline at end of file diff --git a/.changelog/unreleased/dependencies/3109-bump-ibc.md b/.changelog/unreleased/dependencies/3109-bump-ibc.md deleted file mode 100644 index 4b48b4c450d..00000000000 --- a/.changelog/unreleased/dependencies/3109-bump-ibc.md +++ /dev/null @@ -1,3 +0,0 @@ -- Bump [ibc-go](https://github.com/cosmos/ibc-go) to - [v7.5.1](https://github.com/cosmos/ibc-go/releases/tag/v7.5.1) - ([\#3109](https://github.com/cosmos/gaia/pull/3109) and [\#3115](https://github.com/cosmos/gaia/pull/3115)) \ No newline at end of file diff --git a/.changelog/unreleased/dependencies/3149-bump-ibc.md b/.changelog/unreleased/dependencies/3149-bump-ibc.md new file mode 100644 index 00000000000..6466629cd27 --- /dev/null +++ b/.changelog/unreleased/dependencies/3149-bump-ibc.md @@ -0,0 +1,3 @@ +- Bump [ibc-go](https://github.com/cosmos/ibc-go) to + [v7.6.0](https://github.com/cosmos/ibc-go/releases/tag/v7.6.0) + ([\#3149](https://github.com/cosmos/gaia/pull/3149)) \ No newline at end of file diff --git a/.changelog/unreleased/dependencies/3149-bump-sdk.md b/.changelog/unreleased/dependencies/3149-bump-sdk.md new file mode 100644 index 00000000000..c819c8a0a42 --- /dev/null +++ b/.changelog/unreleased/dependencies/3149-bump-sdk.md @@ -0,0 +1,4 @@ +- Bump [cosmos-sdk](https://github.com/cosmos/cosmos-sdk) to + [v0.47.16-ics-lsm](https://github.com/cosmos/cosmos-sdk/tree/v0.47.16-ics-lsm). + This is a special cosmos-sdk branch with support for both ICS and LSM. + ([\#3149](https://github.com/cosmos/gaia/pull/3149)) \ No newline at end of file diff --git a/.changelog/unreleased/features/3051-add-cosmwasm.md b/.changelog/unreleased/features/3051-add-cosmwasm.md new file mode 100644 index 00000000000..3898012f02c --- /dev/null +++ b/.changelog/unreleased/features/3051-add-cosmwasm.md @@ -0,0 +1,2 @@ +- Add the wasmd module. + ([\#3051](https://github.com/cosmos/gaia/pull/3051)) \ No newline at end of file diff --git a/.changelog/unreleased/state-breaking/3051-add-cosmwasm.md b/.changelog/unreleased/state-breaking/3051-add-cosmwasm.md new file mode 100644 index 00000000000..3898012f02c --- /dev/null +++ b/.changelog/unreleased/state-breaking/3051-add-cosmwasm.md @@ -0,0 +1,2 @@ +- Add the wasmd module. + ([\#3051](https://github.com/cosmos/gaia/pull/3051)) \ No newline at end of file diff --git a/.changelog/unreleased/state-breaking/3109-bump-ibc.md b/.changelog/unreleased/state-breaking/3109-bump-ibc.md deleted file mode 100644 index e68c9af6f70..00000000000 --- a/.changelog/unreleased/state-breaking/3109-bump-ibc.md +++ /dev/null @@ -1,3 +0,0 @@ -- Bump [ibc-go](https://github.com/cosmos/ibc-go) to - [v7.5.0](https://github.com/cosmos/ibc-go/releases/tag/v7.5.0) - ([\#3109](https://github.com/cosmos/gaia/pull/3109)) \ No newline at end of file diff --git a/.changelog/unreleased/state-breaking/3149-bump-ibc.md b/.changelog/unreleased/state-breaking/3149-bump-ibc.md new file mode 100644 index 00000000000..6466629cd27 --- /dev/null +++ b/.changelog/unreleased/state-breaking/3149-bump-ibc.md @@ -0,0 +1,3 @@ +- Bump [ibc-go](https://github.com/cosmos/ibc-go) to + [v7.6.0](https://github.com/cosmos/ibc-go/releases/tag/v7.6.0) + ([\#3149](https://github.com/cosmos/gaia/pull/3149)) \ No newline at end of file diff --git a/.changelog/unreleased/state-breaking/3149-bump-ics.md b/.changelog/unreleased/state-breaking/3149-bump-ics.md new file mode 100644 index 00000000000..a71b63ffb73 --- /dev/null +++ b/.changelog/unreleased/state-breaking/3149-bump-ics.md @@ -0,0 +1,3 @@ +- Bump [interchain-security](https://github.com/cosmos/interchain-security) to + [v4.3.0-lsm](https://github.com/cosmos/interchain-security/releases/tag/v4.3.0-lsm). + ([\#3149](https://github.com/cosmos/gaia/pull/3149)) \ No newline at end of file diff --git a/.changelog/unreleased/state-breaking/3149-bump-sdk.md b/.changelog/unreleased/state-breaking/3149-bump-sdk.md new file mode 100644 index 00000000000..c819c8a0a42 --- /dev/null +++ b/.changelog/unreleased/state-breaking/3149-bump-sdk.md @@ -0,0 +1,4 @@ +- Bump [cosmos-sdk](https://github.com/cosmos/cosmos-sdk) to + [v0.47.16-ics-lsm](https://github.com/cosmos/cosmos-sdk/tree/v0.47.16-ics-lsm). + This is a special cosmos-sdk branch with support for both ICS and LSM. + ([\#3149](https://github.com/cosmos/gaia/pull/3149)) \ No newline at end of file diff --git a/.gitignore b/.gitignore index df75354186c..34294f94d42 100644 --- a/.gitignore +++ b/.gitignore @@ -20,6 +20,8 @@ docs/tutorial dist tools-stamp docs/node_modules +docs/versioned_docs +docs/versioned_sidebars # Data - ideally these don't exist baseapp/data/* diff --git a/ante/ante.go b/ante/ante.go index 6833dedceff..afd21811829 100644 --- a/ante/ante.go +++ b/ante/ante.go @@ -73,6 +73,7 @@ func NewAnteHandler(opts HandlerOptions) (sdk.AnteHandler, error) { ante.NewValidateMemoDecorator(opts.AccountKeeper), ante.NewConsumeGasForTxSizeDecorator(opts.AccountKeeper), NewGovVoteDecorator(opts.Codec, opts.StakingKeeper), + NewGovExpeditedProposalsDecorator(opts.Codec), ante.NewSetPubKeyDecorator(opts.AccountKeeper), // SetPubKeyDecorator must be called before all signature verification decorators ante.NewValidateSigCountDecorator(opts.AccountKeeper), ante.NewSigGasConsumeDecorator(opts.AccountKeeper, sigGasConsumer), diff --git a/ante/gov_expedited_ante.go b/ante/gov_expedited_ante.go new file mode 100644 index 00000000000..f9d99962c8e --- /dev/null +++ b/ante/gov_expedited_ante.go @@ -0,0 +1,83 @@ +package ante + +import ( + errorsmod "cosmossdk.io/errors" + + "github.com/cosmos/cosmos-sdk/codec" + sdk "github.com/cosmos/cosmos-sdk/types" + govv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" + + gaiaerrors "github.com/cosmos/gaia/v18/types/errors" +) + +var expeditedPropDecoratorEnabled = true + +// SetExpeditedProposalsEnabled toggles the expedited proposals decorator on/off. +// Should only be used in testing - this is to allow simtests to pass. +func SetExpeditedProposalsEnabled(val bool) { + expeditedPropDecoratorEnabled = val +} + +var expeditedPropsWhitelist = map[string]struct{}{ + "/cosmos.upgrade.v1beta1.MsgSoftwareUpgrade": {}, + "/cosmos.upgrade.v1beta1.MsgCancelUpgrade": {}, + // legacy proposals can still be submitted using govv1.MsgSubmitProposal + "/cosmos.upgrade.v1beta1.SoftwareUpgradeProposal": {}, + "/cosmos.upgrade.v1beta1.CancelSoftwareUpgradeProposal": {}, +} + +// Check if the proposal is whitelisted for expedited voting. +type GovExpeditedProposalsDecorator struct { + cdc codec.BinaryCodec +} + +func NewGovExpeditedProposalsDecorator(cdc codec.BinaryCodec) GovExpeditedProposalsDecorator { + return GovExpeditedProposalsDecorator{ + cdc: cdc, + } +} + +// AnteHandle checks if the proposal is whitelisted for expedited voting. +// Only proposals submitted using "gaiad tx gov submit-proposal" can be expedited. +// Legacy proposals submitted using "gaiad tx gov submit-legacy-proposal" cannot be marked as expedited. +func (g GovExpeditedProposalsDecorator) AnteHandle(ctx sdk.Context, tx sdk.Tx, simulate bool, next sdk.AnteHandler) (newCtx sdk.Context, err error) { + if expeditedPropDecoratorEnabled { + for _, msg := range tx.GetMsgs() { + prop, ok := msg.(*govv1.MsgSubmitProposal) + if !ok { + continue + } + if prop.Expedited { + if err := g.validateExpeditedGovProp(prop); err != nil { + return ctx, err + } + } + } + } + return next(ctx, tx, simulate) +} + +func (g GovExpeditedProposalsDecorator) isWhitelisted(msgType string) bool { + _, ok := expeditedPropsWhitelist[msgType] + return ok +} + +func (g GovExpeditedProposalsDecorator) validateExpeditedGovProp(prop *govv1.MsgSubmitProposal) error { + msgs := prop.GetMessages() + if len(msgs) == 0 { + return gaiaerrors.ErrInvalidExpeditedProposal + } + for _, message := range msgs { + // in case of legacy content submitted using govv1.MsgSubmitProposal + if sdkMsg, isLegacy := message.GetCachedValue().(*govv1.MsgExecLegacyContent); isLegacy { + if !g.isWhitelisted(sdkMsg.Content.TypeUrl) { + return errorsmod.Wrapf(gaiaerrors.ErrInvalidExpeditedProposal, "invalid Msg type: %s", sdkMsg.Content.TypeUrl) + } + continue + } + if !g.isWhitelisted(message.TypeUrl) { + return errorsmod.Wrapf(gaiaerrors.ErrInvalidExpeditedProposal, "invalid Msg type: %s", message.TypeUrl) + } + } + return nil +} diff --git a/ante/gov_expedited_ante_test.go b/ante/gov_expedited_ante_test.go new file mode 100644 index 00000000000..543fae1c854 --- /dev/null +++ b/ante/gov_expedited_ante_test.go @@ -0,0 +1,270 @@ +package ante_test + +import ( + "testing" + + "github.com/stretchr/testify/require" + + sdk "github.com/cosmos/cosmos-sdk/types" + banktypes "github.com/cosmos/cosmos-sdk/x/bank/types" + distrtypes "github.com/cosmos/cosmos-sdk/x/distribution/types" + govv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" + govv1beta1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1beta1" + upgradetypes "github.com/cosmos/cosmos-sdk/x/upgrade/types" + + "github.com/cosmos/gaia/v18/ante" + "github.com/cosmos/gaia/v18/app/helpers" +) + +func TestGovExpeditedProposalsDecorator(t *testing.T) { + gaiaApp := helpers.Setup(t) + + testCases := []struct { + name string + ctx sdk.Context + msgs []sdk.Msg + expectErr bool + }{ + // these cases should pass + { + name: "expedited - govv1.MsgSubmitProposal - MsgSoftwareUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&upgradetypes.MsgSoftwareUpgrade{ + Authority: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + Plan: upgradetypes.Plan{ + Name: "upgrade plan-plan", + Info: "some text here", + Height: 123456789, + }, + }}, true), + }, + expectErr: false, + }, + { + name: "expedited - govv1.MsgSubmitProposal - LegacySoftwareUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newLegacyUpgradeProp(true), // expedite + }, + expectErr: false, + }, + { + name: "expedited - govv1.MsgSubmitProposal - MsgCancelUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&upgradetypes.MsgCancelUpgrade{ + Authority: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + }}, true), + }, + expectErr: false, + }, + { + name: "expedited - govv1.MsgSubmitProposal - LegacyCancelUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newLegacyCancelProp(true), // expedite + }, + expectErr: false, + }, + { + name: "normal - govv1.MsgSubmitProposal - LegacySoftwareUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newLegacyUpgradeProp(false), // normal + }, + expectErr: false, + }, + { + name: "normal - govv1.MsgSubmitProposal - LegacyCancelUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newLegacyCancelProp(false), // normal + }, + expectErr: false, + }, + { + name: "normal - govv1.MsgSubmitProposal - TextProposal", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newLegacyTextProp(false), // normal + }, + expectErr: false, + }, + { + name: "normal - govv1.MsgSubmitProposal - MsgCommunityPoolSpend", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&distrtypes.MsgCommunityPoolSpend{ + Authority: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + Recipient: sdk.AccAddress{}.String(), + Amount: sdk.NewCoins(sdk.NewCoin("stake", sdk.NewInt(100))), + }}, false), // normal + }, + expectErr: false, + }, + { + name: "normal - govv1.MsgSubmitProposal - MsgTransfer", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&banktypes.MsgSend{ + FromAddress: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + ToAddress: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + Amount: sdk.NewCoins(sdk.NewCoin("stake", sdk.NewInt(100))), + }}, false), // normal + }, + expectErr: false, + }, + { + name: "normal - govv1.MsgSubmitProposal - MsgUpdateParams", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&banktypes.MsgUpdateParams{ + Authority: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + }}, false), + }, + expectErr: false, + }, + // legacy proposals - antehandler should not affect them + // submitted using "gaiad tx gov submit-legacy-proposal" + { + name: "normal - govv1beta.MsgSubmitProposal - LegacySoftwareUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{newGovV1BETA1LegacyUpgradeProp()}, + expectErr: false, + }, + { + name: "normal - govv1beta.MsgSubmitProposal - LegacyCancelSoftwareUpgrade", + ctx: sdk.Context{}, + msgs: []sdk.Msg{newGovV1BETA1LegacyCancelUpgradeProp()}, + expectErr: false, + }, + // these cases should fail + // these are normal proposals, not whitelisted for expedited voting + { + name: "fail - expedited - govv1.MsgSubmitProposal - Empty", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{}, true), + }, + expectErr: true, + }, + { + name: "fail - expedited - govv1.MsgSubmitProposal - TextProposal", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newLegacyTextProp(true), // expedite + }, + expectErr: true, + }, + { + name: "fail - expedited - govv1.MsgSubmitProposal - MsgCommunityPoolSpend", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&distrtypes.MsgCommunityPoolSpend{ + Authority: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + Recipient: sdk.AccAddress{}.String(), + Amount: sdk.NewCoins(sdk.NewCoin("stake", sdk.NewInt(100))), + }}, true), + }, + expectErr: true, + }, + { + name: "fail - expedited - govv1.MsgSubmitProposal - MsgTransfer", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&banktypes.MsgSend{ + FromAddress: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + ToAddress: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + Amount: sdk.NewCoins(sdk.NewCoin("stake", sdk.NewInt(100))), + }}, true), + }, + expectErr: true, + }, + { + name: "fail - expedited - govv1.MsgSubmitProposal - MsgUpdateParams", + ctx: sdk.Context{}, + msgs: []sdk.Msg{ + newGovProp([]sdk.Msg{&banktypes.MsgUpdateParams{ + Authority: "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + }}, true), + }, + expectErr: true, + }, + } + + for _, tc := range testCases { + tc := tc + + t.Run(tc.name, func(t *testing.T) { + txCfg := gaiaApp.GetTxConfig() + decorator := ante.NewGovExpeditedProposalsDecorator(gaiaApp.AppCodec()) + + txBuilder := txCfg.NewTxBuilder() + require.NoError(t, txBuilder.SetMsgs(tc.msgs...)) + + _, err := decorator.AnteHandle(tc.ctx, txBuilder.GetTx(), false, + func(ctx sdk.Context, _ sdk.Tx, _ bool) (sdk.Context, error) { return ctx, nil }) + if tc.expectErr { + require.Error(t, err) + } else { + require.NoError(t, err) + } + }) + } +} + +func newLegacyTextProp(expedite bool) *govv1.MsgSubmitProposal { + testProposal := govv1beta1.NewTextProposal("Proposal", "Test as normal proposal") + msgContent, err := govv1.NewLegacyContent(testProposal, "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn") + if err != nil { + return nil + } + return newGovProp([]sdk.Msg{msgContent}, expedite) +} + +func newLegacyUpgradeProp(expedite bool) *govv1.MsgSubmitProposal { + prop := upgradetypes.NewSoftwareUpgradeProposal("test legacy upgrade", "test legacy upgrade", upgradetypes.Plan{ + Name: "upgrade plan-plan", + Info: "some text here", + Height: 123456789, + }) + msgContent, err := govv1.NewLegacyContent(prop, "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn") + if err != nil { + return nil + } + return newGovProp([]sdk.Msg{msgContent}, expedite) +} + +func newGovV1BETA1LegacyUpgradeProp() *govv1beta1.MsgSubmitProposal { + legacyContent := upgradetypes.NewSoftwareUpgradeProposal("test legacy upgrade", "test legacy upgrade", upgradetypes.Plan{ + Name: "upgrade plan-plan", + Info: "some text here", + Height: 123456789, + }) + + msg, _ := govv1beta1.NewMsgSubmitProposal(legacyContent, sdk.NewCoins(), sdk.AccAddress{}) + return msg +} + +func newGovV1BETA1LegacyCancelUpgradeProp() *govv1beta1.MsgSubmitProposal { + legacyContent := upgradetypes.NewCancelSoftwareUpgradeProposal("test legacy upgrade", "test legacy upgrade") + + msg, _ := govv1beta1.NewMsgSubmitProposal(legacyContent, sdk.NewCoins(), sdk.AccAddress{}) + return msg +} + +func newLegacyCancelProp(expedite bool) *govv1.MsgSubmitProposal { + prop := upgradetypes.NewCancelSoftwareUpgradeProposal("test legacy upgrade", "test legacy upgrade") + msgContent, err := govv1.NewLegacyContent(prop, "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn") + if err != nil { + return nil + } + return newGovProp([]sdk.Msg{msgContent}, expedite) +} + +func newGovProp(msgs []sdk.Msg, expedite bool) *govv1.MsgSubmitProposal { + msg, _ := govv1.NewMsgSubmitProposal(msgs, sdk.NewCoins(), sdk.AccAddress{}.String(), "", "expedite", "expedite", expedite) + // fmt.Println("### msg ###", msg, "err", err) + return msg +} diff --git a/app/sim_test.go b/app/sim_test.go index 3aa99b6073e..ed29f36dc1f 100644 --- a/app/sim_test.go +++ b/app/sim_test.go @@ -108,6 +108,10 @@ func TestAppStateDeterminism(t *testing.T) { // due to the minimum staked tokens required to submit a vote ante.SetMinStakedTokens(math.LegacyZeroDec()) + // NOTE: setting to zero to avoid failing the simulation + // gaia ante allows only certain proposals to be expedited - the simulation doesn't know about this + ante.SetExpeditedProposalsEnabled(false) + fmt.Printf( "running non-determinism simulation; seed %d: %d/%d, attempt: %d/%d\n", config.Seed, i+1, numSeeds, j+1, numTimesToRunPerSeed, diff --git a/app/upgrades/v18/upgrades.go b/app/upgrades/v18/upgrades.go index 99dbaa7b8f6..e88d2018ecb 100644 --- a/app/upgrades/v18/upgrades.go +++ b/app/upgrades/v18/upgrades.go @@ -1,10 +1,13 @@ package v18 import ( + "time" + errorsmod "cosmossdk.io/errors" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/module" + govv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" upgradetypes "github.com/cosmos/cosmos-sdk/x/upgrade/types" wasmtypes "github.com/CosmWasm/wasmd/x/wasm/types" @@ -26,6 +29,16 @@ func CreateUpgradeHandler( return vm, err } + expeditedPeriod := 24 * 7 * time.Hour // 7 days + govParams := keepers.GovKeeper.GetParams(ctx) + govParams.ExpeditedVotingPeriod = &expeditedPeriod + govParams.ExpeditedThreshold = govv1.DefaultExpeditedThreshold.String() // 66.7% + govParams.ExpeditedMinDeposit = sdk.NewCoins(sdk.NewCoin(types.UAtomDenom, sdk.NewInt(500_000_000))) // 500 ATOM + err = keepers.GovKeeper.SetParams(ctx, govParams) + if err != nil { + return vm, errorsmod.Wrapf(err, "unable to set gov params") + } + err = ConfigureFeeMarketModule(ctx, keepers) if err != nil { return vm, err diff --git a/cmd/gaiad/cmd/testnet_set_local_validator.go b/cmd/gaiad/cmd/testnet_set_local_validator.go index 8153a789e66..6fe3a26196d 100644 --- a/cmd/gaiad/cmd/testnet_set_local_validator.go +++ b/cmd/gaiad/cmd/testnet_set_local_validator.go @@ -253,10 +253,12 @@ func updateApplicationState(app *gaia.GaiaApp, args valArgs) error { app.SlashingKeeper.SetValidatorSigningInfo(appCtx, newConsAddr, newValidatorSigningInfo) shortVotingPeriod := time.Second * 20 + expeditedVotingPeriod := time.Second * 10 params := app.GovKeeper.GetParams(appCtx) params.VotingPeriod = &shortVotingPeriod + params.ExpeditedVotingPeriod = &expeditedVotingPeriod app.GovKeeper.SetParams(appCtx, params) - appCtx.Logger().Info("Updated governance voting period", "voting_period", shortVotingPeriod) + appCtx.Logger().Info("Updated governance voting period", "voting_period", shortVotingPeriod, "expedited_voting_period", expeditedVotingPeriod) // BANK defaultCoins := sdk.NewCoins(sdk.NewInt64Coin(app.StakingKeeper.BondDenom(appCtx), 1000000000000)) diff --git a/go.mod b/go.mod index 1de1aa1cdd8..14da37c7c49 100644 --- a/go.mod +++ b/go.mod @@ -12,12 +12,12 @@ require ( github.com/Stride-Labs/ibc-rate-limiting v1.0.1 github.com/cometbft/cometbft v0.37.6 github.com/cometbft/cometbft-db v0.11.0 - github.com/cosmos/cosmos-sdk v0.47.12 + github.com/cosmos/cosmos-sdk v0.47.16-ics-lsm github.com/cosmos/go-bip39 v1.0.0 github.com/cosmos/gogoproto v1.5.0 github.com/cosmos/ibc-apps/middleware/packet-forward-middleware/v7 v7.1.3 - github.com/cosmos/ibc-go/v7 v7.5.1 - github.com/cosmos/interchain-security/v4 v4.2.0 + github.com/cosmos/ibc-go/v7 v7.6.0 + github.com/cosmos/interchain-security/v4 v4.3.0 github.com/google/gofuzz v1.2.0 github.com/gorilla/mux v1.8.1 github.com/ory/dockertest/v3 v3.10.0 @@ -230,15 +230,12 @@ replace ( // Use cosmos keyring github.com/99designs/keyring => github.com/cosmos/keyring v1.2.0 - // Use special SDK v0.47.x release with support for both ICS and LSM - github.com/cosmos/cosmos-sdk => github.com/cosmos/cosmos-sdk v0.47.15-ics-lsm - github.com/cosmos/gogoproto => github.com/cosmos/gogoproto v1.4.10 github.com/cosmos/iavl => github.com/cosmos/iavl v0.20.1 // Use special ICS v4.1.0-ics-lsm release with support for LSM - github.com/cosmos/interchain-security/v4 => github.com/cosmos/interchain-security/v4 v4.2.0-lsm + github.com/cosmos/interchain-security/v4 => github.com/cosmos/interchain-security/v4 v4.3.0-lsm github.com/cosmos/ledger-cosmos-go => github.com/cosmos/ledger-cosmos-go v0.12.4 @@ -255,3 +252,5 @@ replace ( // x/exp had a breaking change in further commits golang.org/x/exp => golang.org/x/exp v0.0.0-20230711153332-06a737ee72cb ) + +replace github.com/CosmWasm/wasmd => github.com/informalsystems/wasmd v0.45.0-lsm diff --git a/go.sum b/go.sum index 49051771417..b547b0d4edd 100644 --- a/go.sum +++ b/go.sum @@ -557,8 +557,6 @@ github.com/Azure/go-ansiterm v0.0.0-20210617225240-d185dfc1b5a1/go.mod h1:xomTg6 github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/ChainSafe/go-schnorrkel v1.0.0 h1:3aDA67lAykLaG1y3AOjs88dMxC88PgUuHRrLeDnvGIM= github.com/ChainSafe/go-schnorrkel v1.0.0/go.mod h1:dpzHYVxLZcp8pjlV+O+UR8K0Hp/z7vcchBSbMBEhCw4= -github.com/CosmWasm/wasmd v0.45.0 h1:9zBqrturKJwC2kVsfHvbrA++EN0PS7UTXCffCGbg6JI= -github.com/CosmWasm/wasmd v0.45.0/go.mod h1:RnSAiqbNIZu4QhO+0pd7qGZgnYAMBPGmXpzTADag944= github.com/CosmWasm/wasmvm v1.5.0 h1:3hKeT9SfwfLhxTGKH3vXaKFzBz1yuvP8SlfwfQXbQfw= github.com/CosmWasm/wasmvm v1.5.0/go.mod h1:fXB+m2gyh4v9839zlIXdMZGeLAxqUdYdFQqYsTha2hc= github.com/DATA-DOG/go-sqlmock v1.3.3/go.mod h1:f/Ixk793poVmq4qj/V1dPUg2JEAKC73Q5eFN3EC/SaM= @@ -753,8 +751,8 @@ github.com/cosmos/btcutil v1.0.5 h1:t+ZFcX77LpKtDBhjucvnOH8C2l2ioGsBNEQ3jef8xFk= github.com/cosmos/btcutil v1.0.5/go.mod h1:IyB7iuqZMJlthe2tkIFL33xPyzbFYP0XVdS8P5lUPis= github.com/cosmos/cosmos-proto v1.0.0-beta.5 h1:eNcayDLpip+zVLRLYafhzLvQlSmyab+RC5W7ZfmxJLA= github.com/cosmos/cosmos-proto v1.0.0-beta.5/go.mod h1:hQGLpiIUloJBMdQMMWb/4wRApmI9hjHH05nefC0Ojec= -github.com/cosmos/cosmos-sdk v0.47.15-ics-lsm h1:OvJXkwmAyhG+K+WkQSUNeQls4QnSbnPsyh+Mg0F+bPc= -github.com/cosmos/cosmos-sdk v0.47.15-ics-lsm/go.mod h1:uzvMwHXmuRDSOaF8ec9HickjLHJcItWBREdkaDHcPiE= +github.com/cosmos/cosmos-sdk v0.47.16-ics-lsm h1:+mlfnZ4Cs8HMw9xy7Epjv56avptYSTsX3TVlUDX3Qcs= +github.com/cosmos/cosmos-sdk v0.47.16-ics-lsm/go.mod h1:uzvMwHXmuRDSOaF8ec9HickjLHJcItWBREdkaDHcPiE= github.com/cosmos/go-bip39 v0.0.0-20180819234021-555e2067c45d/go.mod h1:tSxLoYXyBmiFeKpvmq4dzayMdCjCnu8uqmCysIGBT2Y= github.com/cosmos/go-bip39 v1.0.0 h1:pcomnQdrdH22njcAatO0yWojsUnCO3y2tNoV1cb6hHY= github.com/cosmos/go-bip39 v1.0.0/go.mod h1:RNJv0H/pOIVgxw6KS7QeX2a0Uo0aKUlfhZ4xuwvCdJw= @@ -766,12 +764,12 @@ github.com/cosmos/iavl v0.20.1 h1:rM1kqeG3/HBT85vsZdoSNsehciqUQPWrR4BYmqE2+zg= github.com/cosmos/iavl v0.20.1/go.mod h1:WO7FyvaZJoH65+HFOsDir7xU9FWk2w9cHXNW1XHcl7A= github.com/cosmos/ibc-apps/middleware/packet-forward-middleware/v7 v7.1.3 h1:MZGDMETv72suFpTAD6VPGqSIm1FJcChtk2HmVh9D+Bo= github.com/cosmos/ibc-apps/middleware/packet-forward-middleware/v7 v7.1.3/go.mod h1:UvDmcGIWJPIytq+Q78/ff5NTOsuX/7IrNgEugTW5i0s= -github.com/cosmos/ibc-go/v7 v7.5.1 h1:KqS/g7W7EMX1OtOvufS8lWMJibOKpdgtNNZIU6fAgVU= -github.com/cosmos/ibc-go/v7 v7.5.1/go.mod h1:ktFg5GvKOyrGCqTWtW7Grj5uweU4ZapxrNeVS1CLLbo= +github.com/cosmos/ibc-go/v7 v7.6.0 h1:S1G5hcIVe9go+jQV6F9+I9yy+hylbJeLiVHUmktQNrM= +github.com/cosmos/ibc-go/v7 v7.6.0/go.mod h1:LifBA7JHRHl95ujjHIaBEHmUqy2qCGyqDCXB7qmAsZk= github.com/cosmos/ics23/go v0.10.0 h1:iXqLLgp2Lp+EdpIuwXTYIQU+AiHj9mOC2X9ab++bZDM= github.com/cosmos/ics23/go v0.10.0/go.mod h1:ZfJSmng/TBNTBkFemHHHj5YY7VAU/MBU980F4VU1NG0= -github.com/cosmos/interchain-security/v4 v4.2.0-lsm h1:/ET7ibwJ0tWf5SVRDwSVJ0G53b3i89BsOiFaCguUCDE= -github.com/cosmos/interchain-security/v4 v4.2.0-lsm/go.mod h1:xwuWSAibUdRrUK6Lr2r2K5Bf2tHZNXJkeVoZhQhH6s0= +github.com/cosmos/interchain-security/v4 v4.3.0-lsm h1:QZEPone4xBT8Zw2JwkmQxEH97bluEhsTnYnb+pWNutU= +github.com/cosmos/interchain-security/v4 v4.3.0-lsm/go.mod h1:oheLfOdj+k41NwfDZemQTdMYO7j/T+HQWZ1QHQIN/YY= github.com/cosmos/keyring v1.2.0 h1:8C1lBP9xhImmIabyXW4c3vFjjLiBdGCmfLUfeZlV1Yo= github.com/cosmos/keyring v1.2.0/go.mod h1:fc+wB5KTk9wQ9sDx0kFXB3A0MaeGHM9AwRStKOQ5vOA= github.com/cosmos/ledger-cosmos-go v0.12.4 h1:drvWt+GJP7Aiw550yeb3ON/zsrgW0jgh5saFCr7pDnw= @@ -1213,6 +1211,8 @@ github.com/influxdata/promql/v2 v2.12.0/go.mod h1:fxOPu+DY0bqCTCECchSRtWfc+0X19y github.com/influxdata/roaring v0.4.13-0.20180809181101-fc520f41fab6/go.mod h1:bSgUQ7q5ZLSO+bKBGqJiCBGAl+9DxyW63zLTujjUlOE= github.com/influxdata/tdigest v0.0.0-20181121200506-bf2b5ad3c0a9/go.mod h1:Js0mqiSBE6Ffsg94weZZ2c+v/ciT8QRHFOap7EKDrR0= github.com/influxdata/usage-client v0.0.0-20160829180054-6d3895376368/go.mod h1:Wbbw6tYNvwa5dlB6304Sd+82Z3f7PmVZHVKU637d4po= +github.com/informalsystems/wasmd v0.45.0-lsm h1:sRldfkkUjZRIOV9+nNw34dS+wrTX6ShhQZd9WqcI+IQ= +github.com/informalsystems/wasmd v0.45.0-lsm/go.mod h1:m0eKqxW2caVw1CJKEcEDaCiLXuo7+BflIlUOwiQU55c= github.com/jackpal/go-nat-pmp v1.0.2/go.mod h1:QPH045xvCAeXUZOxsnwmrtiCoxIr9eob+4orBN1SBKc= github.com/jedisct1/go-minisign v0.0.0-20190909160543-45766022959e/go.mod h1:G1CVv03EnqU1wYL2dFwXxW2An0az9JTl/ZsqXQeBlkU= github.com/jessevdk/go-flags v0.0.0-20141203071132-1679536dcc89/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= diff --git a/tests/e2e/e2e_exec_test.go b/tests/e2e/e2e_exec_test.go index 63381add68b..14519563df3 100644 --- a/tests/e2e/e2e_exec_test.go +++ b/tests/e2e/e2e_exec_test.go @@ -352,9 +352,13 @@ func (s *IntegrationTestSuite) execDistributionFundCommunityPool(c *chain, valId s.T().Logf("Successfully funded community pool") } -func (s *IntegrationTestSuite) runGovExec(c *chain, valIdx int, submitterAddr, govCommand string, proposalFlags []string, fees string) { +func (s *IntegrationTestSuite) runGovExec(c *chain, valIdx int, submitterAddr, govCommand string, proposalFlags []string, fees string, validationFunc func([]byte, []byte) bool) { ctx, cancel := context.WithTimeout(context.Background(), time.Minute) defer cancel() + validateResponse := s.defaultExecValidation(c, valIdx) + if validationFunc != nil { + validateResponse = validationFunc + } gaiaCommand := []string{ gaiadBinary, @@ -375,7 +379,7 @@ func (s *IntegrationTestSuite) runGovExec(c *chain, valIdx int, submitterAddr, g gaiaCommand = concatFlags(gaiaCommand, proposalFlags, generalFlags) s.T().Logf("Executing gaiad tx gov %s on chain %s", govCommand, c.id) - s.executeGaiaTxCommand(ctx, c, gaiaCommand, valIdx, s.defaultExecValidation(c, valIdx)) + s.executeGaiaTxCommand(ctx, c, gaiaCommand, valIdx, validateResponse) s.T().Logf("Successfully executed %s", govCommand) } @@ -762,6 +766,19 @@ func (s *IntegrationTestSuite) defaultExecValidation(chain *chain, valIdx int) f } } +func (s *IntegrationTestSuite) expectTxSubmitError(expectErrString string) func([]byte, []byte) bool { + return func(stdOut []byte, stdErr []byte) bool { + var txResp sdk.TxResponse + if err := cdc.UnmarshalJSON(stdOut, &txResp); err != nil { + return false + } + if strings.Contains(txResp.RawLog, expectErrString) { + return true + } + return false + } +} + func (s *IntegrationTestSuite) executeValidatorBond(c *chain, valIdx int, valOperAddress, delegatorAddr, home, delegateFees string) { ctx, cancel := context.WithTimeout(context.Background(), time.Minute) defer cancel() diff --git a/tests/e2e/e2e_gov_test.go b/tests/e2e/e2e_gov_test.go index a33dbf7b9bb..1d1389e702f 100644 --- a/tests/e2e/e2e_gov_test.go +++ b/tests/e2e/e2e_gov_test.go @@ -8,6 +8,7 @@ import ( providertypes "github.com/cosmos/interchain-security/v4/x/ccv/provider/types" sdk "github.com/cosmos/cosmos-sdk/types" + govtypesv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" govtypesv1beta1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1beta1" paramtypes "github.com/cosmos/cosmos-sdk/x/params/types/proposal" upgradetypes "github.com/cosmos/cosmos-sdk/x/upgrade/types" @@ -221,7 +222,7 @@ func (s *IntegrationTestSuite) verifyChainPassesUpgradeHeight(c *chain, valIdx, func (s *IntegrationTestSuite) submitGovCommand(chainAAPIEndpoint, sender string, proposalID int, govCommand string, proposalFlags []string, expectedSuccessStatus govtypesv1beta1.ProposalStatus) { s.Run(fmt.Sprintf("Running tx gov %s", govCommand), func() { - s.runGovExec(s.chainA, 0, sender, govCommand, proposalFlags, standardFees.String()) + s.runGovExec(s.chainA, 0, sender, govCommand, proposalFlags, standardFees.String(), nil) s.Require().Eventually( func() bool { @@ -235,6 +236,13 @@ func (s *IntegrationTestSuite) submitGovCommand(chainAAPIEndpoint, sender string }) } +func (s *IntegrationTestSuite) submitGovCommandExpectingFailure(sender string, govCommand string, proposalFlags []string) { + s.Run(fmt.Sprintf("Running failing expedited tx gov %s -- expecting error", govCommand), func() { + // should return an error -- the Tx fails at the ante handler + s.runGovExec(s.chainA, 0, sender, govCommand, proposalFlags, standardFees.String(), s.expectTxSubmitError("unsupported expedited proposal type")) + }) +} + // testSetBlocksPerEpoch tests that we can change `BlocksPerEpoch` through a governance proposal func (s *IntegrationTestSuite) testSetBlocksPerEpoch() { chainEndpoint := fmt.Sprintf("http://%s", s.valResources[s.chainA.id][0].GetHostPort("1317/tcp")) @@ -282,3 +290,60 @@ func (s *IntegrationTestSuite) testSetBlocksPerEpoch() { 5*time.Second, ) } + +// ExpeditedProposalRejected tests that expediting a ParamChange proposal fails. +func (s *IntegrationTestSuite) ExpeditedProposalRejected() { + defaultBlocksPerEpoch := providertypes.DefaultParams().BlocksPerEpoch + + // attempt to change but nothing should happen -> proposal fails at ante handler + expectedBlocksPerEpoch := defaultBlocksPerEpoch + 100 + s.writeFailingExpeditedProposal(s.chainA, expectedBlocksPerEpoch) + + validatorAAddr, _ := s.chainA.validators[0].keyInfo.GetAddress() + submitGovFlags := []string{configFile(proposalFailExpedited)} + + s.T().Logf("Submitting, deposit and vote Gov Proposal: Change BlocksPerEpoch parameter - expecting to fail") + s.submitGovCommandExpectingFailure(validatorAAddr.String(), "submit-proposal", submitGovFlags) +} + +// MsgSoftwareUpgrade can be expedited but it can only be submitted using "tx gov submit-proposal" command. +// Messages submitted using "tx gov submit-legacy-proposal" command cannot be expedited.// submit but vote no so that the proposal is not passed +func (s *IntegrationTestSuite) GovSoftwareUpgradeExpedited() { + chainAAPIEndpoint := fmt.Sprintf("http://%s", s.valResources[s.chainA.id][0].GetHostPort("1317/tcp")) + senderAddress, _ := s.chainA.validators[0].keyInfo.GetAddress() + sender := senderAddress.String() + + proposalCounter++ + s.writeExpeditedSoftwareUpgradeProp(s.chainA) + submitGovFlags := []string{configFile(proposalExpeditedSoftwareUpgrade)} + + depositGovFlags := []string{strconv.Itoa(proposalCounter), depositAmount.String()} + voteGovFlags := []string{strconv.Itoa(proposalCounter), "yes=0.1,no=0.8,abstain=0.05,no_with_veto=0.05"} + + s.Run(fmt.Sprintf("Running expedited tx gov %s", "submit-proposal"), func() { + s.submitGovCommand(chainAAPIEndpoint, sender, proposalCounter, "submit-proposal", submitGovFlags, govtypesv1beta1.StatusDepositPeriod) + + s.Require().Eventually( + func() bool { + proposal, err := queryGovProposalV1(chainAAPIEndpoint, proposalCounter) + s.Require().NoError(err) + return proposal.Proposal.Expedited && proposal.GetProposal().Status == govtypesv1.ProposalStatus_PROPOSAL_STATUS_DEPOSIT_PERIOD + }, + 15*time.Second, + 5*time.Second, + ) + s.submitGovCommand(chainAAPIEndpoint, sender, proposalCounter, "deposit", depositGovFlags, govtypesv1beta1.StatusVotingPeriod) + s.submitGovCommand(chainAAPIEndpoint, sender, proposalCounter, "weighted-vote", voteGovFlags, govtypesv1beta1.StatusRejected) // voting no on prop + + // confirm that the proposal was moved from expedited + s.Require().Eventually( + func() bool { + proposal, err := queryGovProposalV1(chainAAPIEndpoint, proposalCounter) + s.Require().NoError(err) + return proposal.Proposal.Expedited == false + }, + 15*time.Second, + 5*time.Second, + ) + }) +} diff --git a/tests/e2e/e2e_setup_test.go b/tests/e2e/e2e_setup_test.go index 9b87e220ce5..2d664c7577f 100644 --- a/tests/e2e/e2e_setup_test.go +++ b/tests/e2e/e2e_setup_test.go @@ -65,10 +65,12 @@ const ( numberOfEvidences = 10 slashingShares int64 = 10000 - proposalMaxTotalBypassFilename = "proposal_max_total_bypass.json" - proposalCommunitySpendFilename = "proposal_community_spend.json" - proposalLSMParamUpdateFilename = "proposal_lsm_param_update.json" - proposalBlocksPerEpochFilename = "proposal_blocks_per_epoch.json" + proposalMaxTotalBypassFilename = "proposal_max_total_bypass.json" + proposalCommunitySpendFilename = "proposal_community_spend.json" + proposalLSMParamUpdateFilename = "proposal_lsm_param_update.json" + proposalBlocksPerEpochFilename = "proposal_blocks_per_epoch.json" + proposalFailExpedited = "proposal_fail_expedited.json" + proposalExpeditedSoftwareUpgrade = "proposal_expedited_software_upgrade.json" // proposalAddConsumerChainFilename = "proposal_add_consumer.json" // proposalRemoveConsumerChainFilename = "proposal_remove_consumer.json" @@ -689,7 +691,8 @@ func (s *IntegrationTestSuite) writeGovCommunitySpendProposal(c *chain, amount s "proposer": "Proposing validator address", "metadata": "Community Pool Spend", "title": "Fund Team!", - "summary": "summary" + "summary": "summary", + "expedited": false } ` propMsgBody := fmt.Sprintf(template, govModuleAddress, recipient, amount.Denom, amount.Amount.String()) @@ -734,7 +737,8 @@ func (s *IntegrationTestSuite) writeLiquidStakingParamsUpdateProposal(c *chain, "metadata": "ipfs://CID", "deposit": "100uatom", "title": "Update LSM Params", - "summary": "e2e-test updating LSM staking params" + "summary": "e2e-test updating LSM staking params", + "expedited": false }` propMsgBody := fmt.Sprintf(template, govAuthority, @@ -778,7 +782,8 @@ func (s *IntegrationTestSuite) writeGovParamChangeProposalBlocksPerEpoch(c *chai "proposer": "sample proposer", "metadata": "sample metadata", "title": "blocks per epoch title", - "summary": "blocks per epoch summary" + "summary": "blocks per epoch summary", + "expedited": false }` propMsgBody := fmt.Sprintf(template, @@ -790,6 +795,71 @@ func (s *IntegrationTestSuite) writeGovParamChangeProposalBlocksPerEpoch(c *chai s.Require().NoError(err) } +// writeFailingExpeditedProposal writes a governance proposal JSON file. +// The proposal fails because only SoftwareUpgrade and CancelSoftwareUpgrade can be expedited. +func (s *IntegrationTestSuite) writeFailingExpeditedProposal(c *chain, blocksPerEpoch int64) { + template := ` + { + "messages":[ + { + "@type": "/cosmos.gov.v1.MsgExecLegacyContent", + "authority": "%s", + "content": { + "@type": "/cosmos.params.v1beta1.ParameterChangeProposal", + "title": "BlocksPerEpoch", + "description": "change blocks per epoch", + "changes": [{ + "subspace": "provider", + "key": "BlocksPerEpoch", + "value": "\"%d\"" + }] + } + } + ], + "deposit": "100uatom", + "proposer": "sample proposer", + "metadata": "sample metadata", + "title": "blocks per epoch title", + "summary": "blocks per epoch summary", + "expedited": true + }` + + propMsgBody := fmt.Sprintf(template, + govAuthority, + blocksPerEpoch, + ) + + err := writeFile(filepath.Join(c.validators[0].configDir(), "config", proposalFailExpedited), []byte(propMsgBody)) + s.Require().NoError(err) +} + +// MsgSoftwareUpgrade can be expedited but it can only be submitted using "tx gov submit-proposal" command. +// Messages submitted using "tx gov submit-legacy-proposal" command cannot be expedited. +func (s *IntegrationTestSuite) writeExpeditedSoftwareUpgradeProp(c *chain) { + body := `{ + "messages": [ + { + "@type": "/cosmos.upgrade.v1beta1.MsgSoftwareUpgrade", + "authority": "cosmos10d07y265gmmuvt4z0w9aw880jnsr700j6zn9kn", + "plan": { + "name": "test-expedited-upgrade", + "height": "123456789", + "info": "test", + "upgraded_client_state": null + } + } + ], + "metadata": "ipfs://CID", + "deposit": "100uatom", + "title": "title", + "summary": "test", + "expedited": true +}` + + err := writeFile(filepath.Join(c.validators[0].configDir(), "config", proposalExpeditedSoftwareUpgrade), []byte(body)) + s.Require().NoError(err) +} + func configFile(filename string) string { filepath := filepath.Join(gaiaConfigPath, filename) return filepath diff --git a/tests/e2e/e2e_test.go b/tests/e2e/e2e_test.go index d3518cd685f..cff0449716f 100644 --- a/tests/e2e/e2e_test.go +++ b/tests/e2e/e2e_test.go @@ -67,6 +67,8 @@ func (s *IntegrationTestSuite) TestGov() { s.AddRemoveConsumerChain() s.testSetBlocksPerEpoch() + s.ExpeditedProposalRejected() + s.GovSoftwareUpgradeExpedited() } func (s *IntegrationTestSuite) TestIBC() { diff --git a/tests/e2e/genesis.go b/tests/e2e/genesis.go index 95bd02191a7..0b6e145243a 100644 --- a/tests/e2e/genesis.go +++ b/tests/e2e/genesis.go @@ -186,6 +186,7 @@ func modifyGenesis(path, moniker, amountStr string, addrAll []sdk.AccAddress, ba maxDepositPeriod := 10 * time.Minute votingPeriod := 15 * time.Second + expeditedVoting := 13 * time.Second govStateLegacy := govlegacytypes.NewGenesisState(1, govlegacytypes.NewDepositParams(sdk.NewCoins(sdk.NewCoin(denom, amnt)), maxDepositPeriod), @@ -203,6 +204,9 @@ func modifyGenesis(path, moniker, amountStr string, addrAll []sdk.AccAddress, ba return fmt.Errorf("failed to migrate v1beta1 gov genesis state to v4: %w", err) } + govStateV4.Params.ExpeditedVotingPeriod = &expeditedVoting + govStateV4.Params.ExpeditedMinDeposit = sdk.NewCoins(sdk.NewCoin(denom, amnt)) // same as normal for testing + govGenStateBz, err := cdc.MarshalJSON(govStateV4) if err != nil { return fmt.Errorf("failed to marshal gov genesis state: %w", err) diff --git a/tests/e2e/query.go b/tests/e2e/query.go index d9d5bc8c4eb..0c58e70fe24 100644 --- a/tests/e2e/query.go +++ b/tests/e2e/query.go @@ -18,6 +18,7 @@ import ( banktypes "github.com/cosmos/cosmos-sdk/x/bank/types" disttypes "github.com/cosmos/cosmos-sdk/x/distribution/types" evidencetypes "github.com/cosmos/cosmos-sdk/x/evidence/types" + govtypesv1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1" govtypesv1beta1 "github.com/cosmos/cosmos-sdk/x/gov/types/v1beta1" stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types" ) @@ -161,6 +162,22 @@ func queryGovProposal(endpoint string, proposalID int) (govtypesv1beta1.QueryPro return govProposalResp, nil } +func queryGovProposalV1(endpoint string, proposalID int) (govtypesv1.QueryProposalResponse, error) { + var govProposalResp govtypesv1.QueryProposalResponse + + path := fmt.Sprintf("%s/cosmos/gov/v1/proposals/%d", endpoint, proposalID) + + body, err := httpGet(path) + if err != nil { + return govProposalResp, fmt.Errorf("failed to execute HTTP request: %w", err) + } + if err := cdc.UnmarshalJSON(body, &govProposalResp); err != nil { + return govProposalResp, err + } + + return govProposalResp, nil +} + func queryAccount(endpoint, address string) (acc authtypes.AccountI, err error) { var res authtypes.QueryAccountResponse resp, err := http.Get(fmt.Sprintf("%s/cosmos/auth/v1beta1/accounts/%s", endpoint, address)) diff --git a/types/errors/errors.go b/types/errors/errors.go index edcb2089fab..0b1962dee07 100644 --- a/types/errors/errors.go +++ b/types/errors/errors.go @@ -34,4 +34,7 @@ var ( // ErrInsufficientStake is used when the account has insufficient staked tokens. ErrInsufficientStake = errorsmod.Register(codespace, 9, "insufficient stake") + + // ErrInvalidExpeditedProposal is used when an expedite proposal is submitted for an unsupported proposal type. + ErrInvalidExpeditedProposal = errorsmod.Register(codespace, 10, "unsupported expedited proposal type") )