2019-05-28 01:44:04 -07:00
package flags
2018-02-23 01:49:30 -08:00
2018-09-11 17:31:30 -07:00
import (
"fmt"
2019-01-21 19:42:15 -08:00
"os"
2018-09-11 17:31:30 -07:00
"strconv"
"github.com/spf13/cobra"
2018-09-25 14:36:42 -07:00
"github.com/spf13/viper"
2019-05-28 01:44:04 -07:00
tmcli "github.com/tendermint/tendermint/libs/cli"
2020-01-22 09:54:56 -08:00
2020-03-25 08:20:36 -07:00
"github.com/cosmos/cosmos-sdk/crypto/keyring"
2018-09-11 17:31:30 -07:00
)
2018-02-23 01:49:30 -08:00
const (
2019-02-04 15:35:12 -08:00
// DefaultGasAdjustment is applied to gas estimates to avoid tx execution
// failures due to state changes that might occur between the tx simulation
// and the actual run.
2018-08-31 10:04:11 -07:00
DefaultGasAdjustment = 1.0
2018-08-31 10:04:42 -07:00
DefaultGasLimit = 200000
2018-12-20 11:21:07 -08:00
GasFlagAuto = "auto"
2018-08-22 04:38:55 -07:00
2019-12-11 01:45:26 -08:00
// DefaultKeyringBackend
2020-03-25 08:20:36 -07:00
DefaultKeyringBackend = keyring . BackendOS
2020-01-30 07:13:42 -08:00
)
2019-12-11 01:45:26 -08:00
2020-01-30 07:13:42 -08:00
const (
2019-03-25 17:54:23 -07:00
// BroadcastBlock defines a tx broadcasting mode where the client waits for
// the tx to be committed in a block.
BroadcastBlock = "block"
// BroadcastSync defines a tx broadcasting mode where the client waits for
// a CheckTx execution response only.
BroadcastSync = "sync"
// BroadcastAsync defines a tx broadcasting mode where the client returns
// immediately.
BroadcastAsync = "async"
2020-01-30 07:13:42 -08:00
)
2019-03-25 17:54:23 -07:00
2020-01-30 07:13:42 -08:00
// List of CLI flags
const (
2019-05-28 01:44:04 -07:00
FlagHome = tmcli . HomeFlag
2018-11-16 14:21:36 -08:00
FlagUseLedger = "ledger"
FlagChainID = "chain-id"
FlagNode = "node"
FlagHeight = "height"
FlagGasAdjustment = "gas-adjustment"
FlagTrustNode = "trust-node"
FlagFrom = "from"
FlagName = "name"
FlagAccountNumber = "account-number"
FlagSequence = "sequence"
FlagMemo = "memo"
2018-12-19 16:26:33 -08:00
FlagFees = "fees"
2019-01-18 08:45:20 -08:00
FlagGasPrices = "gas-prices"
2019-03-25 17:54:23 -07:00
FlagBroadcastMode = "broadcast-mode"
2018-11-16 14:21:36 -08:00
FlagDryRun = "dry-run"
FlagGenerateOnly = "generate-only"
2020-03-18 18:49:33 -07:00
FlagOffline = "offline"
2018-11-16 14:21:36 -08:00
FlagIndentResponse = "indent"
FlagListenAddr = "laddr"
FlagMaxOpenConnections = "max-open"
2019-05-07 10:04:48 -07:00
FlagRPCReadTimeout = "read-timeout"
FlagRPCWriteTimeout = "write-timeout"
2020-05-07 10:49:08 -07:00
FlagRPCMaxBodyBytes = "max-body-bytes"
2018-12-06 03:03:58 -08:00
FlagOutputDocument = "output-document" // inspired by wget -O
2019-02-26 03:34:01 -08:00
FlagSkipConfirmation = "yes"
2020-01-30 07:13:42 -08:00
FlagProve = "prove"
2019-12-11 01:45:26 -08:00
FlagKeyringBackend = "keyring-backend"
2020-01-16 13:46:51 -08:00
FlagPage = "page"
FlagLimit = "limit"
2020-02-21 03:17:27 -08:00
FlagUnsafeCORS = "unsafe-cors"
2018-02-23 01:49:30 -08:00
)
2018-02-23 02:25:25 -08:00
// LineBreak can be included in a command list to provide a blank line
// to help with readability
2018-09-11 17:31:30 -07:00
var (
LineBreak = & cobra . Command { Run : func ( * cobra . Command , [ ] string ) { } }
GasFlagVar = GasSetting { Gas : DefaultGasLimit }
)
2018-02-23 02:25:25 -08:00
2018-02-23 01:49:30 -08:00
// GetCommands adds common flags to query commands
func GetCommands ( cmds ... * cobra . Command ) [ ] * cobra . Command {
for _ , c := range cmds {
2018-10-04 04:00:24 -07:00
c . Flags ( ) . Bool ( FlagIndentResponse , false , "Add indent to JSON response" )
2018-09-14 11:41:21 -07:00
c . Flags ( ) . Bool ( FlagTrustNode , false , "Trust connected full node (don't verify proofs for responses)" )
2018-06-28 17:54:47 -07:00
c . Flags ( ) . Bool ( FlagUseLedger , false , "Use a connected Ledger device" )
2019-05-28 17:58:33 -07:00
c . Flags ( ) . String ( FlagNode , "tcp://localhost:26657" , "<host>:<port> to Tendermint RPC interface for this chain" )
c . Flags ( ) . Int64 ( FlagHeight , 0 , "Use a specific height to query state at (this can error if the node is pruning state)" )
2020-04-08 06:00:59 -07:00
c . Flags ( ) . String ( FlagKeyringBackend , DefaultKeyringBackend , "Select keyring's backend (os|file|kwallet|pass|test)" )
2019-05-28 17:58:33 -07:00
2018-09-25 14:36:42 -07:00
viper . BindPFlag ( FlagTrustNode , c . Flags ( ) . Lookup ( FlagTrustNode ) )
viper . BindPFlag ( FlagUseLedger , c . Flags ( ) . Lookup ( FlagUseLedger ) )
viper . BindPFlag ( FlagNode , c . Flags ( ) . Lookup ( FlagNode ) )
2020-04-08 06:00:59 -07:00
viper . BindPFlag ( FlagKeyringBackend , c . Flags ( ) . Lookup ( FlagKeyringBackend ) )
2019-01-17 07:40:34 -08:00
c . MarkFlagRequired ( FlagChainID )
2019-12-27 07:23:18 -08:00
c . SetErr ( c . ErrOrStderr ( ) )
2020-05-04 06:55:16 -07:00
c . SetOut ( c . OutOrStdout ( ) )
2018-02-23 01:49:30 -08:00
}
return cmds
}
// PostCommands adds common flags for commands to post tx
func PostCommands ( cmds ... * cobra . Command ) [ ] * cobra . Command {
for _ , c := range cmds {
2018-10-04 04:00:24 -07:00
c . Flags ( ) . Bool ( FlagIndentResponse , false , "Add indent to JSON response" )
2018-09-25 13:48:38 -07:00
c . Flags ( ) . String ( FlagFrom , "" , "Name or address of private key with which to sign" )
2019-03-27 09:16:48 -07:00
c . Flags ( ) . Uint64P ( FlagAccountNumber , "a" , 0 , "The account number of the signing account (offline mode only)" )
2019-03-26 07:36:10 -07:00
c . Flags ( ) . Uint64P ( FlagSequence , "s" , 0 , "The sequence number of the signing account (offline mode only)" )
2018-06-20 12:27:36 -07:00
c . Flags ( ) . String ( FlagMemo , "" , "Memo to send along with transaction" )
2019-03-25 14:15:54 -07:00
c . Flags ( ) . String ( FlagFees , "" , "Fees to pay along with transaction; eg: 10uatom" )
c . Flags ( ) . String ( FlagGasPrices , "" , "Gas prices to determine the transaction fee (e.g. 10uatom)" )
2018-06-13 15:13:51 -07:00
c . Flags ( ) . String ( FlagNode , "tcp://localhost:26657" , "<host>:<port> to tendermint rpc interface for this chain" )
2018-06-28 17:54:47 -07:00
c . Flags ( ) . Bool ( FlagUseLedger , false , "Use a connected Ledger device" )
2018-08-31 10:04:11 -07:00
c . Flags ( ) . Float64 ( FlagGasAdjustment , DefaultGasAdjustment , "adjustment factor to be multiplied against the estimate returned by the tx simulation; if the gas limit is set manually this flag is ignored " )
2019-03-25 17:54:23 -07:00
c . Flags ( ) . StringP ( FlagBroadcastMode , "b" , BroadcastSync , "Transaction broadcasting mode (sync|async|block)" )
2018-09-14 11:41:21 -07:00
c . Flags ( ) . Bool ( FlagTrustNode , true , "Trust connected full node (don't verify proofs for responses)" )
2018-08-31 10:04:11 -07:00
c . Flags ( ) . Bool ( FlagDryRun , false , "ignore the --gas flag and perform a simulation of a transaction, but don't broadcast it" )
2020-03-18 18:49:33 -07:00
c . Flags ( ) . Bool ( FlagGenerateOnly , false , "Build an unsigned transaction and write it to STDOUT (when enabled, the local Keybase is not accessible)" )
c . Flags ( ) . Bool ( FlagOffline , false , "Offline mode (does not allow any online functionality" )
2019-02-26 03:34:01 -08:00
c . Flags ( ) . BoolP ( FlagSkipConfirmation , "y" , false , "Skip tx broadcasting prompt confirmation" )
2020-03-19 09:58:14 -07:00
c . Flags ( ) . String ( FlagKeyringBackend , DefaultKeyringBackend , "Select keyring's backend (os|file|kwallet|pass|test)" )
2019-02-26 03:34:01 -08:00
2018-09-11 17:31:30 -07:00
// --gas can accept integers and "simulate"
c . Flags ( ) . Var ( & GasFlagVar , "gas" , fmt . Sprintf (
2019-02-26 03:34:01 -08:00
"gas limit to set per-transaction; set to %q to calculate required gas automatically (default %d)" ,
GasFlagAuto , DefaultGasLimit ,
) )
2018-09-25 14:36:42 -07:00
viper . BindPFlag ( FlagTrustNode , c . Flags ( ) . Lookup ( FlagTrustNode ) )
viper . BindPFlag ( FlagUseLedger , c . Flags ( ) . Lookup ( FlagUseLedger ) )
viper . BindPFlag ( FlagNode , c . Flags ( ) . Lookup ( FlagNode ) )
2019-12-11 01:45:26 -08:00
viper . BindPFlag ( FlagKeyringBackend , c . Flags ( ) . Lookup ( FlagKeyringBackend ) )
2018-12-18 10:40:01 -08:00
c . MarkFlagRequired ( FlagChainID )
2019-12-27 07:23:18 -08:00
c . SetErr ( c . ErrOrStderr ( ) )
2020-05-04 06:55:16 -07:00
c . SetOut ( c . OutOrStdout ( ) )
2018-02-23 01:49:30 -08:00
}
return cmds
}
2018-09-11 17:31:30 -07:00
2018-11-16 14:21:36 -08:00
// RegisterRestServerFlags registers the flags required for rest server
func RegisterRestServerFlags ( cmd * cobra . Command ) * cobra . Command {
2019-01-30 16:49:14 -08:00
cmd = GetCommands ( cmd ) [ 0 ]
2018-11-16 14:21:36 -08:00
cmd . Flags ( ) . String ( FlagListenAddr , "tcp://localhost:1317" , "The address for the server to listen on" )
2019-05-07 10:04:48 -07:00
cmd . Flags ( ) . Uint ( FlagMaxOpenConnections , 1000 , "The number of maximum open connections" )
cmd . Flags ( ) . Uint ( FlagRPCReadTimeout , 10 , "The RPC read timeout (in seconds)" )
cmd . Flags ( ) . Uint ( FlagRPCWriteTimeout , 10 , "The RPC write timeout (in seconds)" )
2020-05-10 12:21:24 -07:00
cmd . Flags ( ) . Uint ( FlagRPCMaxBodyBytes , 1000000 , "The RPC max body bytes" )
2020-02-21 03:17:27 -08:00
cmd . Flags ( ) . Bool ( FlagUnsafeCORS , false , "Allows CORS requests from all domains. For development purposes only, use it at your own risk." )
2018-11-16 14:21:36 -08:00
return cmd
}
2018-09-11 17:31:30 -07:00
// Gas flag parsing functions
// GasSetting encapsulates the possible values passed through the --gas flag.
type GasSetting struct {
Simulate bool
2018-11-19 09:13:45 -08:00
Gas uint64
2018-09-11 17:31:30 -07:00
}
// Type returns the flag's value type.
func ( v * GasSetting ) Type ( ) string { return "string" }
// Set parses and sets the value of the --gas flag.
func ( v * GasSetting ) Set ( s string ) ( err error ) {
2018-12-19 16:26:33 -08:00
v . Simulate , v . Gas , err = ParseGas ( s )
2018-09-11 17:31:30 -07:00
return
}
func ( v * GasSetting ) String ( ) string {
if v . Simulate {
2018-12-20 11:21:07 -08:00
return GasFlagAuto
2018-09-11 17:31:30 -07:00
}
2018-11-19 09:13:45 -08:00
return strconv . FormatUint ( v . Gas , 10 )
2018-09-11 17:31:30 -07:00
}
2018-12-19 16:26:33 -08:00
// ParseGas parses the value of the gas option.
func ParseGas ( gasStr string ) ( simulateAndExecute bool , gas uint64 , err error ) {
switch gasStr {
2018-09-11 17:31:30 -07:00
case "" :
gas = DefaultGasLimit
2018-12-20 11:21:07 -08:00
case GasFlagAuto :
2018-12-19 16:26:33 -08:00
simulateAndExecute = true
2018-09-11 17:31:30 -07:00
default :
2018-12-19 16:26:33 -08:00
gas , err = strconv . ParseUint ( gasStr , 10 , 64 )
2018-09-11 17:31:30 -07:00
if err != nil {
2018-12-20 11:21:07 -08:00
err = fmt . Errorf ( "gas must be either integer or %q" , GasFlagAuto )
2018-09-11 17:31:30 -07:00
return
}
}
return
}
2019-01-21 19:42:15 -08:00
// NewCompletionCmd builds a cobra.Command that generate bash completion
// scripts for the given root command. If hidden is true, the command
// will not show up in the root command's list of available commands.
func NewCompletionCmd ( rootCmd * cobra . Command , hidden bool ) * cobra . Command {
flagZsh := "zsh"
cmd := & cobra . Command {
Use : "completion" ,
Short : "Generate Bash/Zsh completion script to STDOUT" ,
Long : ` To load completion script run
. < ( completion_script )
To configure your bash shell to load completions for each session add to your bashrc
# ~ / . bashrc or ~ / . profile
. < ( completion_script )
` ,
RunE : func ( _ * cobra . Command , _ [ ] string ) error {
if viper . GetBool ( flagZsh ) {
return rootCmd . GenZshCompletion ( os . Stdout )
}
return rootCmd . GenBashCompletion ( os . Stdout )
} ,
Hidden : hidden ,
Args : cobra . NoArgs ,
}
cmd . Flags ( ) . Bool ( flagZsh , false , "Generate Zsh completion script" )
return cmd
}