Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

VLTCLT-53 Add client method to get or create encryption key id #449

Merged
merged 1 commit into from
Nov 12, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 34 additions & 0 deletions lib/IAMClient.js
Original file line number Diff line number Diff line change
Expand Up @@ -977,6 +977,40 @@ class VaultClient {
}, data, options.reqUid, null, options.logger);
}

/**
* Retrieves the default encryption key id for the given account's canonical id,
* or creates one if it does not exist.
*
* @param {String} canonicalId - The canonical id of the account.
* @param {Object} options - Additional arguments.
* @param {string} options.reqUid - The request UID.
* @param {Function} callback
* - `error` (Error|null) - error object if the operation failed, otherwise null.
* - `result` (Object) - result object on success, containing raw response data and HTTP status code.
* @returns {void}
*/
getOrCreateEncryptionKeyId(canonicalId, options, callback) {
assert(canonicalId !== undefined, 'canonicalId need to be specified');
assert(typeof canonicalId === 'string', 'canonicalId should be a string');
assert(canonicalId !== '', 'canonicalId should not be empty string');
const data = {
Action: 'GetOrCreateEncryptionKeyId',
canonicalId,
};
this.request('POST', '/', false, (err, data, code) => {
if (err) {
return callback(err);
}
return callback(null, {
message: {
body: data,
code,
message: 'Encryption key retrieved or created',
},
});
}, data, options.reqUid, null);
}

healthcheck(reqUid, callback) {
this.request('GET', '/_/healthcheck', false, callback, null,
reqUid, null);
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"engines": {
"node": ">=16"
},
"version": "7.10.13",
"version": "7.10.13-1",
"description": "Client library and binary for Vault, the user directory and key management service",
"main": "index.js",
"repository": "scality/vaultclient",
Expand Down
104 changes: 104 additions & 0 deletions tests/unit/getOrCreateEncryptionKeyId.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
'use strict'; // eslint-disable-line

const assert = require('assert');
const http = require('http');
const IAMClient = require('../../lib/IAMClient');

const encryptionKeyId = '9c07eb04-d85a-48c4-8bc4-87f5ca2b9d5d';
const canonicalId = '79a59dfb37cfe5b3b1b4e58734c14e02b6e9e081ca135a3b02e6b8cc993b6dc7';

const output = {
canonicalId,
encryptionKeyId,
action: 'created',
};

describe('getOrCreateEncryptionKeyId Test', () => {
let server;
let client;
const handler = (req, res) => {
res.writeHead(200);
return res.end(JSON.stringify(output));
};

beforeEach('start server', done => {
server = http.createServer(handler).listen(8500, () => {
client = new IAMClient('127.0.0.1', 8500);
done();
}).on('error', done);
});

afterEach('stop server', () => { server.close(); });

it('should retrieve getOrCreateEncryptionKeyId response', done => {
client.getOrCreateEncryptionKeyId(canonicalId,
{ reqUid: '123' },
(err, response) => {
assert(!err);
assert.deepStrictEqual(response.message.body, output);
done();
});
});

it('should throw error if canonical id is undefined', () => {
assert.throws(
() => client.getOrCreateEncryptionKeyId(undefined, { reqUid: '123' }, () => {}), err => {
assert(err instanceof assert.AssertionError);
assert.strictEqual(err.message, 'canonicalId need to be specified');
return true;
},
);
});

it('should throw error if canonical id is not a string', () => {
assert.throws(
() => client.getOrCreateEncryptionKeyId(0, { reqUid: '123' }, () => {}), err => {
assert(err instanceof assert.AssertionError);
assert.strictEqual(err.message, 'canonicalId should be a string');
return true;
},
);
});

it('should throw error if canonical id is an empty string', () => {
assert.throws(
() => client.getOrCreateEncryptionKeyId('', { reqUid: '123' }, () => {}), err => {
assert(err instanceof assert.AssertionError);
assert.strictEqual(err.message, 'canonicalId should not be empty string');
return true;
},
);
});
});

describe('getOrCreateEncryptionKeyId with server error', () => {
let server;
let client;
const erroredHandler = (req, res) => {
res.writeHead(200);
const serverError = '<ErrorResponse xmlns="https://iam.amazonaws.com/doc/2010-05-08/">'
+ '<Error><Code>ServiceFailure</Code><Message>Server error: the request processing has '
+ 'failed because of an unknown error, exception or failure.</Message></Error>'
+ '<RequestId>3ac25e70c649bd4a6394:897ac94c0240b2a65f96</RequestId></ErrorResponse>';
return res.end(serverError);
};

beforeEach('start server', done => {
server = http.createServer(erroredHandler).listen(8500, () => {
client = new IAMClient('127.0.0.1', 8500);
done();
}).on('error', done);
});

afterEach('stop server', () => { server.close(); });

it('should return an error', done => {
client.getOrCreateEncryptionKeyId(canonicalId,
{ reqUid: '123' },
(err, response) => {
assert(!err);
assert(response.message.body.ErrorResponse);
done();
});
});
});
Loading