Skip to content
This repository was archived by the owner on Apr 25, 2025. It is now read-only.

Commit 2c40482

Browse files
author
Firas Qutishat
committed
[FAB-7606] Validate endorser payload and status
Change-Id: I926fb17b97874af0ac3e2dd64c18dbe845a95e3d Signed-off-by: Firas Qutishat <firas.qutishat@securekey.com>
1 parent c0080e2 commit 2c40482

File tree

6 files changed

+69
-39
lines changed

6 files changed

+69
-39
lines changed

pkg/fabric-client/channel/txnproposer_test.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -174,7 +174,7 @@ func TestAddPeerDuplicateCheck(t *testing.T) {
174174
func TestSendTransactionProposal(t *testing.T) {
175175
channel, _ := setupTestChannel()
176176

177-
peer := mocks.MockPeer{MockName: "Peer1", MockURL: "http://peer1.com", MockRoles: []string{}, MockCert: nil, Payload: []byte("A")}
177+
peer := mocks.MockPeer{MockName: "Peer1", MockURL: "http://peer1.com", MockRoles: []string{}, MockCert: nil, Status: 200, Payload: []byte("A")}
178178
channel.AddPeer(&peer)
179179

180180
request := apitxn.ChaincodeInvokeRequest{
@@ -185,7 +185,7 @@ func TestSendTransactionProposal(t *testing.T) {
185185
if err != nil {
186186
t.Fatalf("Failed to send transaction proposal: %s", err)
187187
}
188-
expectedTpr := &pb.ProposalResponse{Response: &pb.Response{Message: "success", Status: 99, Payload: []byte("A")}}
188+
expectedTpr := &pb.ProposalResponse{Response: &pb.Response{Message: "success", Status: 200, Payload: []byte("A")}}
189189

190190
if txnid.ID != "1234" || !reflect.DeepEqual(tpr[0].ProposalResponse, expectedTpr) {
191191
t.Fatalf("Unexpected transaction proposal response: %v, %v", tpr, txnid)

pkg/fabric-client/channel/txnsender.go

Lines changed: 0 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -63,24 +63,6 @@ func (c *Channel) CreateTransaction(resps []*apitxn.TransactionProposalResponse)
6363
return nil, err
6464
}
6565

66-
// This code is commented out because the ProposalResponsePayload Extension ChaincodeAction Results
67-
// return from endorsements is different so the compare will fail
68-
69-
// var a1 []byte
70-
// for n, r := range resps {
71-
// if n == 0 {
72-
// a1 = r.Payload
73-
// if r.Response.Status != 200 {
74-
// return nil, errors.Errorf("proposal response was not successful, error code %d, msg %s", r.Response.Status, r.Response.Message)
75-
// }
76-
// continue
77-
// }
78-
79-
// if bytes.Compare(a1, r.Payload) != 0 {
80-
// return nil, errors.New("ProposalResponsePayloads do not match")
81-
// }
82-
// }
83-
8466
for _, r := range resps {
8567
if r.ProposalResponse.Response.Status != 200 {
8668
return nil, errors.Errorf("proposal response was not successful, error code %d, msg %s", r.ProposalResponse.Response.Status, r.ProposalResponse.Response.Message)

pkg/fabric-client/mocks/mockpeer.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,12 @@ type MockPeer struct {
2222
MockCert *pem.Block
2323
Payload []byte
2424
MockMSP string
25+
Status int32
2526
}
2627

2728
// NewMockPeer creates basic mock peer
2829
func NewMockPeer(name string, url string) *MockPeer {
29-
mp := &MockPeer{MockName: name, MockURL: url}
30+
mp := &MockPeer{MockName: name, MockURL: url, Status: 200}
3031
return mp
3132
}
3233

@@ -80,7 +81,7 @@ func (p *MockPeer) ProcessTransactionProposal(tp apitxn.TransactionProposal) (ap
8081
return apitxn.TransactionProposalResult{
8182
Endorser: p.MockURL,
8283
Proposal: tp,
83-
ProposalResponse: &pb.ProposalResponse{Response: &pb.Response{Message: "success", Status: 99, Payload: p.Payload}},
84+
ProposalResponse: &pb.ProposalResponse{Response: &pb.Response{Message: "success", Status: p.Status, Payload: p.Payload}},
8485
}, nil
8586

8687
}

pkg/fabric-txn/chclient/chclient.go

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ SPDX-License-Identifier: Apache-2.0
88
package chclient
99

1010
import (
11+
"bytes"
1112
"reflect"
1213
"time"
1314

@@ -36,6 +37,21 @@ type txProposalResponseFilter struct {
3637

3738
// ProcessTxProposalResponse process transaction proposal response
3839
func (txProposalResponseFilter *txProposalResponseFilter) ProcessTxProposalResponse(txProposalResponse []*apitxn.TransactionProposalResponse) ([]*apitxn.TransactionProposalResponse, error) {
40+
var a1 []byte
41+
for n, r := range txProposalResponse {
42+
if r.ProposalResponse.GetResponse().Status != 200 {
43+
return nil, errors.Errorf("proposal response was not successful, error code %d, msg %s", r.ProposalResponse.GetResponse().Status, r.ProposalResponse.GetResponse().Message)
44+
}
45+
if n == 0 {
46+
a1 = r.ProposalResponse.GetResponse().Payload
47+
continue
48+
}
49+
50+
if bytes.Compare(a1, r.ProposalResponse.GetResponse().Payload) != 0 {
51+
return nil, errors.Errorf("ProposalResponsePayloads do not match")
52+
}
53+
}
54+
3955
return txProposalResponse, nil
4056
}
4157

pkg/fabric-txn/chclient/chclient_test.go

Lines changed: 46 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ SPDX-License-Identifier: Apache-2.0
77
package chclient
88

99
import (
10+
"strings"
1011
"testing"
1112
"time"
1213

@@ -20,9 +21,39 @@ import (
2021
txnmocks "github.com/hyperledger/fabric-sdk-go/pkg/fabric-txn/mocks"
2122
)
2223

24+
func TestTxProposalResponseFilter(t *testing.T) {
25+
// failed if status not 200
26+
testPeer1 := fcmocks.NewMockPeer("Peer1", "http://peer1.com")
27+
testPeer2 := fcmocks.NewMockPeer("Peer2", "http://peer2.com")
28+
testPeer2.Status = 300
29+
peers := []apifabclient.Peer{testPeer1, testPeer2}
30+
chClient := setupChannelClient(peers, t)
31+
32+
_, err := chClient.Query(apitxn.QueryRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("b")}})
33+
if err == nil {
34+
t.Fatalf("Should have failed for not success status")
35+
}
36+
if !strings.Contains(err.Error(), "proposal response was not successful, error code 300") {
37+
t.Fatalf("Return wrong error message %v", err)
38+
}
39+
40+
testPeer2.Payload = []byte("wrongPayload")
41+
testPeer2.Status = 200
42+
peers = []apifabclient.Peer{testPeer1, testPeer2}
43+
chClient = setupChannelClient(peers, t)
44+
_, err = chClient.Query(apitxn.QueryRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("b")}})
45+
if err == nil {
46+
t.Fatalf("Should have failed for not success status")
47+
}
48+
if !strings.Contains(err.Error(), "ProposalResponsePayloads do not match") {
49+
t.Fatalf("Return wrong error message %v", err)
50+
}
51+
52+
}
53+
2354
func TestQuery(t *testing.T) {
2455

25-
chClient := setupChannelClient(t)
56+
chClient := setupChannelClient(nil, t)
2657

2758
result, err := chClient.Query(apitxn.QueryRequest{})
2859
if err == nil {
@@ -52,7 +83,7 @@ func TestQuery(t *testing.T) {
5283

5384
func TestQueryDiscoveryError(t *testing.T) {
5485

55-
chClient := setupChannelClientWithError(errors.New("Test Error"), nil, t)
86+
chClient := setupChannelClientWithError(errors.New("Test Error"), nil, nil, t)
5687

5788
_, err := chClient.Query(apitxn.QueryRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("b")}})
5889
if err == nil {
@@ -63,7 +94,7 @@ func TestQueryDiscoveryError(t *testing.T) {
6394

6495
func TestQuerySelectionError(t *testing.T) {
6596

66-
chClient := setupChannelClientWithError(nil, errors.New("Test Error"), t)
97+
chClient := setupChannelClientWithError(nil, errors.New("Test Error"), nil, t)
6798

6899
_, err := chClient.Query(apitxn.QueryRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("b")}})
69100
if err == nil {
@@ -74,7 +105,7 @@ func TestQuerySelectionError(t *testing.T) {
74105

75106
func TestQueryWithOptSync(t *testing.T) {
76107

77-
chClient := setupChannelClient(t)
108+
chClient := setupChannelClient(nil, t)
78109

79110
result, err := chClient.QueryWithOpts(apitxn.QueryRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("query"), []byte("b")}}, apitxn.QueryOpts{})
80111
if err != nil {
@@ -88,7 +119,7 @@ func TestQueryWithOptSync(t *testing.T) {
88119

89120
func TestQueryWithOptAsync(t *testing.T) {
90121

91-
chClient := setupChannelClient(t)
122+
chClient := setupChannelClient(nil, t)
92123

93124
notifier := make(chan apitxn.QueryResponse)
94125

@@ -117,11 +148,11 @@ func TestQueryWithOptAsync(t *testing.T) {
117148

118149
func TestQueryWithOptTarget(t *testing.T) {
119150

120-
chClient := setupChannelClient(t)
151+
chClient := setupChannelClient(nil, t)
121152

122-
testPeer := fcmocks.MockPeer{MockName: "Peer1", MockURL: "http://peer1.com", MockRoles: []string{}, MockCert: nil}
153+
testPeer := fcmocks.NewMockPeer("Peer1", "http://peer1.com")
123154

124-
peers := []apifabclient.Peer{&testPeer}
155+
peers := []apifabclient.Peer{testPeer}
125156

126157
targets := peer.PeersToTxnProcessors(peers)
127158

@@ -137,7 +168,7 @@ func TestQueryWithOptTarget(t *testing.T) {
137168

138169
func TestExecuteTx(t *testing.T) {
139170

140-
chClient := setupChannelClient(t)
171+
chClient := setupChannelClient(nil, t)
141172

142173
_, err := chClient.ExecuteTx(apitxn.ExecuteTxRequest{})
143174
if err == nil {
@@ -159,7 +190,7 @@ func TestExecuteTx(t *testing.T) {
159190

160191
func TestExecuteTxDiscoveryError(t *testing.T) {
161192

162-
chClient := setupChannelClientWithError(errors.New("Test Error"), nil, t)
193+
chClient := setupChannelClientWithError(errors.New("Test Error"), nil, nil, t)
163194

164195
_, err := chClient.ExecuteTx(apitxn.ExecuteTxRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("move"), []byte("a"), []byte("b"), []byte("1")}})
165196
if err == nil {
@@ -170,7 +201,7 @@ func TestExecuteTxDiscoveryError(t *testing.T) {
170201

171202
func TestExecuteTxSelectionError(t *testing.T) {
172203

173-
chClient := setupChannelClientWithError(nil, errors.New("Test Error"), t)
204+
chClient := setupChannelClientWithError(nil, errors.New("Test Error"), nil, t)
174205

175206
_, err := chClient.ExecuteTx(apitxn.ExecuteTxRequest{ChaincodeID: "testCC", Fcn: "invoke", Args: [][]byte{[]byte("move"), []byte("a"), []byte("b"), []byte("1")}})
176207
if err == nil {
@@ -214,12 +245,12 @@ func setupTestSelection(discErr error, peers []apifabclient.Peer) (apifabclient.
214245
return mockSelection.NewSelectionService("mychannel")
215246
}
216247

217-
func setupChannelClient(t *testing.T) *ChannelClient {
248+
func setupChannelClient(peers []apifabclient.Peer, t *testing.T) *ChannelClient {
218249

219-
return setupChannelClientWithError(nil, nil, t)
250+
return setupChannelClientWithError(nil, nil, peers, t)
220251
}
221252

222-
func setupChannelClientWithError(discErr error, selectionErr error, t *testing.T) *ChannelClient {
253+
func setupChannelClientWithError(discErr error, selectionErr error, peers []apifabclient.Peer, t *testing.T) *ChannelClient {
223254

224255
fcClient := setupTestClient()
225256

@@ -236,7 +267,7 @@ func setupChannelClientWithError(discErr error, selectionErr error, t *testing.T
236267
t.Fatalf("Failed to setup discovery service: %s", err)
237268
}
238269

239-
selectionService, err := setupTestSelection(selectionErr, nil)
270+
selectionService, err := setupTestSelection(selectionErr, peers)
240271
if err != nil {
241272
t.Fatalf("Failed to setup discovery service: %s", err)
242273
}

pkg/fabric-txn/mocks/mockselection.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -42,9 +42,9 @@ func (ds *MockSelectionService) GetEndorsersForChaincode(channelPeers []apifabcl
4242
}
4343

4444
if ds.Peers == nil {
45-
mockPeer := mocks.MockPeer{MockName: "Peer1", MockURL: "http://peer1.com", MockRoles: []string{}, MockCert: nil}
45+
mockPeer := mocks.NewMockPeer("Peer1", "http://peer1.com")
4646
peers := make([]apifabclient.Peer, 0)
47-
peers = append(peers, &mockPeer)
47+
peers = append(peers, mockPeer)
4848
ds.Peers = peers
4949
}
5050

0 commit comments

Comments
 (0)