oidc-lib
Version:
A library for creating OIDC Service Providers
998 lines (869 loc) • 27.2 kB
JavaScript
const PERSONALOMNIKEY = 'privateOmniKey';
const INTEGRITYKEY = 'integrityKey';
const STS_MODULENAME = 'sts';
const PERSONAKEY = 'personaKey';
const PAIRWISEKEY = 'pairwiseKey';
const KEY_EXTRACTABLE = true;
var contentModuleSigningKeys = {};
var contentModuleSigningKeystores = {};
var contentModuleSigningKeysPublic = {};
var contentModuleSigningKids = {};
var contentModuleIntegrityKeys = {};
var contentModuleIntegrityKeystores = {};
var pk;
function registerEndpoints(pkInput){
pk = pkInput;
}
async function createOrLoadSingleKey(keyObject){
var dbInfo = pk.dbs[STS_MODULENAME];
var keyObjectArray;
var error_message;
try{
// if no db is defined the key object will be missing key values
if (dbInfo === undefined){
error_message = '';
throw('no database is defined in createOrLoadSingleKey');
}
var target = {
content_module_name: keyObject.content_module_name,
app_id: keyObject.app_id
};
if (keyObject.app_role){
target.app_role = keyObject.app_role;
}
if (keyObject.creation_date){
target.creation_date = keyObject.creation_date;
}
if (keyObject.kid){
target.kid = keyObject.kid;
}
if (keyObject.did){
target.did = keyObject.did;
}
var error_message = '[ClientLib] Error querying keys - ' + koDisplayName(keyObject);
var keyObjectArray = await dbInfo.provider.queryCollection(dbInfo, 'keys', target);
var error_message = 'Error creating single key';
if (keyObject.renew === true || keyObjectArray.length === 0){
var createdKey = await createSingleKey(dbInfo, keyObject);
console.log('A new key was created:', JSON.stringify(createdKey, null, 4) + '\r\n');
keyObjectArray.push(createdKey);
}
var error_message = 'Error in keyObjectArrayToKeyAndStore';
var keyAndStore = await keyObjectArrayToKeyAndStore(keyObjectArray);
pk.util.log_debug('[ClientLib] Success loading keystore - ' + koDisplayName(keyObject));
return keyAndStore;
}
catch(err){
pk.util.log_error('createOrLoadSingleKey','Error in createOrLoadSingleKey', err);
throw ('Error in createOrLoadSingleKey: ' + err);
}
}
async function keyObjectArrayToKeyAndStore(keyObjects){
var newestKeyObject;
var publicKeys = { keys: [] };
var latestTime = 0;
for (var i=0; i<keyObjects.length; i++){
var keyObject = keyObjects[i];
if (keyObject.public !== undefined){
publicKeys.keys.push(keyObject.public);
}
if (keyObject.creation_date > latestTime){
newestKeyObject = keyObject;
latestTime = keyObject.creation_date;
}
}
try{
var loadedKeyStore = await pk.claimer_crypto.JWK.asKeyStore(keyObjects);
var keyAndStore = {
'store': loadedKeyStore,
'keyObject': newestKeyObject,
'publicKeyStore': publicKeys
};
return(keyAndStore);
}
catch(err){
pk.util.log_detail("Error loading keystore", err);
throw("Error loading keystore");
}
}
async function createSingleKey(dbInfo, keyObject){
if (pk.claimer_crypto.provider === 'node-jose'){
return await createSingleKey_nodejs(dbInfo, keyObject)
}
else {
return await createSingleKey_webCryptoApi(dbInfo, keyObject)
}
}
async function createSingleKey_webCryptoApi(dbInfo, keyObject){
var error_message;
try{
var date = new Date();
if (keyObject.creation_date === undefined){
keyObject.creation_date = date.getTime();
}
switch (keyObject.alg){
case "RS256":
var w3c_rsa_algorithm = {
name: "RSASSA-PKCS1-v1_5",
modulusLength: 2048,
publicExponent: new Uint8Array([1, 0, 1]),
hash: { name: "SHA-256" }
};
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify'];
}
error_message = "RS256 key creation error: ";
var keyPair = await crypto.subtle.generateKey(w3c_rsa_algorithm, KEY_EXTRACTABLE, keyObject.key_ops)
keyObject.private = keyPair.privateKey;
keyObject.public = keyPair.publicKey;
error_message = 'RS256 public key export error: ';
var exportedPublic = await crypto.subtle.exportKey("jwk", keyPair.publicKey);
keyObject.jwk_public = exportedPublic;
if (keyPair.privateKey.extractable){
error_message = 'RS256 private key export error: ';
var exportedPrivate = await crypto.subtle.exportKey("jwk", keyPair.privateKey);
keyObject.jwk_private = exportedPrivate;
}
error_message = 'RS256 kid could not be calculated: ';
var kidAsPerSpec = await pk.simple_crypto.jwkThumbprint(exportedPublic);
keyObject.kid = pk.util.randomToURN(kidAsPerSpec);
keyObject.id = keyObject.kid;
error_message = 'RS256 key storage error : ';
break;
case "ECDSA":
var crv = keyObject.crv ? keyObject.crv : 'P-256';
var ecdsa_algorithm = {
name: "ECDSA",
crv: crv // subtle crypto requires 'namedCurve'
};
var subtle_ecdsa_algorithm = {
name: "ECDSA",
namedCurve: crv // subtle crypto requires 'namedCurve'
}
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify'];
}
error_message = "ECDSA key creation error: ";
var keyPair = await crypto.subtle.generateKey(subtle_ecdsa_algorithm, KEY_EXTRACTABLE, keyObject.key_ops)
keyObject.private = keyPair.privateKey;
keyObject.public = keyPair.publicKey;
error_message = 'ECDSA public key export error: ';
var exportedPublic = await crypto.subtle.exportKey("jwk", keyPair.publicKey);
keyObject.jwk_public = exportedPublic;
if (keyPair.privateKey.extractable){
error_message = 'ECDSA private key export error: ';
var exportedPrivate = await crypto.subtle.exportKey("jwk", keyPair.privateKey);
keyObject.jwk_private = exportedPrivate;
}
error_message = 'ECDSA kid could not be calculated: ';
var kidAsPerSpec = await pk.simple_crypto.jwkThumbprint(exportedPublic);
keyObject.kid = kidAsPerSpec;
keyObject.id = keyObject.kid;
error_message = 'ECDSA key storage error : ';
break;
case "EdDSA":
var crv = keyObject.crv ? keyObject.crv : 'Ed25519';
var ed25519_algorithm = {
name: "EdDSA",
crv: crv
};
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify'];
}
error_message = "ed25519_algorithm key creation error: ";
var ed25519 = forge.pki.ed25519;
var keyPair = ed25519.generateKeyPair();
keyObject.private = {
algorithm: ed25519_algorithm,
extractable: true,
type: "private",
usages: ["sign"],
key: keyPair.privateKey
};
keyObject.public = {
algorithm: ed25519_algorithm,
extractable: true,
type: "public",
usages: ["verify"],
key: keyPair.publicKey
};
error_message = 'EdDSA public key export error: ';
// SHOULD x be base64 encoded or base58 encoded?????
keyObject.jwk_public = {
"kty" : "OKP",
"crv" : "Ed25519",
"x" : pk.base64url.encode(keyPair.publicKey),
"use" : "sig",
}
error_message = 'EdDSA private key export error: ';
// SHOULD x be base64 encoded or base58 encoded?????
keyObject.jwk_private = {
"kty" : "OKP",
"crv" : "Ed25519",
'd': pk.base64url.encode(keyPair.privateKey),
"x" : pk.base64url.encode(keyPair.publicKey),
"use" : "sig",
}
error_message = 'EdDSA kid could not be calculated: ';
var kidAsPerSpec = await pk.simple_crypto.jwkThumbprint(keyObject.jwk_public);
keyObject.kid = kidAsPerSpec;
keyObject.jwk_public.kid = keyObject.kid;
keyObject.id = keyObject.kid;
break;
case "RSA-OAEP":
var w3c_rsa_algorithm = {
name: "RSA-OAEP",
modulusLength: 2048,
publicExponent: new Uint8Array([1, 0, 1]),
hash: { name: "SHA-256" }
};
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify', 'encrypt', 'decrypt'];
}
error_message = "RSA-OAEP key creation error: ";
var keyPair = await crypto.subtle.generateKey(w3c_rsa_algorithm, KEY_EXTRACTABLE, keyObject.key_ops)
keyObject.private = keyPair.privateKey;
keyObject.public = keyPair.publicKey;
error_message = 'RSA-OAEP public key export error: '
var exportedPublic = await crypto.subtle.exportKey("jwk", keyPair.publicKey);
keyObject.jwk_public = exportedPublic;
if (keyPair.privateKey.extractable){
error_message = 'RSA_OAEP private key export error: ';
var exportedPrivate = await crypto.subtle.exportKey("jwk", keyPair.privateKey);
keyObject.jwk_private = exportedPrivate;
}
error_message = 'RSA-OAEP kid could not be calculated: ';
var kid = await pk.simple_crypto.jwkThumbprint(exportedPublic);
keyObject.kid = pk.util.randomToURN(kid);
keyObject.id = keyObject.kid;
error_message = 'RSA-OAEP key storage error : ';
break;
case "A128GCM":
var w3c_aes_algorithm = {
name: "AES-GCM",
length: 128
};
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['encrypt', 'decrypt'];
}
error_message = 'AES key could not be generated: ';
var newAesKey = await crypto.subtle.generateKey(w3c_aes_algorithm, KEY_EXTRACTABLE, ['encrypt', 'decrypt']);
keyObject.kid = keyObject.creation_date.toString();
keyObject.id = keyObject.kid;
keyObject.symmetric = newAesKey;
if (newAesKey.extractable){
error_message = 'A128GCM key export error: ';
var exportedSymmetric = await crypto.subtle.exportKey("jwk", newAesKey);
keyObject.jwk_symmetric = exportedSymmetric;
}
error_message = 'symmetric key was not stored as expected: ';
break;
default:
throw ('undefined key algorithm in createSingleKey_webCryptoApi');
}
if (dbInfo){
var confirmation = await pk.dbs.sts.provider.createOrUpdateDocument(
pk.dbs.sts, 'keys', keyObject, null);
}
return (keyObject);
}
catch(err){
throw (error_message + err);
}
}
async function createSingleKey_nodejs(dbInfo, keyObject){
var error_message;
try{
var date = new Date();
var keystore = pk.claimer_crypto.JWK.createKeyStore();
if (keyObject.creation_date === undefined){
keyObject.creation_date = date.getTime();
}
switch (keyObject.alg){
case "RS256":
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify'];
}
var genParams = {
alg: keyObject.alg,
use: 'sig'
};
error_message = 'RS256 kid could not be calculated ';
var result = await keystore.generate("RSA", 2048, genParams);
keyObject.kid = keyObject.kid ? keyObject.kid : pk.util.randomToURN(result.kid);
keyObject.private = keystore.toJSON(true).keys[0];
keyObject.private.kid = pk.util.randomToURN(keyObject.private.kid);
keyObject.public = keystore.toJSON().keys[0];
keyObject.public.kid = pk.util.randomToURN(keyObject.public.kid);
keyObject.jwk_public = keyObject.public;
keyObject.id = result.kid;
error_message = 'keyObject was not stored as expected ';
break;
case "ECDSA":
var curve = keyObject.crv ? keyObject.crv : 'P-256';
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify'];
}
var genParams = {
alg: keyObject.alg,
use: 'sig'
};
error_message = 'EC kid could not be calculated ';
var result = await keystore.generate("EC", curve, genParams);
var jwk = result.toJSON(false);
keyObject.kid = keyObject.kid ? keyObject.kid : pk.util.randomToURN(result.kid);
keyObject.private = keystore.toJSON(true).keys[0];
keyObject.private.kid = pk.util.randomToURN(keyObject.private.kid);
keyObject.public = keystore.toJSON().keys[0];
keyObject.public.kid = pk.util.randomToURN(keyObject.public.kid);
keyObject.jwk_public = keyObject.public;
keyObject.id = result.kid;
error_message = 'keyObject was not stored as expected ';
break;
case "EdDSA":
var crv = keyObject.crv ? keyObject.crv : 'Ed25519';
var ed25519_algorithm = {
name: "EdDSA",
crv: crv
};
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['sign', 'verify'];
}
error_message = "ed25519_algorithm key creation error: ";
var ed25519 = pk.forge.pki.ed25519;
var keyPair = ed25519.generateKeyPair();
keyObject.private = {
algorithm: ed25519_algorithm,
extractable: true,
type: "private",
usages: ["sign"],
key: keyPair.privateKey
};
keyObject.public = {
algorithm: ed25519_algorithm,
extractable: true,
type: "public",
usages: ["verify"],
key: keyPair.publicKey
};
error_message = 'EdDSA public key export error: ';
// SHOULD x be base64 encoded or base58 encoded?????
keyObject.jwk_public = {
"kty" : "OKP",
"crv" : "Ed25519",
"x" : pk.base64url.encode(keyPair.publicKey),
"use" : "sig"
}
error_message = 'EdDSA kid could not be calculated: ';
var kidAsPerSpec = await pk.simple_crypto.jwkThumbprint(keyObject.jwk_public);
keyObject.kid = kidAsPerSpec;
keyObject.jwk_public.kid = kidAsPerSpec;
keyObject.id = keyObject.kid;
break;
case "A128GCM":
if (keyObject.key_ops === undefined){
keyObject.key_ops = ['encrypt', 'decrypt'];
}
var genParams = {
alg: keyObject.alg,
use: 'enc',
kid: keyObject.creation_date.toString()
};
error_message = 'AES key could not be generated: ';
await keystore.generate("oct", 128, genParams);
keyObject.kid = keyObject.kid ? keyObject.kid : keyObject.creation_date.toString();
keyObject.jwk_public = keystore.toJSON(true);
if (pk.claimer_crypto.provider === 'node-jose'){
keyObject.id = keyObject.kid;
}
else{
keyObject.id = keyObject.keyPath;
}
keyObject.symmetric = keyObject.jwk_public.keys[0];
break;
default:
break;
}
if (dbInfo){
await dbInfo.provider.createOrUpdateDocument(
dbInfo, 'keys', keyObject, null);
}
return(keyObject);
}
catch(err){
throw(error_message + err);
}
}
function claimerKeyObject(content_module_name, app_id, ktyOrKeyParams, alg, crv) {
var _content_module_name = content_module_name;
var _app_id = app_id;
var _app_role;
var _kid;
var _key_ops;
var _creation_date;
var _private;
var _public;
var _symmetric;
var _jwk_public;
var _jwk_private;
var _jwk_symmetric;
var _keyParams;
var _renew;
var _did;
var _id; // database id
if (typeof ktyOrKeyParams === 'string'){
_keyParams = pk.wallet_key_types.getKeyParams(
{
kty: ktyOrKeyParams,
alg: alg,
crv: crv
});
}
else{
_keyParams = ktyOrKeyParams;
}
Object.defineProperty(this, "content_module_name", {
get: function() {
return _content_module_name;
},
set: function(newValue){
_content_module_name = newValue;
},
enumerable: true
});
Object.defineProperty(this, "app_id", {
get: function() {
return _app_id;
},
set: function(newValue){
_app_id = newValue;
},
enumerable: true
});
Object.defineProperty(this, "app_role", {
get: function() {
return _app_role;
},
set: function(newValue){
_app_role = newValue;
},
enumerable: true
});
Object.defineProperty(this, "kty", {
get: function() {
return _keyParams.kty;
},
set: function(newValue){
_keyParams.kty = newValue;
},
enumerable: true
});
Object.defineProperty(this, "alg", {
get: function() {
return _keyParams.alg;
},
set: function(newValue){
_keyParams.alg = newValue;
},
enumerable: true
});
Object.defineProperty(this, "crv", {
get: function() {
return _keyParams.crv;
},
set: function(newValue){
_keyParams.crv = newValue;
},
enumerable: true
});
Object.defineProperty(this, "multicodec_bytes", {
get: function() {
return _keyParams.multicodec_bytes;
},
set: function(newValue){
_keyParams.multicodec_bytes = newValue;
},
enumerable: true
});
Object.defineProperty(this, "signature_alg", {
get: function() {
return _keyParams.signature_alg;
},
set: function(newValue){
_keyParams.signature_alg = newValue;
},
enumerable: true
});
Object.defineProperty(this, "kid", {
get: function() {
return _kid;
},
set: function(newValue){
_kid = newValue;
},
enumerable: true
});
Object.defineProperty(this, "did", {
get: function() {
return _did;
},
set: function(newValue){
_did = newValue;
},
enumerable: true
});
Object.defineProperty(this, "key_ops", {
get: function() {
return _key_ops;
},
set: function(newValue){
_key_ops = newValue;
},
enumerable: true
});
Object.defineProperty(this, "creation_date", {
get: function() {
return _creation_date;
},
set: function(newValue){
_creation_date = newValue;
},
enumerable: true
});
Object.defineProperty(this, "private", {
get: function() {
return _private;
},
set: function(newValue){
_private = newValue;
},
enumerable: true
});
Object.defineProperty(this, "public", {
get: function() {
return _public;
},
set: function(newValue){
_public = newValue;
},
enumerable: true
});
Object.defineProperty(this, "symmetric", {
get: function() {
return _symmetric;
},
set: function(newValue){
_symmetric = newValue;
},
enumerable: true
});
Object.defineProperty(this, "jwk_private", {
get: function() {
return _jwk_private;
},
set: function(newValue){
_jwk_private = newValue;
},
enumerable: true
});
Object.defineProperty(this, "jwk_public", {
get: function() {
return _jwk_public;
},
set: function(newValue){
_jwk_public = newValue;
},
enumerable: true
});
Object.defineProperty(this, "jwk_symmetric", {
get: function() {
return _jwk_symmetric;
},
set: function(newValue){
_jwk_symmetric = newValue;
},
enumerable: true
});
Object.defineProperty(this, "renew", {
get: function() {
return _renew;
},
set: function(newValue){
_renew = newValue;
},
enumerable: true,
configurable: true
});
Object.defineProperty(this, "id", {
get: function() {
return _id;
},
set: function(newValue){
_id = newValue;
},
enumerable: true,
configurable: true
});
}
function clientGetProperty(client_id, propertyName) {
var client = clientInfo[client_id];
if (client === undefined){
throw "Invalid Client";
}
return client[propertyName];
}
async function loadSingleKey(keyObjectOrId, props){
var dbInfo = pk.dbs[STS_MODULENAME];
var keyObjectArray;
var potentialError = '';
try {
// if no db is defined the key object will be missing key values
if (dbInfo === undefined){
resolve(null);
return;
}
if (typeof keyObjectOrId === 'string'){
var keyId = keyObjectOrId;
potential_error = 'Error retrieving key id: ' + keyId;
var retrievedKeyObject = await dbInfo.provider.getDocument(dbInfo, 'keys', keyId);
keyObjectArray = [ retrievedKeyObject ];
}
else if (keyObjectOrId.index) {
potential_error = 'Error retrieving indexed key id: ' + keyId;
var retrievedKeyObject = await dbInfo.provider.getDocument(dbInfo, 'keys',
keyObjectOrId.index, keyObjectOrId.value);
keyObjectArray = [ retrievedKeyObject ];
}
else if (keyObjectOrId.dictionary) {
potential_error = 'Error retrieving key via dictionary: ' + JSON.stringify(keyObjectOrId.dictionary, null, 4) + '\r\n';
var keyObjectArray = await dbInfo.provider.queryCollection(dbInfo, 'keys',
keyObjectOrId.dictionary);
if (keyObjectArray.length === 0){
throw ('dictionary produced no key collection');
}
}
else{
var keyObject = keyObjectOrId;
var target = {
content_module_name: keyObject.content_module_name,
app_id: keyObject.app_id
};
if (keyObject.app_role){
target.app_role = keyObject.app_role;
}
if (props){
for (var k in props){
target[k] = props[k];
}
}
potential_error = '[ClientLib] Error querying key collection';
keyObjectArray = await dbInfo.provider.queryCollection(dbInfo, 'keys', target);
if (keyObjectArray.length === 0){
throw ('[ClientLib] key collection returns empty');
}
}
potential_error = '[ClientLib] Error querying keys';
var keyAndStore = await keyObjectArrayToKeyAndStore(keyObjectArray);
pk.util.log_debug('[ClientLib] Success loading keystore');
return keyAndStore;
}
catch(err){
throw ('Error in loadSingleKey: ' + potential_error + ' - ' + err);
}
}
async function updateSingleKey(keyObject, properties){
var potential_error;
try{
var dbInfo = pk.dbs[STS_MODULENAME];
var potential_error = '[UpdateSingleKey] Error querying keys';
var keyAndStore = await loadSingleKey(keyObject);
var keyObj = keyAndStore.keyObject;
for (var key in properties){
keyObj[key] = properties[key];
}
var result = await dbInfo.provider.createOrUpdateDocument(
dbInfo, 'keys', keyObj, null);
return result;
}
catch(err){
throw(err);
}
}
function koDisplayName(keyObject){
return keyObject.content_module_name + ':' + keyObject.app_id + (keyObject.app_role ? ':' + keyObject.app_role : '');
}
async function loadOrCreateKeys() {
try {
var keysRequired = [];
for (var moduleName in pk.feature_modules){
if (!pk.feature_modules[moduleName].code.invokeConsentUserAgent){
continue;
}
var omniKeyObj = new pk.key_management.claimerKeyObject(moduleName, pk.key_management.PERSONALOMNIKEY, "RSA", "RS256");
var omniKeyAndStore = await createOrLoadSingleKey(omniKeyObj);
connectKeyToContentModule(omniKeyAndStore);
var integrityKeyObj = new pk.key_management.claimerKeyObject(moduleName, pk.key_management.INTEGRITYKEY, "oct", "A128GCM");
var integrityKeyAndStore = await createOrLoadSingleKey(integrityKeyObj);
connectKeyToContentModule(integrityKeyAndStore);
}
}
catch(err){
}
}
function connectKeyToContentModule(keyAndStore){
if (keyAndStore !== null){
var keyObject = keyAndStore.keyObject;
switch (keyObject.alg){
case "RS256":
contentModuleSigningKeys[keyObject.content_module_name] = keyObject;
contentModuleSigningKeystores[keyObject.content_module_name] = keyAndStore.store;
contentModuleSigningKids[keyObject.content_module_name] = keyObject.kid;
contentModuleSigningKeysPublic[keyObject.content_module_name] = keyAndStore.publicKeyStore;
break;
case "A128GCM":
contentModuleIntegrityKeys[keyObject.content_module_name] = keyObject;
contentModuleIntegrityKeystores[keyObject.content_module_name] = keyAndStore.store;
break;
default:
alert("Unrecognized key alg in connectKeysToContentModule: " + keyObject.alg);
return;
}
}
}
function signatureAlg(keyObj){
var sigAlg;
switch (keyObj.alg){
case 'RS256':
sigAlg = 'RS256';
break;
case 'ECDSA':
switch (keyObj.crv){
case 'P-256':
sigAlg = 'ES256';
break;
case 'P-384':
sigAlg = 'ES384';
break;
case 'P-512':
sigAlg = 'ES512';
break;
default:
throw ('Invalid Named crv getting signatureAlg: ' + keyObj.crv);
}
break;
case 'EdDSA':
sigAlg = 'EdDSA';
break;
default:
throw('signatureAlg not defined for ' + keyObj.alg);
}
return sigAlg;
}
function expandValidKeyType(keyType){
return pk.wallet_key_types.getKeyParams(keyType);
}
function testKeyTypes(){
// returning keyType
var a = pk.wallet_key_types.keyKeyParams({
alg: 'RS256'
});
a = pk.wallet_key_types.keyKeyParams({
alg: 'RS256',
kty: 'RSA'
});
a = pk.wallet_key_types.keyKeyParams({
alg: 'ECDSA',
kty: 'EC'
});
a = pk.wallet_key_types.keyKeyParams({
alg: 'ECDSA',
kty: 'EC',
crv: 'P-384'
});
a = pk.wallet_key_types.keyKeyParams({
multicodec: [ 0x12, 0x02]
});
var multicodec_bytes = a.multicodec_bytes;
a = pk.wallet_key_types.keyKeyParams({
multicodec_bytes: multicodec_bytes });
// returning undefined
a = pk.wallet_key_types.keyKeyParams({
alg: 'RSA'
});
}
// used when importing keys into index_db
async function keyObjectImportKey(dbName, collectionName, record){
var fixup;
if (dbName === 'sts' && collectionName === 'keys'){
var algorithm;
var cryptoKeyStorage;
var key_usages;
switch (record.alg){
case 'A128GCM':
algorithm = { name: 'AES-GCM' };
cryptoKeyStorage = 'symmetric';
key_usages = [ 'encrypt', 'decrypt'];
break;
case 'RS256':
key_usages = [ 'sign'];
cryptoKeyStorage = 'private'
algorithm = { name: 'RSASSA-PKCS1-v1_5', hash: 'SHA-256'};
break;
case 'RSA-OAEP':
algorithm = { name: 'RSA-OAEP', hash: 'SHA-256'};
cryptoKeyStorage = 'private'
key_usages = [ 'encrypt'];
break;
case 'ECDSA':
key_usages = [ 'sign'];
cryptoKeyStorage = 'private'
algorithm = { name: 'ECDSA', namedCurve: record.jwk_private.crv };
break;
default:
return;
}
const result = await crypto.subtle.importKey(
'jwk',
record['jwk_' + cryptoKeyStorage],
algorithm,
true,
key_usages
);
if (record.multicodec_bytes){
if (typeof record.multicodec_bytes === 'object'){
var len = Object.keys(record.multicodec_bytes).length;
var uint8Array = new Uint8Array(len);
var c = 0;
for (var el in record.multicodec_bytes){
uint8Array[c++] = record.multicodec_bytes[el];
}
record.multicodec_bytes = uint8Array;
}
}
fixup = record;
fixup[cryptoKeyStorage] = result;
return fixup;
}
}
module.exports = {
registerEndpoints: registerEndpoints,
loadOrCreateKeys: loadOrCreateKeys,
createSingleKey: createSingleKey,
createOrLoadSingleKey: createOrLoadSingleKey,
claimerKeyObject: claimerKeyObject,
loadSingleKey: loadSingleKey,
updateSingleKey: updateSingleKey,
signatureAlg: signatureAlg,
PERSONALOMNIKEY: PERSONALOMNIKEY,
INTEGRITYKEY: INTEGRITYKEY,
PERSONAKEY: PERSONAKEY,
PAIRWISEKEY: PAIRWISEKEY,
contentModuleSigningKeys: contentModuleSigningKeys,
contentModuleSigningKeystores: contentModuleSigningKeystores,
contentModuleSigningKeysPublic: contentModuleSigningKeysPublic,
contentModuleSigningKids: contentModuleSigningKids,
contentModuleIntegrityKeys: contentModuleIntegrityKeys,
contentModuleIntegrityKeystores: contentModuleIntegrityKeystores,
expandValidKeyType: expandValidKeyType,
keyObjectImportKey: keyObjectImportKey
};