OSDN Git Service

add query
authorroot <zhouarrogant@outlook.com>
Thu, 7 Sep 2017 07:10:32 +0000 (07:10 +0000)
committerroot <zhouarrogant@outlook.com>
Thu, 7 Sep 2017 07:10:32 +0000 (07:10 +0000)
blockchain/query.go [new file with mode: 0644]
blockchain/reactor.go
cmd/bytomcli/main.go

diff --git a/blockchain/query.go b/blockchain/query.go
new file mode 100644 (file)
index 0000000..39060c3
--- /dev/null
@@ -0,0 +1,218 @@
+package blockchain
+
+import (
+       "context"
+       "math"
+
+       "github.com/bytom/blockchain/query"
+       "github.com/bytom/blockchain/query/filter"
+       "github.com/bytom/errors"
+       "github.com/bytom/net/http/httpjson"
+)
+
+const (
+       defGenericPageSize = 100
+)
+
+// listAccounts is an http handler for listing accounts matching
+// an index or an ad-hoc filter.
+//
+// POST /list-accounts
+func (bcr *BlockchainReactor) listAccounts(ctx context.Context, in requestQuery) (page, error) {
+       limit := in.PageSize
+       if limit == 0 {
+               limit = defGenericPageSize
+       }
+       after := in.After
+/*
+       // Use the filter engine for querying account tags.
+       accounts, after, err := bcr.indexer.Accounts(ctx, in.Filter, in.FilterParams, after, limit)
+       if err != nil {
+               return page{}, errors.Wrap(err, "running acc query")
+       }
+*/
+       // Pull in the accounts by the IDs
+       out := in
+       out.After = after
+       return page{
+//             Items:    httpjson.Array(accounts),
+//             LastPage: len(accounts) < limit,
+               Next:     out,
+       }, nil
+}
+
+// listAssets is an http handler for listing assets matching
+// an index or an ad-hoc filter.
+//
+// POST /list-assets
+func (bcr *BlockchainReactor) listAssets(ctx context.Context, in requestQuery) (page, error) {
+       limit := in.PageSize
+       if limit == 0 {
+               limit = defGenericPageSize
+       }
+       after := in.After
+
+/*     // Use the query engine for querying asset tags.
+       assets, after, err := bcr.indexer.Assets(ctx, in.Filter, in.FilterParams, after, limit)
+       if err != nil {
+               return page{}, errors.Wrap(err, "running asset query")
+       }
+*/
+       out := in
+       out.After = after
+       return page{
+//             Items:    httpjson.Array(assets),
+//             LastPage: len(assets) < limit,
+               Next:     out,
+       }, nil
+}
+
+// POST /list-balances
+func (bcr *BlockchainReactor) listBalances(ctx context.Context, in requestQuery) (result page, err error) {
+       var sumBy []filter.Field
+
+       // Since an empty SumBy yields a meaningless result, we'll provide a
+       // sensible default here.
+       if len(in.SumBy) == 0 {
+               in.SumBy = []string{"asset_alias", "asset_id"}
+       }
+
+       for _, field := range in.SumBy {
+               f, err := filter.ParseField(field)
+               if err != nil {
+                       return result, err
+               }
+               sumBy = append(sumBy, f)
+       }
+
+       timestampMS := in.TimestampMS
+       if timestampMS == 0 {
+               timestampMS = math.MaxInt64
+       } else if timestampMS > math.MaxInt64 {
+               return result, errors.WithDetail(httpjson.ErrBadRequest, "timestamp is too large")
+       }
+
+       // TODO(jackson): paginate this endpoint.
+/*     balances, err := bcr.indexer.Balances(ctx, in.Filter, in.FilterParams, sumBy, timestampMS)
+       if err != nil {
+               return result, err
+       }
+*/
+//     result.Items = httpjson.Array(balances)
+       result.LastPage = true
+       result.Next = in
+       return result, nil
+}
+
+// listTransactions is an http handler for listing transactions matching
+// an index or an ad-hoc filter.
+//
+// POST /list-transactions
+func (bcr *BlockchainReactor) listTransactions(ctx context.Context, in requestQuery) (result page, err error) {
+       var c context.CancelFunc
+       timeout := in.Timeout.Duration
+       if timeout != 0 {
+               ctx, c = context.WithTimeout(ctx, timeout)
+               defer c()
+       }
+
+       limit := in.PageSize
+       if limit == 0 {
+               limit = defGenericPageSize
+       }
+
+       endTimeMS := in.EndTimeMS
+       if endTimeMS == 0 {
+               endTimeMS = math.MaxInt64
+       } else if endTimeMS > math.MaxInt64 {
+               return result, errors.WithDetail(httpjson.ErrBadRequest, "end timestamp is too large")
+       }
+
+       // Either parse the provided `after` or look one up for the time range.
+//     var after query.TxAfter
+       if in.After != "" {
+               _, err = query.DecodeTxAfter(in.After)
+               if err != nil {
+                       return result, errors.Wrap(err, "decoding `after`")
+               }
+       } else {
+/*             after, err = bcr.indexer.LookupTxAfter(ctx, in.StartTimeMS, endTimeMS)
+               if err != nil {
+                       return result, err
+               }
+*/
+       }
+
+/*     txns, nextAfter, err := bcr.indexer.Transactions(ctx, in.Filter, in.FilterParams, after, limit, in.AscLongPoll)
+       if err != nil {
+               return result, errors.Wrap(err, "running tx query")
+       }
+*/
+       out := in
+//     out.After = nextAfter.String()
+       return page{
+//             Items:    httpjson.Array(txns),
+//             LastPage: len(txns) < limit,
+               Next:     out,
+       }, nil
+}
+
+// listTxFeeds is an http handler for listing txfeeds. It does not take a filter.
+//
+// POST /list-transaction-feeds
+func (bcr *BlockchainReactor) listTxFeeds(ctx context.Context, in requestQuery) (page, error) {
+       limit := in.PageSize
+       if limit == 0 {
+               limit = defGenericPageSize
+       }
+
+       after := in.After
+
+/*     txfeeds, after, err := bcr.txFeeds.Query(ctx, after, limit)
+       if err != nil {
+               return page{}, errors.Wrap(err, "running txfeed query")
+       }
+*/
+       out := in
+       out.After = after
+       return page{
+//             Items:    httpjson.Array(txfeeds),
+//             LastPage: len(txfeeds) < limit,
+               Next:     out,
+       }, nil
+}
+
+// POST /list-unspent-outputs
+func (bcr *BlockchainReactor) listUnspentOutputs(ctx context.Context, in requestQuery) (result page, err error) {
+       limit := in.PageSize
+       if limit == 0 {
+               limit = defGenericPageSize
+       }
+
+//     var after *query.OutputsAfter
+       if in.After != "" {
+               _, err = query.DecodeOutputsAfter(in.After)
+               if err != nil {
+                       return result, errors.Wrap(err, "decoding `after`")
+               }
+       }
+
+       timestampMS := in.TimestampMS
+       if timestampMS == 0 {
+               timestampMS = math.MaxInt64
+       } else if timestampMS > math.MaxInt64 {
+               return result, errors.WithDetail(httpjson.ErrBadRequest, "timestamp is too large")
+       }
+/*     outputs, nextAfter, err := bcr.indexer.Outputs(ctx, in.Filter, in.FilterParams, timestampMS, after, limit)
+       if err != nil {
+               return result, errors.Wrap(err, "querying outputs")
+       }
+*/
+       outQuery := in
+//     outQuery.After = nextAfter.String()
+       return page{
+//             Items:    httpjson.Array(outputs),
+//             LastPage: len(outputs) < limit,
+               Next:     outQuery,
+       }, nil
+}
index 8c20f44..e9c30e1 100644 (file)
@@ -13,6 +13,7 @@ import (
        "github.com/bytom/types"
     "github.com/bytom/protocol/bc/legacy"
     "github.com/bytom/protocol"
+       "github.com/bytom/blockchain/query"
        "github.com/bytom/encoding/json"
        cmn "github.com/tendermint/tmlibs/common"
        "github.com/bytom/blockchain/txdb"
@@ -67,6 +68,7 @@ type BlockchainReactor struct {
        accounts         *account.Manager
        assets           *asset.Registry
        txFeeds          *txfeed.TxFeed
+       indexer         *query.Indexer
        pool         *BlockPool
        mux          *http.ServeMux
        handler      http.Handler
@@ -169,6 +171,12 @@ func (bcr *BlockchainReactor) BuildHander() {
        m.Handle("/get-transaction-feed", jsonHandler(bcr.getTxFeed))
        m.Handle("/update-transaction-feed", jsonHandler(bcr.updateTxFeed))
        m.Handle("/delete-transaction-feed", jsonHandler(bcr.deleteTxFeed))
+       m.Handle("/list-accounts", jsonHandler(bcr.listAccounts))
+        m.Handle("/list-assets", jsonHandler(bcr.listAssets))
+        m.Handle("/list-transaction-feeds", jsonHandler(bcr.listTxFeeds))
+        m.Handle("/list-transactions", jsonHandler(bcr.listTransactions))
+        m.Handle("/list-balances", jsonHandler(bcr.listBalances))
+        m.Handle("/list-unspent-outputs", jsonHandler(bcr.listUnspentOutputs))
        m.Handle("/", alwaysError(errors.New("not Found")))
        m.Handle("/info", jsonHandler(bcr.info))
        m.Handle("/create-block-key", jsonHandler(bcr.createblockkey))
index cee214d..a31ee79 100644 (file)
@@ -20,6 +20,7 @@ import (
        "github.com/bytom/blockchain"
 //     "chain/core/accesstoken"
        //"github.com/bytom/config"
+       "github.com/bytom/encoding/json"
        "github.com/bytom/blockchain/rpc"
        "github.com/bytom/crypto/ed25519"
        "github.com/bytom/env"
@@ -73,7 +74,12 @@ var commands = map[string]*command{
        "create-transaction-feed": {createTxFeed},
        "get-transaction-feed":    {getTxFeed},
        "update-transaction-feed": {updateTxFeed},
-       "delete-transaction-feed": {deleteTxFeed},
+        "list-accounts":           {listAccounts},
+        "list-assets":             {listAssets},
+        "list-transaction-feeds":  {listTxFeeds},
+        "list-transactions":       {listTransactions},
+        "list-balances":           {listBalances},
+        "list-unspent-outputs":    {listUnspentOutputs},
 }
 
 func main() {
@@ -544,7 +550,7 @@ func createAsset(client *rpc.Client, args []string) {
        ins.Quorum = 1
        ins.Alias = "aa"
        ins.Tags = map[string]interface{}{"test_tag": "v0",}
-       ins.Definition = map[string]interface{}{"test_definition": "v0"}
+       ins.Definition = map[string]interface{}{}
        ins.ClientToken = args[0]
        responses := make([]interface{}, 50)
        client.Call(context.Background(), "/create-asset", &[]Ins{ins,}, &responses)
@@ -682,3 +688,154 @@ func deleteTxFeed(client *rpc.Client, args []string){
         in.Alias = "qwerty"
         client.Call(context.Background(),"/delete-transaction-feed",&[]In{in,},nil)
 }
+
+func listAccounts(client *rpc.Client, args []string){
+        if len(args) != 0{
+                fatalln("error:listAccounts not use args")
+        }
+       type requestQuery struct {
+                Filter       string        `json:"filter,omitempty"`
+                FilterParams []interface{} `json:"filter_params,omitempty"`
+                SumBy        []string      `json:"sum_by,omitempty"`
+                PageSize     int           `json:"page_size"`
+                AscLongPoll bool          `json:"ascending_with_long_poll,omitempty"`
+                Timeout     json.Duration `json:"timeout"`
+                After string `json:"after"`
+                StartTimeMS uint64 `json:"start_time,omitempty"`
+                EndTimeMS   uint64 `json:"end_time,omitempty"`
+                TimestampMS uint64 `json:"timestamp,omitempty"`
+                Type string `json:"type"`
+                Aliases []string `json:"aliases,omitempty"`
+}
+       var in requestQuery
+       after := in.After
+       out := in
+       out.After = after
+        client.Call(context.Background(),"/list-accounts",&[]requestQuery{in,},nil)
+}
+
+func listAssets(client *rpc.Client, args []string){
+        if len(args) != 0{
+                fatalln("error:listAssets not use args")
+        }
+       type requestQuery struct {
+                Filter       string        `json:"filter,omitempty"`
+                FilterParams []interface{} `json:"filter_params,omitempty"`
+                SumBy        []string      `json:"sum_by,omitempty"`
+                PageSize     int           `json:"page_size"`
+                AscLongPoll bool          `json:"ascending_with_long_poll,omitempty"`
+                Timeout     json.Duration `json:"timeout"`
+                After string `json:"after"`
+                StartTimeMS uint64 `json:"start_time,omitempty"`
+                EndTimeMS   uint64 `json:"end_time,omitempty"`
+                TimestampMS uint64 `json:"timestamp,omitempty"`
+                Type string `json:"type"`
+                Aliases []string `json:"aliases,omitempty"`
+}
+       var in requestQuery
+       after := in.After
+       out := in
+       out.After = after
+       client.Call(context.Background(),"/list-assets",&[]requestQuery{in,},nil)
+}
+
+func listTxFeeds(client *rpc.Client, args []string){
+        if len(args) != 0{
+                fatalln("error:listTxFeeds not use args")
+        }
+       type requestQuery struct {
+                Filter       string        `json:"filter,omitempty"`
+                FilterParams []interface{} `json:"filter_params,omitempty"`
+                SumBy        []string      `json:"sum_by,omitempty"`
+                PageSize     int           `json:"page_size"`
+                AscLongPoll bool          `json:"ascending_with_long_poll,omitempty"`
+                Timeout     json.Duration `json:"timeout"`
+                After string `json:"after"`
+                StartTimeMS uint64 `json:"start_time,omitempty"`
+                EndTimeMS   uint64 `json:"end_time,omitempty"`
+                TimestampMS uint64 `json:"timestamp,omitempty"`
+                Type string `json:"type"`
+                Aliases []string `json:"aliases,omitempty"`
+}
+       var in requestQuery
+       after := in.After
+       out := in
+       out.After = after
+               client.Call(context.Background(),"/list-transactions-feeds",&[]requestQuery{in,},nil)
+}
+
+func listTransactions(client *rpc.Client, args []string){
+        if len(args) != 0{
+                fatalln("error:listTransactions not use args")
+        }
+       type requestQuery struct {
+                Filter       string        `json:"filter,omitempty"`
+                FilterParams []interface{} `json:"filter_params,omitempty"`
+                SumBy        []string      `json:"sum_by,omitempty"`
+                PageSize     int           `json:"page_size"`
+                AscLongPoll bool          `json:"ascending_with_long_poll,omitempty"`
+                Timeout     json.Duration `json:"timeout"`
+                After string `json:"after"`
+                StartTimeMS uint64 `json:"start_time,omitempty"`
+                EndTimeMS   uint64 `json:"end_time,omitempty"`
+                TimestampMS uint64 `json:"timestamp,omitempty"`
+                Type string `json:"type"`
+                Aliases []string `json:"aliases,omitempty"`
+}
+       var in requestQuery
+       after := in.After
+       out := in
+       out.After = after
+        client.Call(context.Background(),"/list-transactions",&[]requestQuery{in,},nil)
+}
+
+func listBalances(client *rpc.Client, args []string){
+        if len(args) != 0{
+                fatalln("error:listBalances not use args")
+        }
+type requestQuery struct {
+                Filter       string        `json:"filter,omitempty"`
+                FilterParams []interface{} `json:"filter_params,omitempty"`
+                SumBy        []string      `json:"sum_by,omitempty"`
+                PageSize     int           `json:"page_size"`
+                AscLongPoll bool          `json:"ascending_with_long_poll,omitempty"`
+                Timeout     json.Duration `json:"timeout"`
+                After string `json:"after"`
+                StartTimeMS uint64 `json:"start_time,omitempty"`
+                EndTimeMS   uint64 `json:"end_time,omitempty"`
+                TimestampMS uint64 `json:"timestamp,omitempty"`
+                Type string `json:"type"`
+                Aliases []string `json:"aliases,omitempty"`
+}
+
+       var in requestQuery
+       after := in.After
+       out := in
+       out.After = after
+        client.Call(context.Background(),"/list-balance",&[]requestQuery{in,},nil)
+}
+
+func listUnspentOutputs(client *rpc.Client, args []string){
+        if len(args) != 0{
+                fatalln("error:listUnspentOutputs not use args")
+        }
+type requestQuery struct {
+                Filter       string        `json:"filter,omitempty"`
+                FilterParams []interface{} `json:"filter_params,omitempty"`
+                SumBy        []string      `json:"sum_by,omitempty"`
+                PageSize     int           `json:"page_size"`
+                AscLongPoll bool          `json:"ascending_with_long_poll,omitempty"`
+                Timeout     json.Duration `json:"timeout"`
+                After string `json:"after"`
+                StartTimeMS uint64 `json:"start_time,omitempty"`
+                EndTimeMS   uint64 `json:"end_time,omitempty"`
+                TimestampMS uint64 `json:"timestamp,omitempty"`
+                Type string `json:"type"`
+                Aliases []string `json:"aliases,omitempty"`
+}
+       var in requestQuery
+       after := in.After
+       out := in
+       out.After = after
+        client.Call(context.Background(),"/list-unspent-outputs",&[]requestQuery{in,},nil)
+}