Advanced Security:
MFA in minutes
Security models based on a single password have a structural problem: a single stolen credential is all it takes for the entire system to collapse. The use of stolen credentials is at the heart of Basic Web Application Attacks (source Verizon DBIR) and a VPN alone does not stop an attack that starts from a valid account. If your system doesn't verify who is doing what for every critical action, serious problems can arise.
In this article, we'll implement a complete MFA (Multi-Factor Authentication) flow based on TOTP, using the Open Source library `@volcanicminds/tools`.
We'll explore secret generation, QR code creation, token verification, and generating codes for testing. All in just a few lines of TypeScript.
Potentially, SMS codes are vulnerable to SIM swapping and man-in-the-middle attacks on the cellular network. TOTP (Time-based One-Time Password) solves the problem at its root because the secret lives only on the user's device and the server, without traveling over external networks.
It is the RFC 6238 standard and works with Google Authenticator, Authy, 1Password, and any compatible app. And as if that weren't enough, it has no third-party dependencies (for SMS delivery) and requires no subscriptions or additional message sending costs.
The package is available on npm and requires Node.js 24+ with an ESM project.
npm install @volcanicminds/toolsIn your package.json, make sure you have the classic "type": "module".
Targeted importing avoids loading unnecessary modules (native tree-shaking).
The first step is to create a secret for the user. This secret must be stored securely in the database, encrypted and associated with the account.
// tree-shaking
import * as mfa from "@volcanicminds/tools/mfa";
// Generate a standalone secret (useful if you need to store it before full setup)
const secret = mfa.generateSecret();
console.log(secret); // e.g. "JBSWY3DPEHPK3PXP"In many cases, you won't need this step separately because `generateSetupDetails` (next step) automatically generates it if you don't provide one.
However, having the generateSecret method available is useful in various scenarios.
This is where the magic happens. With a single call, we obtain the secret, the otpauth URI, and the QR code ready to be displayed on the frontend.
const setup = await mfa.generateSetupDetails(
"AppName", // issuer (the name shown in the authenticator app)
"user@company.com", // user account
secret, // optional: if omitted, a new one is generated
);
// What we get:
console.log(setup.secret); // base32 secret, store encrypted in DB
console.log(setup.qrCode); // QR code data URL (base64), ready for <img> tagThe `setup.qrCode` returns a Data URL that you can inject directly into an img tag without needing additional frontend libraries.
When the user opens their authenticator app and enters the 6-digit code, the verification is immediate.
const userToken = "483920"; // the code entered by the user
const isValid = mfa.verifyToken(userToken, setup.secret);
if (isValid) {
// Proceed with login or protected action
} else {
// Invalid or expired token
}The method internally handles the TOTP time window (typically 30 seconds). There is no need to worry about managing clock drift or expirations; everything is encapsulated.
Writing automated tests when passing through MFA is annoying, so how do you simulate a valid code without opening an authenticator app? Like this:
const currentToken = mfa.generateToken(setup.secret);
console.log(currentToken); // es. "847291" (valido per ~30 secondi)This method is designed for your end-to-end tests and for generating recovery codes. No workarounds, no complex mocks.
Put together, these methods cover the lifecycle of MFA. From user registration to protected login, from recovery to automated testing. The architecture is deliberately minimal and does not bind you to any specific framework. It works with Express, Fastify, Nuxt, NestJS, or any other Node.js stack.
Of course, when it comes to MFA there is more, but this article is intentionally minimal to show that even with little effort, it is possible to increase the security of an Enterprise platform without jeopardizing development times and costs.
This is exactly what we mean when we talk about Security by Design. The second factor is not an expensive plugin that you buy, configure, and hope works. It is code that lives within the project, which can be inspected, tested, and controlled. We can govern the risk.
No, the `@volcanicminds/tools` library doesn't stop at MFA. It includes modules for mailing (Mailer with simplified nodemailer), structured logging (Pino), S3/Minio storage, resumable uploads (Tus.io), and an AI module to integrate providers like OpenAI, Anthropic, and Google Gemini (Mastra inside).
For more information, you can check out the following resources:
If you need an assessment of your system's security architecture, or need to implement a complete MFA workflow in your applications, contact us for a technical review.
Publication date: March 23, 2026
Latest revision: March 23, 2026