Skip to content

Commit eff0046

Browse files
Simon Stonedenyeart
Simon Stone
authored andcommitted
[FAB-12877] Add fabcar app using new prog model (JS)
Add a new version of the FabCar applications using the new programming model (fabric-network), written in JavaScript. Change-Id: I0fcc2e8a10291805d5389c7fc8d1e529debd600a Signed-off-by: Simon Stone <sstone1@uk.ibm.com>
1 parent c184196 commit eff0046

File tree

11 files changed

+405
-1
lines changed

11 files changed

+405
-1
lines changed

fabcar/javascript/.editorconfig

+16
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
#
2+
# SPDX-License-Identifier: Apache-2.0
3+
#
4+
5+
root = true
6+
7+
[*]
8+
indent_style = space
9+
indent_size = 4
10+
end_of_line = lf
11+
charset = utf-8
12+
trim_trailing_whitespace = true
13+
insert_final_newline = true
14+
15+
[*.md]
16+
trim_trailing_whitespace = false

fabcar/javascript/.eslintignore

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
#
2+
# SPDX-License-Identifier: Apache-2.0
3+
#
4+
5+
coverage

fabcar/javascript/.eslintrc.js

+37
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
/*
2+
* SPDX-License-Identifier: Apache-2.0
3+
*/
4+
5+
module.exports = {
6+
env: {
7+
node: true,
8+
mocha: true
9+
},
10+
parserOptions: {
11+
ecmaVersion: 8,
12+
sourceType: 'script'
13+
},
14+
extends: "eslint:recommended",
15+
rules: {
16+
indent: ['error', 4],
17+
'linebreak-style': ['error', 'unix'],
18+
quotes: ['error', 'single'],
19+
semi: ['error', 'always'],
20+
'no-unused-vars': ['error', { args: 'none' }],
21+
'no-console': 'off',
22+
curly: 'error',
23+
eqeqeq: 'error',
24+
'no-throw-literal': 'error',
25+
strict: 'error',
26+
'no-var': 'error',
27+
'dot-notation': 'error',
28+
'no-tabs': 'error',
29+
'no-trailing-spaces': 'error',
30+
'no-use-before-define': 'error',
31+
'no-useless-call': 'error',
32+
'no-with': 'error',
33+
'operator-linebreak': 'error',
34+
yoda: 'error',
35+
'quote-props': ['error', 'as-needed']
36+
}
37+
};

fabcar/javascript/.gitignore

+80
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
#
2+
# SPDX-License-Identifier: Apache-2.0
3+
#
4+
5+
# Logs
6+
logs
7+
*.log
8+
npm-debug.log*
9+
yarn-debug.log*
10+
yarn-error.log*
11+
12+
# Runtime data
13+
pids
14+
*.pid
15+
*.seed
16+
*.pid.lock
17+
18+
# Directory for instrumented libs generated by jscoverage/JSCover
19+
lib-cov
20+
21+
# Coverage directory used by tools like istanbul
22+
coverage
23+
24+
# nyc test coverage
25+
.nyc_output
26+
27+
# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)
28+
.grunt
29+
30+
# Bower dependency directory (https://bower.io/)
31+
bower_components
32+
33+
# node-waf configuration
34+
.lock-wscript
35+
36+
# Compiled binary addons (https://nodejs.org/api/addons.html)
37+
build/Release
38+
39+
# Dependency directories
40+
node_modules/
41+
jspm_packages/
42+
43+
# TypeScript v1 declaration files
44+
typings/
45+
46+
# Optional npm cache directory
47+
.npm
48+
49+
# Optional eslint cache
50+
.eslintcache
51+
52+
# Optional REPL history
53+
.node_repl_history
54+
55+
# Output of 'npm pack'
56+
*.tgz
57+
58+
# Yarn Integrity file
59+
.yarn-integrity
60+
61+
# dotenv environment variables file
62+
.env
63+
64+
# parcel-bundler cache (https://parceljs.org/)
65+
.cache
66+
67+
# next.js build output
68+
.next
69+
70+
# nuxt.js build output
71+
.nuxt
72+
73+
# vuepress build output
74+
.vuepress/dist
75+
76+
# Serverless directories
77+
.serverless
78+
79+
wallet
80+
!wallet/.gitkeep

