reorganize basecli appTx commands

int
This commit is contained in:
rigel rozanski 2017-06-16 04:57:45 -04:00 committed by Ethan Frey
parent ad17fcf347
commit 9c8ccefd35
4 changed files with 100 additions and 107 deletions

View File

@ -10,41 +10,48 @@ import (
"github.com/tendermint/light-client/commands"
txcmd "github.com/tendermint/light-client/commands/txs"
ctypes "github.com/tendermint/tendermint/rpc/core/types"
cmn "github.com/tendermint/tmlibs/common"
btypes "github.com/tendermint/basecoin/types"
)
/*** Here is the sendtx command ***/
/******** SendTx *********/
// SendTxCmd is CLI command to send tokens between basecoin accounts
var SendTxCmd = &cobra.Command{
Use: "send",
Short: "send tokens from one account to another",
RunE: doSendTx,
}
//nolint
const (
ToFlag = "to"
AmountFlag = "amount"
FeeFlag = "fee"
GasFlag = "gas"
SequenceFlag = "sequence"
FlagTo = "to"
FlagAmount = "amount"
FlagFee = "fee"
FlagGas = "gas"
FlagSequence = "sequence"
)
func init() {
flags := SendTxCmd.Flags()
flags.String(ToFlag, "", "Destination address for the bits")
flags.String(AmountFlag, "", "Coins to send in the format <amt><coin>,<amt><coin>...")
flags.String(FeeFlag, "0mycoin", "Coins for the transaction fee of the format <amt><coin>")
flags.Int64(GasFlag, 0, "Amount of gas for this transaction")
flags.Int(SequenceFlag, -1, "Sequence number for this transaction")
flags.String(FlagTo, "", "Destination address for the bits")
flags.String(FlagAmount, "", "Coins to send in the format <amt><coin>,<amt><coin>...")
flags.String(FlagFee, "0mycoin", "Coins for the transaction fee of the format <amt><coin>")
flags.Int64(FlagGas, 0, "Amount of gas for this transaction")
flags.Int(FlagSequence, -1, "Sequence number for this transaction")
}
// runDemo is an example of how to make a tx
func doSendTx(cmd *cobra.Command, args []string) error {
tx := new(btypes.SendTx)
// load data from json or flags
tx := new(btypes.SendTx)
found, err := txcmd.LoadJSON(tx)
if err != nil {
return err
}
if !found {
err = readSendTxFlags(tx)
}
@ -52,6 +59,7 @@ func doSendTx(cmd *cobra.Command, args []string) error {
return err
}
// Wrap and add signer
send := &SendTx{
chainID: commands.GetChainID(),
Tx: tx,
@ -64,34 +72,34 @@ func doSendTx(cmd *cobra.Command, args []string) error {
return err
}
// output result
// Output result
return txcmd.OutputTx(bres)
}
func readSendTxFlags(tx *btypes.SendTx) error {
// parse to address
to, err := ParseHexFlag(ToFlag)
to, err := ParseHexFlag(FlagTo)
if err != nil {
return errors.Errorf("To address is invalid hex: %v\n", err)
}
//parse the fee and amounts into coin types
tx.Fee, err = btypes.ParseCoin(viper.GetString(FeeFlag))
tx.Fee, err = btypes.ParseCoin(viper.GetString(FlagFee))
if err != nil {
return err
}
amountCoins, err := btypes.ParseCoins(viper.GetString(AmountFlag))
amountCoins, err := btypes.ParseCoins(viper.GetString(FlagAmount))
if err != nil {
return err
}
// set the gas
tx.Gas = viper.GetInt64(GasFlag)
tx.Gas = viper.GetInt64(FlagGas)
// craft the inputs and outputs
tx.Inputs = []btypes.TxInput{{
Coins: amountCoins,
Sequence: viper.GetInt(SequenceFlag),
Sequence: viper.GetInt(FlagSequence),
}}
tx.Outputs = []btypes.TxOutput{{
Address: to,
@ -103,39 +111,53 @@ func readSendTxFlags(tx *btypes.SendTx) error {
/******** AppTx *********/
// BroadcastAppTx wraps, signs, and executes an app tx basecoin transaction
func BroadcastAppTx(tx *btypes.AppTx) (*ctypes.ResultBroadcastTxCommit, error) {
// Generate app transaction to be broadcast
appTx := WrapAppTx(tx)
appTx.AddSigner(txcmd.GetSigner())
// Sign if needed and post to the node. This it the work-horse
return txcmd.SignAndPostTx(appTx)
}
// AddAppTxFlags adds flags required by apptx
func AddAppTxFlags(fs *flag.FlagSet) {
fs.String(AmountFlag, "", "Coins to send in the format <amt><coin>,<amt><coin>...")
fs.String(FeeFlag, "0mycoin", "Coins for the transaction fee of the format <amt><coin>")
fs.Int64(GasFlag, 0, "Amount of gas for this transaction")
fs.Int(SequenceFlag, -1, "Sequence number for this transaction")
fs.String(FlagAmount, "", "Coins to send in the format <amt><coin>,<amt><coin>...")
fs.String(FlagFee, "0mycoin", "Coins for the transaction fee of the format <amt><coin>")
fs.Int64(FlagGas, 0, "Amount of gas for this transaction")
fs.Int(FlagSequence, -1, "Sequence number for this transaction")
}
// ReadAppTxFlags reads in the standard flags
// your command should parse info to set tx.Name and tx.Data
func ReadAppTxFlags(tx *btypes.AppTx) error {
//parse the fee and amounts into coin types
var err error
tx.Fee, err = btypes.ParseCoin(viper.GetString(FeeFlag))
func ReadAppTxFlags() (gas int64, fee btypes.Coin, txInput btypes.TxInput, err error) {
// Set the gas
gas = viper.GetInt64(FlagGas)
// Parse the fee and amounts into coin types
fee, err = btypes.ParseCoin(viper.GetString(FlagFee))
if err != nil {
return err
return
}
amountCoins, err := btypes.ParseCoins(viper.GetString(AmountFlag))
// craft the inputs
var amount btypes.Coins
amount, err = btypes.ParseCoins(viper.GetString(FlagAmount))
if err != nil {
return err
return
}
txInput = btypes.TxInput{
Coins: amount,
Sequence: viper.GetInt(FlagSequence),
}
// set the gas
tx.Gas = viper.GetInt64(GasFlag)
// craft the inputs and outputs
tx.Input = btypes.TxInput{
Coins: amountCoins,
Sequence: viper.GetInt(SequenceFlag),
}
return nil
return
}
// WrapAppTx wraps the transaction with chain id
func WrapAppTx(tx *btypes.AppTx) *AppTx {
return &AppTx{
chainID: commands.GetChainID(),
@ -145,25 +167,7 @@ func WrapAppTx(tx *btypes.AppTx) *AppTx {
/** TODO copied from basecoin cli - put in common somewhere? **/
// ParseHexFlag parses a flag string to byte array
func ParseHexFlag(flag string) ([]byte, error) {
return hex.DecodeString(StripHex(viper.GetString(flag)))
}
// Returns true for non-empty hex-string prefixed with "0x"
func isHex(s string) bool {
if len(s) > 2 && s[:2] == "0x" {
_, err := hex.DecodeString(s[2:])
if err != nil {
return false
}
return true
}
return false
}
func StripHex(s string) string {
if isHex(s) {
return s[2:]
}
return s
return hex.DecodeString(cmn.StripHex(viper.GetString(flag)))
}

View File

@ -12,68 +12,72 @@ import (
btypes "github.com/tendermint/basecoin/types"
)
//CounterTxCmd is the CLI command to execute the counter
// through the appTx Command
var CounterTxCmd = &cobra.Command{
Use: "counter",
Short: "add a vote to the counter",
Long: `Add a vote to the counter.
You must pass --valid for it to count and the countfee will be added to the counter.`,
RunE: doCounterTx,
RunE: counterTxCmd,
}
const (
CountFeeFlag = "countfee"
ValidFlag = "valid"
flagCountFee = "countfee"
flagValid = "valid"
)
func init() {
fs := CounterTxCmd.Flags()
bcmd.AddAppTxFlags(fs)
fs.String(CountFeeFlag, "", "Coins to send in the format <amt><coin>,<amt><coin>...")
fs.Bool(ValidFlag, false, "Is count valid?")
fs.String(flagCountFee, "", "Coins to send in the format <amt><coin>,<amt><coin>...")
fs.Bool(flagValid, false, "Is count valid?")
}
func doCounterTx(cmd *cobra.Command, args []string) error {
tx := new(btypes.AppTx)
func counterTxCmd(cmd *cobra.Command, args []string) error {
// Note: we don't support loading apptx from json currently, so skip that
// read the standard flags
err := bcmd.ReadAppTxFlags(tx)
// Read the app-specific flags
name, data, err := getAppData()
if err != nil {
return err
}
// now read the app-specific flags
err = readCounterFlags(tx)
// Read the standard app-tx flags
gas, fee, txInput, err := bcmd.ReadAppTxFlags()
if err != nil {
return err
}
app := bcmd.WrapAppTx(tx)
app.AddSigner(txcmd.GetSigner())
// Sign if needed and post. This it the work-horse
bres, err := txcmd.SignAndPostTx(app)
// Create AppTx and broadcast
tx := &btypes.AppTx{
Gas: gas,
Fee: fee,
Name: name,
Input: txInput,
Data: data,
}
res, err := bcmd.BroadcastAppTx(tx)
if err != nil {
return err
}
// output result
return txcmd.OutputTx(bres)
// Output result
return txcmd.OutputTx(res)
}
// readCounterFlags sets the app-specific data in the AppTx
func readCounterFlags(tx *btypes.AppTx) error {
countFee, err := btypes.ParseCoins(viper.GetString(CountFeeFlag))
func getAppData() (name string, data []byte, err error) {
countFee, err := btypes.ParseCoins(viper.GetString(flagCountFee))
if err != nil {
return err
return
}
ctx := counter.CounterTx{
Valid: viper.GetBool(ValidFlag),
Valid: viper.GetBool(flagValid),
Fee: countFee,
}
tx.Name = counter.New().Name()
tx.Data = wire.BinaryBytes(ctx)
return nil
name = counter.New().Name()
data = wire.BinaryBytes(ctx)
return
}

View File

@ -8,13 +8,14 @@ import (
"github.com/tendermint/basecoin/plugins/counter"
)
//CounterQueryCmd CLI command to query the counter state
var CounterQueryCmd = &cobra.Command{
Use: "counter",
Short: "Query counter state, with proof",
RunE: doCounterQuery,
RunE: counterQueryCmd,
}
func doCounterQuery(cmd *cobra.Command, args []string) error {
func counterQueryCmd(cmd *cobra.Command, args []string) error {
key := counter.New().StateKey()
var cp counter.CounterPluginState
@ -25,18 +26,3 @@ func doCounterQuery(cmd *cobra.Command, args []string) error {
return proofcmd.OutputProof(cp, proof.BlockHeight())
}
/*** doesn't seem to be needed anymore??? ***/
// type CounterPresenter struct{}
// func (_ CounterPresenter) MakeKey(str string) ([]byte, error) {
// key := counter.New().StateKey()
// return key, nil
// }
// func (_ CounterPresenter) ParseData(raw []byte) (interface{}, error) {
// var cp counter.CounterPluginState
// err := wire.ReadBinaryBytes(raw, &cp)
// return cp, err
// }

View File

@ -32,26 +32,25 @@ tmcli to work for any custom abci app.
func main() {
commands.AddBasicFlags(BaseCli)
// prepare queries
// Prepare queries
pr := proofs.RootCmd
// these are default parsers, but you optional in your app
// These are default parsers, but you optional in your app
pr.AddCommand(proofs.TxCmd)
pr.AddCommand(proofs.KeyCmd)
pr.AddCommand(bcmd.AccountQueryCmd)
pr.AddCommand(bcount.CounterQueryCmd)
// here is how you would add the custom txs... but don't really add demo in your app
// Here is how you add custom txs... but don't really add counter in your app
proofs.TxPresenters.Register("base", bcmd.BaseTxPresenter{})
tr := txs.RootCmd
tr.AddCommand(bcmd.SendTxCmd)
tr.AddCommand(bcount.CounterTxCmd)
// TODO
// txs.Register("send", bcmd.SendTxMaker{})
// txs.Register("counter", bcount.CounterTxMaker{})
// set up the various commands to use
// Set up the various commands to use
BaseCli.AddCommand(
commands.InitCmd,
commands.ResetCmd,