ASP.NET Core 5.0 - Multiple FIDO2 Credentials

This article will demonstrate management of multiple FIDO2 devices in the Users Without Passwords Project (UWPP). I will assume you have downloaded the ASP.NET Core 5.0 - Users Without Passwords Project.

Users Without Passwords Project and Article Series

I have developed two separate projects in the Users Without Passwords Project (UWPP) solution. The Users Without Passwords v4 project supports Bootstrap v4 and the new Users Without Passwords project supports Bootstrap v5. The new version is published at Fido.KenHaggerty.Com. You can register a new user with Windows Hello or a FIDO2 security key. Details, screenshots, and related articles can be found at ASP.NET Core 5.0 - Users Without Passwords Project. The details page includes the version change log.

An early objective was to implement multiple credentials and credential management per user. At the time, my first FIDO2 device was a yubico Security Key NFC and my second FIDO2 device was Windows Hello. The yubico security key uses Elliptic Curve cryptography and Windows Hello uses RSA cryptography. With the help of GitHub - passwordless-lib / fido2-net-lib, I implemented RSA cryptography. The UWPP configures a list of AllowCredentials, including Transport hints, which are all the Credential Ids related to the user before the user calls the navigator. credentials. get() function from JavaScript during the log in or assertion ceremony. See ASP.NET Core 5.0 - Credential Get.

Credentials Add Backup Device.
Credentials Add Backup Device Mobile.

When the user adds a new credential, the ExcludedCredentials list is used by the attestation ceremony and excludes known authenticators.

CredentialChallenge.cshtml.cs > OnGetAsync:
// 5.4
// excludeCredentials, of type sequence<PublicKeyCredentialDescriptor>, defaulting to []
var excludeCredentials = new List<ExcludedCredential>();
var credentialIds = await _credentialService.GetCredentialIdsByAppUserIdAsync(AppUserId);
if (credentialIds.Count == 0)
    throw new InvalidOperationException($"No Credentials found for AppUser.Id = {AppUserId})");
foreach (var cid in credentialIds)
    excludeCredentials.Add(new ExcludedCredential()
        Type = _challengeOptions.CredentialType,
        Id = cid
CredentialChallenge.cshtml > JavaScript:
let createOptions = @@Html.Raw(Model.CreateOptions);
CredentialChallenge.cshtml > createCredential:
// Update byte string to expected Uint8Array
try {
    if (typeof (createOptions.challenge) != Uint8Array)
        createOptions.challenge = getUint8Array(createOptions.challenge);

    if (typeof ( != Uint8Array) = getUint8Array(;

    let l = createOptions.excludeCredentials.length;
        for (let i = 0; i < l; i++)
            if (typeof (createOptions.excludeCredentials[i].id) != Uint8Array)
                createOptions.excludeCredentials[i].id = getUint8Array(createOptions.excludeCredentials[i].id);

} catch (e) {
    showMessageModal(e, 'alert-warning');
New Credential Challenge.
New Credential Challenge Mobile.

The UWPP implements credential management with a primary credential and editable credential name.

Manage Multiple Credentials.
Manage Multiple Credentials Mobile.

The user can delete non primary credentials.

Confirm Delete Credential.
Confirm Delete Credential Mobile.

Administrators can manage credentials by user.

Admin AppUser Index.
Admin AppUser Index Mobile.
Admin AppUser
Admin AppUser
Ken Haggerty
Created 08/16/21
Updated 08/16/21 04:02 GMT

Log In or Reset Quota to read more.

Article Tags:

Authorization FIDO Modal
Successfully completed. Thank you for contributing.
Contribute to enjoy content without advertisments.
Something went wrong. Please try again.



Not accepting new comments.

Submit your comment. Comments are moderated.

User Image.
DisplayedName - Member Since ?