Skip to content

Commit 986ae84

Browse files
Merge remote-tracking branch 'origin/improvement/CLDSRV-625-kms-ip' into w/8.8/improvement/CLDSRV-625-kms-ip
2 parents ab04f84 + f676d8e commit 986ae84

4 files changed

Lines changed: 138 additions & 124 deletions

File tree

lib/Config.js

Lines changed: 109 additions & 104 deletions
Original file line numberDiff line numberDiff line change
@@ -690,6 +690,114 @@ class Config extends EventEmitter {
690690
return kmsAWS;
691691
}
692692

693+
_parseKmipTransport(transportKmip) {
694+
const transport = {
695+
/** Specify the request pipeline depth here.
696+
* If for some reason the server sends the replies
697+
* out of order and confuses the client, a value of 1
698+
* should be a convenient workaround for a server side bug.
699+
* The default value of 8 is fine and there is almost no
700+
* benefit to tune this value for performance improvement.
701+
* Note: 0 is not an appropriate value and will fall back to 1.
702+
*/
703+
pipelineDepth: process.env.S3KMIP_PIPELINE_DEPTH || 8,
704+
tls: {
705+
port: process.env.S3KMIP_PORT || 5696,
706+
// ignore multiple hosts via env
707+
// prefer array of transport in config file
708+
// for customization per host
709+
host: process.env.S3KMIP_HOSTS || process.env.S3KMIP_HOST,
710+
key: this._loadTlsFile(process.env.S3KMIP_KEY || undefined),
711+
cert: this._loadTlsFile(process.env.S3KMIP_CERT ||
712+
undefined),
713+
ca: (process.env.S3KMIP_CA
714+
? process.env.S3KMIP_CA.split(',')
715+
: []).map(ca => this._loadTlsFile(ca)),
716+
},
717+
};
718+
if (transportKmip.pipelineDepth) {
719+
assert(typeof transportKmip.pipelineDepth === 'number');
720+
transport.pipelineDepth = transportKmip.pipelineDepth;
721+
}
722+
if (transportKmip.tls) {
723+
const { host, port, key, cert, ca } = transportKmip.tls;
724+
if (!!key !== !!cert) {
725+
throw new Error('bad config: KMIP TLS certificate ' +
726+
'and key must come along');
727+
}
728+
if (port) {
729+
assert(typeof port === 'number',
730+
'bad config: KMIP TLS Port must be a number');
731+
transport.tls.port = port;
732+
}
733+
if (host) {
734+
assert(typeof host === 'string',
735+
'bad config: KMIP TLS Host must be a string');
736+
transport.tls.host = host;
737+
}
738+
if (key) {
739+
transport.tls.key = this._loadTlsFile(key);
740+
}
741+
if (cert) {
742+
transport.tls.cert = this._loadTlsFile(cert);
743+
}
744+
if (Array.isArray(ca)) {
745+
transport.tls.ca = ca.map(ca => this._loadTlsFile(ca));
746+
} else {
747+
transport.tls.ca = this._loadTlsFile(ca);
748+
}
749+
}
750+
return transport;
751+
}
752+
753+
_parseKmsKmip(config) {
754+
this.kmip = {
755+
client: {
756+
/** Enable this option if the KMIP Server supports
757+
* Create and Activate in one operation.
758+
* Leave it disabled to prevent clock desynchronisation
759+
* issues because the two steps creation uses server's
760+
* time for `now' instead of client specified activation date
761+
* which also targets the present instant.
762+
*/
763+
compoundCreateActivate:
764+
(process.env.S3KMIP_COMPOUND_CREATE === 'true') || false,
765+
/** Set the bucket name attribute name here if the KMIP
766+
* server supports storing custom attributes along
767+
* with the keys.
768+
*/
769+
bucketNameAttributeName:
770+
process.env.S3KMIP_BUCKET_ATTRIBUTE_NAME || '',
771+
},
772+
transport: this._parseKmipTransport({}),
773+
};
774+
if (config.kmip) {
775+
if (config.kmip.client) {
776+
if (config.kmip.client.compoundCreateActivate) {
777+
assert(typeof config.kmip.client.compoundCreateActivate ===
778+
'boolean');
779+
this.kmip.client.compoundCreateActivate =
780+
config.kmip.client.compoundCreateActivate;
781+
}
782+
if (config.kmip.client.bucketNameAttributeName) {
783+
assert(typeof config.kmip.client.bucketNameAttributeName ===
784+
'string');
785+
this.kmip.client.bucketNameAttributeName =
786+
config.kmip.client.bucketNameAttributeName;
787+
}
788+
}
789+
if (config.kmip.transport) {
790+
if (Array.isArray(config.kmip.transport)) {
791+
this.kmip.transport = config.kmip.transport.map(t =>
792+
this._parseKmipTransport(t));
793+
} else {
794+
this.kmip.transport =
795+
this._parseKmipTransport(config.kmip.transport);
796+
}
797+
}
798+
}
799+
}
800+
693801
_getLocationConfig() {
694802
let locationConfig;
695803
try {
@@ -1394,110 +1502,7 @@ class Config extends EventEmitter {
13941502
}
13951503
}
13961504

1397-
this.kmip = {
1398-
client: {
1399-
/* Enable this option if the KMIP Server supports
1400-
* Create and Activate in one operation.
1401-
* Leave it disabled to prevent clock desynchronisation
1402-
* issues because the two steps creation uses server's
1403-
* time for `now' instead of client specified activation date
1404-
* which also targets the present instant.
1405-
*/
1406-
compoundCreateActivate:
1407-
(process.env.S3KMIP_COMPOUND_CREATE === 'true') || false,
1408-
/* Set the bucket name attribute name here if the KMIP
1409-
* server supports storing custom attributes along
1410-
* with the keys.
1411-
*/
1412-
bucketNameAttributeName:
1413-
process.env.S3KMIP_BUCKET_ATTRIBUTE_NAME || '',
1414-
},
1415-
transport: {
1416-
/* Specify the request pipeline depth here.
1417-
* If for some reason the server sends the replies
1418-
* out of order and confuses the client, a value of 1
1419-
* should be a convenient workaround for a server side bug.
1420-
* The default value of 8 is fine and there is almost no
1421-
* benefit to tune this value for performance improvement.
1422-
* Note: 0 is not an appropriate value and will fall back to 1.
1423-
*/
1424-
pipelineDepth: process.env.S3KMIP_PIPELINE_DEPTH || 8,
1425-
tls: {
1426-
port: process.env.S3KMIP_PORT || 5696,
1427-
/* TODO: HA is not implmented yet.
1428-
* The code expects only one host, but the
1429-
* configuration already permits to provide
1430-
* plenty of them (separated with commas).
1431-
* This comment must be removed, the
1432-
* S3KMIP_HOSTS must be split and transformed
1433-
* into an array of strings. And the 'host' attribute
1434-
* must become 'hosts'
1435-
*/
1436-
host: process.env.S3KMIP_HOSTS,
1437-
key: this._loadTlsFile(process.env.S3KMIP_KEY || undefined),
1438-
cert: this._loadTlsFile(process.env.S3KMIP_CERT ||
1439-
undefined),
1440-
ca: (process.env.S3KMIP_CA
1441-
? process.env.S3KMIP_CA.split(',')
1442-
: []).map(this._loadTlsFile),
1443-
},
1444-
},
1445-
};
1446-
if (config.kmip) {
1447-
if (config.kmip.client) {
1448-
if (config.kmip.client.compoundCreateActivate) {
1449-
assert(typeof config.kmip.client.compoundCreateActivate ===
1450-
'boolean');
1451-
this.kmip.client.compoundCreateActivate =
1452-
config.kmip.client.compoundCreateActivate;
1453-
}
1454-
if (config.kmip.client.bucketNameAttributeName) {
1455-
assert(typeof config.kmip.client.bucketNameAttributeName ===
1456-
'string');
1457-
this.kmip.client.bucketNameAttributeName =
1458-
config.kmip.client.bucketNameAttributeName;
1459-
}
1460-
}
1461-
if (config.kmip.transport) {
1462-
if (config.kmip.transport.pipelineDepth) {
1463-
assert(typeof config.kmip.transport.pipelineDepth ===
1464-
'number');
1465-
this.kmip.transport.pipelineDepth =
1466-
config.kmip.transport.pipelineDepth;
1467-
}
1468-
if (config.kmip.transport.tls) {
1469-
const { host, port, key, cert, ca } =
1470-
config.kmip.transport.tls;
1471-
if (!!key !== !!cert) {
1472-
throw new Error('bad config: KMIP TLS certificate ' +
1473-
'and key must come along');
1474-
}
1475-
if (port) {
1476-
assert(typeof port === 'number',
1477-
'bad config: KMIP TLS Port must be a number');
1478-
this.kmip.transport.tls.port = port;
1479-
}
1480-
if (host) {
1481-
assert(typeof host === 'string',
1482-
'bad config: KMIP TLS Host must be a string');
1483-
this.kmip.transport.tls.host = host;
1484-
}
1485-
1486-
if (key) {
1487-
this.kmip.transport.tls.key = this._loadTlsFile(key);
1488-
}
1489-
if (cert) {
1490-
this.kmip.transport.tls.cert = this._loadTlsFile(cert);
1491-
}
1492-
if (Array.isArray(ca)) {
1493-
this.kmip.transport.tls.ca = ca.map(this._loadTlsFile);
1494-
} else {
1495-
this.kmip.transport.tls.ca = this._loadTlsFile(ca);
1496-
}
1497-
}
1498-
}
1499-
}
1500-
1505+
this._parseKmsKmip(config);
15011506
this.kmsAWS = this._parseKmsAWS(config);
15021507

15031508
const globalEncryptionEnabled = config.globalEncryptionEnabled;

lib/kms/wrapper.js

Lines changed: 25 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,24 +7,30 @@ const logger = require('../utilities/logger');
77
const inMemory = require('./in_memory/backend').backend;
88
const file = require('./file/backend');
99
const KMIPClient = require('arsenal').network.kmipClient;
10+
const KMIPClusterClient = require('arsenal').network.kmipClusterClient;
1011
const { KmsAWSClient } = require('arsenal').network;
1112
const Common = require('./common');
1213
const vault = require('../auth/vault');
1314
const Cache = require('./Cache');
1415
const cache = new Cache();
15-
let scalityKMS;
16-
let scalityKMSImpl;
17-
try {
18-
// eslint-disable-next-line import/no-unresolved
19-
const ScalityKMS = require('scality-kms');
20-
scalityKMS = new ScalityKMS(config.kms);
21-
scalityKMSImpl = 'scalityKms';
22-
} catch (error) {
23-
logger.warn('scality kms unavailable. ' +
24-
'Using file kms backend unless mem specified.',
25-
{ error });
26-
scalityKMS = file;
27-
scalityKMSImpl = 'fileKms';
16+
17+
function getScalityKms() {
18+
let scalityKMS;
19+
let scalityKMSImpl;
20+
21+
try {
22+
// eslint-disable-next-line import/no-unresolved
23+
const ScalityKMS = require('scality-kms');
24+
scalityKMS = new ScalityKMS(config.kms);
25+
scalityKMSImpl = 'scalityKms';
26+
} catch (error) {
27+
logger.warn('scality kms unavailable. ' +
28+
'Using file kms backend unless mem specified.',
29+
{ error });
30+
scalityKMS = file;
31+
scalityKMSImpl = 'fileKms';
32+
}
33+
return { scalityKMS, scalityKMSImpl };
2834
}
2935

3036
let client;
@@ -37,14 +43,17 @@ if (config.backends.kms === 'mem') {
3743
client = file;
3844
implName = 'fileKms';
3945
} else if (config.backends.kms === 'scality') {
40-
client = scalityKMS;
41-
implName = scalityKMSImpl;
46+
({ scalityKMS: client, scalityKMSImpl: implName } = getScalityKms());
4247
} else if (config.backends.kms === 'kmip') {
4348
const kmipConfig = { kmip: config.kmip };
4449
if (!kmipConfig.kmip) {
4550
throw new Error('KMIP KMS driver configuration is missing.');
4651
}
47-
client = new KMIPClient(kmipConfig);
52+
if (Array.isArray(config.kmip.transport)) {
53+
client = new KMIPClusterClient(kmipConfig);
54+
} else {
55+
client = new KMIPClient(kmipConfig);
56+
}
4857
implName = 'kmip';
4958
} else if (config.backends.kms === 'aws') {
5059
const awsConfig = { kmsAWS: config.kmsAWS };

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
"dependencies": {
2222
"@azure/storage-blob": "^12.12.0",
2323
"@hapi/joi": "^17.1.0",
24-
"arsenal": "git+https://github.com/scality/arsenal#8.1.149",
24+
"arsenal": "git+https://github.com/scality/arsenal#8.1.150",
2525
"async": "~2.5.0",
2626
"aws-sdk": "2.905.0",
2727
"bucketclient": "scality/bucketclient#8.1.9",

yarn.lock

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1220,9 +1220,9 @@ arraybuffer.slice@~0.0.7:
12201220
optionalDependencies:
12211221
ioctl "^2.0.2"
12221222

1223-
"arsenal@git+https://github.com/scality/arsenal#8.1.149":
1224-
version "8.1.149"
1225-
resolved "git+https://github.com/scality/arsenal#10a57341688644bf3aaf5316b8e0b09f40eb5479"
1223+
"arsenal@git+https://github.com/scality/arsenal#8.1.150":
1224+
version "8.1.150"
1225+
resolved "git+https://github.com/scality/arsenal#3eea86afaecb40e39cae441700bb186b68e453e0"
12261226
dependencies:
12271227
"@azure/identity" "^3.1.1"
12281228
"@azure/storage-blob" "^12.12.0"

0 commit comments

Comments
 (0)