diff --git a/build/tasks/eslint.js b/build/tasks/eslint.js
index 0f229879ac..c5f927c4a0 100644
--- a/build/tasks/eslint.js
+++ b/build/tasks/eslint.js
@@ -8,6 +8,8 @@ gulp.task('lint', function () {
'fabric-ca-client/lib/*.js',
'examples/**/*.js',
'!node_modules/**',
+ '!fabric-client/node_modules/**',
+ '!fabric-ca-client/node_modules/**',
'!docs/**',
'!coverage/**',
'!tmp/**'
diff --git a/fabric-ca-client/lib/FabricCAClientImpl.js b/fabric-ca-client/lib/FabricCAClientImpl.js
index 12550c44a9..e76de7219d 100644
--- a/fabric-ca-client/lib/FabricCAClientImpl.js
+++ b/fabric-ca-client/lib/FabricCAClientImpl.js
@@ -76,7 +76,8 @@ var FabricCAServices = class {
* @param {Object} req Registration request with the following fields:
*
- enrollmentID {string}. ID which will be used for enrollment
*
- role {string}. An arbitrary string representing a role value for the user
- *
- group {string}. Group to which this user will be assigned, like a company or an organization
+ *
- affiliation {string}. Affiliation with which this user will be associated, like a company or an organization
+ *
- maxEnrollments {number}. The maximum number of times this user will be permitted to enroll
*
- attrs {{@link KeyValueAttribute}[]}. Array of key/value attributes to assign to the user.
* @param registrar {User}. The identity of the registrar (i.e. who is performing the registration)
* @returns {Promise} The enrollment secret to use when this user enrolls
@@ -90,9 +91,15 @@ var FabricCAServices = class {
throw new Error('Missing required argument "request.enrollmentID"');
}
+ if (typeof req.maxEnrollments === 'undefined' || req.maxEnrollments === null) {
+ // set maxEnrollments to 1
+ req.maxEnrollments = 1;
+ }
+
checkRegistrar(registrar);
- return this._fabricCAClient.register(req.enrollmentID, req.role, req.group, req.attrs, registrar.getSigningIdentity());
+ return this._fabricCAClient.register(req.enrollmentID, req.role, req.affiliation, req.maxEnrollments, req.attrs,
+ registrar.getSigningIdentity());
}
/**
@@ -128,10 +135,11 @@ var FabricCAServices = class {
var csr = privateKey.generateCSR('CN=' + req.enrollmentID);
self._fabricCAClient.enroll(req.enrollmentID, req.enrollmentSecret, csr)
.then(
- function (csrPEM) {
+ function (enrollResponse) {
return resolve({
key: privateKey,
- certificate: csrPEM
+ certificate: enrollResponse.enrollmentCert,
+ rootCertificate: enrollResponse.caCertChain
});
},
function (err) {
@@ -298,19 +306,20 @@ var FabricCAClient = class {
* Register a new user and return the enrollment secret
* @param {string} enrollmentID ID which will be used for enrollment
* @param {string} role Type of role for this user
- * @param {string} group Group to which this user will be assigned
+ * @param {string} affiliation Affiliation with which this user will be associated
+ * @param {number} maxEnrollments The maximum number of times the user is permitted to enroll
* @param {KeyValueAttribute[]} attrs Array of key/value attributes to assign to the user
* @param {SigningIdentity} signingIdentity The instance of a SigningIdentity encapsulating the
* signing certificate, hash algorithm and signature algorithm
* @returns {Promise} The enrollment secret to use when this user enrolls
*/
- register(enrollmentID, role, group, attrs, signingIdentity) {
+ register(enrollmentID, role, affiliation, maxEnrollments, attrs, signingIdentity) {
var self = this;
var numArgs = arguments.length;
//all arguments are required
if (numArgs < 5) {
- throw new Error('Missing required parameters. \'enrollmentID\', \'role\', \'group\', \'attrs\', \
+ throw new Error('Missing required parameters. \'enrollmentID\', \'role\', \'affiliation\', \'attrs\', \
and \'signingIdentity\' are all required.');
}
@@ -318,13 +327,14 @@ var FabricCAClient = class {
var regRequest = {
'id': enrollmentID,
'type': role ? role : 'client',
- 'group': group,
+ 'affiliation': affiliation,
+ 'max_enrollments': maxEnrollments,
'attrs': attrs
};
return self.post('register', regRequest, signingIdentity)
.then(function (response) {
- return resolve(response.result.credential);
+ return resolve(response.result.secret);
}).catch(function (err) {
return reject(err);
});
@@ -358,10 +368,15 @@ var FabricCAClient = class {
return new Promise(function (resolve, reject) {
+ if (serial!=null){
+ if (serial.length < 80){
+ serial = '0' + serial;
+ }
+ }
var regRequest = {
'id': enrollmentID,
'aki': aki,
- 'serial': parseInt(serial, 16) + '', // per CFSSL, serial numbers are saved as decimals instead of hex strings in cert database
+ 'serial': serial,
'reason': reason
};
@@ -446,12 +461,19 @@ var FabricCAClient = class {
return cert + '.' + b64Sign;
}
+ /**
+ * @typedef {Object} EnrollmentResponse
+ * @property {string} enrollmentCert PEM-encoded X509 enrollment certificate
+ * @property {string} caCertChain PEM-encoded X509 certificate chain for the issuing
+ * certificate authority
+ */
+
/**
* Enroll a registered user in order to receive a signed X509 certificate
* @param {string} enrollmentID The registered ID to use for enrollment
* @param {string} enrollmentSecret The secret associated with the enrollment ID
* @param {string} csr PEM-encoded PKCS#10 certificate signing request
- * @returns {Promise} PEM-encoded X509 certificate
+ * @returns {Promise} {@link EnrollmentResponse}
* @throws Will throw an error if all parameters are not provided
* @throws Will throw an error if calling the enroll API fails for any reason
*/
@@ -495,10 +517,14 @@ var FabricCAClient = class {
}
//response should be JSON
try {
- var enrollResponse = JSON.parse(payload);
- if (enrollResponse.success) {
+ var res = JSON.parse(payload);
+ if (res.success) {
//we want the result field which is Base64-encoded PEM
- return resolve(new Buffer.from(enrollResponse.result, 'base64').toString());
+ var enrollResponse = new Object();
+ // Cert field is Base64-encoded PEM
+ enrollResponse.enrollmentCert = new Buffer.from(res.result.Cert, 'base64').toString();
+ enrollResponse.caCertChain = new Buffer.from(res.result.ServerInfo.CAChain, 'base64').toString();
+ return resolve(enrollResponse);
} else {
return reject(new Error(
util.format('Enrollment failed with errors [%s]', JSON.stringify(enrollResponse.errors))));
diff --git a/fabric-ca-client/package.json b/fabric-ca-client/package.json
index 850d9b6954..fad324e774 100644
--- a/fabric-ca-client/package.json
+++ b/fabric-ca-client/package.json
@@ -28,8 +28,10 @@
"winston": "^2.2.0"
},
"license": "Apache-2.0",
- "licenses": [{
- "type": "Apache-2.0",
- "url": "https://github.com/hyperledger/fabric/blob/master/LICENSE"
- }]
+ "licenses": [
+ {
+ "type": "Apache-2.0",
+ "url": "https://github.com/hyperledger/fabric/blob/master/LICENSE"
+ }
+ ]
}
diff --git a/test/integration/fabric-ca-services-tests.js b/test/integration/fabric-ca-services-tests.js
index 8f5bc59897..4897a1fe3a 100644
--- a/test/integration/fabric-ca-services-tests.js
+++ b/test/integration/fabric-ca-services-tests.js
@@ -85,11 +85,12 @@ test('FabricCAServices: Test enroll() With Dynamic CSR', function (t) {
var signingIdentity = new SigningIdentity('testSigningIdentity', eResult.certificate, pubKey, msp, new Signer(msp.cryptoSuite, eResult.key));
- return cop._fabricCAClient.register(enrollmentID, 'client', 'org1', [], signingIdentity);
+ return cop._fabricCAClient.register(enrollmentID, 'client', 'org1', 1, [], signingIdentity);
},(err) => {
t.fail('Failed to import the public key from the enrollment certificate. ' + err.stack ? err.stack : err);
t.end();
}).then((secret) => {
+ console.log('secret: ' + JSON.stringify(secret));
t.comment(secret);
enrollmentSecret = secret; // to be used in the next test case
@@ -110,17 +111,16 @@ test('FabricCAServices: Test enroll() With Dynamic CSR', function (t) {
return member.setEnrollment(eResult.key, eResult.certificate);
}).then(() => {
t.comment('Successfully constructed a user object based on the enrollment');
-
- return cop.register({enrollmentID: 'testUserX', group: 'bank_X'}, member);
+ return cop.register({enrollmentID: 'testUserX', affiliation: 'bank_X'}, member);
}).then((secret) => {
- t.fail('Should not have been able to register user of a group "bank_X" because "admin" does not belong to that group');
+ t.fail('Should not have been able to register user of a affiliation "bank_X" because "admin" does not belong to that affiliation');
t.end();
},(err) => {
- t.pass('Successfully rejected registration request "testUserX" in group "bank_X"');
+ t.pass('Successfully rejected registration request "testUserX" in affiliation "bank_X"');
- return cop.register({enrollmentID: 'testUserX', group: 'org1'}, member);
+ return cop.register({enrollmentID: 'testUserX', affiliation: 'org1'}, member);
}).then((secret) => {
- t.pass('Successfully registered "testUserX" in group "org1" with enrollment secret returned: ' + secret);
+ t.pass('Successfully registered "testUserX" in affiliation "org1" with enrollment secret returned: ' + secret);
return cop.revoke({enrollmentID: 'testUserX'}, member);
},(err) => {
@@ -129,7 +129,7 @@ test('FabricCAServices: Test enroll() With Dynamic CSR', function (t) {
}).then((response) => {
t.equal(response.success, true, 'Successfully revoked "testUserX"');
- return cop.register({enrollmentID: 'testUserY', group: 'org2.department1'}, member);
+ return cop.register({enrollmentID: 'testUserY', affiliation: 'org2.department1'}, member);
},(err) => {
t.fail('Failed to revoke "testUserX". ' + err.stack ? err.stack : err);
t.end();
@@ -148,11 +148,12 @@ test('FabricCAServices: Test enroll() With Dynamic CSR', function (t) {
t.comment(util.format('Ready to revoke certificate serial # "%s" with aki "%s"', serial, aki));
return cop.revoke({serial: serial, aki: aki}, member);
+ //return;
}).then((response) => {
t.equal(response.success, true, 'Successfully revoked "testUserY" using serial number and AKI');
// register a new user 'webAdmin' that can register other users of the role 'client'
- return cop.register({enrollmentID: 'webAdmin', group: 'org1.department2', attrs: [{name: 'hf.Registrar.Roles', value: 'client'}]}, member);
+ return cop.register({enrollmentID: 'webAdmin', affiliation: 'org1.department2', attrs: [{name: 'hf.Registrar.Roles', value: 'client'}]}, member);
}).then((secret) => {
t.pass('Successfully registered "webAdmin" who can register other users of the "client" role');
@@ -175,7 +176,7 @@ test('FabricCAServices: Test enroll() With Dynamic CSR', function (t) {
},(err) => {
t.pass('Successfully rejected attempt to register a user of invalid role. ' + err);
- return cop.register({enrollmentID: 'auditor', role: 'client', group: 'org2.department1'}, webAdmin);
+ return cop.register({enrollmentID: 'auditor', role: 'client', affiliation: 'org2.department1'}, webAdmin);
}).then(() => {
t.pass('Successfully registered "auditor" of role "client" from "webAdmin"');
t.end();
@@ -195,12 +196,12 @@ test('FabricCAClient: Test enroll With Static CSR', function (t) {
t.comment(util.format('Sending enroll request for user %s with enrollment secret %s', enrollmentID, enrollmentSecret));
return client.enroll(enrollmentID, enrollmentSecret, csr.toString())
- .then(function (pem) {
- t.comment(pem);
+ .then(function (enrollResponse) {
+ t.comment(enrollResponse.enrollmentCert);
t.pass('Successfully invoked enroll API with enrollmentID \'' + enrollmentID + '\'');
//check that we got back the expected certificate
var cert = new X509();
- cert.readCertPEM(pem);
+ cert.readCertPEM(enrollResponse.enrollmentCert);
t.comment(cert.getSubjectString());
t.equal(cert.getSubjectString(), '/CN=' + enrollmentID, 'Subject should be /CN=' + enrollmentID);
t.end();