@@ -16,6 +16,10 @@ import {
1616 decryptBranchKey ,
1717} from './branch_keystore_helpers'
1818import { KMS_CLIENT_USER_AGENT , TABLE_FIELD } from './constants'
19+ import {
20+ createBranchAndBeaconKeys ,
21+ versionActiveBranchKey ,
22+ } from './key_helpers'
1923
2024import {
2125 IBranchKeyStorage ,
@@ -45,8 +49,15 @@ interface IBranchKeyStoreNode {
4549 //= type=implication
4650 //# - [GetKeyStoreInfo](#getkeystoreinfo)
4751 getKeyStoreInfo ( ) : KeyStoreInfoOutput
52+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#operations
53+ //= type=implication
54+ //# - [VersionKey](#versionkey)
55+ versionKey ( input : VersionKeyInput ) : Promise < void >
56+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#operations
57+ //= type=implication
58+ //# - [CreateKey](#createkey)
59+ createKey ( input ?: CreateKeyInput ) : Promise < CreateKeyOutput >
4860}
49-
5061//= aws-encryption-sdk-specification/framework/branch-key-store.md#getkeystoreinfo
5162//= type=implication
5263//# This MUST include:
@@ -64,6 +75,19 @@ export interface KeyStoreInfoOutput {
6475 kmsConfiguration : KmsConfig
6576}
6677
78+ export interface VersionKeyInput {
79+ branchKeyIdentifier : string
80+ }
81+
82+ export interface CreateKeyInput {
83+ branchKeyIdentifier ?: string
84+ encryptionContext ?: { [ key : string ] : string }
85+ }
86+
87+ export interface CreateKeyOutput {
88+ branchKeyIdentifier : string
89+ }
90+
6791export class BranchKeyStoreNode implements IBranchKeyStoreNode {
6892 public declare readonly logicalKeyStoreName : string
6993 public declare readonly kmsConfiguration : Readonly < KmsKeyConfig >
@@ -383,6 +407,83 @@ export class BranchKeyStoreNode implements IBranchKeyStoreNode {
383407 return branchKeyMaterials
384408 }
385409
410+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#createkey
411+ //# The CreateKey caller MUST provide:
412+ //# - An optional branch key id
413+ //# - An optional encryption context
414+ async createKey ( input ?: CreateKeyInput ) : Promise < CreateKeyOutput > {
415+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#createkey
416+ //# If the Keystore's KMS Configuration is `Discovery` or `MRDiscovery`,
417+ //# this operation MUST fail.
418+ needs (
419+ typeof this . kmsConfiguration . _config === 'object' &&
420+ ( 'identifier' in this . kmsConfiguration . _config ||
421+ 'mrkIdentifier' in this . kmsConfiguration . _config ) ,
422+ 'CreateKey is not supported with Discovery or MRDiscovery KMS Configuration'
423+ )
424+
425+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#createkey
426+ //# If an optional branch key id is provided and no encryption context is provided
427+ //# this operation MUST fail.
428+ if ( input ?. branchKeyIdentifier ) {
429+ needs (
430+ input . encryptionContext &&
431+ Object . keys ( input . encryptionContext ) . length > 0 ,
432+ 'If branch key identifier is provided, encryption context must also be provided'
433+ )
434+ }
435+
436+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#createkey
437+ //# If no branch key id is provided, then this operation MUST create a
438+ //# version 4 UUID to be used as the branch key id.
439+ const branchKeyIdentifier = input ?. branchKeyIdentifier || v4 ( )
440+ const customEncryptionContext = input ?. encryptionContext || { }
441+
442+ await createBranchAndBeaconKeys ( {
443+ branchKeyIdentifier,
444+ customEncryptionContext,
445+ logicalKeyStoreName : this . logicalKeyStoreName ,
446+ kmsConfiguration : this . kmsConfiguration ,
447+ grantTokens : this . grantTokens ,
448+ kmsClient : this . kmsClient ,
449+ ddbClient : ( this . storage as any ) . ddbClient ,
450+ ddbTableName : ( this . storage as any ) . ddbTableName ,
451+ } )
452+
453+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#createkey
454+ //# If writing to the keystore succeeds,
455+ //# the operation MUST return the branch-key-id that maps to both the branch key and the beacon key.
456+ return { branchKeyIdentifier }
457+ }
458+
459+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#versionkey
460+ //# On invocation, the caller:
461+ //# - MUST supply a `branch-key-id`
462+ async versionKey ( input : VersionKeyInput ) : Promise < void > {
463+ needs ( input . branchKeyIdentifier , 'MUST supply a branch-key-id' )
464+
465+ //= aws-encryption-sdk-specification/framework/branch-key-store.md#versionkey
466+ //# If the Keystore's KMS Configuration is `Discovery` or `MRDiscovery`,
467+ //# this operation MUST immediately fail.
468+ needs (
469+ typeof this . kmsConfiguration . _config === 'object' &&
470+ ( 'identifier' in this . kmsConfiguration . _config ||
471+ 'mrkIdentifier' in this . kmsConfiguration . _config ) ,
472+ 'VersionKey is not supported with Discovery or MRDiscovery KMS Configuration'
473+ )
474+
475+ await versionActiveBranchKey ( {
476+ branchKeyIdentifier : input . branchKeyIdentifier ,
477+ logicalKeyStoreName : this . logicalKeyStoreName ,
478+ kmsConfiguration : this . kmsConfiguration ,
479+ grantTokens : this . grantTokens ,
480+ kmsClient : this . kmsClient ,
481+ ddbClient : ( this . storage as any ) . ddbClient ,
482+ ddbTableName : ( this . storage as any ) . ddbTableName ,
483+ storage : this . storage ,
484+ } )
485+ }
486+
386487 //= aws-encryption-sdk-specification/framework/branch-key-store.md#getkeystoreinfo
387488 //= type=implication
388489 //# This operation MUST return the keystore information in this keystore configuration.
0 commit comments