В этом документе обсуждается, что такое userVerification
в WebAuthn, а также поведение браузера, которое возникает при указании userVerification
во время создания ключа доступа или аутентификации.
Что такое «проверка пользователя» в WebAuthn?
Ключи доступа основаны на криптографии с открытым ключом. При создании ключа доступа генерируется пара открытого и закрытого ключей, закрытый ключ сохраняется поставщиком ключей доступа, а открытый ключ возвращается на сервер проверяющей стороны (RP) для хранения. Сервер может аутентифицировать пользователя, проверив подпись, подписанную тем же ключом доступа, используя парный открытый ключ. Флаг «присутствие пользователя» (UP) в учётных данных открытого ключа подтверждает, что кто-то взаимодействовал с устройством во время аутентификации.
Верификация пользователя — это дополнительный уровень безопасности, призванный подтвердить присутствие нужного человека во время аутентификации, а не просто какого-то другого, как это подтверждается присутствием пользователя. На смартфонах это обычно делается с помощью механизма блокировки экрана, будь то биометрическая проверка, PIN-код или пароль. Информация о том, была ли выполнена верификация пользователя, отображается в флаге «UV», который возвращается в данных аутентификатора во время регистрации ключа доступа и аутентификации.


Как UP и UV проверяются на сервере
Булевы флаги присутствия пользователя (UP) и проверки пользователя (UV) передаются серверу в поле данных аутентификатора. Во время аутентификации содержимое поля данных аутентификатора может быть проверено путем проверки подписи с использованием сохранённого открытого ключа. Пока подпись действительна, сервер может считать флаги подлинными.

При регистрации и аутентификации ключа доступа сервер должен проверить, является ли флаг UP true
или false
, а также является ли флаг UV true
или false
, в зависимости от требования.
Указание параметра userVerification
Согласно спецификации WebAuthn , проверяющая сторона может запрашивать верификацию пользователя с помощью параметра userVerification
как при создании, так и при подтверждении учётных данных. Она принимает значения 'preferred'
, 'required'
или 'discouraged'
, что означает соответственно:
-
'preferred'
(по умолчанию): использование метода проверки пользователя на устройстве является предпочтительным , но его можно пропустить, если он недоступен. Учётные данные ответа содержат значение флага UV:true
, если проверка пользователя была выполнена, иfalse
если UV не была выполнена. -
'required'
: Требуется вызов метода проверки пользователя, доступного на устройстве. Если метод недоступен, запрос локально завершается ошибкой. Это означает, что учётные данные ответа всегда возвращаются с флагом UV, установленным вtrue
. -
'discouraged'
: использование метода пользовательской верификации не рекомендуется. Однако, в зависимости от устройства, пользовательская верификация может быть выполнена в любом случае, а флаг UV может содержатьtrue
илиfalse
.
Пример кода для создания ключа доступа:
const publicKeyCredentialCreationOptions = {
// ...
authenticatorSelection: {
authenticatorAttachment: 'platform',
residentKey: 'required',
requireResidentKey: true,
userVerification: 'preferred'
}
};
const credential = await navigator.credentials.create({
publicKey: publicKeyCredentialCreationOptions
});
Пример кода для аутентификации по ключу доступа:
const publicKeyCredentialRequestOptions = {
challenge: /* Omitted challenge data... */,
rpId: 'example.com',
userVerification: 'preferred'
};
const credential = await navigator.credentials.get({
publicKey: publicKeyCredentialRequestOptions
});
Какой вариант userVerification
следует выбрать?
Значение userVerification
, которое следует использовать, зависит от требований вашего приложения, а также от потребностей вашего пользовательского опыта.
Когда следует использовать userVerification='preferred'
Используйте userVerification='preferred'
, если для вас удобство использования важнее защиты.
Существуют среды, в которых верификация пользователя скорее создает неудобства, чем обеспечивает защиту. Например, в macOS, где Touch ID недоступен (устройство не поддерживает его, отключено или устройство находится в режиме раскладушки), пользователю предлагается ввести системный пароль. Это создает неудобства, и пользователь может полностью отказаться от аутентификации. Если для вас важнее отсутствие неудобств, используйте userVerification='preferred'
.

При userVerification='preferred'
флаг UV имеет значение true
, если верификация пользователя выполнена успешно, и false
если верификация пропущена. Например, в macOS, где Touch ID недоступен, пользователю предлагается нажать кнопку, чтобы пропустить верификацию, а учётные данные открытого ключа содержат false
флаг UV.
УФ-флаг может служить сигналом в вашем анализе рисков. Если попытка входа кажется рискованной из-за других факторов, вы можете предоставить пользователю дополнительные сложности при входе, если верификация не была выполнена.
Когда следует использовать userVerification='required'
Используйте userVerification='required'
, если вы считаете, что и UP, и UV абсолютно необходимы.
Недостатком этого варианта является то, что пользователь может столкнуться с дополнительными трудностями при входе в систему. Например, в macOS, где Touch ID недоступен, пользователю предлагается ввести системный пароль.
Параметр userVerification='required'
гарантирует, что на устройстве выполняется верификация пользователя. Убедитесь, что сервер проверяет, что флаг UV имеет true
.
Заключение
Используя проверку пользователя, стороны, использующие ключ доступа, могут оценить вероятность входа владельца устройства в систему. Они сами решают, требовать ли проверку пользователя или сделать её необязательной, в зависимости от того, насколько критически механизм резервного входа влияет на пользовательский процесс. Убедитесь, что сервер проверяет флаги UP и UV для аутентификации пользователя с ключом доступа.