mirror of https://github.com/certusone/wasmd.git
Add wasm gov proposals to cli (#183)
* Add wasm gov proposals to cli * Update changelog * Rework gov proposal rest handlers * Fix json naming * Pretty print byte arrays in CLI * Replace ambiguous cli flag and rest routes * Minor cli usage doc update
This commit is contained in:
parent
09a20da7c6
commit
9ab18fc46f
|
@ -37,6 +37,7 @@ Ref: https://keepachangelog.com/en/1.0.0/
|
|||
## [Unreleased]
|
||||
|
||||
### Features
|
||||
* (wasmd) [\#178](https://github.com/CosmWasm/wasmd/issues/178) Add cli support for wasm gov proposals
|
||||
* (wasmd) [\#163](https://github.com/CosmWasm/wasmd/issues/163) Control who can instantiate code
|
||||
* (wasmd) [\#164](https://github.com/CosmWasm/wasmd/issues/164) Control who can upload code
|
||||
* (wasmd) [\#173](https://github.com/CosmWasm/wasmd/issues/173) Gov proposal types and handler
|
||||
|
|
|
@ -5,9 +5,8 @@ import (
|
|||
"os"
|
||||
"path/filepath"
|
||||
|
||||
"github.com/spf13/viper"
|
||||
|
||||
"github.com/CosmWasm/wasmd/x/wasm"
|
||||
wasmclient "github.com/CosmWasm/wasmd/x/wasm/client"
|
||||
bam "github.com/cosmos/cosmos-sdk/baseapp"
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
"github.com/cosmos/cosmos-sdk/simapp"
|
||||
|
@ -30,6 +29,7 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/x/supply"
|
||||
"github.com/cosmos/cosmos-sdk/x/upgrade"
|
||||
upgradeclient "github.com/cosmos/cosmos-sdk/x/upgrade/client"
|
||||
"github.com/spf13/viper"
|
||||
abci "github.com/tendermint/tendermint/abci/types"
|
||||
"github.com/tendermint/tendermint/libs/cli"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
|
@ -56,7 +56,7 @@ var (
|
|||
staking.AppModuleBasic{},
|
||||
mint.AppModuleBasic{},
|
||||
distr.AppModuleBasic{},
|
||||
gov.NewAppModuleBasic(paramsclient.ProposalHandler, distr.ProposalHandler, upgradeclient.ProposalHandler),
|
||||
gov.NewAppModuleBasic(append(wasmclient.ProposalHandlers, paramsclient.ProposalHandler, distr.ProposalHandler, upgradeclient.ProposalHandler)...),
|
||||
params.AppModuleBasic{},
|
||||
wasm.AppModuleBasic{},
|
||||
crisis.AppModuleBasic{},
|
||||
|
|
|
@ -17,7 +17,6 @@ import (
|
|||
authrest "github.com/cosmos/cosmos-sdk/x/auth/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank"
|
||||
bankcmd "github.com/cosmos/cosmos-sdk/x/bank/client/cli"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
"github.com/spf13/viper"
|
||||
|
||||
|
|
|
@ -0,0 +1,295 @@
|
|||
package cli
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
|
||||
"github.com/CosmWasm/wasmd/x/wasm/internal/types"
|
||||
"github.com/cosmos/cosmos-sdk/client/context"
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
sdkerrors "github.com/cosmos/cosmos-sdk/types/errors"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/client/utils"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/client/cli"
|
||||
govtypes "github.com/cosmos/cosmos-sdk/x/gov/types"
|
||||
"github.com/pkg/errors"
|
||||
"github.com/spf13/cobra"
|
||||
"github.com/spf13/viper"
|
||||
)
|
||||
|
||||
func ProposalStoreCodeCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
Use: "wasm-store [wasm file] --source [source] --builder [builder] --title [text] --description [text] --run-as [address]",
|
||||
Short: "Submit a wasm binary proposal",
|
||||
Args: cobra.ExactArgs(1),
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
inBuf := bufio.NewReader(cmd.InOrStdin())
|
||||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
src, err := parseStoreCodeArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if len(viper.GetString(flagRunAs)) == 0 {
|
||||
return errors.New("run-as address is required")
|
||||
}
|
||||
runAsAddr, err := sdk.AccAddressFromBech32(viper.GetString(flagRunAs))
|
||||
if err != nil {
|
||||
return errors.Wrap(err, "run-as")
|
||||
}
|
||||
content := types.StoreCodeProposal{
|
||||
WasmProposal: types.WasmProposal{
|
||||
Title: viper.GetString(cli.FlagTitle),
|
||||
Description: viper.GetString(cli.FlagDescription),
|
||||
},
|
||||
RunAs: runAsAddr,
|
||||
WASMByteCode: src.WASMByteCode,
|
||||
Source: src.Source,
|
||||
Builder: src.Builder,
|
||||
InstantiatePermission: src.InstantiatePermission,
|
||||
}
|
||||
|
||||
deposit, err := sdk.ParseCoins(viper.GetString(cli.FlagDeposit))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
msg := govtypes.NewMsgSubmitProposal(content, deposit, cliCtx.GetFromAddress())
|
||||
if err = msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
|
||||
cmd.Flags().String(flagSource, "", "A valid URI reference to the contract's source code, optional")
|
||||
cmd.Flags().String(flagBuilder, "", "A valid docker tag for the build system, optional")
|
||||
cmd.Flags().String(flagRunAs, "", "The address that is stored as code creator")
|
||||
cmd.Flags().String(flagInstantiateByEverybody, "", "Everybody can instantiate a contract from the code, optional")
|
||||
cmd.Flags().String(flagInstantiateByAddress, "", "Only this address can instantiate a contract instance from the code, optional")
|
||||
|
||||
// proposal flags
|
||||
cmd.Flags().String(cli.FlagTitle, "", "Title of proposal")
|
||||
cmd.Flags().String(cli.FlagDescription, "", "Description of proposal")
|
||||
cmd.Flags().String(cli.FlagDeposit, "", "Deposit of proposal")
|
||||
cmd.Flags().String(cli.FlagProposal, "", "Proposal file path (if this path is given, other proposal flags are ignored)")
|
||||
// type values must match the "ProposalHandler" "routes" in cli
|
||||
cmd.Flags().String(flagProposalType, "", "Type of proposal, types: store-code/instantiate/migrate/update-admin/clear-admin/text/parameter_change/software_upgrade")
|
||||
return cmd
|
||||
}
|
||||
|
||||
func ProposalInstantiateContractCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
Use: "instantiate-contract [code_id_int64] [json_encoded_init_args] --label [text] --title [text] --description [text] --run-as [address] --admin [address,optional] --amount [coins,optional]",
|
||||
Short: "Submit an instantiate wasm contract proposal",
|
||||
Args: cobra.ExactArgs(2),
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
inBuf := bufio.NewReader(cmd.InOrStdin())
|
||||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
src, err := parseInstantiateArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if len(viper.GetString(flagRunAs)) == 0 {
|
||||
return errors.New("creator address is required")
|
||||
}
|
||||
creator, err := sdk.AccAddressFromBech32(viper.GetString(flagRunAs))
|
||||
if err != nil {
|
||||
return errors.Wrap(err, "creator")
|
||||
}
|
||||
content := types.InstantiateContractProposal{
|
||||
WasmProposal: types.WasmProposal{
|
||||
Title: viper.GetString(cli.FlagTitle),
|
||||
Description: viper.GetString(cli.FlagDescription),
|
||||
},
|
||||
RunAs: creator,
|
||||
Admin: src.Admin,
|
||||
Code: src.Code,
|
||||
Label: src.Label,
|
||||
InitMsg: src.InitMsg,
|
||||
InitFunds: src.InitFunds,
|
||||
}
|
||||
|
||||
deposit, err := sdk.ParseCoins(viper.GetString(cli.FlagDeposit))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
msg := govtypes.NewMsgSubmitProposal(content, deposit, cliCtx.GetFromAddress())
|
||||
if err = msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
cmd.Flags().String(flagAmount, "", "Coins to send to the contract during instantiation")
|
||||
cmd.Flags().String(flagLabel, "", "A human-readable name for this contract in lists")
|
||||
cmd.Flags().String(flagAdmin, "", "Address of an admin")
|
||||
cmd.Flags().String(flagRunAs, "", "The address that pays the init funds. It is the creator of the contract and passed to the contract as sender on proposal execution")
|
||||
|
||||
// proposal flags
|
||||
cmd.Flags().String(cli.FlagTitle, "", "Title of proposal")
|
||||
cmd.Flags().String(cli.FlagDescription, "", "Description of proposal")
|
||||
cmd.Flags().String(cli.FlagDeposit, "", "Deposit of proposal")
|
||||
cmd.Flags().String(cli.FlagProposal, "", "Proposal file path (if this path is given, other proposal flags are ignored)")
|
||||
// type values must match the "ProposalHandler" "routes" in cli
|
||||
cmd.Flags().String(flagProposalType, "", "Type of proposal, types: store-code/instantiate/migrate/update-admin/clear-admin/text/parameter_change/software_upgrade")
|
||||
return cmd
|
||||
}
|
||||
|
||||
func ProposalMigrateContractCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
Use: "migrate-contract [contract_addr_bech32] [new_code_id_int64] [json_encoded_migration_args]",
|
||||
Short: "Submit a migrate wasm contract to a new code version proposal",
|
||||
Args: cobra.ExactArgs(3),
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
inBuf := bufio.NewReader(cmd.InOrStdin())
|
||||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
src, err := parseMigrateContractArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if len(viper.GetString(flagRunAs)) == 0 {
|
||||
return errors.New("run-as address is required")
|
||||
}
|
||||
runAs, err := sdk.AccAddressFromBech32(viper.GetString(flagRunAs))
|
||||
if err != nil {
|
||||
return errors.Wrap(err, "run-as")
|
||||
}
|
||||
|
||||
content := types.MigrateContractProposal{
|
||||
WasmProposal: types.WasmProposal{
|
||||
Title: viper.GetString(cli.FlagTitle),
|
||||
Description: viper.GetString(cli.FlagDescription),
|
||||
},
|
||||
Contract: src.Contract,
|
||||
Code: src.Code,
|
||||
MigrateMsg: src.MigrateMsg,
|
||||
RunAs: runAs,
|
||||
}
|
||||
|
||||
deposit, err := sdk.ParseCoins(viper.GetString(cli.FlagDeposit))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
msg := govtypes.NewMsgSubmitProposal(content, deposit, cliCtx.GetFromAddress())
|
||||
if err = msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
cmd.Flags().String(flagRunAs, "", "The address that is passed as sender to the contract on proposal execution")
|
||||
|
||||
// proposal flags
|
||||
cmd.Flags().String(cli.FlagTitle, "", "Title of proposal")
|
||||
cmd.Flags().String(cli.FlagDescription, "", "Description of proposal")
|
||||
cmd.Flags().String(cli.FlagDeposit, "", "Deposit of proposal")
|
||||
cmd.Flags().String(cli.FlagProposal, "", "Proposal file path (if this path is given, other proposal flags are ignored)")
|
||||
// type values must match the "ProposalHandler" "routes" in cli
|
||||
cmd.Flags().String(flagProposalType, "", "Type of proposal, types: store-code/instantiate/migrate/update-admin/clear-admin/text/parameter_change/software_upgrade")
|
||||
return cmd
|
||||
}
|
||||
|
||||
func ProposalUpdateContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
Use: "set-contract-admin [contract_addr_bech32] [new_admin_addr_bech32]",
|
||||
Short: "Submit a new admin for a contract proposal",
|
||||
Args: cobra.ExactArgs(2),
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
inBuf := bufio.NewReader(cmd.InOrStdin())
|
||||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
src, err := parseUpdateContractAdminArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
content := types.UpdateAdminProposal{
|
||||
WasmProposal: types.WasmProposal{
|
||||
Title: viper.GetString(cli.FlagTitle),
|
||||
Description: viper.GetString(cli.FlagDescription),
|
||||
},
|
||||
Contract: src.Contract,
|
||||
NewAdmin: src.NewAdmin,
|
||||
}
|
||||
|
||||
deposit, err := sdk.ParseCoins(viper.GetString(cli.FlagDeposit))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
msg := govtypes.NewMsgSubmitProposal(content, deposit, cliCtx.GetFromAddress())
|
||||
if err = msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
// proposal flags
|
||||
cmd.Flags().String(cli.FlagTitle, "", "Title of proposal")
|
||||
cmd.Flags().String(cli.FlagDescription, "", "Description of proposal")
|
||||
cmd.Flags().String(cli.FlagDeposit, "", "Deposit of proposal")
|
||||
cmd.Flags().String(cli.FlagProposal, "", "Proposal file path (if this path is given, other proposal flags are ignored)")
|
||||
// type values must match the "ProposalHandler" "routes" in cli
|
||||
cmd.Flags().String(flagProposalType, "", "Type of proposal, types: store-code/instantiate/migrate/update-admin/clear-admin/text/parameter_change/software_upgrade")
|
||||
return cmd
|
||||
}
|
||||
|
||||
func ProposalClearContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
Use: "clear-contract-admin [contract_addr_bech32]",
|
||||
Short: "Submit a clear admin for a contract to prevent further migrations proposal",
|
||||
Args: cobra.ExactArgs(1),
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
inBuf := bufio.NewReader(cmd.InOrStdin())
|
||||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
contractAddr, err := sdk.AccAddressFromBech32(args[0])
|
||||
if err != nil {
|
||||
return sdkerrors.Wrap(err, "contract")
|
||||
}
|
||||
|
||||
content := types.ClearAdminProposal{
|
||||
WasmProposal: types.WasmProposal{
|
||||
Title: viper.GetString(cli.FlagTitle),
|
||||
Description: viper.GetString(cli.FlagDescription),
|
||||
},
|
||||
Contract: contractAddr,
|
||||
}
|
||||
|
||||
deposit, err := sdk.ParseCoins(viper.GetString(cli.FlagDeposit))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
msg := govtypes.NewMsgSubmitProposal(content, deposit, cliCtx.GetFromAddress())
|
||||
if err = msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
// proposal flags
|
||||
cmd.Flags().String(cli.FlagTitle, "", "Title of proposal")
|
||||
cmd.Flags().String(cli.FlagDescription, "", "Description of proposal")
|
||||
cmd.Flags().String(cli.FlagDeposit, "", "Deposit of proposal")
|
||||
cmd.Flags().String(cli.FlagProposal, "", "Proposal file path (if this path is given, other proposal flags are ignored)")
|
||||
// type values must match the "ProposalHandler" "routes" in cli
|
||||
cmd.Flags().String(flagProposalType, "", "Type of proposal, types: store-code/instantiate/migrate/update-admin/clear-admin/text/parameter_change/software_upgrade")
|
||||
return cmd
|
||||
}
|
|
@ -25,24 +25,12 @@ func MigrateContractCmd(cdc *codec.Codec) *cobra.Command {
|
|||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
contractAddr, err := sdk.AccAddressFromBech32(args[0])
|
||||
msg, err := parseMigrateContractArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return sdkerrors.Wrap(err, "contract")
|
||||
return err
|
||||
}
|
||||
|
||||
// get the id of the code to instantiate
|
||||
codeID, err := strconv.ParseUint(args[1], 10, 64)
|
||||
if err != nil {
|
||||
return sdkerrors.Wrap(err, "code id")
|
||||
}
|
||||
|
||||
migrateMsg := args[2]
|
||||
|
||||
msg := types.MsgMigrateContract{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
Contract: contractAddr,
|
||||
Code: codeID,
|
||||
MigrateMsg: []byte(migrateMsg),
|
||||
if err := msg.ValidateBasic(); err != nil {
|
||||
return nil
|
||||
}
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
|
@ -50,6 +38,29 @@ func MigrateContractCmd(cdc *codec.Codec) *cobra.Command {
|
|||
return cmd
|
||||
}
|
||||
|
||||
func parseMigrateContractArgs(args []string, cliCtx context.CLIContext) (types.MsgMigrateContract, error) {
|
||||
contractAddr, err := sdk.AccAddressFromBech32(args[0])
|
||||
if err != nil {
|
||||
return types.MsgMigrateContract{}, sdkerrors.Wrap(err, "contract")
|
||||
}
|
||||
|
||||
// get the id of the code to instantiate
|
||||
codeID, err := strconv.ParseUint(args[1], 10, 64)
|
||||
if err != nil {
|
||||
return types.MsgMigrateContract{}, sdkerrors.Wrap(err, "code id")
|
||||
}
|
||||
|
||||
migrateMsg := args[2]
|
||||
|
||||
msg := types.MsgMigrateContract{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
Contract: contractAddr,
|
||||
Code: codeID,
|
||||
MigrateMsg: []byte(migrateMsg),
|
||||
}
|
||||
return msg, nil
|
||||
}
|
||||
|
||||
// UpdateContractAdminCmd sets an new admin for a contract
|
||||
func UpdateContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
|
@ -61,19 +72,12 @@ func UpdateContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
|||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
contractAddr, err := sdk.AccAddressFromBech32(args[0])
|
||||
msg, err := parseUpdateContractAdminArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return sdkerrors.Wrap(err, "contract")
|
||||
return err
|
||||
}
|
||||
newAdmin, err := sdk.AccAddressFromBech32(args[1])
|
||||
if err != nil {
|
||||
return sdkerrors.Wrap(err, "new admin")
|
||||
}
|
||||
|
||||
msg := types.MsgUpdateAdmin{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
Contract: contractAddr,
|
||||
NewAdmin: newAdmin,
|
||||
if err := msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
|
@ -81,6 +85,24 @@ func UpdateContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
|||
return cmd
|
||||
}
|
||||
|
||||
func parseUpdateContractAdminArgs(args []string, cliCtx context.CLIContext) (types.MsgUpdateAdmin, error) {
|
||||
contractAddr, err := sdk.AccAddressFromBech32(args[0])
|
||||
if err != nil {
|
||||
return types.MsgUpdateAdmin{}, sdkerrors.Wrap(err, "contract")
|
||||
}
|
||||
newAdmin, err := sdk.AccAddressFromBech32(args[1])
|
||||
if err != nil {
|
||||
return types.MsgUpdateAdmin{}, sdkerrors.Wrap(err, "new admin")
|
||||
}
|
||||
|
||||
msg := types.MsgUpdateAdmin{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
Contract: contractAddr,
|
||||
NewAdmin: newAdmin,
|
||||
}
|
||||
return msg, nil
|
||||
}
|
||||
|
||||
// ClearContractAdminCmd clears an admin for a contract
|
||||
func ClearContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
|
@ -101,6 +123,9 @@ func ClearContractAdminCmd(cdc *codec.Codec) *cobra.Command {
|
|||
Sender: cliCtx.GetFromAddress(),
|
||||
Contract: contractAddr,
|
||||
}
|
||||
if err := msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
|
|
|
@ -23,13 +23,15 @@ import (
|
|||
)
|
||||
|
||||
const (
|
||||
flagTo = "to"
|
||||
flagAmount = "amount"
|
||||
flagSource = "source"
|
||||
flagBuilder = "builder"
|
||||
flagLabel = "label"
|
||||
flagAdmin = "admin"
|
||||
flagNoAdmin = "no-admin"
|
||||
flagAmount = "amount"
|
||||
flagSource = "source"
|
||||
flagBuilder = "builder"
|
||||
flagLabel = "label"
|
||||
flagAdmin = "admin"
|
||||
flagRunAs = "run-as"
|
||||
flagInstantiateByEverybody = "instantiate-everybody"
|
||||
flagInstantiateByAddress = "instantiate-only-address"
|
||||
flagProposalType = "type"
|
||||
)
|
||||
|
||||
// GetTxCmd returns the transaction commands for this module
|
||||
|
@ -63,37 +65,11 @@ func StoreCodeCmd(cdc *codec.Codec) *cobra.Command {
|
|||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
// parse coins trying to be sent
|
||||
wasm, err := ioutil.ReadFile(args[0])
|
||||
msg, err := parseStoreCodeArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
source := viper.GetString(flagSource)
|
||||
|
||||
builder := viper.GetString(flagBuilder)
|
||||
|
||||
// gzip the wasm file
|
||||
if wasmUtils.IsWasm(wasm) {
|
||||
wasm, err = wasmUtils.GzipIt(wasm)
|
||||
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
} else if !wasmUtils.IsGzip(wasm) {
|
||||
return fmt.Errorf("invalid input file. Use wasm binary or gzip")
|
||||
}
|
||||
|
||||
// build and sign the transaction, then broadcast to Tendermint
|
||||
msg := types.MsgStoreCode{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
WASMByteCode: wasm,
|
||||
Source: source,
|
||||
Builder: builder,
|
||||
}
|
||||
err = msg.ValidateBasic()
|
||||
|
||||
if err != nil {
|
||||
if err = msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
|
@ -103,58 +79,70 @@ func StoreCodeCmd(cdc *codec.Codec) *cobra.Command {
|
|||
|
||||
cmd.Flags().String(flagSource, "", "A valid URI reference to the contract's source code, optional")
|
||||
cmd.Flags().String(flagBuilder, "", "A valid docker tag for the build system, optional")
|
||||
cmd.Flags().String(flagInstantiateByEverybody, "", "Everybody can instantiate a contract from the code, optional")
|
||||
cmd.Flags().String(flagInstantiateByAddress, "", "Only this address can instantiate a contract instance from the code, optional")
|
||||
|
||||
return cmd
|
||||
}
|
||||
|
||||
func parseStoreCodeArgs(args []string, cliCtx context.CLIContext) (types.MsgStoreCode, error) {
|
||||
wasm, err := ioutil.ReadFile(args[0])
|
||||
if err != nil {
|
||||
return types.MsgStoreCode{}, err
|
||||
}
|
||||
|
||||
// gzip the wasm file
|
||||
if wasmUtils.IsWasm(wasm) {
|
||||
wasm, err = wasmUtils.GzipIt(wasm)
|
||||
|
||||
if err != nil {
|
||||
return types.MsgStoreCode{}, err
|
||||
}
|
||||
} else if !wasmUtils.IsGzip(wasm) {
|
||||
return types.MsgStoreCode{}, fmt.Errorf("invalid input file. Use wasm binary or gzip")
|
||||
}
|
||||
|
||||
var perm *types.AccessConfig
|
||||
if onlyAddrStr := viper.GetString(flagInstantiateByAddress); onlyAddrStr != "" {
|
||||
allowedAddr, err := sdk.AccAddressFromBech32(onlyAddrStr)
|
||||
if err != nil {
|
||||
return types.MsgStoreCode{}, sdkerrors.Wrap(err, flagInstantiateByAddress)
|
||||
}
|
||||
x := types.OnlyAddress.With(allowedAddr)
|
||||
perm = &x
|
||||
} else if everybody := viper.GetBool(flagInstantiateByEverybody); everybody {
|
||||
perm = &types.AllowEverybody
|
||||
}
|
||||
|
||||
// build and sign the transaction, then broadcast to Tendermint
|
||||
msg := types.MsgStoreCode{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
WASMByteCode: wasm,
|
||||
Source: viper.GetString(flagSource),
|
||||
Builder: viper.GetString(flagBuilder),
|
||||
InstantiatePermission: perm,
|
||||
}
|
||||
return msg, nil
|
||||
}
|
||||
|
||||
// InstantiateContractCmd will instantiate a contract from previously uploaded code.
|
||||
func InstantiateContractCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
Use: "instantiate [code_id_int64] [json_encoded_init_args]",
|
||||
Use: "instantiate [code_id_int64] [json_encoded_init_args] --label [text] --admin [address,optional] --amount [coins,optional]",
|
||||
Short: "Instantiate a wasm contract",
|
||||
Args: cobra.RangeArgs(2, 3),
|
||||
Args: cobra.ExactArgs(2),
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
inBuf := bufio.NewReader(cmd.InOrStdin())
|
||||
txBldr := auth.NewTxBuilderFromCLI(inBuf).WithTxEncoder(utils.GetTxEncoder(cdc))
|
||||
cliCtx := context.NewCLIContextWithInput(inBuf).WithCodec(cdc)
|
||||
|
||||
// get the id of the code to instantiate
|
||||
codeID, err := strconv.ParseUint(args[0], 10, 64)
|
||||
msg, err := parseInstantiateArgs(args, cliCtx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
amounstStr := viper.GetString(flagAmount)
|
||||
amount, err := sdk.ParseCoins(amounstStr)
|
||||
if err != nil {
|
||||
if err := msg.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
label := viper.GetString(flagLabel)
|
||||
if label == "" {
|
||||
return fmt.Errorf("Label is required on all contracts")
|
||||
}
|
||||
|
||||
initMsg := args[1]
|
||||
|
||||
adminStr := viper.GetString(flagAdmin)
|
||||
var adminAddr sdk.AccAddress
|
||||
if len(adminStr) != 0 {
|
||||
adminAddr, err = sdk.AccAddressFromBech32(adminStr)
|
||||
if err != nil {
|
||||
return sdkerrors.Wrap(err, "admin")
|
||||
}
|
||||
}
|
||||
|
||||
// build and sign the transaction, then broadcast to Tendermint
|
||||
msg := types.MsgInstantiateContract{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
Code: codeID,
|
||||
Label: label,
|
||||
InitFunds: amount,
|
||||
InitMsg: []byte(initMsg),
|
||||
Admin: adminAddr,
|
||||
}
|
||||
return utils.GenerateOrBroadcastMsgs(cliCtx, txBldr, []sdk.Msg{msg})
|
||||
},
|
||||
}
|
||||
|
@ -165,6 +153,47 @@ func InstantiateContractCmd(cdc *codec.Codec) *cobra.Command {
|
|||
return cmd
|
||||
}
|
||||
|
||||
func parseInstantiateArgs(args []string, cliCtx context.CLIContext) (types.MsgInstantiateContract, error) {
|
||||
// get the id of the code to instantiate
|
||||
codeID, err := strconv.ParseUint(args[0], 10, 64)
|
||||
if err != nil {
|
||||
return types.MsgInstantiateContract{}, err
|
||||
}
|
||||
|
||||
amounstStr := viper.GetString(flagAmount)
|
||||
amount, err := sdk.ParseCoins(amounstStr)
|
||||
if err != nil {
|
||||
return types.MsgInstantiateContract{}, err
|
||||
}
|
||||
|
||||
label := viper.GetString(flagLabel)
|
||||
if label == "" {
|
||||
return types.MsgInstantiateContract{}, fmt.Errorf("Label is required on all contracts")
|
||||
}
|
||||
|
||||
initMsg := args[1]
|
||||
|
||||
adminStr := viper.GetString(flagAdmin)
|
||||
var adminAddr sdk.AccAddress
|
||||
if len(adminStr) != 0 {
|
||||
adminAddr, err = sdk.AccAddressFromBech32(adminStr)
|
||||
if err != nil {
|
||||
return types.MsgInstantiateContract{}, sdkerrors.Wrap(err, "admin")
|
||||
}
|
||||
}
|
||||
|
||||
// build and sign the transaction, then broadcast to Tendermint
|
||||
msg := types.MsgInstantiateContract{
|
||||
Sender: cliCtx.GetFromAddress(),
|
||||
Code: codeID,
|
||||
Label: label,
|
||||
InitFunds: amount,
|
||||
InitMsg: []byte(initMsg),
|
||||
Admin: adminAddr,
|
||||
}
|
||||
return msg, nil
|
||||
}
|
||||
|
||||
// ExecuteContractCmd will instantiate a contract from previously uploaded code.
|
||||
func ExecuteContractCmd(cdc *codec.Codec) *cobra.Command {
|
||||
cmd := &cobra.Command{
|
||||
|
|
|
@ -0,0 +1,16 @@
|
|||
package client
|
||||
|
||||
import (
|
||||
"github.com/CosmWasm/wasmd/x/wasm/client/cli"
|
||||
"github.com/CosmWasm/wasmd/x/wasm/client/rest"
|
||||
govclient "github.com/cosmos/cosmos-sdk/x/gov/client"
|
||||
)
|
||||
|
||||
// ProposalHandlers define the wasm cli proposal types and rest handler.
|
||||
var ProposalHandlers = []govclient.ProposalHandler{
|
||||
govclient.NewProposalHandler(cli.ProposalStoreCodeCmd, rest.StoreCodeProposalHandler),
|
||||
govclient.NewProposalHandler(cli.ProposalInstantiateContractCmd, rest.InstantiateProposalHandler),
|
||||
govclient.NewProposalHandler(cli.ProposalMigrateContractCmd, rest.MigrateProposalHandler),
|
||||
govclient.NewProposalHandler(cli.ProposalUpdateContractAdminCmd, rest.UpdateContractAdminProposalHandler),
|
||||
govclient.NewProposalHandler(cli.ProposalClearContractAdminCmd, rest.ClearContractAdminProposalHandler),
|
||||
}
|
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,270 @@
|
|||
package rest
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"net/http"
|
||||
|
||||
"github.com/CosmWasm/wasmd/x/wasm/internal/types"
|
||||
"github.com/cosmos/cosmos-sdk/client/context"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/types/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/client/utils"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov"
|
||||
govrest "github.com/cosmos/cosmos-sdk/x/gov/client/rest"
|
||||
)
|
||||
|
||||
type StoreCodeProposalJsonReq struct {
|
||||
BaseReq rest.BaseReq `json:"base_req" yaml:"base_req"`
|
||||
|
||||
Title string `json:"title" yaml:"title"`
|
||||
Description string `json:"description" yaml:"description"`
|
||||
Proposer sdk.AccAddress `json:"proposer" yaml:"proposer"`
|
||||
Deposit sdk.Coins `json:"deposit" yaml:"deposit"`
|
||||
|
||||
RunAs sdk.AccAddress `json:"run_as" yaml:"run_as"`
|
||||
// WASMByteCode can be raw or gzip compressed
|
||||
WASMByteCode []byte `json:"wasm_byte_code" yaml:"wasm_byte_code"`
|
||||
// Source is a valid absolute HTTPS URI to the contract's source code, optional
|
||||
Source string `json:"source" yaml:"source"`
|
||||
// Builder is a valid docker image name with tag, optional
|
||||
Builder string `json:"builder" yaml:"builder"`
|
||||
// InstantiatePermission to apply on contract creation, optional
|
||||
InstantiatePermission *types.AccessConfig `json:"instantiate_permission" yaml:"instantiate_permission"`
|
||||
}
|
||||
|
||||
func (s StoreCodeProposalJsonReq) Content() gov.Content {
|
||||
return types.StoreCodeProposal{
|
||||
WasmProposal: types.WasmProposal{
|
||||
Title: s.Title,
|
||||
Description: s.Description,
|
||||
},
|
||||
RunAs: s.RunAs,
|
||||
WASMByteCode: s.WASMByteCode,
|
||||
Source: s.Source,
|
||||
Builder: s.Builder,
|
||||
InstantiatePermission: s.InstantiatePermission,
|
||||
}
|
||||
}
|
||||
func (s StoreCodeProposalJsonReq) GetProposer() sdk.AccAddress {
|
||||
return s.Proposer
|
||||
}
|
||||
func (s StoreCodeProposalJsonReq) GetDeposit() sdk.Coins {
|
||||
return s.Deposit
|
||||
}
|
||||
func (s StoreCodeProposalJsonReq) GetBaseReq() rest.BaseReq {
|
||||
return s.BaseReq
|
||||
}
|
||||
|
||||
func StoreCodeProposalHandler(cliCtx context.CLIContext) govrest.ProposalRESTHandler {
|
||||
return govrest.ProposalRESTHandler{
|
||||
SubRoute: "wasm_store_code",
|
||||
Handler: func(w http.ResponseWriter, r *http.Request) {
|
||||
var req StoreCodeProposalJsonReq
|
||||
if !rest.ReadRESTReq(w, r, cliCtx.Codec, &req) {
|
||||
return
|
||||
}
|
||||
toStdTxResponse(cliCtx, w, req)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
type InstantiateProposalJsonReq struct {
|
||||
BaseReq rest.BaseReq `json:"base_req" yaml:"base_req"`
|
||||
|
||||
Title string `json:"title" yaml:"title"`
|
||||
Description string `json:"description" yaml:"description"`
|
||||
|
||||
Proposer sdk.AccAddress `json:"proposer" yaml:"proposer"`
|
||||
Deposit sdk.Coins `json:"deposit" yaml:"deposit"`
|
||||
|
||||
RunAs sdk.AccAddress `json:"run_as" yaml:"run_as"`
|
||||
// Admin is an optional address that can execute migrations
|
||||
Admin sdk.AccAddress `json:"admin,omitempty" yaml:"admin"`
|
||||
Code uint64 `json:"code_id" yaml:"code_id"`
|
||||
Label string `json:"label" yaml:"label"`
|
||||
InitMsg json.RawMessage `json:"init_msg" yaml:"init_msg"`
|
||||
InitFunds sdk.Coins `json:"init_funds" yaml:"init_funds"`
|
||||
}
|
||||
|
||||
func (s InstantiateProposalJsonReq) Content() gov.Content {
|
||||
return types.InstantiateContractProposal{
|
||||
WasmProposal: types.WasmProposal{Title: s.Title, Description: s.Description},
|
||||
RunAs: s.RunAs,
|
||||
Admin: s.Admin,
|
||||
Code: s.Code,
|
||||
Label: s.Label,
|
||||
InitMsg: s.InitMsg,
|
||||
InitFunds: s.InitFunds,
|
||||
}
|
||||
}
|
||||
func (s InstantiateProposalJsonReq) GetProposer() sdk.AccAddress {
|
||||
return s.Proposer
|
||||
}
|
||||
func (s InstantiateProposalJsonReq) GetDeposit() sdk.Coins {
|
||||
return s.Deposit
|
||||
}
|
||||
func (s InstantiateProposalJsonReq) GetBaseReq() rest.BaseReq {
|
||||
return s.BaseReq
|
||||
}
|
||||
|
||||
func InstantiateProposalHandler(cliCtx context.CLIContext) govrest.ProposalRESTHandler {
|
||||
return govrest.ProposalRESTHandler{
|
||||
SubRoute: "wasm_instantiate",
|
||||
Handler: func(w http.ResponseWriter, r *http.Request) {
|
||||
var req InstantiateProposalJsonReq
|
||||
if !rest.ReadRESTReq(w, r, cliCtx.Codec, &req) {
|
||||
return
|
||||
}
|
||||
toStdTxResponse(cliCtx, w, req)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
type MigrateProposalJsonReq struct {
|
||||
BaseReq rest.BaseReq `json:"base_req" yaml:"base_req"`
|
||||
|
||||
Title string `json:"title" yaml:"title"`
|
||||
Description string `json:"description" yaml:"description"`
|
||||
|
||||
Proposer sdk.AccAddress `json:"proposer" yaml:"proposer"`
|
||||
Deposit sdk.Coins `json:"deposit" yaml:"deposit"`
|
||||
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
Code uint64 `json:"code_id" yaml:"code_id"`
|
||||
MigrateMsg json.RawMessage `json:"msg" yaml:"msg"`
|
||||
// RunAs is the role that is passed to the contract's environment
|
||||
RunAs sdk.AccAddress `json:"run_as" yaml:"run_as"`
|
||||
}
|
||||
|
||||
func (s MigrateProposalJsonReq) Content() gov.Content {
|
||||
return types.MigrateContractProposal{
|
||||
WasmProposal: types.WasmProposal{Title: s.Title, Description: s.Description},
|
||||
Contract: s.Contract,
|
||||
Code: s.Code,
|
||||
MigrateMsg: s.MigrateMsg,
|
||||
RunAs: s.RunAs,
|
||||
}
|
||||
}
|
||||
func (s MigrateProposalJsonReq) GetProposer() sdk.AccAddress {
|
||||
return s.Proposer
|
||||
}
|
||||
func (s MigrateProposalJsonReq) GetDeposit() sdk.Coins {
|
||||
return s.Deposit
|
||||
}
|
||||
func (s MigrateProposalJsonReq) GetBaseReq() rest.BaseReq {
|
||||
return s.BaseReq
|
||||
}
|
||||
func MigrateProposalHandler(cliCtx context.CLIContext) govrest.ProposalRESTHandler {
|
||||
return govrest.ProposalRESTHandler{
|
||||
SubRoute: "wasm_migrate",
|
||||
Handler: func(w http.ResponseWriter, r *http.Request) {
|
||||
var req MigrateProposalJsonReq
|
||||
if !rest.ReadRESTReq(w, r, cliCtx.Codec, &req) {
|
||||
return
|
||||
}
|
||||
toStdTxResponse(cliCtx, w, req)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
type UpdateAdminJsonReq struct {
|
||||
BaseReq rest.BaseReq `json:"base_req" yaml:"base_req"`
|
||||
|
||||
Title string `json:"title" yaml:"title"`
|
||||
Description string `json:"description" yaml:"description"`
|
||||
|
||||
Proposer sdk.AccAddress `json:"proposer" yaml:"proposer"`
|
||||
Deposit sdk.Coins `json:"deposit" yaml:"deposit"`
|
||||
|
||||
NewAdmin sdk.AccAddress `json:"new_admin" yaml:"new_admin"`
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
}
|
||||
|
||||
func (s UpdateAdminJsonReq) Content() gov.Content {
|
||||
return types.UpdateAdminProposal{
|
||||
WasmProposal: types.WasmProposal{Title: s.Title, Description: s.Description},
|
||||
Contract: s.Contract,
|
||||
NewAdmin: s.NewAdmin,
|
||||
}
|
||||
}
|
||||
func (s UpdateAdminJsonReq) GetProposer() sdk.AccAddress {
|
||||
return s.Proposer
|
||||
}
|
||||
func (s UpdateAdminJsonReq) GetDeposit() sdk.Coins {
|
||||
return s.Deposit
|
||||
}
|
||||
func (s UpdateAdminJsonReq) GetBaseReq() rest.BaseReq {
|
||||
return s.BaseReq
|
||||
}
|
||||
func UpdateContractAdminProposalHandler(cliCtx context.CLIContext) govrest.ProposalRESTHandler {
|
||||
return govrest.ProposalRESTHandler{
|
||||
SubRoute: "wasm_update_admin",
|
||||
Handler: func(w http.ResponseWriter, r *http.Request) {
|
||||
var req UpdateAdminJsonReq
|
||||
if !rest.ReadRESTReq(w, r, cliCtx.Codec, &req) {
|
||||
return
|
||||
}
|
||||
toStdTxResponse(cliCtx, w, req)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
type ClearAdminJsonReq struct {
|
||||
BaseReq rest.BaseReq `json:"base_req" yaml:"base_req"`
|
||||
|
||||
Title string `json:"title" yaml:"title"`
|
||||
Description string `json:"description" yaml:"description"`
|
||||
|
||||
Proposer sdk.AccAddress `json:"proposer" yaml:"proposer"`
|
||||
Deposit sdk.Coins `json:"deposit" yaml:"deposit"`
|
||||
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
}
|
||||
|
||||
func (s ClearAdminJsonReq) Content() gov.Content {
|
||||
return types.ClearAdminProposal{
|
||||
WasmProposal: types.WasmProposal{Title: s.Title, Description: s.Description},
|
||||
Contract: s.Contract,
|
||||
}
|
||||
}
|
||||
func (s ClearAdminJsonReq) GetProposer() sdk.AccAddress {
|
||||
return s.Proposer
|
||||
}
|
||||
func (s ClearAdminJsonReq) GetDeposit() sdk.Coins {
|
||||
return s.Deposit
|
||||
}
|
||||
func (s ClearAdminJsonReq) GetBaseReq() rest.BaseReq {
|
||||
return s.BaseReq
|
||||
}
|
||||
func ClearContractAdminProposalHandler(cliCtx context.CLIContext) govrest.ProposalRESTHandler {
|
||||
return govrest.ProposalRESTHandler{
|
||||
SubRoute: "wasm_clear_admin",
|
||||
Handler: func(w http.ResponseWriter, r *http.Request) {
|
||||
var req ClearAdminJsonReq
|
||||
if !rest.ReadRESTReq(w, r, cliCtx.Codec, &req) {
|
||||
return
|
||||
}
|
||||
toStdTxResponse(cliCtx, w, req)
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
type wasmProposalData interface {
|
||||
Content() gov.Content
|
||||
GetProposer() sdk.AccAddress
|
||||
GetDeposit() sdk.Coins
|
||||
GetBaseReq() rest.BaseReq
|
||||
}
|
||||
|
||||
func toStdTxResponse(cliCtx context.CLIContext, w http.ResponseWriter, data wasmProposalData) {
|
||||
msg := gov.NewMsgSubmitProposal(data.Content(), data.GetDeposit(), data.GetProposer())
|
||||
if err := msg.ValidateBasic(); err != nil {
|
||||
rest.WriteErrorResponse(w, http.StatusBadRequest, err.Error())
|
||||
return
|
||||
}
|
||||
baseReq := data.GetBaseReq().Sanitize()
|
||||
if !baseReq.ValidateBasic(w) {
|
||||
return
|
||||
}
|
||||
utils.WriteGenerateStdTxResponse(w, cliCtx, baseReq, []sdk.Msg{msg})
|
||||
}
|
|
@ -197,7 +197,7 @@ func (k Keeper) instantiate(ctx sdk.Context, codeID uint64, creator, admin sdk.A
|
|||
store := ctx.KVStore(k.storeKey)
|
||||
bz := store.Get(types.GetCodeKey(codeID))
|
||||
if bz == nil {
|
||||
return nil, sdkerrors.Wrap(types.ErrNotFound, "contract")
|
||||
return nil, sdkerrors.Wrap(types.ErrNotFound, "code")
|
||||
}
|
||||
var codeInfo types.CodeInfo
|
||||
k.cdc.MustUnmarshalBinaryBare(bz, &codeInfo)
|
||||
|
|
|
@ -47,7 +47,7 @@ func handleStoreCodeProposal(ctx sdk.Context, k Keeper, p types.StoreCodeProposa
|
|||
return err
|
||||
}
|
||||
|
||||
codeID, err := k.create(ctx, p.Creator, p.WASMByteCode, p.Source, p.Builder, p.InstantiatePermission, GovAuthorizationPolicy{})
|
||||
codeID, err := k.create(ctx, p.RunAs, p.WASMByteCode, p.Source, p.Builder, p.InstantiatePermission, GovAuthorizationPolicy{})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -55,7 +55,7 @@ func handleStoreCodeProposal(ctx sdk.Context, k Keeper, p types.StoreCodeProposa
|
|||
ourEvent := sdk.NewEvent(
|
||||
sdk.EventTypeMessage,
|
||||
sdk.NewAttribute(sdk.AttributeKeyModule, types.ModuleName),
|
||||
//sdk.NewAttribute(AttributeSigner, p.Creator.String()), // todo: creator is not signer. rename attribute?
|
||||
//sdk.NewAttribute(AttributeSigner, p.RunAs.String()), // todo: creator is not signer. rename attribute?
|
||||
sdk.NewAttribute(AttributeKeyCodeID, fmt.Sprintf("%d", codeID)),
|
||||
)
|
||||
ctx.EventManager().EmitEvent(ourEvent)
|
||||
|
@ -67,7 +67,7 @@ func handleInstantiateProposal(ctx sdk.Context, k Keeper, p types.InstantiateCon
|
|||
return err
|
||||
}
|
||||
|
||||
contractAddr, err := k.instantiate(ctx, p.Code, p.Creator, p.Admin, p.InitMsg, p.Label, p.InitFunds, GovAuthorizationPolicy{})
|
||||
contractAddr, err := k.instantiate(ctx, p.Code, p.RunAs, p.Admin, p.InitMsg, p.Label, p.InitFunds, GovAuthorizationPolicy{})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -75,7 +75,7 @@ func handleInstantiateProposal(ctx sdk.Context, k Keeper, p types.InstantiateCon
|
|||
ourEvent := sdk.NewEvent(
|
||||
sdk.EventTypeMessage,
|
||||
sdk.NewAttribute(sdk.AttributeKeyModule, types.ModuleName),
|
||||
//sdk.NewAttribute(AttributeSigner, p.Creator.String()),
|
||||
//sdk.NewAttribute(AttributeSigner, p.RunAs.String()),
|
||||
sdk.NewAttribute(AttributeKeyCodeID, fmt.Sprintf("%d", p.Code)),
|
||||
sdk.NewAttribute(AttributeKeyContract, contractAddr.String()),
|
||||
)
|
||||
|
@ -88,7 +88,7 @@ func handleMigrateProposal(ctx sdk.Context, k Keeper, p types.MigrateContractPro
|
|||
return err
|
||||
}
|
||||
|
||||
res, err := k.migrate(ctx, p.Contract, p.Sender, p.Code, p.MigrateMsg, GovAuthorizationPolicy{})
|
||||
res, err := k.migrate(ctx, p.Contract, p.RunAs, p.Code, p.MigrateMsg, GovAuthorizationPolicy{})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -96,7 +96,7 @@ func handleMigrateProposal(ctx sdk.Context, k Keeper, p types.MigrateContractPro
|
|||
ourEvent := sdk.NewEvent(
|
||||
sdk.EventTypeMessage,
|
||||
sdk.NewAttribute(sdk.AttributeKeyModule, types.ModuleName),
|
||||
//sdk.NewAttribute(AttributeSigner, p.Creator.String()),
|
||||
//sdk.NewAttribute(AttributeSigner, p.RunAs.String()),
|
||||
sdk.NewAttribute(AttributeKeyContract, p.Contract.String()),
|
||||
)
|
||||
ctx.EventManager().EmitEvents(append(res.Events, ourEvent))
|
||||
|
@ -108,14 +108,14 @@ func handleUpdateAdminProposal(ctx sdk.Context, k Keeper, p types.UpdateAdminPro
|
|||
return err
|
||||
}
|
||||
|
||||
if err := k.setContractAdmin(ctx, p.Contract, p.Sender, p.NewAdmin, GovAuthorizationPolicy{}); err != nil {
|
||||
if err := k.setContractAdmin(ctx, p.Contract, nil, p.NewAdmin, GovAuthorizationPolicy{}); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
ourEvent := sdk.NewEvent(
|
||||
sdk.EventTypeMessage,
|
||||
sdk.NewAttribute(sdk.AttributeKeyModule, types.ModuleName),
|
||||
//sdk.NewAttribute(AttributeSigner, p.Creator.String()),
|
||||
//sdk.NewAttribute(AttributeSigner, p.RunAs.String()),
|
||||
sdk.NewAttribute(AttributeKeyContract, p.Contract.String()),
|
||||
)
|
||||
ctx.EventManager().EmitEvent(ourEvent)
|
||||
|
@ -127,13 +127,13 @@ func handleClearAdminProposal(ctx sdk.Context, k Keeper, p types.ClearAdminPropo
|
|||
return err
|
||||
}
|
||||
|
||||
if err := k.setContractAdmin(ctx, p.Contract, p.Sender, nil, GovAuthorizationPolicy{}); err != nil {
|
||||
if err := k.setContractAdmin(ctx, p.Contract, nil, nil, GovAuthorizationPolicy{}); err != nil {
|
||||
return err
|
||||
}
|
||||
ourEvent := sdk.NewEvent(
|
||||
sdk.EventTypeMessage,
|
||||
sdk.NewAttribute(sdk.AttributeKeyModule, types.ModuleName),
|
||||
//sdk.NewAttribute(AttributeSigner, p.Creator.String()),
|
||||
//sdk.NewAttribute(AttributeSigner, p.RunAs.String()),
|
||||
sdk.NewAttribute(AttributeKeyContract, p.Contract.String()),
|
||||
)
|
||||
ctx.EventManager().EmitEvent(ourEvent)
|
||||
|
|
|
@ -30,7 +30,7 @@ func TestStoreCodeProposal(t *testing.T) {
|
|||
var anyAddress sdk.AccAddress = make([]byte, sdk.AddrLen)
|
||||
|
||||
src := types.StoreCodeProposalFixture(func(p *types.StoreCodeProposal) {
|
||||
p.Creator = anyAddress
|
||||
p.RunAs = anyAddress
|
||||
p.WASMByteCode = wasmCode
|
||||
p.Source = "https://example.com/mysource"
|
||||
p.Builder = "foo/bar:v0.0.0"
|
||||
|
@ -80,7 +80,7 @@ func TestInstantiateProposal(t *testing.T) {
|
|||
)
|
||||
src := types.InstantiateContractProposalFixture(func(p *types.InstantiateContractProposal) {
|
||||
p.Code = 1
|
||||
p.Creator = oneAddress
|
||||
p.RunAs = oneAddress
|
||||
p.Admin = otherAddress
|
||||
p.Label = "testing"
|
||||
})
|
||||
|
@ -152,7 +152,7 @@ func TestMigrateProposal(t *testing.T) {
|
|||
Code: 2,
|
||||
Contract: contractAddr,
|
||||
MigrateMsg: migMsgBz,
|
||||
Sender: otherAddress,
|
||||
RunAs: otherAddress,
|
||||
}
|
||||
|
||||
// when stored
|
||||
|
@ -176,7 +176,6 @@ func TestMigrateProposal(t *testing.T) {
|
|||
|
||||
func TestAdminProposals(t *testing.T) {
|
||||
var (
|
||||
anyAddress sdk.AccAddress = bytes.Repeat([]byte{0x1}, sdk.AddrLen)
|
||||
otherAddress sdk.AccAddress = bytes.Repeat([]byte{0x2}, sdk.AddrLen)
|
||||
contractAddr = contractAddress(1, 1)
|
||||
)
|
||||
|
@ -196,7 +195,6 @@ func TestAdminProposals(t *testing.T) {
|
|||
Description: "Bar",
|
||||
},
|
||||
Contract: contractAddr,
|
||||
Sender: anyAddress,
|
||||
NewAdmin: otherAddress,
|
||||
},
|
||||
expAdmin: otherAddress,
|
||||
|
@ -211,7 +209,6 @@ func TestAdminProposals(t *testing.T) {
|
|||
Description: "Bar",
|
||||
},
|
||||
Contract: contractAddr,
|
||||
Sender: anyAddress,
|
||||
NewAdmin: otherAddress,
|
||||
},
|
||||
expAdmin: otherAddress,
|
||||
|
@ -224,7 +221,6 @@ func TestAdminProposals(t *testing.T) {
|
|||
Description: "Bar",
|
||||
},
|
||||
Contract: contractAddr,
|
||||
Sender: anyAddress,
|
||||
},
|
||||
expAdmin: nil,
|
||||
},
|
||||
|
@ -238,7 +234,6 @@ func TestAdminProposals(t *testing.T) {
|
|||
Description: "Bar",
|
||||
},
|
||||
Contract: contractAddr,
|
||||
Sender: anyAddress,
|
||||
},
|
||||
expAdmin: nil,
|
||||
},
|
||||
|
|
|
@ -0,0 +1,219 @@
|
|||
{
|
||||
"genesis_time": "2020-07-13T07:49:08.2945876Z",
|
||||
"chain_id": "testing",
|
||||
"consensus_params": {
|
||||
"block": {
|
||||
"max_bytes": "22020096",
|
||||
"max_gas": "-1",
|
||||
"time_iota_ms": "1000"
|
||||
},
|
||||
"evidence": {
|
||||
"max_age_num_blocks": "100000",
|
||||
"max_age_duration": "172800000000000"
|
||||
},
|
||||
"validator": {
|
||||
"pub_key_types": [
|
||||
"ed25519"
|
||||
]
|
||||
}
|
||||
},
|
||||
"app_hash": "",
|
||||
"app_state": {
|
||||
"upgrade": {},
|
||||
"evidence": {
|
||||
"params": {
|
||||
"max_evidence_age": "120000000000"
|
||||
},
|
||||
"evidence": []
|
||||
},
|
||||
"supply": {
|
||||
"supply": []
|
||||
},
|
||||
"mint": {
|
||||
"minter": {
|
||||
"inflation": "0.130000000000000000",
|
||||
"annual_provisions": "0.000000000000000000"
|
||||
},
|
||||
"params": {
|
||||
"mint_denom": "ustake",
|
||||
"inflation_rate_change": "0.130000000000000000",
|
||||
"inflation_max": "0.200000000000000000",
|
||||
"inflation_min": "0.070000000000000000",
|
||||
"goal_bonded": "0.670000000000000000",
|
||||
"blocks_per_year": "6311520"
|
||||
}
|
||||
},
|
||||
"gov": {
|
||||
"starting_proposal_id": "1",
|
||||
"deposits": null,
|
||||
"votes": null,
|
||||
"proposals": null,
|
||||
"deposit_params": {
|
||||
"min_deposit": [
|
||||
{
|
||||
"denom": "ustake",
|
||||
"amount": "1"
|
||||
}
|
||||
],
|
||||
"max_deposit_period": "172800000000000"
|
||||
},
|
||||
"voting_params": {
|
||||
"voting_period": "60000000000",
|
||||
"voting_period_desc": "1minute"
|
||||
},
|
||||
"tally_params": {
|
||||
"quorum": "0.000000000000000001",
|
||||
"threshold": "0.000000000000000001",
|
||||
"veto": "0.334000000000000000"
|
||||
}
|
||||
},
|
||||
"slashing": {
|
||||
"params": {
|
||||
"signed_blocks_window": "100",
|
||||
"min_signed_per_window": "0.500000000000000000",
|
||||
"downtime_jail_duration": "600000000000",
|
||||
"slash_fraction_double_sign": "0.050000000000000000",
|
||||
"slash_fraction_downtime": "0.010000000000000000"
|
||||
},
|
||||
"signing_infos": {},
|
||||
"missed_blocks": {}
|
||||
},
|
||||
"wasm": {
|
||||
"params": {
|
||||
"upload_access": {
|
||||
"type": 3,
|
||||
"address": ""
|
||||
},
|
||||
"instantiate_default_permission": 3
|
||||
},
|
||||
"codes": null,
|
||||
"contracts": null,
|
||||
"sequences": null
|
||||
},
|
||||
"bank": {
|
||||
"send_enabled": true
|
||||
},
|
||||
"distribution": {
|
||||
"params": {
|
||||
"community_tax": "0.020000000000000000",
|
||||
"base_proposer_reward": "0.010000000000000000",
|
||||
"bonus_proposer_reward": "0.040000000000000000",
|
||||
"withdraw_addr_enabled": true
|
||||
},
|
||||
"fee_pool": {
|
||||
"community_pool": []
|
||||
},
|
||||
"delegator_withdraw_infos": [],
|
||||
"previous_proposer": "",
|
||||
"outstanding_rewards": [],
|
||||
"validator_accumulated_commissions": [],
|
||||
"validator_historical_rewards": [],
|
||||
"validator_current_rewards": [],
|
||||
"delegator_starting_infos": [],
|
||||
"validator_slash_events": []
|
||||
},
|
||||
"crisis": {
|
||||
"constant_fee": {
|
||||
"denom": "ustake",
|
||||
"amount": "1000"
|
||||
}
|
||||
},
|
||||
"genutil": {
|
||||
"gentxs": [
|
||||
{
|
||||
"type": "cosmos-sdk/StdTx",
|
||||
"value": {
|
||||
"msg": [
|
||||
{
|
||||
"type": "cosmos-sdk/MsgCreateValidator",
|
||||
"value": {
|
||||
"description": {
|
||||
"moniker": "testing",
|
||||
"identity": "",
|
||||
"website": "",
|
||||
"security_contact": "",
|
||||
"details": ""
|
||||
},
|
||||
"commission": {
|
||||
"rate": "0.100000000000000000",
|
||||
"max_rate": "0.200000000000000000",
|
||||
"max_change_rate": "0.010000000000000000"
|
||||
},
|
||||
"min_self_delegation": "1",
|
||||
"delegator_address": "cosmos1ve557a5g9yw2g2z57js3pdmcvd5my6g8ze20np",
|
||||
"validator_address": "cosmosvaloper1ve557a5g9yw2g2z57js3pdmcvd5my6g88d76lj",
|
||||
"pubkey": "cosmosvalconspub1zcjduepqddfln4tujr2p8actpgqz4h2xnls9y7tu9c9tu5lqkdglmdjalzuqah4neg",
|
||||
"value": {
|
||||
"denom": "ustake",
|
||||
"amount": "250000000"
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
"fee": {
|
||||
"amount": [],
|
||||
"gas": "200000"
|
||||
},
|
||||
"signatures": [
|
||||
{
|
||||
"pub_key": {
|
||||
"type": "tendermint/PubKeySecp256k1",
|
||||
"value": "A//cqZxkpH1re0VrHBtH308nb5t8K+Y/hF0GeRdRBmaJ"
|
||||
},
|
||||
"signature": "5QEEIuUVQTEBMuAtOOHnnKo6rPsIbmfzUxUqRnDFERVqwVr1Kg+ex4f/UGIK0yrOAvOG8zDADwFP4yF8lw+o5g=="
|
||||
}
|
||||
],
|
||||
"memo": "836fc54e9cad58f4ed6420223ec6290f75342afa@172.17.0.2:26656"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"auth": {
|
||||
"params": {
|
||||
"max_memo_characters": "256",
|
||||
"tx_sig_limit": "7",
|
||||
"tx_size_cost_per_byte": "10",
|
||||
"sig_verify_cost_ed25519": "590",
|
||||
"sig_verify_cost_secp256k1": "1000"
|
||||
},
|
||||
"accounts": [
|
||||
{
|
||||
"type": "cosmos-sdk/Account",
|
||||
"value": {
|
||||
"address": "cosmos1ve557a5g9yw2g2z57js3pdmcvd5my6g8ze20np",
|
||||
"coins": [
|
||||
{
|
||||
"denom": "ucosm",
|
||||
"amount": "1000000000"
|
||||
},
|
||||
{
|
||||
"denom": "ustake",
|
||||
"amount": "1000000000"
|
||||
}
|
||||
],
|
||||
"public_key": "",
|
||||
"account_number": 0,
|
||||
"sequence": 0
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"params": null,
|
||||
"staking": {
|
||||
"params": {
|
||||
"unbonding_time": "1814400000000000",
|
||||
"max_validators": 100,
|
||||
"max_entries": 7,
|
||||
"historical_entries": 0,
|
||||
"bond_denom": "ustake"
|
||||
},
|
||||
"last_total_power": "0",
|
||||
"last_validator_powers": null,
|
||||
"validators": null,
|
||||
"delegations": null,
|
||||
"unbonding_delegations": null,
|
||||
"redelegations": null,
|
||||
"exported": false
|
||||
}
|
||||
}
|
||||
}
|
|
@ -13,11 +13,11 @@ func RegisterCodec(cdc *codec.Codec) {
|
|||
cdc.RegisterConcrete(&MsgUpdateAdmin{}, "wasm/update-contract-admin", nil)
|
||||
cdc.RegisterConcrete(&MsgClearAdmin{}, "wasm/clear-contract-admin", nil)
|
||||
|
||||
cdc.RegisterConcrete(&StoreCodeProposal{}, "wasm/store-proposal", nil)
|
||||
cdc.RegisterConcrete(&InstantiateContractProposal{}, "wasm/instantiate-proposal", nil)
|
||||
cdc.RegisterConcrete(&MigrateContractProposal{}, "wasm/migrate-proposal", nil)
|
||||
cdc.RegisterConcrete(&UpdateAdminProposal{}, "wasm/update-admin-proposal", nil)
|
||||
cdc.RegisterConcrete(&ClearAdminProposal{}, "wasm/clear-admin-proposal", nil)
|
||||
cdc.RegisterConcrete(StoreCodeProposal{}, "wasm/store-proposal", nil)
|
||||
cdc.RegisterConcrete(InstantiateContractProposal{}, "wasm/instantiate-proposal", nil)
|
||||
cdc.RegisterConcrete(MigrateContractProposal{}, "wasm/migrate-proposal", nil)
|
||||
cdc.RegisterConcrete(UpdateAdminProposal{}, "wasm/update-admin-proposal", nil)
|
||||
cdc.RegisterConcrete(ClearAdminProposal{}, "wasm/clear-admin-proposal", nil)
|
||||
}
|
||||
|
||||
// ModuleCdc generic sealed codec to be used throughout module
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package types
|
||||
|
||||
import (
|
||||
"encoding/base64"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"strings"
|
||||
|
@ -26,6 +27,19 @@ var DefaultEnabledProposals = map[string]struct{}{
|
|||
ProposalTypeClearAdmin: {},
|
||||
}
|
||||
|
||||
func init() { // register new content types with the sdk
|
||||
govtypes.RegisterProposalType(ProposalTypeStoreCode)
|
||||
govtypes.RegisterProposalType(ProposalTypeStoreInstantiateContract)
|
||||
govtypes.RegisterProposalType(ProposalTypeMigrateContract)
|
||||
govtypes.RegisterProposalType(ProposalTypeUpdateAdmin)
|
||||
govtypes.RegisterProposalType(ProposalTypeClearAdmin)
|
||||
govtypes.RegisterProposalTypeCodec(StoreCodeProposal{}, "wasm/store-proposal")
|
||||
govtypes.RegisterProposalTypeCodec(InstantiateContractProposal{}, "wasm/instantiate-proposal")
|
||||
govtypes.RegisterProposalTypeCodec(MigrateContractProposal{}, "wasm/migrate-proposal")
|
||||
govtypes.RegisterProposalTypeCodec(UpdateAdminProposal{}, "wasm/update-admin-proposal")
|
||||
govtypes.RegisterProposalTypeCodec(ClearAdminProposal{}, "wasm/clear-admin-proposal")
|
||||
}
|
||||
|
||||
type WasmProposal struct {
|
||||
Title string `json:"title" yaml:"title"`
|
||||
Description string `json:"description" yaml:"description"`
|
||||
|
@ -65,16 +79,16 @@ func (p WasmProposal) ValidateBasic() error {
|
|||
|
||||
type StoreCodeProposal struct {
|
||||
WasmProposal
|
||||
// Creator is the address that "owns" the code object
|
||||
Creator sdk.AccAddress `json:"creator" yaml:"creator"`
|
||||
// RunAs is the address that "owns" the code object
|
||||
RunAs sdk.AccAddress `json:"run_as"`
|
||||
// WASMByteCode can be raw or gzip compressed
|
||||
WASMByteCode []byte `json:"wasm_byte_code" yaml:"wasm_byte_code"`
|
||||
WASMByteCode []byte `json:"wasm_byte_code"`
|
||||
// Source is a valid absolute HTTPS URI to the contract's source code, optional
|
||||
Source string `json:"source" yaml:"source"`
|
||||
Source string `json:"source"`
|
||||
// Builder is a valid docker image name with tag, optional
|
||||
Builder string `json:"builder" yaml:"builder"`
|
||||
Builder string `json:"builder"`
|
||||
// InstantiatePermission to apply on contract creation, optional
|
||||
InstantiatePermission *AccessConfig `json:"instantiate_permission" yaml:"instantiate_permission"`
|
||||
InstantiatePermission *AccessConfig `json:"instantiate_permission"`
|
||||
}
|
||||
|
||||
// ProposalType returns the type
|
||||
|
@ -85,8 +99,8 @@ func (p StoreCodeProposal) ValidateBasic() error {
|
|||
if err := p.WasmProposal.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := sdk.VerifyAddressFormat(p.Creator); err != nil {
|
||||
return err
|
||||
if err := sdk.VerifyAddressFormat(p.RunAs); err != nil {
|
||||
return sdkerrors.Wrap(err, "run as")
|
||||
}
|
||||
|
||||
if err := validateWasmCode(p.WASMByteCode); err != nil {
|
||||
|
@ -113,23 +127,41 @@ func (p StoreCodeProposal) String() string {
|
|||
return fmt.Sprintf(`Store Code Proposal:
|
||||
Title: %s
|
||||
Description: %s
|
||||
Creator: %s
|
||||
Run as: %s
|
||||
WasmCode: %X
|
||||
Source: %s
|
||||
Builder: %s
|
||||
`, p.Title, p.Description, p.Creator, p.WASMByteCode, p.Source, p.Builder)
|
||||
`, p.Title, p.Description, p.RunAs, p.WASMByteCode, p.Source, p.Builder)
|
||||
}
|
||||
|
||||
func (p StoreCodeProposal) MarshalYAML() (interface{}, error) {
|
||||
return struct {
|
||||
WasmProposal `yaml:",inline"`
|
||||
RunAs sdk.AccAddress `yaml:"run_as"`
|
||||
WASMByteCode string `yaml:"wasm_byte_code"`
|
||||
Source string `yaml:"source"`
|
||||
Builder string `yaml:"builder"`
|
||||
InstantiatePermission *AccessConfig `yaml:"instantiate_permission"`
|
||||
}{
|
||||
WasmProposal: p.WasmProposal,
|
||||
RunAs: p.RunAs,
|
||||
WASMByteCode: base64.StdEncoding.EncodeToString(p.WASMByteCode),
|
||||
Source: p.Source,
|
||||
Builder: p.Builder,
|
||||
InstantiatePermission: p.InstantiatePermission,
|
||||
}, nil
|
||||
}
|
||||
|
||||
type InstantiateContractProposal struct {
|
||||
WasmProposal
|
||||
// Creator is the address that pays the init funds
|
||||
Creator sdk.AccAddress `json:"sender" yaml:"sender"`
|
||||
// RunAs is the address that pays the init funds
|
||||
RunAs sdk.AccAddress `json:"run_as"`
|
||||
// Admin is an optional address that can execute migrations
|
||||
Admin sdk.AccAddress `json:"admin,omitempty" yaml:"admin"`
|
||||
Code uint64 `json:"code_id" yaml:"code_id"`
|
||||
Label string `json:"label" yaml:"label"`
|
||||
InitMsg json.RawMessage `json:"init_msg" yaml:"init_msg"`
|
||||
InitFunds sdk.Coins `json:"init_funds" yaml:"init_funds"`
|
||||
Admin sdk.AccAddress `json:"admin,omitempty"`
|
||||
Code uint64 `json:"code_id"`
|
||||
Label string `json:"label"`
|
||||
InitMsg json.RawMessage `json:"init_msg"`
|
||||
InitFunds sdk.Coins `json:"init_funds"`
|
||||
}
|
||||
|
||||
// ProposalType returns the type
|
||||
|
@ -142,12 +174,12 @@ func (p InstantiateContractProposal) ValidateBasic() error {
|
|||
if err := p.WasmProposal.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := sdk.VerifyAddressFormat(p.Creator); err != nil {
|
||||
return sdkerrors.Wrap(sdkerrors.ErrInvalidRequest, "creator is required")
|
||||
if err := sdk.VerifyAddressFormat(p.RunAs); err != nil {
|
||||
return sdkerrors.Wrap(sdkerrors.ErrInvalidRequest, "run as")
|
||||
}
|
||||
|
||||
if p.Code == 0 {
|
||||
return sdkerrors.Wrap(sdkerrors.ErrInvalidRequest, "code_id is required")
|
||||
return sdkerrors.Wrap(sdkerrors.ErrInvalidRequest, "code id is required")
|
||||
}
|
||||
|
||||
if err := validateLabel(p.Label); err != nil {
|
||||
|
@ -172,23 +204,42 @@ func (p InstantiateContractProposal) String() string {
|
|||
return fmt.Sprintf(`Instantiate Code Proposal:
|
||||
Title: %s
|
||||
Description: %s
|
||||
Creator: %s
|
||||
Run as: %s
|
||||
Admin: %s
|
||||
Code id: %d
|
||||
Label: %s
|
||||
InitMsg: %q
|
||||
InitFunds: %s
|
||||
`, p.Title, p.Description, p.Creator, p.Admin, p.Code, p.Label, p.InitMsg, p.InitFunds)
|
||||
`, p.Title, p.Description, p.RunAs, p.Admin, p.Code, p.Label, p.InitMsg, p.InitFunds)
|
||||
}
|
||||
|
||||
func (p InstantiateContractProposal) MarshalYAML() (interface{}, error) {
|
||||
return struct {
|
||||
WasmProposal `yaml:",inline"`
|
||||
RunAs sdk.AccAddress `yaml:"run_as"`
|
||||
Admin sdk.AccAddress `yaml:"admin"`
|
||||
Code uint64 `yaml:"code_id"`
|
||||
Label string `yaml:"label"`
|
||||
InitMsg string `yaml:"init_msg"`
|
||||
InitFunds sdk.Coins `yaml:"init_funds"`
|
||||
}{
|
||||
WasmProposal: p.WasmProposal,
|
||||
RunAs: p.RunAs,
|
||||
Admin: p.Admin,
|
||||
Code: p.Code,
|
||||
Label: p.Label,
|
||||
InitMsg: string(p.InitMsg),
|
||||
InitFunds: p.InitFunds,
|
||||
}, nil
|
||||
}
|
||||
|
||||
type MigrateContractProposal struct {
|
||||
WasmProposal
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
Code uint64 `json:"code_id" yaml:"code_id"`
|
||||
MigrateMsg json.RawMessage `json:"msg" yaml:"msg"`
|
||||
// Sender is the role that is passed to the contract's environment
|
||||
Sender sdk.AccAddress `json:"sender" yaml:"sender"`
|
||||
WasmProposal `yaml:",inline"`
|
||||
Contract sdk.AccAddress `json:"contract"`
|
||||
Code uint64 `json:"code_id"`
|
||||
MigrateMsg json.RawMessage `json:"msg"`
|
||||
// RunAs is the address that is passed to the contract's environment as sender
|
||||
RunAs sdk.AccAddress `json:"run_as"`
|
||||
}
|
||||
|
||||
// ProposalType returns the type
|
||||
|
@ -205,8 +256,8 @@ func (p MigrateContractProposal) ValidateBasic() error {
|
|||
if err := sdk.VerifyAddressFormat(p.Contract); err != nil {
|
||||
return sdkerrors.Wrap(err, "contract")
|
||||
}
|
||||
if err := sdk.VerifyAddressFormat(p.Sender); err != nil {
|
||||
return sdkerrors.Wrap(err, "sender")
|
||||
if err := sdk.VerifyAddressFormat(p.RunAs); err != nil {
|
||||
return sdkerrors.Wrap(err, "run as")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
@ -218,17 +269,31 @@ func (p MigrateContractProposal) String() string {
|
|||
Description: %s
|
||||
Contract: %s
|
||||
Code id: %d
|
||||
Sender: %s
|
||||
Run as: %s
|
||||
MigrateMsg %q
|
||||
`, p.Title, p.Description, p.Contract, p.Code, p.Sender, p.MigrateMsg)
|
||||
`, p.Title, p.Description, p.Contract, p.Code, p.RunAs, p.MigrateMsg)
|
||||
}
|
||||
|
||||
func (p MigrateContractProposal) MarshalYAML() (interface{}, error) {
|
||||
return struct {
|
||||
WasmProposal `yaml:",inline"`
|
||||
Contract sdk.AccAddress `yaml:"contract"`
|
||||
Code uint64 `yaml:"code_id"`
|
||||
MigrateMsg string `yaml:"msg"`
|
||||
RunAs sdk.AccAddress `yaml:"run_as"`
|
||||
}{
|
||||
WasmProposal: p.WasmProposal,
|
||||
Contract: p.Contract,
|
||||
Code: p.Code,
|
||||
MigrateMsg: string(p.MigrateMsg),
|
||||
RunAs: p.RunAs,
|
||||
}, nil
|
||||
}
|
||||
|
||||
type UpdateAdminProposal struct {
|
||||
WasmProposal
|
||||
NewAdmin sdk.AccAddress `json:"new_admin" yaml:"new_admin"`
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
// Sender is the role that is passed to the contract's environment
|
||||
Sender sdk.AccAddress `json:"sender" yaml:"sender"`
|
||||
WasmProposal `yaml:",inline"`
|
||||
NewAdmin sdk.AccAddress `json:"new_admin" yaml:"new_admin"`
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
}
|
||||
|
||||
// ProposalType returns the type
|
||||
|
@ -245,9 +310,6 @@ func (p UpdateAdminProposal) ValidateBasic() error {
|
|||
if err := sdk.VerifyAddressFormat(p.NewAdmin); err != nil {
|
||||
return sdkerrors.Wrap(err, "new admin")
|
||||
}
|
||||
if err := sdk.VerifyAddressFormat(p.Sender); err != nil {
|
||||
return sdkerrors.Wrap(err, "sender")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
|
@ -257,17 +319,14 @@ func (p UpdateAdminProposal) String() string {
|
|||
Title: %s
|
||||
Description: %s
|
||||
Contract: %s
|
||||
Sender: %s
|
||||
New Admin: %s
|
||||
`, p.Title, p.Description, p.Contract, p.Sender, p.NewAdmin)
|
||||
`, p.Title, p.Description, p.Contract, p.NewAdmin)
|
||||
}
|
||||
|
||||
type ClearAdminProposal struct {
|
||||
WasmProposal
|
||||
WasmProposal `yaml:",inline"`
|
||||
|
||||
Contract sdk.AccAddress `json:"contract" yaml:"contract"`
|
||||
// Sender is the role that is passed to the contract's environment
|
||||
Sender sdk.AccAddress `json:"sender" yaml:"sender"`
|
||||
}
|
||||
|
||||
// ProposalType returns the type
|
||||
|
@ -281,9 +340,6 @@ func (p ClearAdminProposal) ValidateBasic() error {
|
|||
if err := sdk.VerifyAddressFormat(p.Contract); err != nil {
|
||||
return sdkerrors.Wrap(err, "contract")
|
||||
}
|
||||
if err := sdk.VerifyAddressFormat(p.Sender); err != nil {
|
||||
return sdkerrors.Wrap(err, "sender")
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
|
@ -293,6 +349,5 @@ func (p ClearAdminProposal) String() string {
|
|||
Title: %s
|
||||
Description: %s
|
||||
Contract: %s
|
||||
Sender: %s
|
||||
`, p.Title, p.Description, p.Contract, p.Sender)
|
||||
`, p.Title, p.Description, p.Contract)
|
||||
}
|
||||
|
|
|
@ -10,6 +10,7 @@ import (
|
|||
govtypes "github.com/cosmos/cosmos-sdk/x/gov/types"
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
"gopkg.in/yaml.v2"
|
||||
)
|
||||
|
||||
func TestValidateWasmProposal(t *testing.T) {
|
||||
|
@ -119,15 +120,15 @@ func TestValidateStoreCodeProposal(t *testing.T) {
|
|||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"creator missing": {
|
||||
"run_as missing": {
|
||||
src: StoreCodeProposalFixture(func(p *StoreCodeProposal) {
|
||||
p.Creator = nil
|
||||
p.RunAs = nil
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"creator invalid": {
|
||||
"run_as invalid": {
|
||||
src: StoreCodeProposalFixture(func(p *StoreCodeProposal) {
|
||||
p.Creator = invalidAddress
|
||||
p.RunAs = invalidAddress
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
|
@ -207,15 +208,15 @@ func TestValidateInstantiateContractProposal(t *testing.T) {
|
|||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"creator missing": {
|
||||
"run_as missing": {
|
||||
src: InstantiateContractProposalFixture(func(p *InstantiateContractProposal) {
|
||||
p.Creator = nil
|
||||
p.RunAs = nil
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"creator invalid": {
|
||||
"run_as invalid": {
|
||||
src: InstantiateContractProposalFixture(func(p *InstantiateContractProposal) {
|
||||
p.Creator = invalidAddress
|
||||
p.RunAs = invalidAddress
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
|
@ -303,15 +304,15 @@ func TestValidateMigrateContractProposal(t *testing.T) {
|
|||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"sender missing": {
|
||||
"run_as missing": {
|
||||
src: MigrateContractProposalFixture(func(p *MigrateContractProposal) {
|
||||
p.Sender = nil
|
||||
p.RunAs = nil
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"sender invalid": {
|
||||
"run_as invalid": {
|
||||
src: MigrateContractProposalFixture(func(p *MigrateContractProposal) {
|
||||
p.Sender = invalidAddress
|
||||
p.RunAs = invalidAddress
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
|
@ -370,18 +371,6 @@ func TestValidateUpdateAdminProposal(t *testing.T) {
|
|||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"sender missing": {
|
||||
src: UpdateAdminProposalFixture(func(p *UpdateAdminProposal) {
|
||||
p.Sender = nil
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"sender invalid": {
|
||||
src: UpdateAdminProposalFixture(func(p *UpdateAdminProposal) {
|
||||
p.Sender = invalidAddress
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
}
|
||||
for msg, spec := range specs {
|
||||
t.Run(msg, func(t *testing.T) {
|
||||
|
@ -425,18 +414,6 @@ func TestValidateClearAdminProposal(t *testing.T) {
|
|||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"sender missing": {
|
||||
src: ClearAdminProposalFixture(func(p *ClearAdminProposal) {
|
||||
p.Sender = nil
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
"sender invalid": {
|
||||
src: ClearAdminProposalFixture(func(p *ClearAdminProposal) {
|
||||
p.Sender = invalidAddress
|
||||
}),
|
||||
expErr: true,
|
||||
},
|
||||
}
|
||||
for msg, spec := range specs {
|
||||
t.Run(msg, func(t *testing.T) {
|
||||
|
@ -462,7 +439,7 @@ func TestProposalStrings(t *testing.T) {
|
|||
exp: `Store Code Proposal:
|
||||
Title: Foo
|
||||
Description: Bar
|
||||
Creator: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Run as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
WasmCode: 0102030405060708090A
|
||||
Source: https://example.com/code
|
||||
Builder: foo/bar:latest
|
||||
|
@ -475,7 +452,7 @@ func TestProposalStrings(t *testing.T) {
|
|||
exp: `Instantiate Code Proposal:
|
||||
Title: Foo
|
||||
Description: Bar
|
||||
Creator: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Run as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Admin: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Code id: 1
|
||||
Label: testing
|
||||
|
@ -488,7 +465,7 @@ func TestProposalStrings(t *testing.T) {
|
|||
exp: `Instantiate Code Proposal:
|
||||
Title: Foo
|
||||
Description: Bar
|
||||
Creator: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Run as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Admin: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Code id: 1
|
||||
Label: testing
|
||||
|
@ -501,7 +478,7 @@ func TestProposalStrings(t *testing.T) {
|
|||
exp: `Instantiate Code Proposal:
|
||||
Title: Foo
|
||||
Description: Bar
|
||||
Creator: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Run as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Admin:
|
||||
Code id: 1
|
||||
Label: testing
|
||||
|
@ -516,7 +493,7 @@ func TestProposalStrings(t *testing.T) {
|
|||
Description: Bar
|
||||
Contract: cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5
|
||||
Code id: 1
|
||||
Sender: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
Run as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
MigrateMsg "{\"verifier\":\"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du\"}"
|
||||
`,
|
||||
},
|
||||
|
@ -526,7 +503,6 @@ func TestProposalStrings(t *testing.T) {
|
|||
Title: Foo
|
||||
Description: Bar
|
||||
Contract: cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5
|
||||
Sender: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
New Admin: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
`,
|
||||
},
|
||||
|
@ -536,7 +512,6 @@ func TestProposalStrings(t *testing.T) {
|
|||
Title: Foo
|
||||
Description: Bar
|
||||
Contract: cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5
|
||||
Sender: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
`,
|
||||
},
|
||||
}
|
||||
|
@ -545,5 +520,99 @@ func TestProposalStrings(t *testing.T) {
|
|||
assert.Equal(t, spec.exp, spec.src.String())
|
||||
})
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func TestProposalYaml(t *testing.T) {
|
||||
specs := map[string]struct {
|
||||
src gov.Content
|
||||
exp string
|
||||
}{
|
||||
"store code": {
|
||||
src: StoreCodeProposalFixture(func(p *StoreCodeProposal) {
|
||||
p.WASMByteCode = []byte{01, 02, 03, 04, 05, 06, 07, 0x08, 0x09, 0x0a}
|
||||
}),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
run_as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
wasm_byte_code: AQIDBAUGBwgJCg==
|
||||
source: https://example.com/code
|
||||
builder: foo/bar:latest
|
||||
instantiate_permission: null
|
||||
`,
|
||||
},
|
||||
"instantiate contract": {
|
||||
src: InstantiateContractProposalFixture(func(p *InstantiateContractProposal) {
|
||||
p.InitFunds = sdk.Coins{{Denom: "foo", Amount: sdk.NewInt(1)}, {Denom: "bar", Amount: sdk.NewInt(2)}}
|
||||
}),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
run_as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
admin: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
code_id: 1
|
||||
label: testing
|
||||
init_msg: '{"verifier":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du","beneficiary":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du"}'
|
||||
init_funds:
|
||||
- denom: foo
|
||||
amount: "1"
|
||||
- denom: bar
|
||||
amount: "2"
|
||||
`,
|
||||
},
|
||||
"instantiate contract without funds": {
|
||||
src: InstantiateContractProposalFixture(func(p *InstantiateContractProposal) { p.InitFunds = nil }),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
run_as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
admin: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
code_id: 1
|
||||
label: testing
|
||||
init_msg: '{"verifier":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du","beneficiary":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du"}'
|
||||
init_funds: []
|
||||
`,
|
||||
},
|
||||
"instantiate contract without admin": {
|
||||
src: InstantiateContractProposalFixture(func(p *InstantiateContractProposal) { p.Admin = nil }),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
run_as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
admin: ""
|
||||
code_id: 1
|
||||
label: testing
|
||||
init_msg: '{"verifier":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du","beneficiary":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du"}'
|
||||
init_funds: []
|
||||
`,
|
||||
},
|
||||
"migrate contract": {
|
||||
src: MigrateContractProposalFixture(),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
contract: cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5
|
||||
code_id: 1
|
||||
msg: '{"verifier":"cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du"}'
|
||||
run_as: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
`,
|
||||
},
|
||||
"update admin": {
|
||||
src: UpdateAdminProposalFixture(),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
new_admin: cosmos1qyqszqgpqyqszqgpqyqszqgpqyqszqgpjnp7du
|
||||
contract: cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5
|
||||
`,
|
||||
},
|
||||
"clear admin": {
|
||||
src: ClearAdminProposalFixture(),
|
||||
exp: `title: Foo
|
||||
description: Bar
|
||||
contract: cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5
|
||||
`,
|
||||
},
|
||||
}
|
||||
for msg, spec := range specs {
|
||||
t.Run(msg, func(t *testing.T) {
|
||||
v, err := yaml.Marshal(&spec.src)
|
||||
require.NoError(t, err)
|
||||
assert.Equal(t, spec.exp, string(v))
|
||||
})
|
||||
}
|
||||
}
|
||||
|
|
|
@ -119,7 +119,7 @@ func StoreCodeProposalFixture(mutators ...func(*StoreCodeProposal)) StoreCodePro
|
|||
Title: "Foo",
|
||||
Description: "Bar",
|
||||
},
|
||||
Creator: anyValidAddress,
|
||||
RunAs: anyValidAddress,
|
||||
WASMByteCode: []byte{0x0},
|
||||
Source: "https://example.com/code",
|
||||
Builder: "foo/bar:latest",
|
||||
|
@ -152,7 +152,7 @@ func InstantiateContractProposalFixture(mutators ...func(p *InstantiateContractP
|
|||
Title: "Foo",
|
||||
Description: "Bar",
|
||||
},
|
||||
Creator: anyValidAddress,
|
||||
RunAs: anyValidAddress,
|
||||
Admin: anyValidAddress,
|
||||
Code: 1,
|
||||
Label: "testing",
|
||||
|
@ -192,7 +192,7 @@ func MigrateContractProposalFixture(mutators ...func(p *MigrateContractProposal)
|
|||
Contract: contractAddr,
|
||||
Code: 1,
|
||||
MigrateMsg: migMsgBz,
|
||||
Sender: anyValidAddress,
|
||||
RunAs: anyValidAddress,
|
||||
}
|
||||
|
||||
for _, m := range mutators {
|
||||
|
@ -216,7 +216,6 @@ func UpdateAdminProposalFixture(mutators ...func(p *UpdateAdminProposal)) Update
|
|||
},
|
||||
NewAdmin: anyValidAddress,
|
||||
Contract: contractAddr,
|
||||
Sender: anyValidAddress,
|
||||
}
|
||||
for _, m := range mutators {
|
||||
m(&p)
|
||||
|
@ -225,8 +224,6 @@ func UpdateAdminProposalFixture(mutators ...func(p *UpdateAdminProposal)) Update
|
|||
}
|
||||
|
||||
func ClearAdminProposalFixture(mutators ...func(p *ClearAdminProposal)) ClearAdminProposal {
|
||||
var anyValidAddress sdk.AccAddress = bytes.Repeat([]byte{0x1}, sdk.AddrLen)
|
||||
|
||||
contractAddr, err := sdk.AccAddressFromBech32("cosmos18vd8fpwxzck93qlwghaj6arh4p7c5n89uzcee5")
|
||||
if err != nil {
|
||||
panic(err)
|
||||
|
@ -238,7 +235,6 @@ func ClearAdminProposalFixture(mutators ...func(p *ClearAdminProposal)) ClearAdm
|
|||
Description: "Bar",
|
||||
},
|
||||
Contract: contractAddr,
|
||||
Sender: anyValidAddress,
|
||||
}
|
||||
for _, m := range mutators {
|
||||
m(&p)
|
||||
|
|
Loading…
Reference in New Issue