11import { base64ToByteArray , byteArrayToBase64 , concatenate } from "./utils" ;
2- import { ivLength , keyExportFormat , PIN , saltLength } from "./constants" ;
2+ import { BACKUP_KEY , BD_ENDPOINT , DEFAULT_BD_ENDPOINT , ivLength , keyExportFormat , PIN , saltLength } from "./constants" ;
33import { getLogger } from "./logging" ;
4+ import { BackupKey } from "./webauthn_psk" ;
45
56const log = getLogger ( 'auth_storage' ) ;
67
8+ export class PSKStorage {
9+ public static async getBDEndpoint ( ) : Promise < string > {
10+ return new Promise < string > ( async ( res , rej ) => {
11+ chrome . storage . local . get ( { [ BD_ENDPOINT ] : null } , async ( resp ) => {
12+ if ( ! ! chrome . runtime . lastError ) {
13+ log . error ( 'Could not perform PSKStorage.getBDEndpoint' , chrome . runtime . lastError . message ) ;
14+ rej ( chrome . runtime . lastError ) ;
15+ return ;
16+ }
17+
18+ if ( resp [ BACKUP_KEY ] == null ) {
19+ log . warn ( `No endpoint found, use default endpoint` ) ;
20+ res ( DEFAULT_BD_ENDPOINT ) ;
21+ }
22+ log . debug ( 'Loaded BD endpoint successfully' ) ;
23+ res ( resp [ BACKUP_KEY ] ) ;
24+ } ) ;
25+ } ) ;
26+ }
27+
28+ public static async setBDEndpoint ( endpoint : string ) : Promise < void > {
29+ log . debug ( 'Set BD endpoint to' , endpoint ) ;
30+ return new Promise < void > ( async ( res , rej ) => {
31+ chrome . storage . local . set ( { [ BD_ENDPOINT ] : endpoint } , ( ) => {
32+ if ( ! ! chrome . runtime . lastError ) {
33+ log . error ( 'Could not perform PSKStorage.setBDEndpoint' , chrome . runtime . lastError . message ) ;
34+ rej ( chrome . runtime . lastError ) ;
35+ } else {
36+ res ( ) ;
37+ }
38+ } ) ;
39+ } ) ;
40+ }
41+
42+ public static async storeBackupKeys ( backupKeys : BackupKey [ ] , override : boolean = false ) : Promise < void > {
43+ log . debug ( `Storing backup keys` ) ;
44+ const backupKeysExists = await this . existBackupKeys ( ) ;
45+ if ( backupKeysExists && ! override ) {
46+ log . debug ( 'Backup keys already exist. Update entry.' ) ;
47+ const entries = await this . loadBackupKeys ( ) ;
48+ backupKeys = entries . concat ( backupKeys ) ;
49+ }
50+
51+ let exportJSON = JSON . stringify ( backupKeys ) ;
52+ return new Promise < void > ( async ( res , rej ) => {
53+ chrome . storage . local . set ( { [ BACKUP_KEY ] : exportJSON } , ( ) => {
54+ if ( ! ! chrome . runtime . lastError ) {
55+ log . error ( 'Could not perform PSKStorage.storeBackupKeys' , chrome . runtime . lastError . message ) ;
56+ rej ( chrome . runtime . lastError ) ;
57+ } else {
58+ res ( ) ;
59+ }
60+ } ) ;
61+ } ) ;
62+ } ;
63+
64+ public static async loadBackupKeys ( ) : Promise < BackupKey [ ] > {
65+ log . debug ( `Loading backup keys` ) ;
66+ return new Promise < BackupKey [ ] > ( async ( res , rej ) => {
67+ chrome . storage . local . get ( { [ BACKUP_KEY ] : null } , async ( resp ) => {
68+ if ( ! ! chrome . runtime . lastError ) {
69+ log . error ( 'Could not perform PSKStorage.loadBackupKeys' , chrome . runtime . lastError . message ) ;
70+ rej ( chrome . runtime . lastError ) ;
71+ return ;
72+ }
73+
74+ if ( resp [ BACKUP_KEY ] == null ) {
75+ log . warn ( `No backup keys found` ) ;
76+ res ( [ ] ) ;
77+ }
78+
79+ const backupKeys = await JSON . parse ( resp [ BACKUP_KEY ] ) ;
80+ log . debug ( 'Loaded backup keys successfully' ) ;
81+ res ( backupKeys ) ;
82+ } ) ;
83+ } ) ;
84+ }
85+
86+ private static async existBackupKeys ( ) : Promise < boolean > {
87+ return new Promise < boolean > ( async ( res , rej ) => {
88+ chrome . storage . local . get ( { [ BACKUP_KEY ] : null } , async ( resp ) => {
89+ if ( ! ! chrome . runtime . lastError ) {
90+ log . error ( 'Could not perform PSKStorage.existBackupKeys' , chrome . runtime . lastError . message ) ;
91+ rej ( chrome . runtime . lastError ) ;
92+ } else {
93+ res ( ! ( resp [ BACKUP_KEY ] == null ) ) ;
94+ }
95+ } ) ;
96+ } ) ;
97+ } ;
98+ }
799
8100export class CredentialsMap {
9101 public static async put ( rpId : string , credSrc : PublicKeyCredentialSource ) : Promise < void > {
10102 log . debug ( `Storing credential map entry for ${ rpId } ` ) ;
11- const mapEntryExists = await this . exits ( rpId ) ;
103+ const mapEntryExists = await this . exists ( rpId ) ;
12104 let credSrcs : PublicKeyCredentialSource [ ] ;
13105 if ( mapEntryExists ) {
14106 log . debug ( 'Credential map entry does already exist. Update entry.' ) ;
@@ -75,11 +167,11 @@ export class CredentialsMap {
75167 }
76168 }
77169
78- public static async exits ( rpId : string ) : Promise < boolean > {
170+ public static async exists ( rpId : string ) : Promise < boolean > {
79171 return new Promise < boolean > ( async ( res , rej ) => {
80172 chrome . storage . local . get ( { [ rpId ] : null } , async ( resp ) => {
81173 if ( ! ! chrome . runtime . lastError ) {
82- log . error ( 'Could not perform CredentialsMap.exits ' , chrome . runtime . lastError . message ) ;
174+ log . error ( 'Could not perform CredentialsMap.exists ' , chrome . runtime . lastError . message ) ;
83175 rej ( chrome . runtime . lastError ) ;
84176 } else {
85177 res ( ! ( resp [ rpId ] == null ) ) ;
@@ -91,7 +183,6 @@ export class CredentialsMap {
91183
92184export class PublicKeyCredentialSource {
93185 public static async import ( json : any ) : Promise < PublicKeyCredentialSource > {
94- log . debug ( 'Import PublicKeyCredentialSource' , json ) ;
95186 const _id = json . id ;
96187 const _rpId = json . rpId ;
97188 const _userHandle = json . userHandle ;
@@ -124,7 +215,7 @@ export class PublicKeyCredentialSource {
124215 true ,
125216 [ 'sign' ] ,
126217 ) ;
127- log . debug ( 'Imported PublicKeyCredentialSource with id' , _id )
218+
128219 return new PublicKeyCredentialSource ( _id , _privateKey , _rpId , _userHandle ) ;
129220 }
130221
@@ -178,7 +269,6 @@ export class PublicKeyCredentialSource {
178269 type : this . type
179270 }
180271
181- log . debug ( 'Exported PublicKeyCredentialSource with id' , this . id )
182272 return json ;
183273 }
184274}
0 commit comments