Skip to content

Commit 3c418c5

Browse files
[FAB-11595] Java cc pvtdata integration test
Added java chaincode that use private data Added integration test to run it Change-Id: If440706c4606a2d281ff3c22d8254577614b7abe Signed-off-by: gennady <gennady@il.ibm.com>
1 parent 623eaa9 commit 3c418c5

File tree

5 files changed

+261
-6
lines changed

5 files changed

+261
-6
lines changed
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
/*
2+
* Copyright IBM Corp. 2018 All Rights Reserved.
3+
*
4+
* SPDX-License-Identifier: Apache-2.0
5+
*/
6+
7+
plugins {
8+
id 'com.github.johnrengelman.shadow' version '2.0.3'
9+
id 'java'
10+
}
11+
12+
group 'org.hyperledger.fabric'
13+
version '1.0-SNAPSHOT'
14+
15+
sourceCompatibility = 1.8
16+
17+
repositories {
18+
mavenLocal()
19+
mavenCentral()
20+
}
21+
22+
dependencies {
23+
compile group: 'org.hyperledger.fabric', name: 'fabric-chaincode-shim', version: '1.3.0-SNAPSHOT'
24+
testCompile group: 'junit', name: 'junit', version: '4.12'
25+
}
26+
27+
shadowJar {
28+
baseName = 'chaincode'
29+
version = null
30+
classifier = null
31+
32+
manifest {
33+
attributes 'Main-Class': 'org.hyperledger.fabric.example.SimpleChaincode'
34+
}
35+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
/*
2+
* Copyright IBM Corp. 2018 All Rights Reserved.
3+
*
4+
* SPDX-License-Identifier: Apache-2.0
5+
*/
6+
7+
rootProject.name = 'fabric-chaincode-example-gradle'
8+
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,161 @@
1+
/*
2+
Copyright IBM Corp All Rights Reserved.
3+
4+
SPDX-License-Identifier: Apache-2.0
5+
*/
6+
package org.hyperledger.fabric.example;
7+
8+
import java.nio.charset.StandardCharsets;
9+
import java.util.List;
10+
11+
import com.google.protobuf.ByteString;
12+
import io.netty.handler.ssl.OpenSsl;
13+
import org.apache.commons.logging.Log;
14+
import org.apache.commons.logging.LogFactory;
15+
import org.hyperledger.fabric.shim.ChaincodeBase;
16+
import org.hyperledger.fabric.shim.ChaincodeStub;
17+
18+
import static java.nio.charset.StandardCharsets.UTF_8;
19+
20+
public class SimpleChaincode extends ChaincodeBase {
21+
22+
private static Log _logger = LogFactory.getLog(SimpleChaincode.class);
23+
24+
public static String COLLECTION = "simplecollection";
25+
26+
@Override
27+
public Response init(ChaincodeStub stub) {
28+
try {
29+
_logger.info("Init java simple chaincode");
30+
String func = stub.getFunction();
31+
if (!func.equals("init")) {
32+
return newErrorResponse("function other than init is not supported");
33+
}
34+
List<String> args = stub.getParameters();
35+
if (args.size() != 4) {
36+
newErrorResponse("Incorrect number of arguments. Expecting 4");
37+
}
38+
// Initialize the chaincode
39+
String account1Key = args.get(0);
40+
int account1Value = Integer.parseInt(args.get(1));
41+
String account2Key = args.get(2);
42+
int account2Value = Integer.parseInt(args.get(3));
43+
44+
_logger.info(String.format("account %s, value = %s; account %s, value %s", account1Key, account1Value, account2Key, account2Value));
45+
stub.putStringState(account1Key, args.get(1));
46+
stub.putStringState(account2Key, args.get(3));
47+
48+
return newSuccessResponse();
49+
} catch (Throwable e) {
50+
return newErrorResponse(e);
51+
}
52+
}
53+
54+
@Override
55+
public Response invoke(ChaincodeStub stub) {
56+
try {
57+
_logger.info("Invoke java simple chaincode");
58+
String func = stub.getFunction();
59+
List<String> params = stub.getParameters();
60+
if (func.equals("invoke")) {
61+
return invoke(stub, params);
62+
}
63+
if (func.equals("delete")) {
64+
return delete(stub, params);
65+
}
66+
if (func.equals("query")) {
67+
return query(stub, params);
68+
}
69+
return newErrorResponse("Invalid invoke function name. Expecting one of: [\"invoke\", \"delete\", \"query\"]");
70+
} catch (Throwable e) {
71+
return newErrorResponse(e);
72+
}
73+
}
74+
75+
private Response invoke(ChaincodeStub stub, List<String> args) {
76+
if (args.size() != 3) {
77+
return newErrorResponse("Incorrect number of arguments. Expecting 3");
78+
}
79+
String accountFromKey = args.get(0);
80+
String accountToKey = args.get(1);
81+
82+
_logger.info(String.format("Arguments : %s, %s, %s", accountFromKey, accountToKey, args.get(2)));
83+
84+
String accountFromValueStr;
85+
accountFromValueStr = stub.getPrivateDataUTF8(COLLECTION, accountFromKey);
86+
_logger.info(String.format("Get value for %s=%s from private data", accountFromKey, accountFromValueStr));
87+
if (accountFromValueStr == null || accountFromValueStr.isEmpty()) {
88+
accountFromValueStr = stub.getStringState(accountFromKey);
89+
if (accountFromValueStr == null || accountFromValueStr.isEmpty()) {
90+
return newErrorResponse(String.format("Entity %s not found", accountFromKey));
91+
}
92+
}
93+
int accountFromValue = Integer.parseInt(accountFromValueStr);
94+
95+
String accountToValueStr;
96+
accountToValueStr = stub.getPrivateDataUTF8(COLLECTION, accountToKey);
97+
if (accountToValueStr == null || accountToValueStr.isEmpty()) {
98+
accountToValueStr = stub.getStringState(accountToKey);
99+
if (accountToValueStr == null || accountToValueStr.isEmpty()) {
100+
return newErrorResponse(String.format("Entity %s not found", accountToKey));
101+
}
102+
}
103+
int accountToValue = Integer.parseInt(accountToValueStr);
104+
105+
int amount = Integer.parseInt(args.get(2));
106+
107+
if (amount > accountFromValue) {
108+
return newErrorResponse(String.format("not enough money in account %s", accountFromKey));
109+
}
110+
111+
accountFromValue -= amount;
112+
accountToValue += amount;
113+
114+
_logger.info(String.format("new value of A: %s", accountFromValue));
115+
_logger.info(String.format("new value of B: %s", accountToValue));
116+
117+
stub.putPrivateData(COLLECTION, accountFromKey, Integer.toString(accountFromValue));
118+
stub.putPrivateData(COLLECTION, accountToKey, Integer.toString(accountToValue));
119+
120+
_logger.info("Transfer complete");
121+
122+
return newSuccessResponse("invoke finished successfully");
123+
}
124+
125+
// Deletes an entity from state
126+
private Response delete(ChaincodeStub stub, List<String> args) {
127+
if (args.size() != 1) {
128+
return newErrorResponse("Incorrect number of arguments. Expecting 1");
129+
}
130+
String key = args.get(0);
131+
// Delete the key from the state in ledger
132+
stub.delState(key);
133+
stub.delPrivateData(COLLECTION, key);
134+
return newSuccessResponse();
135+
}
136+
137+
// query callback representing the query of a chaincode
138+
private Response query(ChaincodeStub stub, List<String> args) {
139+
if (args.size() != 1) {
140+
return newErrorResponse("Incorrect number of arguments. Expecting name of the person to query");
141+
}
142+
String key = args.get(0);
143+
//byte[] stateBytes
144+
String val;
145+
val = new String(stub.getPrivateData(COLLECTION, key), StandardCharsets.UTF_8);
146+
if (val == null || val.isEmpty()) {
147+
val = stub.getStringState(key);
148+
if (val == null) {
149+
return newErrorResponse(String.format("Error: state for %s is null", key));
150+
}
151+
}
152+
_logger.info(String.format("Query Response:\nName: %s, Amount: %s\n", key, val));
153+
return newSuccessResponse(val, ByteString.copyFrom(val, UTF_8).toByteArray());
154+
}
155+
156+
public static void main(String[] args) {
157+
System.out.println("OpenSSL avaliable: " + OpenSsl.isAvailable());
158+
new SimpleChaincode().start(args);
159+
}
160+
161+
}

integration/java_chaincode/javacc_test.go

Lines changed: 48 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ var _ = Describe("EndToEnd-JavaCC", func() {
4444

4545
AfterEach(func() {
4646
if process != nil {
47-
process.Signal(syscall.SIGTERM)
47+
process.Signal(syscall.SIGILL)
4848
Eventually(process.Wait(), time.Minute).Should(Receive())
4949
}
5050
if network != nil {
@@ -86,22 +86,63 @@ var _ = Describe("EndToEnd-JavaCC", func() {
8686
By("getting the client peer by name")
8787
peer := network.Peer("Org1", "peer0")
8888

89+
RunQueryInvokeQuery(network, orderer, peer)
90+
})
91+
It("support for private data in java chaincode", func() {
92+
chaincode = nwo.Chaincode{
93+
Name: "mycc",
94+
Version: "0.0",
95+
Path: "../chaincode/java/simple_pvtdata/gradle/",
96+
Ctor: `{"Args":["init","a","100","b","200"]}`,
97+
Policy: `OR ('Org1MSP.member','Org2MSP.member')`,
98+
Lang: "java",
99+
CollectionsConfig: "testdata/collection_config.json",
100+
}
101+
102+
By("getting the orderer by name")
103+
orderer := network.Orderer("orderer")
104+
105+
By("setting up the channel")
106+
network.CreateAndJoinChannel(orderer, "testchannel")
107+
108+
By("deploying the chaincode")
109+
nwo.DeployChaincode(network, "testchannel", orderer, chaincode)
110+
111+
By("getting the client peer by name")
112+
peer := network.Peer("Org1", "peer0")
113+
89114
RunQueryInvokeQuery(network, orderer, peer)
90115
})
91116
})
92117
})
93118

94119
func RunQueryInvokeQuery(n *nwo.Network, orderer *nwo.Orderer, peer *nwo.Peer) {
95-
By("querying the chaincode")
96-
sess, err := n.PeerUserSession(peer, "User1", commands.ChaincodeQuery{
120+
By("invoking the chaincode - 1")
121+
sess, err := n.PeerUserSession(peer, "User1", commands.ChaincodeInvoke{
122+
ChannelID: "testchannel",
123+
Orderer: n.OrdererAddress(orderer, nwo.ListenPort),
124+
Name: "mycc",
125+
Ctor: `{"Args":["invoke","a","b","10"]}`,
126+
PeerAddresses: []string{
127+
n.PeerAddress(n.Peer("Org1", "peer0"), nwo.ListenPort),
128+
},
129+
WaitForEvent: true,
130+
})
131+
Expect(err).NotTo(HaveOccurred())
132+
Eventually(sess, time.Minute).Should(gexec.Exit(0))
133+
Expect(sess.Err).To(gbytes.Say("Chaincode invoke successful. result: status:200"))
134+
135+
By("querying the chaincode - 1")
136+
sess, err = n.PeerUserSession(peer, "User1", commands.ChaincodeQuery{
97137
ChannelID: "testchannel",
98138
Name: "mycc",
99139
Ctor: `{"Args":["query","a"]}`,
100140
})
101141
Expect(err).NotTo(HaveOccurred())
102142
Eventually(sess, time.Minute).Should(gexec.Exit(0))
103-
Expect(sess).To(gbytes.Say("100"))
143+
Expect(sess).To(gbytes.Say("90"))
104144

145+
By("invoking the chaincode - 2")
105146
sess, err = n.PeerUserSession(peer, "User1", commands.ChaincodeInvoke{
106147
ChannelID: "testchannel",
107148
Orderer: n.OrdererAddress(orderer, nwo.ListenPort),
@@ -116,12 +157,13 @@ func RunQueryInvokeQuery(n *nwo.Network, orderer *nwo.Orderer, peer *nwo.Peer) {
116157
Eventually(sess, time.Minute).Should(gexec.Exit(0))
117158
Expect(sess.Err).To(gbytes.Say("Chaincode invoke successful. result: status:200"))
118159

160+
By("querying the chaincode - 2")
119161
sess, err = n.PeerUserSession(peer, "User1", commands.ChaincodeQuery{
120162
ChannelID: "testchannel",
121163
Name: "mycc",
122-
Ctor: `{"Args":["query","a"]}`,
164+
Ctor: `{"Args":["query","b"]}`,
123165
})
124166
Expect(err).NotTo(HaveOccurred())
125167
Eventually(sess, time.Minute).Should(gexec.Exit(0))
126-
Expect(sess).To(gbytes.Say("90"))
168+
Expect(sess).To(gbytes.Say("220"))
127169
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
[
2+
{
3+
"name": "simplecollection",
4+
"policy": "OR('Org1MSP.member', 'Org2MSP.member')",
5+
"requiredPeerCount": 0,
6+
"maxPeerCount": 2,
7+
"blockToLive":1000000
8+
}
9+
]

0 commit comments

Comments
 (0)