Skip to main content
‹ Options
Constants

AccessControl

What unlocks an item: nothing, any enrolled biometrics, the biometrics enrolled at write time, the device passcode, or biometrics with the passcode as a fallback. A constant object and a type of the same name.

Import
import { AccessControl } from '@apexnative/keychain';

AccessControl is the value of the accessControl option, of canUseAccessControl, and what getItemInfo reports. Anything but None locks the value with a key the system releases only after the user passes the prompt: a read shows the prompt, a write never does. AccessControl.BiometryCurrentSet is the string 'biometryCurrentSet'; both forms are accepted.

Usage​

import { AccessControl, canUseAccessControl, createKeychain } from '@apexnative/keychain';

const vault = createKeychain({ service: 'vault', accessControl: AccessControl.BiometryCurrentSet });

if ((await canUseAccessControl(AccessControl.BiometryCurrentSet)).available) {
await vault.setItem('refreshToken', token);
}

Signature​

const AccessControl: {
readonly None: 'none';
readonly BiometryAny: 'biometryAny';
readonly BiometryCurrentSet: 'biometryCurrentSet';
readonly BiometryAnyOrPasscode: 'biometryAnyOrPasscode';
readonly BiometryCurrentSetOrPasscode: 'biometryCurrentSetOrPasscode';
readonly Passcode: 'passcode';
};

type AccessControl = (typeof AccessControl)[keyof typeof AccessControl];
Type'none' | 'biometryAny' | 'biometryCurrentSet' | 'biometryAnyOrPasscode' | 'biometryCurrentSetOrPasscode' | 'passcode'Default'none'PlatformsiOSAndroid

Values​

ConstantStringWho unlocks the itemiOSAndroid prompt
None'none'Nobody: no prompt. The defaultOnly kSecAttrAccessible—
BiometryAny'biometryAny'Any enrolled biometrics, now or added later.biometryAnyBIOMETRIC_STRONG
BiometryCurrentSet'biometryCurrentSet'Only the biometrics enrolled when the item was written.biometryCurrentSetBIOMETRIC_STRONG
BiometryAnyOrPasscode'biometryAnyOrPasscode'Biometrics or the device passcode.userPresenceBIOMETRIC_STRONG | DEVICE_CREDENTIAL
BiometryCurrentSetOrPasscode'biometryCurrentSetOrPasscode'Today's biometrics or the device passcode.biometryCurrentSet, .or, .devicePasscodeBIOMETRIC_STRONG | DEVICE_CREDENTIAL
Passcode'passcode'The device passcode, PIN or pattern.devicePasscodeDEVICE_CREDENTIAL
  • CurrentSet. A new fingerprint or face, or one removed, invalidates the item: the next read throws KEY_INVALIDATED and the item is removed. With Any, the item survives such changes. See How biometrics works.
  • Biometrics on Android is Class 3 (strong), the only kind that can unlock a Keystore key. A phone whose face unlock is Class 2 offers only its fingerprint sensor to these items.
  • The passcode on Android needs Android 11 (API 30). Before it, the three values with a passcode are unsupportedOS for canUseAccessControl, and a write throws UNSUPPORTED.
  • authValidity. BiometryCurrentSet and BiometryCurrentSetOrPasscode can't have a window: authValidity above 0 with them is INVALID_ARGUMENT.
  • iCloud. An item with an accessControl other than None can't be synchronizable (INVALID_ARGUMENT).

What a write needs​

A write of an item whose protection the device can't give fails; it never stores the item with less:

The deviceBiometryAny, BiometryCurrentSetBiometryCurrentSetOrPasscodeBiometryAnyOrPasscodePasscode
No biometric sensorBIOMETRY_NOT_AVAILABLEBIOMETRY_NOT_AVAILABLEWritten: the passcode opens itWritten
No biometrics enrolledBIOMETRY_NOT_ENROLLEDBIOMETRY_NOT_ENROLLED: the passcode doesn't make up for itWrittenWritten
No passcodePASSCODE_NOT_SETPASSCODE_NOT_SETPASSCODE_NOT_SETPASSCODE_NOT_SET
Android 7–10WrittenUNSUPPORTEDUNSUPPORTEDUNSUPPORTED

On iOS a biometric value (all but None and Passcode) also needs NSFaceIDUsageDescription in the app's Info.plist on a device with Face ID: without it the write, the read and canUseAccessControl fail with MISSING_USAGE_DESCRIPTION. canUseAccessControl answers all of this before a write.

See also​