fabcar/javascript/enrollAdmin.js

+47
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
/*
2+
* SPDX-License-Identifier: Apache-2.0
3+
*/
4+
5+
'use strict';
6+
7+
const FabricCAServices = require('fabric-ca-client');
8+
const { FileSystemWallet, X509WalletMixin } = require('fabric-network');
9+
const fs = require('fs');
10+
const path = require('path');
11+
12+
const ccpPath = path.resolve(__dirname, '..', '..', 'basic-network', 'connection.json');
13+
const ccpJSON = fs.readFileSync(ccpPath, 'utf8');
14+
const ccp = JSON.parse(ccpJSON);
15+
16+
async function main() {
17+
try {
18+
19+
// Create a new CA client for interacting with the CA.
20+
const caURL = ccp.certificateAuthorities['ca.example.com'].url;
21+
const ca = new FabricCAServices(caURL);
22+
23+
// Create a new file system based wallet for managing identities.
24+
const walletPath = path.join(process.cwd(), 'wallet');
25+
const wallet = new FileSystemWallet(walletPath);
26+
console.log(`Wallet path: ${walletPath}`);
27+
28+
// Check to see if we've already enrolled the admin user.
29+
const adminExists = await wallet.exists('admin');
30+
if (adminExists) {
31+
console.log('An identity for the admin user "admin" already exists in the wallet');
32+
return;
33+
}
34+
35+
// Enroll the admin user, and import the new identity into the wallet.
36+
const enrollment = await ca.enroll({ enrollmentID: 'admin', enrollmentSecret: 'adminpw' });
37+
const identity = X509WalletMixin.createIdentity('Org1MSP', enrollment.certificate, enrollment.key.toBytes());
38+
wallet.import('admin', identity);
39+
console.log('Successfully enrolled admin user "admin" and imported it into the wallet');
40+
41+
} catch (error) {
42+
console.error(`Failed to enroll admin user "admin": ${error}`);
43+
process.exit(1);
44+
}
45+
}
46+
47+
main();

fabcar/javascript/invoke.js

+56
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
/*
2+
* SPDX-License-Identifier: Apache-2.0
3+
*/
4+
5+
'use strict';
6+
7+
const { FileSystemWallet, Gateway } = require('fabric-network');
8+
const fs = require('fs');
9+
const path = require('path');
10+
11+
const ccpPath = path.resolve(__dirname, '..', '..', 'basic-network', 'connection.json');
12+
const ccpJSON = fs.readFileSync(ccpPath, 'utf8');
13+
const ccp = JSON.parse(ccpJSON);
14+
15+
async function main() {
16+
try {
17+
18+
// Create a new file system based wallet for managing identities.
19+
const walletPath = path.join(process.cwd(), 'wallet');
20+
const wallet = new FileSystemWallet(walletPath);
21+
console.log(`Wallet path: ${walletPath}`);
22+
23+
// Check to see if we've already enrolled the user.
24+
const userExists = await wallet.exists('user1');
25+
if (!userExists) {
26+
console.log('An identity for the user "user1" does not exist in the wallet');
27+
console.log('Run the registerUser.js application before retrying');
28+
return;
29+
}
30+
31+
// Create a new gateway for connecting to our peer node.
32+
const gateway = new Gateway();
33+
await gateway.connect(ccp, { wallet, identity: 'user1', discovery: { useLocalhost: true } });
34+
35+
// Get the network (channel) our contract is deployed to.
36+
const network = await gateway.getNetwork('mychannel');
37+
38+
// Get the contract from the network.
39+
const contract = network.getContract('fabcar');
40+
41+
// Submit the specified transaction.
42+
// createCar transaction - requires 5 argument, ex: ('createCar', 'CAR12', 'Honda', 'Accord', 'Black', 'Tom')
43+
// changeCarOwner transaction - requires 2 args , ex: ('changeCarOwner', 'CAR10', 'Dave')
44+
await contract.submitTransaction('createCar', 'CAR12', 'Honda', 'Accord', 'Black', 'Tom');
45+
console.log('Transaction has been submitted');
46+
47+
// Disconnect from the gateway.
48+
await gateway.disconnect();
49+
50+
} catch (error) {
51+
console.error(`Failed to submit transaction: ${error}`);
52+
process.exit(1);
53+
}
54+
}
55+
56+
main();

