1e41f4b71Sopenharmony_ci# Refined Key Access Control Development 2e41f4b71Sopenharmony_ci 3e41f4b71Sopenharmony_ciAs an extension of the access control based on user identity authentication, the refined key access control provides fine-grained access control capabilities via secondary identity authentication based on biometric features and lock screen passwords. You can set whether identity authentication is required for a key in one or more scenarios such as encryption, decryption, signing, signature verification, key agreement, and key derivation. 4e41f4b71Sopenharmony_ci 5e41f4b71Sopenharmony_ciFor example, a service needs to use a HUKS key to encrypt the account password information. In this scenario, identity authentication is not required in encryption but required in decryption. To achieve this purpose, you can use the refined access control feature provided by HUKS. 6e41f4b71Sopenharmony_ci 7e41f4b71Sopenharmony_ciTo implement this feature, you only need to set **HuksTag** to **HUKS_TAG_KEY_AUTH_PURPOSE**. 8e41f4b71Sopenharmony_ci 9e41f4b71Sopenharmony_ci> **NOTE**<br> 10e41f4b71Sopenharmony_ci> For symmetric encryption and decryption, only the AES/CBC, AES/GCM, and SM4/CBC modes support fine-grained access control. 11e41f4b71Sopenharmony_ci 12e41f4b71Sopenharmony_ci## How to Develop 13e41f4b71Sopenharmony_ci 14e41f4b71Sopenharmony_ci1. Generate a key, set HuksUserAuthType to fingerprint authentication, and set other parameters including **HUKS_TAG_KEY_AUTH_PURPOSE**. 15e41f4b71Sopenharmony_ci 16e41f4b71Sopenharmony_ci ```ts 17e41f4b71Sopenharmony_ci import { huks } from "@kit.UniversalKeystoreKit"; 18e41f4b71Sopenharmony_ci /* 19e41f4b71Sopenharmony_ci * Set the key alias and encapsulate the key property set. 20e41f4b71Sopenharmony_ci */ 21e41f4b71Sopenharmony_ci let keyAlias = 'test_sm4_key_alias'; 22e41f4b71Sopenharmony_ci class throwObject { 23e41f4b71Sopenharmony_ci isThrow: boolean = false; 24e41f4b71Sopenharmony_ci } 25e41f4b71Sopenharmony_ci 26e41f4b71Sopenharmony_ci let properties: Array<huks.HuksParam> = [ 27e41f4b71Sopenharmony_ci { 28e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_ALGORITHM, 29e41f4b71Sopenharmony_ci value: huks.HuksKeyAlg.HUKS_ALG_SM4, 30e41f4b71Sopenharmony_ci }, 31e41f4b71Sopenharmony_ci { 32e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_PURPOSE, 33e41f4b71Sopenharmony_ci value: huks.HuksKeyPurpose.HUKS_KEY_PURPOSE_ENCRYPT | huks.HuksKeyPurpose.HUKS_KEY_PURPOSE_DECRYPT, 34e41f4b71Sopenharmony_ci }, 35e41f4b71Sopenharmony_ci { 36e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_KEY_SIZE, 37e41f4b71Sopenharmony_ci value: huks.HuksKeySize.HUKS_SM4_KEY_SIZE_128, 38e41f4b71Sopenharmony_ci }, 39e41f4b71Sopenharmony_ci { 40e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_BLOCK_MODE, 41e41f4b71Sopenharmony_ci value: huks.HuksCipherMode.HUKS_MODE_CBC, 42e41f4b71Sopenharmony_ci }, 43e41f4b71Sopenharmony_ci { 44e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_PADDING, 45e41f4b71Sopenharmony_ci value: huks.HuksKeyPadding.HUKS_PADDING_NONE, 46e41f4b71Sopenharmony_ci }, 47e41f4b71Sopenharmony_ci { 48e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_USER_AUTH_TYPE, 49e41f4b71Sopenharmony_ci value: huks.HuksUserAuthType.HUKS_USER_AUTH_TYPE_FINGERPRINT 50e41f4b71Sopenharmony_ci }, 51e41f4b71Sopenharmony_ci { 52e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_KEY_AUTH_ACCESS_TYPE, 53e41f4b71Sopenharmony_ci value: huks.HuksAuthAccessType.HUKS_AUTH_ACCESS_INVALID_NEW_BIO_ENROLL 54e41f4b71Sopenharmony_ci }, 55e41f4b71Sopenharmony_ci { 56e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_CHALLENGE_TYPE, 57e41f4b71Sopenharmony_ci value: huks.HuksChallengeType.HUKS_CHALLENGE_TYPE_NORMAL 58e41f4b71Sopenharmony_ci }, 59e41f4b71Sopenharmony_ci { 60e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_KEY_AUTH_PURPOSE, 61e41f4b71Sopenharmony_ci value: huks.HuksKeyPurpose.HUKS_KEY_PURPOSE_DECRYPT 62e41f4b71Sopenharmony_ci } 63e41f4b71Sopenharmony_ci ]; 64e41f4b71Sopenharmony_ci 65e41f4b71Sopenharmony_ci let huksOptions: huks.HuksOptions = { 66e41f4b71Sopenharmony_ci properties: properties, 67e41f4b71Sopenharmony_ci inData: new Uint8Array(new Array()) 68e41f4b71Sopenharmony_ci } 69e41f4b71Sopenharmony_ci /* 70e41f4b71Sopenharmony_ci * Generate a key. 71e41f4b71Sopenharmony_ci */ 72e41f4b71Sopenharmony_ci async function generateKeyItem(keyAlias: string, huksOptions: huks.HuksOptions, throwObject: throwObject) { 73e41f4b71Sopenharmony_ci return new Promise<void>((resolve, reject) => { 74e41f4b71Sopenharmony_ci try { 75e41f4b71Sopenharmony_ci huks.generateKeyItem(keyAlias, huksOptions, (error, data) => { 76e41f4b71Sopenharmony_ci if (error) { 77e41f4b71Sopenharmony_ci reject(error); 78e41f4b71Sopenharmony_ci } else { 79e41f4b71Sopenharmony_ci resolve(data); 80e41f4b71Sopenharmony_ci } 81e41f4b71Sopenharmony_ci }); 82e41f4b71Sopenharmony_ci } catch (error) { 83e41f4b71Sopenharmony_ci throwObject.isThrow = true; 84e41f4b71Sopenharmony_ci throw(error as Error); 85e41f4b71Sopenharmony_ci } 86e41f4b71Sopenharmony_ci }); 87e41f4b71Sopenharmony_ci } 88e41f4b71Sopenharmony_ci async function publicGenKeyFunc(keyAlias: string, huksOptions: huks.HuksOptions) { 89e41f4b71Sopenharmony_ci console.info(`enter promise generateKeyItem`); 90e41f4b71Sopenharmony_ci let throwObject: throwObject = {isThrow: false}; 91e41f4b71Sopenharmony_ci try { 92e41f4b71Sopenharmony_ci await generateKeyItem(keyAlias, huksOptions, throwObject) 93e41f4b71Sopenharmony_ci .then((data) => { 94e41f4b71Sopenharmony_ci console.info(`promise: generateKeyItem success, data = ${JSON.stringify(data)}`); 95e41f4b71Sopenharmony_ci }) 96e41f4b71Sopenharmony_ci .catch((error: Error) => { 97e41f4b71Sopenharmony_ci if (throwObject.isThrow) { 98e41f4b71Sopenharmony_ci throw(error as Error); 99e41f4b71Sopenharmony_ci } else { 100e41f4b71Sopenharmony_ci console.error(`promise: generateKeyItem failed` + JSON.stringify(error)); 101e41f4b71Sopenharmony_ci } 102e41f4b71Sopenharmony_ci }); 103e41f4b71Sopenharmony_ci } catch (error) { 104e41f4b71Sopenharmony_ci console.error(`promise: generateKeyItem input arg invalid` + JSON.stringify(error)); 105e41f4b71Sopenharmony_ci } 106e41f4b71Sopenharmony_ci } 107e41f4b71Sopenharmony_ci async function TestGenKeyForFingerprintAccessControl() { 108e41f4b71Sopenharmony_ci await publicGenKeyFunc(keyAlias, huksOptions); 109e41f4b71Sopenharmony_ci } 110e41f4b71Sopenharmony_ci ``` 111e41f4b71Sopenharmony_ci 112e41f4b71Sopenharmony_ci2. Use the key. User identity authentication is not required when the key is used for encryption. 113e41f4b71Sopenharmony_ci 114e41f4b71Sopenharmony_ci ```ts 115e41f4b71Sopenharmony_ci import { huks } from "@kit.UniversalKeystoreKit"; 116e41f4b71Sopenharmony_ci class HuksProperties { 117e41f4b71Sopenharmony_ci tag: huks.HuksTag = huks.HuksTag.HUKS_TAG_ALGORITHM; 118e41f4b71Sopenharmony_ci value: huks.HuksKeyAlg | huks.HuksKeySize | huks.HuksKeyPurpose | huks.HuksKeyPadding | huks.HuksCipherMode 119e41f4b71Sopenharmony_ci | Uint8Array = huks.HuksKeyAlg.HUKS_ALG_ECC; 120e41f4b71Sopenharmony_ci } 121e41f4b71Sopenharmony_ci /* 122e41f4b71Sopenharmony_ci * Set the key alias and encapsulate the key property set. 123e41f4b71Sopenharmony_ci */ 124e41f4b71Sopenharmony_ci let cipherInData = 'Hks_SM4_Cipher_Test_101010101010101010110_string'; // Plaintext 125e41f4b71Sopenharmony_ci let IV = '1234567890123456'; 126e41f4b71Sopenharmony_ci let handle = 0; 127e41f4b71Sopenharmony_ci let cipherText: Uint8Array; // Ciphertext after encryption. 128e41f4b71Sopenharmony_ci function StringToUint8Array(str: string) { 129e41f4b71Sopenharmony_ci let arr: number[] = []; 130e41f4b71Sopenharmony_ci for (let i = 0, j = str.length; i < j; ++i) { 131e41f4b71Sopenharmony_ci arr.push(str.charCodeAt(i)); 132e41f4b71Sopenharmony_ci } 133e41f4b71Sopenharmony_ci return new Uint8Array(arr); 134e41f4b71Sopenharmony_ci } 135e41f4b71Sopenharmony_ci /* Set the key generation parameter set and key encryption parameter set. */ 136e41f4b71Sopenharmony_ci let propertiesEncrypt: HuksProperties[] = [ 137e41f4b71Sopenharmony_ci { 138e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_ALGORITHM, 139e41f4b71Sopenharmony_ci value: huks.HuksKeyAlg.HUKS_ALG_SM4, 140e41f4b71Sopenharmony_ci }, 141e41f4b71Sopenharmony_ci { 142e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_PURPOSE, 143e41f4b71Sopenharmony_ci value: huks.HuksKeyPurpose.HUKS_KEY_PURPOSE_ENCRYPT, 144e41f4b71Sopenharmony_ci }, 145e41f4b71Sopenharmony_ci { 146e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_KEY_SIZE, 147e41f4b71Sopenharmony_ci value: huks.HuksKeySize.HUKS_SM4_KEY_SIZE_128, 148e41f4b71Sopenharmony_ci }, 149e41f4b71Sopenharmony_ci { 150e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_PADDING, 151e41f4b71Sopenharmony_ci value: huks.HuksKeyPadding.HUKS_PADDING_NONE, 152e41f4b71Sopenharmony_ci }, 153e41f4b71Sopenharmony_ci { 154e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_BLOCK_MODE, 155e41f4b71Sopenharmony_ci value: huks.HuksCipherMode.HUKS_MODE_CBC, 156e41f4b71Sopenharmony_ci }, 157e41f4b71Sopenharmony_ci { 158e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_IV, 159e41f4b71Sopenharmony_ci value: StringToUint8Array(IV), 160e41f4b71Sopenharmony_ci } 161e41f4b71Sopenharmony_ci ]; 162e41f4b71Sopenharmony_ci let encryptOptions: huks.HuksOptions = { 163e41f4b71Sopenharmony_ci properties: propertiesEncrypt, 164e41f4b71Sopenharmony_ci inData: new Uint8Array(new Array()) 165e41f4b71Sopenharmony_ci } 166e41f4b71Sopenharmony_ci class throwObject1{ 167e41f4b71Sopenharmony_ci isThrow: boolean = false; 168e41f4b71Sopenharmony_ci } 169e41f4b71Sopenharmony_ci function initSession(keyAlias: string, huksOptions: huks.HuksOptions, throwObject: throwObject1) { 170e41f4b71Sopenharmony_ci return new Promise<huks.HuksSessionHandle>((resolve, reject) => { 171e41f4b71Sopenharmony_ci try { 172e41f4b71Sopenharmony_ci huks.initSession(keyAlias, huksOptions, (error, data) => { 173e41f4b71Sopenharmony_ci if (error) { 174e41f4b71Sopenharmony_ci reject(error); 175e41f4b71Sopenharmony_ci } else { 176e41f4b71Sopenharmony_ci resolve(data); 177e41f4b71Sopenharmony_ci } 178e41f4b71Sopenharmony_ci }); 179e41f4b71Sopenharmony_ci } catch (error) { 180e41f4b71Sopenharmony_ci throwObject.isThrow = true; 181e41f4b71Sopenharmony_ci throw (error as Error); 182e41f4b71Sopenharmony_ci } 183e41f4b71Sopenharmony_ci }); 184e41f4b71Sopenharmony_ci } 185e41f4b71Sopenharmony_ci async function publicInitFunc(keyAlias: string, huksOptions: huks.HuksOptions) { 186e41f4b71Sopenharmony_ci console.info(`enter promise doInit`); 187e41f4b71Sopenharmony_ci let throwObject: throwObject1 = { isThrow: false }; 188e41f4b71Sopenharmony_ci try { 189e41f4b71Sopenharmony_ci await initSession(keyAlias, huksOptions, throwObject) 190e41f4b71Sopenharmony_ci .then((data) => { 191e41f4b71Sopenharmony_ci console.info(`promise: doInit success, data = ${JSON.stringify(data)}`); 192e41f4b71Sopenharmony_ci handle = data.handle as number; 193e41f4b71Sopenharmony_ci }) 194e41f4b71Sopenharmony_ci .catch((error: Error) => { 195e41f4b71Sopenharmony_ci if (throwObject.isThrow) { 196e41f4b71Sopenharmony_ci throw (error as Error); 197e41f4b71Sopenharmony_ci } else { 198e41f4b71Sopenharmony_ci console.error(`promise: doInit failed` + JSON.stringify(error)); 199e41f4b71Sopenharmony_ci } 200e41f4b71Sopenharmony_ci }); 201e41f4b71Sopenharmony_ci } catch (error) { 202e41f4b71Sopenharmony_ci console.error(`promise: doInit input arg invalid` + JSON.stringify(error)); 203e41f4b71Sopenharmony_ci } 204e41f4b71Sopenharmony_ci } 205e41f4b71Sopenharmony_ci function finishSession(handle: number, huksOptions: huks.HuksOptions, throwObject: throwObject1) { 206e41f4b71Sopenharmony_ci return new Promise<huks.HuksReturnResult>((resolve, reject) => { 207e41f4b71Sopenharmony_ci try { 208e41f4b71Sopenharmony_ci huks.finishSession(handle, huksOptions, (error, data) => { 209e41f4b71Sopenharmony_ci if (error) { 210e41f4b71Sopenharmony_ci reject(error); 211e41f4b71Sopenharmony_ci } else { 212e41f4b71Sopenharmony_ci resolve(data); 213e41f4b71Sopenharmony_ci } 214e41f4b71Sopenharmony_ci }); 215e41f4b71Sopenharmony_ci } catch (error) { 216e41f4b71Sopenharmony_ci throwObject.isThrow = true; 217e41f4b71Sopenharmony_ci throw (error as Error); 218e41f4b71Sopenharmony_ci } 219e41f4b71Sopenharmony_ci }); 220e41f4b71Sopenharmony_ci } 221e41f4b71Sopenharmony_ci async function publicFinishFunc(handle: number, huksOptions: huks.HuksOptions) { 222e41f4b71Sopenharmony_ci console.info(`enter promise doFinish`); 223e41f4b71Sopenharmony_ci let throwObject: throwObject1 = { isThrow: false }; 224e41f4b71Sopenharmony_ci try { 225e41f4b71Sopenharmony_ci await finishSession(handle, huksOptions, throwObject) 226e41f4b71Sopenharmony_ci .then((data) => { 227e41f4b71Sopenharmony_ci cipherText = data.outData as Uint8Array; 228e41f4b71Sopenharmony_ci console.info(`promise: doFinish success, data = ${JSON.stringify(data)}`); 229e41f4b71Sopenharmony_ci }) 230e41f4b71Sopenharmony_ci .catch((error: Error) => { 231e41f4b71Sopenharmony_ci if (throwObject.isThrow) { 232e41f4b71Sopenharmony_ci throw (error as Error); 233e41f4b71Sopenharmony_ci } else { 234e41f4b71Sopenharmony_ci console.error(`promise: doFinish failed` + JSON.stringify(error)); 235e41f4b71Sopenharmony_ci } 236e41f4b71Sopenharmony_ci }); 237e41f4b71Sopenharmony_ci } catch (error) { 238e41f4b71Sopenharmony_ci console.error(`promise: doFinish input arg invalid` + JSON.stringify(error)); 239e41f4b71Sopenharmony_ci } 240e41f4b71Sopenharmony_ci } 241e41f4b71Sopenharmony_ci async function testSm4Cipher() { 242e41f4b71Sopenharmony_ci /* Initialize the key session to obtain a challenge. */ 243e41f4b71Sopenharmony_ci await publicInitFunc(keyAlias, encryptOptions); 244e41f4b71Sopenharmony_ci /** Encryption */ 245e41f4b71Sopenharmony_ci encryptOptions.inData = StringToUint8Array(cipherInData); 246e41f4b71Sopenharmony_ci await publicFinishFunc(handle, encryptOptions); 247e41f4b71Sopenharmony_ci } 248e41f4b71Sopenharmony_ci ``` 249e41f4b71Sopenharmony_ci 250e41f4b71Sopenharmony_ci3. Use the key. User identity authentication is required when the key is used for decryption. 251e41f4b71Sopenharmony_ci 252e41f4b71Sopenharmony_ci ```ts 253e41f4b71Sopenharmony_ci import { huks } from "@kit.UniversalKeystoreKit"; 254e41f4b71Sopenharmony_ci import { userAuth } from '@kit.UserAuthenticationKit'; 255e41f4b71Sopenharmony_ci import { BusinessError } from "@kit.BasicServicesKit" 256e41f4b71Sopenharmony_ci 257e41f4b71Sopenharmony_ci let keyAlias = 'test_sm4_key_alias'; 258e41f4b71Sopenharmony_ci let IV = '1234567890123456'; 259e41f4b71Sopenharmony_ci let handle = 0; 260e41f4b71Sopenharmony_ci let cipherText: Uint8Array; // Data in ciphertext. 261e41f4b71Sopenharmony_ci /* 262e41f4b71Sopenharmony_ci * Determine the key property set to be encapsulated. 263e41f4b71Sopenharmony_ci */ 264e41f4b71Sopenharmony_ci let finishOutData: Uint8Array; // Plaintext after decryption. 265e41f4b71Sopenharmony_ci let fingerAuthToken: Uint8Array; 266e41f4b71Sopenharmony_ci let challenge: Uint8Array; 267e41f4b71Sopenharmony_ci let authType = userAuth.UserAuthType.FINGERPRINT; 268e41f4b71Sopenharmony_ci let authTrustLevel = userAuth.AuthTrustLevel.ATL1; 269e41f4b71Sopenharmony_ci class throwObject { 270e41f4b71Sopenharmony_ci isThrow: boolean = false; 271e41f4b71Sopenharmony_ci } 272e41f4b71Sopenharmony_ci function StringToUint8Array(str: string) { 273e41f4b71Sopenharmony_ci let arr: number[] = []; 274e41f4b71Sopenharmony_ci for (let i = 0, j = str.length; i < j; ++i) { 275e41f4b71Sopenharmony_ci arr.push(str.charCodeAt(i)); 276e41f4b71Sopenharmony_ci } 277e41f4b71Sopenharmony_ci return new Uint8Array(arr); 278e41f4b71Sopenharmony_ci } 279e41f4b71Sopenharmony_ci /* Set the key generation parameter set and key encryption parameter set. */ 280e41f4b71Sopenharmony_ci class propertyDecryptType { 281e41f4b71Sopenharmony_ci tag: huks.HuksTag = huks.HuksTag.HUKS_TAG_ALGORITHM 282e41f4b71Sopenharmony_ci value: huks.HuksKeyAlg | huks.HuksKeyPurpose | huks.HuksKeySize | huks.HuksKeyPadding | huks.HuksCipherMode 283e41f4b71Sopenharmony_ci | Uint8Array = huks.HuksKeyAlg.HUKS_ALG_SM4 284e41f4b71Sopenharmony_ci } 285e41f4b71Sopenharmony_ci let propertiesDecrypt: propertyDecryptType[] = [ 286e41f4b71Sopenharmony_ci { 287e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_ALGORITHM, 288e41f4b71Sopenharmony_ci value: huks.HuksKeyAlg.HUKS_ALG_SM4, 289e41f4b71Sopenharmony_ci }, 290e41f4b71Sopenharmony_ci { 291e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_PURPOSE, 292e41f4b71Sopenharmony_ci value: huks.HuksKeyPurpose.HUKS_KEY_PURPOSE_DECRYPT, 293e41f4b71Sopenharmony_ci }, 294e41f4b71Sopenharmony_ci { 295e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_KEY_SIZE, 296e41f4b71Sopenharmony_ci value: huks.HuksKeySize.HUKS_SM4_KEY_SIZE_128, 297e41f4b71Sopenharmony_ci }, 298e41f4b71Sopenharmony_ci { 299e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_PADDING, 300e41f4b71Sopenharmony_ci value: huks.HuksKeyPadding.HUKS_PADDING_NONE, 301e41f4b71Sopenharmony_ci }, 302e41f4b71Sopenharmony_ci { 303e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_BLOCK_MODE, 304e41f4b71Sopenharmony_ci value: huks.HuksCipherMode.HUKS_MODE_CBC, 305e41f4b71Sopenharmony_ci }, 306e41f4b71Sopenharmony_ci { 307e41f4b71Sopenharmony_ci tag: huks.HuksTag.HUKS_TAG_IV, 308e41f4b71Sopenharmony_ci value: StringToUint8Array(IV), 309e41f4b71Sopenharmony_ci } 310e41f4b71Sopenharmony_ci ] 311e41f4b71Sopenharmony_ci let decryptOptions: huks.HuksOptions = { 312e41f4b71Sopenharmony_ci properties: propertiesDecrypt, 313e41f4b71Sopenharmony_ci inData: new Uint8Array(new Array()) 314e41f4b71Sopenharmony_ci } 315e41f4b71Sopenharmony_ci function initSession(keyAlias: string, huksOptions: huks.HuksOptions, throwObject: throwObject) { 316e41f4b71Sopenharmony_ci return new Promise<huks.HuksSessionHandle>((resolve, reject) => { 317e41f4b71Sopenharmony_ci try { 318e41f4b71Sopenharmony_ci huks.initSession(keyAlias, huksOptions, (error, data) => { 319e41f4b71Sopenharmony_ci if (error) { 320e41f4b71Sopenharmony_ci reject(error); 321e41f4b71Sopenharmony_ci } else { 322e41f4b71Sopenharmony_ci resolve(data); 323e41f4b71Sopenharmony_ci } 324e41f4b71Sopenharmony_ci }); 325e41f4b71Sopenharmony_ci } catch (error) { 326e41f4b71Sopenharmony_ci throwObject.isThrow = true; 327e41f4b71Sopenharmony_ci throw(error as Error); 328e41f4b71Sopenharmony_ci } 329e41f4b71Sopenharmony_ci }); 330e41f4b71Sopenharmony_ci } 331e41f4b71Sopenharmony_ci async function publicInitFunc(keyAlias: string, huksOptions: huks.HuksOptions) { 332e41f4b71Sopenharmony_ci console.info(`enter promise doInit`); 333e41f4b71Sopenharmony_ci let throwObject: throwObject = {isThrow: false}; 334e41f4b71Sopenharmony_ci try { 335e41f4b71Sopenharmony_ci await initSession(keyAlias, huksOptions, throwObject) 336e41f4b71Sopenharmony_ci .then ((data) => { 337e41f4b71Sopenharmony_ci console.info(`promise: doInit success, data = ${JSON.stringify(data)}`); 338e41f4b71Sopenharmony_ci handle = data.handle; 339e41f4b71Sopenharmony_ci challenge = data.challenge as Uint8Array; 340e41f4b71Sopenharmony_ci }) 341e41f4b71Sopenharmony_ci .catch((error: BusinessError) => { 342e41f4b71Sopenharmony_ci if (throwObject.isThrow) { 343e41f4b71Sopenharmony_ci throw(error as Error); 344e41f4b71Sopenharmony_ci } else { 345e41f4b71Sopenharmony_ci console.error(`promise: doInit failed` + JSON.stringify(error)); 346e41f4b71Sopenharmony_ci } 347e41f4b71Sopenharmony_ci }); 348e41f4b71Sopenharmony_ci } catch (error) { 349e41f4b71Sopenharmony_ci console.error(`promise: doInit input arg invalid` + JSON.stringify(error)); 350e41f4b71Sopenharmony_ci } 351e41f4b71Sopenharmony_ci } 352e41f4b71Sopenharmony_ci function userIAMAuthFinger(huksChallenge: Uint8Array) { 353e41f4b71Sopenharmony_ci // Obtain an authentication object. 354e41f4b71Sopenharmony_ci let authTypeList:userAuth.UserAuthType[]= [ authType ]; 355e41f4b71Sopenharmony_ci const authParam:userAuth.AuthParam = { 356e41f4b71Sopenharmony_ci challenge: huksChallenge, 357e41f4b71Sopenharmony_ci authType: authTypeList, 358e41f4b71Sopenharmony_ci authTrustLevel: userAuth.AuthTrustLevel.ATL1 359e41f4b71Sopenharmony_ci }; 360e41f4b71Sopenharmony_ci const widgetParam:userAuth.WidgetParam = { 361e41f4b71Sopenharmony_ci title: 'Enter password', 362e41f4b71Sopenharmony_ci }; 363e41f4b71Sopenharmony_ci let auth : userAuth.UserAuthInstance; 364e41f4b71Sopenharmony_ci try { 365e41f4b71Sopenharmony_ci auth = userAuth.getUserAuthInstance(authParam, widgetParam); 366e41f4b71Sopenharmony_ci console.info("get auth instance success"); 367e41f4b71Sopenharmony_ci } catch (error) { 368e41f4b71Sopenharmony_ci console.error("get auth instance failed" + JSON.stringify(error)); 369e41f4b71Sopenharmony_ci return; 370e41f4b71Sopenharmony_ci } 371e41f4b71Sopenharmony_ci // Subscribe to the authentication result. 372e41f4b71Sopenharmony_ci try { 373e41f4b71Sopenharmony_ci auth.on("result", { 374e41f4b71Sopenharmony_ci onResult(result) { 375e41f4b71Sopenharmony_ci console.info("[HUKS] -> [IAM] userAuthInstance callback result = " + JSON.stringify(result)); 376e41f4b71Sopenharmony_ci fingerAuthToken = result.token; 377e41f4b71Sopenharmony_ci } 378e41f4b71Sopenharmony_ci }); 379e41f4b71Sopenharmony_ci console.info("subscribe authentication event success"); 380e41f4b71Sopenharmony_ci } catch (error) { 381e41f4b71Sopenharmony_ci console.error("subscribe authentication event failed " + JSON.stringify(error)); 382e41f4b71Sopenharmony_ci } 383e41f4b71Sopenharmony_ci // Start user authentication. 384e41f4b71Sopenharmony_ci try { 385e41f4b71Sopenharmony_ci auth.start(); 386e41f4b71Sopenharmony_ci console.info("authV9 start auth success"); 387e41f4b71Sopenharmony_ci } catch (error) { 388e41f4b71Sopenharmony_ci console.error("authV9 start auth failed, error = " + JSON.stringify(error)); 389e41f4b71Sopenharmony_ci } 390e41f4b71Sopenharmony_ci } 391e41f4b71Sopenharmony_ci function finishSession(handle: number, huksOptions: huks.HuksOptions, token: Uint8Array, throwObject: throwObject) { 392e41f4b71Sopenharmony_ci return new Promise<huks.HuksReturnResult>((resolve, reject) => { 393e41f4b71Sopenharmony_ci try { 394e41f4b71Sopenharmony_ci huks.finishSession(handle, huksOptions, token, (error, data) => { 395e41f4b71Sopenharmony_ci if (error) { 396e41f4b71Sopenharmony_ci reject(error); 397e41f4b71Sopenharmony_ci } else { 398e41f4b71Sopenharmony_ci resolve(data); 399e41f4b71Sopenharmony_ci } 400e41f4b71Sopenharmony_ci }); 401e41f4b71Sopenharmony_ci } catch (error) { 402e41f4b71Sopenharmony_ci throwObject.isThrow = true; 403e41f4b71Sopenharmony_ci throw(error as Error); 404e41f4b71Sopenharmony_ci } 405e41f4b71Sopenharmony_ci }); 406e41f4b71Sopenharmony_ci } 407e41f4b71Sopenharmony_ci async function publicFinishFunc(handle: number, token: Uint8Array, huksOptions: huks.HuksOptions) { 408e41f4b71Sopenharmony_ci console.info(`enter promise doFinish`); 409e41f4b71Sopenharmony_ci let throwObject: throwObject = {isThrow: false}; 410e41f4b71Sopenharmony_ci try { 411e41f4b71Sopenharmony_ci await finishSession(handle, huksOptions, token, throwObject) 412e41f4b71Sopenharmony_ci .then ((data) => { 413e41f4b71Sopenharmony_ci finishOutData = data.outData as Uint8Array; 414e41f4b71Sopenharmony_ci console.info(`promise: doFinish success, data = ${JSON.stringify(data)}`); 415e41f4b71Sopenharmony_ci }) 416e41f4b71Sopenharmony_ci .catch((error: BusinessError) => { 417e41f4b71Sopenharmony_ci if (throwObject.isThrow) { 418e41f4b71Sopenharmony_ci throw(error as Error); 419e41f4b71Sopenharmony_ci } else { 420e41f4b71Sopenharmony_ci console.error(`promise: doFinish failed` + JSON.stringify(error)); 421e41f4b71Sopenharmony_ci } 422e41f4b71Sopenharmony_ci }); 423e41f4b71Sopenharmony_ci } catch (error) { 424e41f4b71Sopenharmony_ci console.error(`promise: doFinish input arg invalid` + JSON.stringify(error)); 425e41f4b71Sopenharmony_ci } 426e41f4b71Sopenharmony_ci } 427e41f4b71Sopenharmony_ci async function testSm4Cipher() { 428e41f4b71Sopenharmony_ci /* Initialize the key session to obtain a challenge. */ 429e41f4b71Sopenharmony_ci await publicInitFunc(keyAlias, decryptOptions); 430e41f4b71Sopenharmony_ci /* Invoke userIAM to perform user identity authentication. */ 431e41f4b71Sopenharmony_ci userIAMAuthFinger(challenge); 432e41f4b71Sopenharmony_ci /* Perform decryption after the authentication is successful. The **authToken** value returned after the authentication needs to be passed in. */ 433e41f4b71Sopenharmony_ci decryptOptions.inData = StringToUint8Array(cipherText); 434e41f4b71Sopenharmony_ci await publicFinishFunc(handle, fingerAuthToken, decryptOptions); 435e41f4b71Sopenharmony_ci } 436e41f4b71Sopenharmony_ci ``` 437