Multi-Factor Authentication (MFA) is a crucial security measure designed to enhance our application's protection and reduce the chances of unauthorized access.
This article walks you through the steps to implement MFA in a .NET 8 application, focusing on Time-based One-Time Password (OTP) compatible with Google Authenticator and Microsoft Authenticator.
Prerequisites
- A working .NET Web API
- Google Authenticator or Microsoft Authenticator installed on your phone
Step 1: Setting up
Install the following NuGet packages:
dotnet add package QRCoder
dotnet add package OtpNet
Step 2: Adding TOTP Service
This service will generate the secret Key for each user, generate QR codes, and validate OTP
using OtpNet;
using QRCoder;
namespace MFA;
public class TotpService
{
public string GenerateSecretKey()
{
var secretKey = KeyGeneration.GenerateRandomKey(20);
return Base32Encoding.ToString(secretKey);
}
public string GenerateQrCodeUrl(string email, string secretKey)
{
var issuer = Uri.EscapeDataString("yourAppName");
var userEmail = Uri.EscapeDataString(email);
return $"otpauth://totp/{issuer}:{userEmail}?secret={secretKey}&issuer={issuer}&algorithm=SHA1&digits=6&period=30";
}
public byte[] GenerateQRCode(string uri)
{
using var qrGenerator = new QRCodeGenerator();
using var qrCodeData = qrGenerator.CreateQrCode(uri, QRCodeGenerator.ECCLevel.Q);
using var qrCode = new PngByteQRCode(qrCodeData);
return qrCode.GetGraphic(20);
}
public bool ValidateOTP(string secretKey, string otp)
{
var totp = new Totp(Base32Encoding.ToBytes(secretKey));
return totp.VerifyTotp(otp, out _, VerificationWindow.RfcSpecifiedNetworkDelay);
}
}
Step 3: Integration TOTP Service into application
User Registration
- When registering a user, generate a secret key and a QR code. The secret key should be saved with the user's information in the database, and the QR Code should be displayed to the user.
- Using this QR users can register using either Google Authenticator or Microsoft Authenticator.
- As a best practice do not keep the 'secretKey' in clear text format. Encrypt this value.
var secretKey = _totpService.GenerateSecretKey();
var uri = _totpService.GenerateQrCodeUrl("chinthakapb@gmail.com", secretKey);
var qrCodeImage = _totpService.GenerateQRCode(uri);
Validating OTP
- Once the user logs into the application, provide a place for the user to enter the Time-based OTP generated from either Google Authenticator or Microsoft Authenticator.
- Get the 'secretKey' from the database and validate the OTP from the backend.
bool result = _totpService.ValidateOTP(request.SecretKey, request.Code);
The above code will return whether the OTP is valid is not. You can use this to navigate the user into the system or not.
Happy Coding 😀
Top comments (0)