fabcar/javascript/package.json

+46
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
{
2+
"name": "fabcar",
3+
"version": "1.0.0",
4+
"description": "FabCar application implemented in JavaScript",
5+
"engines": {
6+
"node": ">=8",
7+
"npm": ">=5"
8+
},
9+
"scripts": {
10+
"lint": "eslint .",
11+
"pretest": "npm run lint",
12+
"test": "nyc mocha --recursive"
13+
},
14+
"engineStrict": true,
15+
"author": "Hyperledger",
16+
"license": "Apache-2.0",
17+
"dependencies": {
18+
"fabric-ca-client": "unstable",
19+
"fabric-client": "unstable",
20+
"fabric-network": "unstable"
21+
},
22+
"devDependencies": {
23+
"chai": "^4.2.0",
24+
"eslint": "^5.9.0",
25+
"mocha": "^5.2.0",
26+
"nyc": "^13.1.0",
27+
"sinon": "^7.1.1",
28+
"sinon-chai": "^3.3.0"
29+
},
30+
"nyc": {
31+
"exclude": [
32+
"coverage/**",
33+
"test/**"
34+
],
35+
"reporter": [
36+
"text-summary",
37+
"html"
38+
],
39+
"all": true,
40+
"check-coverage": true,
41+
"statements": 100,
42+
"branches": 100,
43+
"functions": 100,
44+
"lines": 100
45+
}
46+
}

fabcar/javascript/query.js

+53
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
/*
2+
* SPDX-License-Identifier: Apache-2.0
3+
*/
4+
5+
'use strict';
6+
7+
const { FileSystemWallet, Gateway } = require('fabric-network');
8+
const fs = require('fs');
9+
const path = require('path');
10+
11+
const ccpPath = path.resolve(__dirname, '..', '..', 'basic-network', 'connection.json');
12+
const ccpJSON = fs.readFileSync(ccpPath, 'utf8');
13+
const ccp = JSON.parse(ccpJSON);
14+
15+
async function main() {
16+
try {
17+
18+
// Create a new file system based wallet for managing identities.
19+
const walletPath = path.join(process.cwd(), 'wallet');
20+
const wallet = new FileSystemWallet(walletPath);
21+
console.log(`Wallet path: ${walletPath}`);
22+
23+
// Check to see if we've already enrolled the user.
24+
const userExists = await wallet.exists('user1');
25+
if (!userExists) {
26+
console.log('An identity for the user "user1" does not exist in the wallet');
27+
console.log('Run the registerUser.js application before retrying');
28+
return;
29+
}
30+
31+
// Create a new gateway for connecting to our peer node.
32+
const gateway = new Gateway();
33+
await gateway.connect(ccp, { wallet, identity: 'user1' });
34+
35+
// Get the network (channel) our contract is deployed to.
36+
const network = await gateway.getNetwork('mychannel');
37+
38+
// Get the contract from the network.
39+
const contract = network.getContract('fabcar');
40+
41+
// Evaluate the specified transaction.
42+
// queryCar transaction - requires 1 argument, ex: ('queryCar', 'CAR4')
43+
// queryAllCars transaction - requires no arguments, ex: ('queryAllCars')
44+
const result = await contract.evaluateTransaction('queryAllCars');
45+
console.log(`Transaction has been evaluated, result is: ${result.toString()}`);
46+
47+
} catch (error) {
48+
console.error(`Failed to evaluate transaction: ${error}`);
49+
process.exit(1);
50+
}
51+
}
52+
53+
main();

0 commit comments

Comments
 (0)