Implement test of logged socket.io communication

This commit is contained in:
Martin Boehm 2018-05-04 18:35:11 +02:00
parent 9401e0a61e
commit f1d7d6b023

View File

@ -12,6 +12,7 @@ import (
"time" "time"
"github.com/gorilla/websocket" "github.com/gorilla/websocket"
"github.com/juju/errors"
"github.com/martinboehm/golang-socketio" "github.com/martinboehm/golang-socketio"
"github.com/martinboehm/golang-socketio/transport" "github.com/martinboehm/golang-socketio/transport"
) )
@ -64,25 +65,55 @@ func unmarshalResponses(t *testing.T, id int, lrs *logRequestResponse, bbResStr
return nil return nil
} }
func verifyGetAddressHistory(t *testing.T, id int, lrs *logRequestResponse, bbResStr string, stat *verifyStats, ws *gosocketio.Client, bbRequest map[string]json.RawMessage) { func getFullAddressHistory(addr []string, rr addrOpts, ws *gosocketio.Client) (*resultGetAddressHistory, error) {
type reqParamsData struct { rr.From = 0
Start int `json:"start"` rr.To = 100000000
End int `json:"end"` rq := map[string]interface{}{
QueryMempoolOnly bool `json:"queryMempoolOnly"` "method": "getAddressHistory",
From int `json:"from"` "params": []interface{}{
To int `json:"to"` addr,
rr,
},
}
rrq, err := json.Marshal(rq)
if err != nil {
return nil, err
}
res, err := ws.Ack("message", json.RawMessage(rrq), time.Second*30)
if err != nil {
return nil, err
} }
bbResponse := resultGetAddressHistory{}
err = json.Unmarshal([]byte(res), &bbResponse)
if err != nil {
return nil, err
}
return &bbResponse, nil
}
func equalAddressHistoryItem(logItem addressHistoryItem, bbItem addressHistoryItem) error {
if logItem.Tx.Hash != bbItem.Tx.Hash {
return errors.Errorf("Different hash bb: %v log: %v", bbItem.Tx.Hash, logItem.Tx.Hash)
}
if logItem.Tx.Hex != bbItem.Tx.Hex {
return errors.Errorf("Different hex bb: %v log: %v", bbItem.Tx.Hex, logItem.Tx.Hex)
}
return nil
}
func verifyGetAddressHistory(t *testing.T, id int, lrs *logRequestResponse, bbResStr string, stat *verifyStats, ws *gosocketio.Client, bbRequest map[string]json.RawMessage) {
bbResponse := resultGetAddressHistory{} bbResponse := resultGetAddressHistory{}
logResponse := resultGetAddressHistory{} logResponse := resultGetAddressHistory{}
var bbFullResponse *resultGetAddressHistory
if err := unmarshalResponses(t, id, lrs, bbResStr, &bbResponse, &logResponse); err != nil { if err := unmarshalResponses(t, id, lrs, bbResStr, &bbResponse, &logResponse); err != nil {
return return
} }
// parse request // parse request to check params
addr, rr, err := unmarshalGetAddressRequest(bbRequest["params"]) addr, rr, err := unmarshalGetAddressRequest(bbRequest["params"])
if err != nil { if err != nil {
t.Log(id, ": getAddressHistory error unmarshal BB request ", err) t.Log(id, ": getAddressHistory error unmarshal BB request ", err)
return return
} }
// mempool transactions are not comparable
if !rr.QueryMempoolOnly { if !rr.QueryMempoolOnly {
if (logResponse.Result.TotalCount != bbResponse.Result.TotalCount) || if (logResponse.Result.TotalCount != bbResponse.Result.TotalCount) ||
len(logResponse.Result.Items) != len(bbResponse.Result.Items) { len(logResponse.Result.Items) != len(bbResponse.Result.Items) {
@ -93,41 +124,36 @@ func verifyGetAddressHistory(t *testing.T, id int, lrs *logRequestResponse, bbRe
if logResponse.Result.TotalCount > 0 { if logResponse.Result.TotalCount > 0 {
for i, logItem := range logResponse.Result.Items { for i, logItem := range logResponse.Result.Items {
bbItem := bbResponse.Result.Items[i] bbItem := bbResponse.Result.Items[i]
if logItem.Tx.Hash != bbItem.Tx.Hash || logItem.Tx.Hex != bbItem.Tx.Hex { if err = equalAddressHistoryItem(logItem, bbItem); err != nil {
t.Log("getAddressHistory", id, "mismatch in tx", i, "bb:", bbItem.Tx.Hash,
"log:", logItem.Tx.Hash)
// if multiple addresses are specified, BlockBook returns transactions in different order // if multiple addresses are specified, BlockBook returns transactions in different order
// which causes problems in paged responses // which causes problems in paged responses
// we have to get all transactions from blockbook and check that they are in the logged response // we have to get all transactions from blockbook and check that they are in the logged response
rr.From = 0 var err1 error
rr.To = 100000000 if bbFullResponse == nil {
rq := map[string]interface{}{ bbFullResponse, err1 = getFullAddressHistory(addr, rr, ws)
"method": "getAddressHistory", if err1 != nil {
"params": []interface{}{ t.Log("getFullAddressHistory error", err)
addr, return
rr, }
}, if bbFullResponse.Result.TotalCount != logResponse.Result.TotalCount {
t.Log("getFullAddressHistory count mismatch", bbFullResponse.Result.TotalCount, logResponse.Result.TotalCount)
return
}
} }
rrq, err := json.Marshal(rq) found := false
if err != nil { for _, bbFullItem := range bbFullResponse.Result.Items {
t.Log(id, ", getAddressHistory: rq marshall error ", err) if err1 = equalAddressHistoryItem(logItem, bbFullItem); err1 == nil {
found = true
break
}
}
if !found {
t.Log("getAddressHistory", id, "addresses", addr, "mismatch ", err)
bf, _ := json.Marshal(bbFullResponse.Result)
bl, _ := json.Marshal(logResponse.Result)
t.Log("{ \"bf\":", string(bf), ",\"bl\":", string(bl), "}")
return return
} }
res, err := ws.Ack("message", json.RawMessage(rrq), time.Second*30)
if err != nil {
t.Log(id, ", getAddressHistory: ws.Ack error ", err)
return
}
bbFullResponse := resultGetAddressHistory{}
t.Log(id, ": bbResponse", bbResponse.Result.TotalCount, "bbFullResponse", bbFullResponse.Result.TotalCount)
t.Log(string(rrq))
err = json.Unmarshal([]byte(res), &bbFullResponse)
if err != nil {
t.Log(id, ": getAddressHistory error unmarshal BB response ", err)
return
}
return
} }
} }
} }
@ -181,6 +207,26 @@ func verifyEstimateSmartFee(t *testing.T, id int, lrs *logRequestResponse, bbRes
} }
} }
func verifySendTransaction(t *testing.T, id int, lrs *logRequestResponse, bbResStr string, stat *verifyStats) {
bbResponse := resultSendTransaction{}
logResponse := resultSendTransaction{}
if err := unmarshalResponses(t, id, lrs, bbResStr, &bbResponse, &logResponse); err != nil {
return
}
bbResponseError := resultError{}
err := json.Unmarshal([]byte(bbResStr), bbResponseError)
if err != nil {
t.Log(id, ": error unmarshal resultError ", err)
return
}
// it is not possible to repeat sendTransaction, expect error
if bbResponse.Result == "" && bbResponseError.Error.Message != "" {
stat.SuccessCount++
} else {
t.Log("sendTransaction", id, "problem:", bbResponse.Result, bbResponseError)
}
}
func verifyMessage(t *testing.T, ws *gosocketio.Client, id int, lrs *logRequestResponse, stats map[string]*verifyStats) { func verifyMessage(t *testing.T, ws *gosocketio.Client, id int, lrs *logRequestResponse, stats map[string]*verifyStats) {
req := make(map[string]json.RawMessage) req := make(map[string]json.RawMessage)
err := json.Unmarshal(lrs.Request, &req) err := json.Unmarshal(lrs.Request, &req)
@ -208,7 +254,6 @@ func verifyMessage(t *testing.T, ws *gosocketio.Client, id int, lrs *logRequestR
stat.TotalLogNs += lrs.LogElapsedTime stat.TotalLogNs += lrs.LogElapsedTime
stat.TotalBlockbookNs += ts stat.TotalBlockbookNs += ts
switch method { switch method {
// case "getAddressTxids":
case "getAddressHistory": case "getAddressHistory":
verifyGetAddressHistory(t, id, lrs, res, stat, ws, req) verifyGetAddressHistory(t, id, lrs, res, stat, ws, req)
case "getBlockHeader": case "getBlockHeader":
@ -218,8 +263,10 @@ func verifyMessage(t *testing.T, ws *gosocketio.Client, id int, lrs *logRequestR
verifyGetInfo(t, id, lrs, res, stat) verifyGetInfo(t, id, lrs, res, stat)
case "estimateSmartFee": case "estimateSmartFee":
verifyEstimateSmartFee(t, id, lrs, res, stat) verifyEstimateSmartFee(t, id, lrs, res, stat)
case "sendTransaction":
verifySendTransaction(t, id, lrs, res, stat)
// case "estimateFee": // case "estimateFee":
// case "sendTransaction": // case "getAddressTxids":
// case "getMempoolEntry": // case "getMempoolEntry":
default: default:
t.Log(id, ",", method, ": unknown/unverified method", method) t.Log(id, ",", method, ": unknown/unverified method", method)
@ -248,6 +295,8 @@ func Test_VerifyLog(t *testing.T) {
} }
defer file.Close() defer file.Close()
scanner := bufio.NewScanner(file) scanner := bufio.NewScanner(file)
buf := make([]byte, 1<<25)
scanner.Buffer(buf, 1<<25)
scanner.Split(bufio.ScanLines) scanner.Split(bufio.ScanLines)
line := 0 line := 0
stats := make(map[string]*verifyStats) stats := make(map[string]*verifyStats)