Start on coin handler
This commit is contained in:
parent
a0f1e5e66a
commit
37796002ae
|
@ -8,6 +8,7 @@ import (
|
|||
"fmt"
|
||||
|
||||
abci "github.com/tendermint/abci/types"
|
||||
"github.com/tendermint/basecoin"
|
||||
)
|
||||
|
||||
const (
|
||||
|
@ -26,8 +27,14 @@ const (
|
|||
msgTooManySignatures = "Too many signatures"
|
||||
msgNoChain = "No chain id provided"
|
||||
msgWrongChain = "Tx belongs to different chain - %s"
|
||||
msgUnknownTxType = "We cannot handle this tx - %v"
|
||||
)
|
||||
|
||||
func UnknownTxType(tx basecoin.Tx) TMError {
|
||||
msg := fmt.Sprintf(msgUnknownTxType, tx)
|
||||
return New(msg, abci.CodeType_UnknownRequest)
|
||||
}
|
||||
|
||||
func InternalError(msg string) TMError {
|
||||
return New(msg, abci.CodeType_InternalError)
|
||||
}
|
||||
|
|
|
@ -0,0 +1,64 @@
|
|||
package coin
|
||||
|
||||
import (
|
||||
"github.com/tendermint/basecoin"
|
||||
"github.com/tendermint/basecoin/errors"
|
||||
"github.com/tendermint/basecoin/types"
|
||||
)
|
||||
|
||||
const (
|
||||
NameCoin = "coin"
|
||||
)
|
||||
|
||||
// Handler writes
|
||||
type Handler struct{}
|
||||
|
||||
var _ basecoin.Handler = Handler{}
|
||||
|
||||
func (_ Handler) Name() string {
|
||||
return NameCoin
|
||||
}
|
||||
|
||||
// CheckTx checks if there is enough money in the account
|
||||
func (h Handler) CheckTx(ctx basecoin.Context, store types.KVStore, tx basecoin.Tx) (res basecoin.Result, err error) {
|
||||
_, err = checkTx(ctx, tx)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
// now make sure there is money
|
||||
|
||||
// otherwise, we are good
|
||||
return res, nil
|
||||
}
|
||||
|
||||
// DeliverTx moves the money
|
||||
func (h Handler) DeliverTx(ctx basecoin.Context, store types.KVStore, tx basecoin.Tx) (res basecoin.Result, err error) {
|
||||
_, err = checkTx(ctx, tx)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
// now move the money
|
||||
return basecoin.Result{}, nil
|
||||
}
|
||||
|
||||
func checkTx(ctx basecoin.Context, tx basecoin.Tx) (*SendTx, error) {
|
||||
// check if the tx is proper type and valid
|
||||
send, ok := tx.Unwrap().(*SendTx)
|
||||
if !ok {
|
||||
return nil, errors.UnknownTxType(tx)
|
||||
}
|
||||
err := send.ValidateBasic()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// check if all inputs have permission
|
||||
for _, in := range send.Inputs {
|
||||
if !ctx.HasPermission(in.Address) {
|
||||
return nil, errors.Unauthorized()
|
||||
}
|
||||
}
|
||||
return send, nil
|
||||
}
|
|
@ -98,15 +98,23 @@ func (tx SendTx) ValidateBasic() error {
|
|||
if len(tx.Outputs) == 0 {
|
||||
return errors.NoOutputs()
|
||||
}
|
||||
// make sure all inputs and outputs are individually valid
|
||||
var totalIn, totalOut types.Coins
|
||||
for _, in := range tx.Inputs {
|
||||
if err := in.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
totalIn.Plus(in.Coins)
|
||||
}
|
||||
for _, out := range tx.Outputs {
|
||||
if err := out.ValidateBasic(); err != nil {
|
||||
return err
|
||||
}
|
||||
totalOut.Plus(out.Coins)
|
||||
}
|
||||
// make sure inputs and outputs match
|
||||
if !totalIn.IsEqual(totalOut) {
|
||||
return errors.InvalidCoins()
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -1,9 +1,13 @@
|
|||
package stack
|
||||
|
||||
import (
|
||||
"strings"
|
||||
|
||||
"github.com/tendermint/basecoin"
|
||||
"github.com/tendermint/basecoin/txs"
|
||||
"github.com/tendermint/basecoin/types"
|
||||
wire "github.com/tendermint/go-wire"
|
||||
"github.com/tendermint/go-wire/data"
|
||||
)
|
||||
|
||||
const (
|
||||
|
@ -45,7 +49,17 @@ func runAll(ctx basecoin.Context, store types.KVStore, txs []basecoin.Tx, next b
|
|||
return combine(rs), nil
|
||||
}
|
||||
|
||||
func combine(res []basecoin.Result) basecoin.Result {
|
||||
// TODO: how to combine???
|
||||
return res[0]
|
||||
// combines all data bytes as a go-wire array.
|
||||
// joins all log messages with \n
|
||||
func combine(all []basecoin.Result) basecoin.Result {
|
||||
datas := make([]data.Bytes, len(all))
|
||||
logs := make([]string, len(all))
|
||||
for i, r := range all {
|
||||
datas[i] = r.Data
|
||||
logs[i] = r.Log
|
||||
}
|
||||
return basecoin.Result{
|
||||
Data: wire.BinaryBytes(datas),
|
||||
Log: strings.Join(logs, "\n"),
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue