{"_id":"@bymax-one/nest-auth","_rev":"25-f6ea7b655cb3b266cb12e8a6ea89539f","name":"@bymax-one/nest-auth","dist-tags":{"latest":"1.4.5"},"versions":{"1.0.0":{"name":"@bymax-one/nest-auth","version":"1.0.0","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"contact@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.0","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"5c63625b595b11676baad7a9c4504ebfab46599d","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.0.tgz","fileCount":24,"integrity":"sha512-dWccMujxXYwlrlIEi41uPnET51pWeXjv3Zmj1emsgarbL30Unc2Y6IiTO+2ietVhU0fTizi3pJx2DoGCebgGPg==","signatures":[{"sig":"MEUCIQCdauiZ19RLNe6sHIdfUI+A73gPE9lkhLpKfaB2cpuIvgIgHMh8GVPHPYFNJldG3R95x1YtSgUxB1A9NNa5YQxM/AY=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"unpackedSize":1549205},"type":"module","_from":"file:bymax-one-nest-auth-1.0.0.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"bymax.one","email":"bymaxone.core@gmail.com"},"_resolved":"/private/var/folders/zf/_zr7t0ms60x6rcwj5zxk90cr0000gn/T/bcc69c6a9555eb8e82d5e0b94f8975dd/bymax-one-nest-auth-1.0.0.tgz","_integrity":"sha512-dWccMujxXYwlrlIEi41uPnET51pWeXjv3Zmj1emsgarbL30Unc2Y6IiTO+2ietVhU0fTizi3pJx2DoGCebgGPg==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.13.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.16.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.0_1779739790932_0.7251549674707753","host":"s3://npm-registry-packages-npm-production"}},"1.0.1":{"name":"@bymax-one/nest-auth","version":"1.0.1","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"contact@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.1","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"ae9ac951a83248a0dd9e544ed3fd63e184697c52","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.1.tgz","fileCount":24,"integrity":"sha512-RaRBB71GWfDQsktiwA30uiugNWColQux6lxsJzNkagXPF+5bGoqmxqTs5yriSE4AbJaAqs+29Q+aumQhhNWdXg==","signatures":[{"sig":"MEUCIQDhfP5YhBtFz5QGSIJlQsX0ZinnOn0Zg8x5OQoLPtY/XwIgJmaMmE0PNK0JHkbzNo+W0e3bzYMHC/iXKkjvkQi5MoU=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.1","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1550040},"type":"module","_from":"file:bymax-one-nest-auth-1.0.1.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/688bc77751b6b050cdc8299f7968d0d6/bymax-one-nest-auth-1.0.1.tgz","_integrity":"sha512-RaRBB71GWfDQsktiwA30uiugNWColQux6lxsJzNkagXPF+5bGoqmxqTs5yriSE4AbJaAqs+29Q+aumQhhNWdXg==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.1_1779740986107_0.31434116197130924","host":"s3://npm-registry-packages-npm-production"}},"1.0.2":{"name":"@bymax-one/nest-auth","version":"1.0.2","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.2","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"cef7d07eb9f2fe61d098c7bf5737099cf88e2eba","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.2.tgz","fileCount":24,"integrity":"sha512-tzgWTet/0v5WS0vop5GnzL9R8KP0coFoO4gXTI2bRbMT3ZSlOQ3p7CvmfleFsMQnLJqmKD2gpLMHt7kxbP5hXQ==","signatures":[{"sig":"MEQCIAlqWY7pPiEhsg27GQHlUU6G53qcIC+daEhEhRXvBRs5AiBvWymj18lOCvZIc2Xzoms2tRHnuhx4C+Fy1UaShNUVDg==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.2","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1552854},"type":"module","_from":"file:bymax-one-nest-auth-1.0.2.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/84598c3d14071b11c59c8a849c5f2e78/bymax-one-nest-auth-1.0.2.tgz","_integrity":"sha512-tzgWTet/0v5WS0vop5GnzL9R8KP0coFoO4gXTI2bRbMT3ZSlOQ3p7CvmfleFsMQnLJqmKD2gpLMHt7kxbP5hXQ==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.2_1779744086777_0.6400849039547623","host":"s3://npm-registry-packages-npm-production"}},"1.0.3":{"name":"@bymax-one/nest-auth","version":"1.0.3","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.3","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"bc9beeadb2d4bbdd34d1accc35eb9bee69f50e54","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.3.tgz","fileCount":24,"integrity":"sha512-/GzEPipqbMOu2300ArJ1q/ovdhlq73odrcAJx9lyCXXjptSRplyNAfNavaUZE5VRmGJ8ROmtRIiimlgrNUezPg==","signatures":[{"sig":"MEYCIQCLkg6kMWv8qI+OPY1J9ky623gM78Yz2RUQs00hP7TzJAIhAMSifdwFyOz6BvT3JYBrLh/YLXBHSN5UgoyZJ8h/kTvc","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.3","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1561337},"type":"module","_from":"file:bymax-one-nest-auth-1.0.3.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/0e44ce482b14597cd87f6bf718abe9c7/bymax-one-nest-auth-1.0.3.tgz","_integrity":"sha512-/GzEPipqbMOu2300ArJ1q/ovdhlq73odrcAJx9lyCXXjptSRplyNAfNavaUZE5VRmGJ8ROmtRIiimlgrNUezPg==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.3_1779755849133_0.25489705110964467","host":"s3://npm-registry-packages-npm-production"}},"1.0.4":{"name":"@bymax-one/nest-auth","version":"1.0.4","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.4","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"351169a49cc058fc2612d7eb50cbc9146c437b0f","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.4.tgz","fileCount":24,"integrity":"sha512-/3WwKviPGgzNzSM5jIf1DFIqPNpID9OFN+kFD/wste0MCWkNfnMJt4828KTsF+w9cjgguWk5/80fuw4kX/pIeA==","signatures":[{"sig":"MEUCIBKND7Hcdolt+aL9tFqmxn7uTgHO2mI71/thY2fkm8lAAiEA2B2Djf0JNx+mb2iu6TilIK0LJkRMhEERHyUrUGdvR9o=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.4","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1569912},"type":"module","_from":"file:bymax-one-nest-auth-1.0.4.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/cb125bb634d111f81148900c20517c1d/bymax-one-nest-auth-1.0.4.tgz","_integrity":"sha512-/3WwKviPGgzNzSM5jIf1DFIqPNpID9OFN+kFD/wste0MCWkNfnMJt4828KTsF+w9cjgguWk5/80fuw4kX/pIeA==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.4_1779759197865_0.6942164003363391","host":"s3://npm-registry-packages-npm-production"}},"1.0.5":{"name":"@bymax-one/nest-auth","version":"1.0.5","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.5","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"6c99f0b44174f46109a84146256ca2585f5ddd50","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.5.tgz","fileCount":24,"integrity":"sha512-qyV1LAZKV2YsbaJPNgli3+15rruXsrPEUvwjhgf7I6mS7zyHoH0tGi4Q1PLjlZkHZ9lFiBPXsxdSV3SDxx2QhQ==","signatures":[{"sig":"MEYCIQCLuR0I+Yay/71jbanUTcGj9lacWMgyWxOXsnmBUzQ94wIhAL90D2nIBL/eS6jh+QVI7Ofzh7e2fi7bKyY1oovnOgo5","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.5","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1578966},"type":"module","_from":"file:bymax-one-nest-auth-1.0.5.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/93c1c50f62e883ff473f69994a2851c5/bymax-one-nest-auth-1.0.5.tgz","_integrity":"sha512-qyV1LAZKV2YsbaJPNgli3+15rruXsrPEUvwjhgf7I6mS7zyHoH0tGi4Q1PLjlZkHZ9lFiBPXsxdSV3SDxx2QhQ==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.5_1779804824596_0.23699050013453737","host":"s3://npm-registry-packages-npm-production"}},"1.0.6":{"name":"@bymax-one/nest-auth","version":"1.0.6","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.6","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"2a7050fb129511a6ed3ce5e251d7c80cddc21173","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.6.tgz","fileCount":24,"integrity":"sha512-tNSReGePvwlw2+tn9I7dDUwgyrputDPvOgGuhies4sTIAiVEgqINi2XkCdENmx8t1TkMjyS/OTvqocDzsXT43Q==","signatures":[{"sig":"MEQCIEeq7Hebg14bOifAHttmsQ1hEmjoq5pSi4fxVffEAKs3AiA+2bcn2ofzGKY22o0wRBIvq2x3aQ7GFubkFX0UKhz63w==","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.6","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1627415},"type":"module","_from":"file:bymax-one-nest-auth-1.0.6.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/25f42849b8394d0ca7bab6f38edcfeab/bymax-one-nest-auth-1.0.6.tgz","_integrity":"sha512-tNSReGePvwlw2+tn9I7dDUwgyrputDPvOgGuhies4sTIAiVEgqINi2XkCdENmx8t1TkMjyS/OTvqocDzsXT43Q==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.6_1779814044222_0.8757476293012627","host":"s3://npm-registry-packages-npm-production"}},"1.0.7":{"name":"@bymax-one/nest-auth","version":"1.0.7","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.7","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"598a3ee2a095a3e741743089817f78d27a6bc444","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.7.tgz","fileCount":24,"integrity":"sha512-6xzIixkj9HIHPPIwhBY1IVsTxScv62c++kdpNEWZYdZpalUlo0WP5fZJ6Olgr3sB9JVPknzgefwdtq2WQuX3ug==","signatures":[{"sig":"MEYCIQCS/6lYtvpT2cf7Xa5kVtDTK2JlVTBhudSK6D53NQYbkgIhAJ5QIYLRdzG/oucY4HEVcQKf2ZcsOveIM5hVbBLWANd9","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.7","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1661903},"type":"module","_from":"file:bymax-one-nest-auth-1.0.7.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/b60b3e9120031a9a2e41bdc0edea6046/bymax-one-nest-auth-1.0.7.tgz","_integrity":"sha512-6xzIixkj9HIHPPIwhBY1IVsTxScv62c++kdpNEWZYdZpalUlo0WP5fZJ6Olgr3sB9JVPknzgefwdtq2WQuX3ug==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.7_1779821763108_0.01681602908617852","host":"s3://npm-registry-packages-npm-production"}},"1.0.8":{"name":"@bymax-one/nest-auth","version":"1.0.8","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.8","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"77c8ce23d8b0847acf326249f12252e3882c76c3","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.8.tgz","fileCount":24,"integrity":"sha512-ncN6XRTZ+i5C4hkG1NJ6nT0flySsjPbxDL49lti5Hs/6EkieJe9B0xYRiENiSAmd66p1ZYmdq4DDSyAOJzTXBQ==","signatures":[{"sig":"MEUCIBAxyL9I5mk14YeS6lANcPb/xWJ8rz3fwuYoHruUXQ4AAiEAmI2xCjDvzkj6O0VHAPkgCNA91gn4RUrUQDCzg9SZMTQ=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.8","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1676063},"type":"module","_from":"file:bymax-one-nest-auth-1.0.8.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/b88ac792a94c8b844f9a71b879ceb02f/bymax-one-nest-auth-1.0.8.tgz","_integrity":"sha512-ncN6XRTZ+i5C4hkG1NJ6nT0flySsjPbxDL49lti5Hs/6EkieJe9B0xYRiENiSAmd66p1ZYmdq4DDSyAOJzTXBQ==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.8_1779825718486_0.6648906512827455","host":"s3://npm-registry-packages-npm-production"}},"1.0.9":{"name":"@bymax-one/nest-auth","version":"1.0.9","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.9","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"af21797e40581ed74239707225e47b6e7f080721","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.9.tgz","fileCount":24,"integrity":"sha512-t/FBObyPrlSa8wOSkRbAcIb5KtGl14CEeEQBIqvD22KIZr2+57lm2xPj8O/t0B5Dyy9/EzaAOU7sXuf3ptqHfQ==","signatures":[{"sig":"MEYCIQC03vygCZ0GHaAitobUxBwfwvyPj1UNAPMX2fjXXYD/cAIhAN8tpttfYtd8+f0lpaxuMzw+fuaW3xDTFjZJO/Fw2vqb","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.9","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1682830},"type":"module","_from":"file:bymax-one-nest-auth-1.0.9.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/52f53439594baf91c0bdbe9604b3597d/bymax-one-nest-auth-1.0.9.tgz","_integrity":"sha512-t/FBObyPrlSa8wOSkRbAcIb5KtGl14CEeEQBIqvD22KIZr2+57lm2xPj8O/t0B5Dyy9/EzaAOU7sXuf3ptqHfQ==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","jscpd":"4.2.3","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","size-limit":"12.1.0","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@size-limit/preset-small-lib":"12.1.0","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.9_1779828617288_0.27435229639627456","host":"s3://npm-registry-packages-npm-production"}},"1.0.10":{"name":"@bymax-one/nest-auth","version":"1.0.10","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.10","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"1a92ed395ae771dec2bd0c0afc57551d506a64c6","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.10.tgz","fileCount":24,"integrity":"sha512-VFG/9F0aUXvlsQIaDNPZzDVYjLEq/Fn6YJ7s3IptsYl+RY5QLkjoAgBtagCnEqISS6ivBaxgtok5RTW/VRQgtQ==","signatures":[{"sig":"MEUCIQDhxfnFgo4R1l5Ezf0Pon1GBS/c1vksuJRpy0vsD5Z2xQIgW7t2I93yp4y09hXWeRXylhn4EL2NhtmII9X5OA7+fTk=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.10","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1700140},"type":"module","_from":"file:bymax-one-nest-auth-1.0.10.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/1b9fc0509743126c5f7fa3d20a899e02/bymax-one-nest-auth-1.0.10.tgz","_integrity":"sha512-VFG/9F0aUXvlsQIaDNPZzDVYjLEq/Fn6YJ7s3IptsYl+RY5QLkjoAgBtagCnEqISS6ivBaxgtok5RTW/VRQgtQ==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.12.1","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"sideEffects":false,"_nodeVersion":"24.15.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","jscpd":"4.2.3","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"^1.15.33","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","size-limit":"12.1.0","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^25.7.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@size-limit/preset-small-lib":"12.1.0","@stryker-mutator/jest-runner":"^9","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.10_1779831263353_0.2137306394527989","host":"s3://npm-registry-packages-npm-production"}},"1.0.11":{"name":"@bymax-one/nest-auth","version":"1.0.11","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.0.11","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"016e85c10ad84d3e22fbcbf3f2c55d9ce59bc148","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.0.11.tgz","fileCount":24,"integrity":"sha512-DwQGhjOhj25Rvg+sYKwn98bvI1jDT5Ey2VauFe7m9a2gyCpqjlj3VJcCE9Ez9TkDuMtebTUG+hzZZCW3k5KYog==","signatures":[{"sig":"MEMCHyfeFu9d9ABaqXkgIODmUNMMsk1JNncQialRb25V7CgCIB2zmcXS8gG6z5hGq70Yjw6eloi50CVl1FLzfTllpeQq","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.0.11","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":1701028},"type":"module","_from":"file:bymax-one-nest-auth-1.0.11.tgz","engines":{"node":">=24.0.0"},"exports":{".":{"types":"./dist/server/index.d.ts","import":"./dist/server/index.mjs","require":"./dist/server/index.cjs"},"./react":{"types":"./dist/react/index.d.ts","import":"./dist/react/index.mjs","require":"./dist/react/index.cjs"},"./client":{"types":"./dist/client/index.d.ts","import":"./dist/client/index.mjs","require":"./dist/client/index.cjs"},"./nextjs":{"types":"./dist/nextjs/index.d.ts","import":"./dist/nextjs/index.mjs","require":"./dist/nextjs/index.cjs"},"./shared":{"types":"./dist/shared/index.d.ts","import":"./dist/shared/index.mjs","require":"./dist/shared/index.cjs"}},"scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","release":"pnpm publish --provenance","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","test:cov:all":"jest --config jest.coverage.config.ts --coverage","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"_resolved":"/tmp/3744191549445e3c5e1941cafc1d56d3/bymax-one-nest-auth-1.0.11.tgz","_integrity":"sha512-DwQGhjOhj25Rvg+sYKwn98bvI1jDT5Ey2VauFe7m9a2gyCpqjlj3VJcCE9Ez9TkDuMtebTUG+hzZZCW3k5KYog==","repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.13.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.16.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/"},"_hasShrinkwrap":false,"devDependencies":{"jest":"^30.4.2","next":"^16.2.6","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^15.2.10","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^19.6.0","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@stryker-mutator/core":"^9","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^19.6.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.0.0","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","@nestjs/core":"^11.0.0","@nestjs/common":"^11.0.0","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.0.11_1780166235269_0.1471252642646892","host":"s3://npm-registry-packages-npm-production"}},"1.1.0":{"name":"@bymax-one/nest-auth","version":"1.1.0","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.1.0","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"72431ca86153c1521af6e4613ab1138dc56663b3","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.1.0.tgz","fileCount":24,"integrity":"sha512-JszocrMhNQmHw6UiQmdAPQbAAdlprHRqSMU3k4JGOO1RCBnOZjPfUWLj66vo2wWt0wKRk30Yf7smbTfvXbxujg==","signatures":[{"sig":"MEUCIQCOXANlebeaRcDuXa9UDabWlGObEcvCx7PnHEq332NmpAIgDZ+Ez0aJ4377IwDEeAUgmZm7jveqxud4UiOi7J8ohtQ=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.1.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2505265},"main":"./dist/server/index.cjs","pnpm":{"overrides":{"tmp@<0.2.6":">=0.2.6","ws@<8.20.1":">=8.20.1","sharp@<0.35.0":">=0.35.0","postcss@<8.5.10":">=8.5.10","qs@>=6.11.1 <=6.15.1":">=6.15.2","brace-expansion@<5.0.6":">=5.0.6","esbuild@>=0.27.3 <0.28.1":">=0.28.1"}},"type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"77dd23ee68c5a2790294cf70b7f41b5bc268fb7f","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@10.8.1","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.1.0_1785858616099_0.4092939477636941","host":"s3://npm-registry-packages-npm-production"}},"1.1.1":{"name":"@bymax-one/nest-auth","version":"1.1.1","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.1.1","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"c393f05fa13982ab36fb71fc5fc4e2c975559987","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.1.1.tgz","fileCount":24,"integrity":"sha512-iDKLZnrpayoL5sbR5ylFOsPTxApCmRvkfS3p1pG+dr9h5so/Uef8gaBPmkQa9VLqCIyK83PVewQRa1Buo/ujNg==","signatures":[{"sig":"MEYCIQCvqOOTj64MW3mmQPJ4K4/KoTHqPi8EjDstCyWyZw+KlAIhAK3Rv7jv54XpwBzzbRpNZNi+eSKVR4QI6cS+bthm411I","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.1.1","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2539901},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"cf12e09482ea38e36d61dfa7a116a8fa25584300","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly","mutation:incremental":"stryker run --incremental"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.40","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.1.1_1786194420807_0.811192451465998","host":"s3://npm-registry-packages-npm-production"}},"1.2.0":{"name":"@bymax-one/nest-auth","version":"1.2.0","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.2.0","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"1091856440bb7ba84e996e07d965b139de04165c","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.2.0.tgz","fileCount":24,"integrity":"sha512-Itp3+bS3ebR8V81Fy2dWWhFCR/quCYiDilb5L8/lUKKbP/T3Re/WW2nDC3dF8Hpe/5Hq+hYVXT72Ila1hvqvlA==","signatures":[{"sig":"MEUCIQCPWa5ZgRmSJ1GLGTtywHq1bJNE/9wsMPhstVEgVNQKWwIgUpd1b6N5/kdfbtPQ9EXv1sFXiqHfU5680ay2p1oFb6c=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.2.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2612476},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"55cf7a1106df7f3c4161cd76e02861cbd5b00d69","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.40","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.2.0_1786195787496_0.6554050936424602","host":"s3://npm-registry-packages-npm-production"}},"1.3.0":{"name":"@bymax-one/nest-auth","version":"1.3.0","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.3.0","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"6e0aea79b02884bb4ffa211f1948bb119a5c0f36","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.3.0.tgz","fileCount":24,"integrity":"sha512-+GhNbNJ3RR3AI1d6Ou2QIqL5PmKPit6cHB61yz8d3dhxvHIjAgRe9jFjHY6Tt+OmVHDT1Bsxzg2b2Xnsw1atXg==","signatures":[{"sig":"MEUCIHlR9r/J1KC0XwDpmvMMnvCuTLauCiJJIepnlKFXHzfMAiEA1+TVsnRBIW93wzfKnIHmdwS0hsQfqeTTl1BFvRPPLl8=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.3.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2618142},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"4ff623ad1e96af6a3dde7825b6494d5a62d980b6","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.40","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.3.0_1786206020888_0.5685741446947064","host":"s3://npm-registry-packages-npm-production"}},"1.3.1":{"name":"@bymax-one/nest-auth","version":"1.3.1","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.3.1","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"e1fb8329d9b445f1fc306b61cda249825b81a1cf","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.3.1.tgz","fileCount":24,"integrity":"sha512-VzOmS9+pA9czI5uBa9m8TqjsBmoDHlVRZXsUUOcwuqYLRGTNfkNAZI4Qdm/WeMUmdHUJg1+AHLCkEGDTV6l1wA==","signatures":[{"sig":"MEYCIQCJwIKq9Ce8rYpRhJrhLCggrQe4ZqrEcsRcl/R9GBaFiwIhAN60pU/42d80PcYA0LrSZNBDvt0ih9S6GR5qMTy5AmXm","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.3.1","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2672354},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"ef1c6b392a67fbd25619e3a06c702e3b2cab78cb","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.40","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.3.1_1786229815443_0.5053440619035254","host":"s3://npm-registry-packages-npm-production"}},"1.3.2":{"name":"@bymax-one/nest-auth","version":"1.3.2","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.3.2","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"333a529b5121a5c7fd381bd8a5b273d990a4877d","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.3.2.tgz","fileCount":24,"integrity":"sha512-egAxUNLbMHAKCnM7YfE8cXSb6MT8zfukai8bXDyAFwpZ0cxEOqOFULXjop/gx6V5T9sGUYUGgOHFTbaMOXBPAw==","signatures":[{"sig":"MEYCIQCC9bGQAQU7DrYhLGVWcF53jlLLLir+n+XZn+x6j+N+ogIhAIQAZWpZlcOuMzF0uMkRq1Ajbmda0Jz8s9VtgOJCBUgA","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.3.2","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2729657},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"65d8bd19c7a184739bb82d5f4c0c44d20d24bff0","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^5.10.1","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.47","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^5.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.3.2_1786381441692_0.6935023335379016","host":"s3://npm-registry-packages-npm-production"}},"1.4.0":{"name":"@bymax-one/nest-auth","version":"1.4.0","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.4.0","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"c849730ac572dab5ad50dbe4f5b2de77515c913a","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.4.0.tgz","fileCount":24,"integrity":"sha512-gQzxIpQUlQQm6WV+g5P5M1atiGliycwDX0VuvpFthguPk1yXJfbNkbhSz7TwZ4Sg1bWv51P+9gr2jYNfFpUerQ==","signatures":[{"sig":"MEUCIQDwBzb9eurxdSxEyEuABa/JXCgVOVGk5ICOCVh113lRfgIgUE3WEQ1b0ksFQg0eH2MRXYDMTf/FeNxqwrm+gMZsiwo=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.4.0","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2731499},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"00416d77a8d1492fe963235e4cbd0d71aec69339","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^6.0.0","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.47","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^6.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.4.0_1786446053650_0.57516812382993","host":"s3://npm-registry-packages-npm-production"}},"1.4.1":{"name":"@bymax-one/nest-auth","version":"1.4.1","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.4.1","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"17b5235bd9c133340eaae3a013c29a86dea21d3e","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.4.1.tgz","fileCount":24,"integrity":"sha512-vRnpaIq3rc9PjMLslTcz+RRp9TB3qngsZIck3ZGvPaV2pOIoMf0MhQgatz+vRJA2Witq9RscJG1prBdvWJtU9Q==","signatures":[{"sig":"MEUCIQC83Z7sxoi42FlBZjF2uX+0ieZWvU2SreQgoJ0TzBINJgIgGdo1cI2dBFBSUQtsVF67Y3MVwcgKfDDNMsYkdNVcayE=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.4.1","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2753269},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"b6b73d3532b55dfd8707ca218bccb3e2a3899e3c","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^6.0.0","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.47","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^6.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.4.1_1786566631796_0.5252349233137168","host":"s3://npm-registry-packages-npm-production"}},"1.4.2":{"name":"@bymax-one/nest-auth","version":"1.4.2","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.4.2","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"50ca1614e3bfb9562c56635bd23cb8bab237bc2d","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.4.2.tgz","fileCount":24,"integrity":"sha512-5cvo6N9Zky9t5Kk48nh0a0YP1/MYOzqPsHjoPAAObkXsByTfa0u37UtjtFAb3UVbthgX7FKRC5/SwPoqKDhg3A==","signatures":[{"sig":"MEYCIQDCK5R2WASoKJZDmQ3LA3dhUHBEYB0sMJNyz2/Qw0WDOQIhANZxBFFj/3zD78qXNTJftIoLBNS8C2RqcSDspBn3hOG/","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.4.2","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2761084},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"c3fd98fc6e03c9b687d29538640cdc35c5b9d962","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly","gen:openapi-schemas":"UPDATE_OPENAPI_SCHEMAS=1 jest src/server/openapi/request-schemas.conformance.spec.ts"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.16.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.18.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^6.0.0","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.47","react-dom":"^19.2.6","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^6.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.4.2_1786643392322_0.5851443939625955","host":"s3://npm-registry-packages-npm-production"}},"1.4.3":{"name":"@bymax-one/nest-auth","version":"1.4.3","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.4.3","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"eda8e3f281d5bc0e28abbfc3b7f532daad45cb67","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.4.3.tgz","fileCount":24,"integrity":"sha512-xgruf2JcQsTAWYSs+fk4r8Pq2xuOfXJT1WBGi3h1uR5tum4NDLp+xsbzznU5GUnxdwSDY6olgsioPKcHGTB2oQ==","signatures":[{"sig":"MEYCIQCg57jVJkziI29CGhJ/Wp/kvkkCMh6FGMfAN/Lk7oK2uwIhALhcEy2neSnSFwQeQ/Ezu87C2GYCeor1Nm9ODkIrM3Iu","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.4.3","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":2918610},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"7a84880a2b5b6535a4d5456ef4fcc3c2833c2d1e","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly","gen:openapi-schemas":"UPDATE_OPENAPI_SCHEMAS=1 jest src/server/openapi/request-schemas.conformance.spec.ts"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.17.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.19.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"ws":"^8.21.3","jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^6.0.0","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.15.47","@types/ws":"^8.18.1","react-dom":"^19.2.6","socket.io":"^4.8.3","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","socket.io-client":"^4.8.3","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","@nestjs/platform-ws":"^11.1.29","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^9","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@nestjs/platform-socket.io":"^11.1.29","@stryker-mutator/jest-runner":"^9","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^9"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^6.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.4.3_1786795135592_0.37579054568855774","host":"s3://npm-registry-packages-npm-production"}},"1.4.4":{"name":"@bymax-one/nest-auth","version":"1.4.4","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","_id":"@bymax-one/nest-auth@1.4.4","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"homepage":"https://github.com/bymaxone/nest-auth#readme","bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"dist":{"shasum":"4027247716c3012666b2aea25cc15b3dbc14c955","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.4.4.tgz","fileCount":24,"integrity":"sha512-K+QqiB/cLYP6x7HFhpIHz5gpr5UGG+RHOGz1sNvlbAxMr1QsjwbxQ5GXP6uc5+FtzfTbRC1K5p7/3SimmKGrFw==","signatures":[{"sig":"MEUCIQCWKdBvleUGnBcAx6Uo4D+ylqG4ERln8Z5mi5/+S7jYewIgAxS0qRhf5wt+l5bQ1/ZFwoQNa9rWRhdlxrOEW0xsb3g=","keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U"}],"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.4.4","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"unpackedSize":3207448},"main":"./dist/server/index.cjs","type":"module","types":"./dist/server/index.d.cts","module":"./dist/server/index.mjs","engines":{"node":">=24.0.0"},"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./package.json":"./package.json"},"gitHead":"fe3d83b700e0b2a92bebe59f7ada9402f58741ef","scripts":{"lint":"eslint src","size":"node scripts/check-size.mjs","test":"jest","build":"pnpm clean && tsup","clean":"rm -rf dist coverage","format":"prettier --write .","prepare":"husky","release":"npm publish --provenance --access public","lint:fix":"eslint src --fix","mutation":"stryker run","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:e2e":"jest --config jest.e2e.config.ts","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json","test:watch":"jest --watch","format:check":"prettier --check .","test:cov:all":"jest --config jest.coverage.config.ts --coverage","check:exports":"node scripts/check-exports.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","check:published":"node scripts/check-published-surface.mjs","mutation:dry-run":"stryker run --dryRunOnly","gen:openapi-schemas":"UPDATE_OPENAPI_SCHEMAS=1 jest src/server/openapi/request-schemas.conformance.spec.ts"},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"repository":{"url":"git+https://github.com/bymaxone/nest-auth.git","type":"git"},"_npmVersion":"11.17.0","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","directories":{},"lint-staged":{"*.{json,md,yml,yaml}":["prettier --write"],"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"]},"sideEffects":false,"_nodeVersion":"24.19.0","publishConfig":{"access":"public","registry":"https://registry.npmjs.org/","provenance":true},"typesVersions":{"*":{"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"]}},"_hasShrinkwrap":false,"packageManager":"pnpm@11.20.0","devDependencies":{"ws":"^8.21.3","jest":"^30.4.2","next":"^16.2.11","tsup":"^8.5.1","husky":"^9.1.7","react":"^19.2.6","eslint":"^9.39.4","globals":"^17.6.0","ioredis":"^6.0.0","ts-jest":"^29.4.9","ts-node":"^10.9.2","prettier":"^3.8.3","@swc/core":"1.16.0","@types/ws":"^8.18.1","react-dom":"^19.2.6","socket.io":"^4.8.3","supertest":"^7.2.2","@eslint/js":"^9.39.4","typescript":"^5.9.3","@nestjs/jwt":"^11.0.2","@types/jest":"^30.0.0","@types/node":"^24","lint-staged":"^17.2.0","@nestjs/core":"^11.1.20","@types/react":"^19.2.14","ioredis-mock":"^8.13.1","@nestjs/common":"^11.1.20","@types/express":"^5.0.6","@commitlint/cli":"^21.2.1","@nestjs/testing":"^11.1.20","class-validator":"^0.15.1","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","reflect-metadata":"^0.2.2","socket.io-client":"^4.8.3","@nestjs/throttler":"^6.5.0","class-transformer":"^0.5.1","@nestjs/websockets":"^11.1.20","@nestjs/platform-ws":"^11.1.29","eslint-plugin-import":"^2.32.0","@arethetypeswrong/cli":"^0.18.2","@stryker-mutator/core":"^10.0.0","jest-environment-node":"^30.4.1","@testing-library/react":"^16.3.2","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","jest-environment-jsdom":"^30.4.1","@nestjs/platform-express":"^11.1.20","@typescript-eslint/parser":"^8.59.3","@nestjs/platform-socket.io":"^11.1.29","@stryker-mutator/jest-runner":"^10.0.0","@commitlint/config-conventional":"^21.2.0","@typescript-eslint/eslint-plugin":"^8.59.3","eslint-import-resolver-typescript":"^4.4.4","@stryker-mutator/typescript-checker":"^10.0.0"},"peerDependencies":{"next":"^16.2.11","react":"^19.0.0","express":"^5.0.0","ioredis":"^6.0.0","@nestjs/jwt":"^11.0.0","server-only":"^0.0.1","@nestjs/core":"^11.1.18","@nestjs/common":"^11.0.16","@types/express":"^5.0.0","class-validator":"^0.14.0 || ^0.15.0","reflect-metadata":"^0.2.0","@nestjs/throttler":"^6.0.0","class-transformer":"^0.5.0","@nestjs/websockets":"^11.0.0"},"peerDependenciesMeta":{"next":{"optional":true},"react":{"optional":true},"express":{"optional":true},"ioredis":{"optional":true},"@nestjs/jwt":{"optional":true},"server-only":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/common":{"optional":true},"@types/express":{"optional":true},"class-validator":{"optional":true},"reflect-metadata":{"optional":true},"@nestjs/throttler":{"optional":true},"class-transformer":{"optional":true},"@nestjs/websockets":{"optional":true}},"_npmOperationalInternal":{"tmp":"tmp/nest-auth_1.4.4_1787173152512_0.9054747114528028","host":"s3://npm-registry-packages-npm-production"}},"1.4.5":{"name":"@bymax-one/nest-auth","version":"1.4.5","description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","homepage":"https://github.com/bymaxone/nest-auth#readme","repository":{"type":"git","url":"git+https://github.com/bymaxone/nest-auth.git"},"bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"type":"module","sideEffects":false,"exports":{".":{"import":{"types":"./dist/server/index.d.ts","default":"./dist/server/index.mjs"},"require":{"types":"./dist/server/index.d.cts","default":"./dist/server/index.cjs"}},"./shared":{"import":{"types":"./dist/shared/index.d.ts","default":"./dist/shared/index.mjs"},"require":{"types":"./dist/shared/index.d.cts","default":"./dist/shared/index.cjs"}},"./client":{"import":{"types":"./dist/client/index.d.ts","default":"./dist/client/index.mjs"},"require":{"types":"./dist/client/index.d.cts","default":"./dist/client/index.cjs"}},"./react":{"import":{"types":"./dist/react/index.d.ts","default":"./dist/react/index.mjs"},"require":{"types":"./dist/react/index.d.cts","default":"./dist/react/index.cjs"}},"./nextjs":{"import":{"types":"./dist/nextjs/index.d.ts","default":"./dist/nextjs/index.mjs"},"require":{"types":"./dist/nextjs/index.d.cts","default":"./dist/nextjs/index.cjs"}},"./package.json":"./package.json"},"scripts":{"build":"pnpm clean && tsup","check:exports":"node scripts/check-exports.mjs","check:published":"node scripts/check-published-surface.mjs","check:runtime":"node scripts/check-consumer-runtime.mjs","clean":"rm -rf dist coverage","format":"prettier --write .","gen:openapi-schemas":"UPDATE_OPENAPI_SCHEMAS=1 jest src/server/openapi/request-schemas.conformance.spec.ts","format:check":"prettier --check .","lint":"eslint src","lint:fix":"eslint src --fix","mutation":"stryker run","mutation:full":"node -e \"require('node:fs').rmSync('reports/stryker-incremental.json',{force:true,recursive:true})\" && stryker run","mutation:dry-run":"stryker run --dryRunOnly","prepare":"husky","prepublishOnly":"pnpm clean && pnpm typecheck && pnpm lint && pnpm test:cov:all && pnpm build && pnpm size && pnpm check:exports && pnpm check:published && pnpm check:runtime","release":"npm publish --provenance --access public","size":"node scripts/check-size.mjs","test":"jest","test:all":"pnpm test && pnpm test:e2e","test:cov":"jest --coverage","test:cov:all":"jest --config jest.coverage.config.ts --coverage","test:e2e":"jest --config jest.e2e.config.ts","test:watch":"jest --watch","typecheck":"tsc --noEmit && tsc --noEmit -p tsconfig.server.json"},"lint-staged":{"*.{ts,tsx,js,mjs,cjs}":["eslint --fix","prettier --write"],"*.{json,md,yml,yaml}":["prettier --write"]},"peerDependencies":{"@nestjs/common":"^11.0.16","@nestjs/core":"^11.1.18","@nestjs/jwt":"^11.0.0","@nestjs/throttler":"^6.0.0","@nestjs/websockets":"^11.0.0","@types/express":"^5.0.0","class-transformer":"^0.5.0","class-validator":"^0.14.0 || ^0.15.0","express":"^5.0.0","ioredis":"^6.0.0","next":"^16.2.11","react":"^19.0.0","reflect-metadata":"^0.2.0","server-only":"^0.0.1"},"peerDependenciesMeta":{"@nestjs/common":{"optional":true},"@nestjs/core":{"optional":true},"@nestjs/jwt":{"optional":true},"@nestjs/throttler":{"optional":true},"@nestjs/websockets":{"optional":true},"class-transformer":{"optional":true},"class-validator":{"optional":true},"express":{"optional":true},"@types/express":{"optional":true},"ioredis":{"optional":true},"reflect-metadata":{"optional":true},"server-only":{"optional":true},"react":{"optional":true},"next":{"optional":true}},"devDependencies":{"@arethetypeswrong/cli":"^0.18.2","@commitlint/cli":"^21.2.1","@commitlint/config-conventional":"^21.2.0","@eslint/js":"^9.39.4","@nestjs/common":"^11.1.20","@nestjs/core":"^11.1.20","@nestjs/jwt":"^11.0.2","@nestjs/platform-express":"^11.1.20","@nestjs/platform-socket.io":"^11.1.29","@nestjs/platform-ws":"^11.1.29","@nestjs/testing":"^11.1.20","@nestjs/throttler":"^6.5.0","@nestjs/websockets":"^11.1.20","@stryker-mutator/core":"^10.0.0","@stryker-mutator/jest-runner":"^10.0.0","@stryker-mutator/typescript-checker":"^10.0.0","@swc/core":"1.16.1","@testing-library/react":"^16.3.2","@types/express":"^5.0.6","@types/jest":"^30.0.0","@types/node":"^24","@types/react":"^19.2.14","@types/react-dom":"^19.2.3","@types/supertest":"^7.2.0","@types/ws":"^8.18.1","@typescript-eslint/eslint-plugin":"^8.59.3","@typescript-eslint/parser":"^8.59.3","class-transformer":"^0.5.1","class-validator":"^0.15.1","eslint":"^9.39.4","eslint-config-prettier":"^10.1.8","eslint-import-resolver-typescript":"^4.4.4","eslint-plugin-import":"^2.32.0","eslint-plugin-prettier":"^5.5.5","eslint-plugin-security":"^4.0.0","globals":"^17.6.0","husky":"^9.1.7","ioredis":"^6.0.0","ioredis-mock":"^8.13.1","jest":"^30.4.2","jest-environment-jsdom":"^30.4.1","jest-environment-node":"^30.4.1","lint-staged":"^17.2.0","next":"^16.2.11","prettier":"^3.8.3","react":"^19.2.6","react-dom":"^19.2.6","reflect-metadata":"^0.2.2","socket.io":"^4.8.3","socket.io-client":"^4.8.3","supertest":"^7.2.2","ts-jest":"^29.4.9","ts-node":"^10.9.2","tsup":"^8.5.1","typescript":"^5.9.3","ws":"^8.21.3"},"keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"packageManager":"pnpm@11.20.0","engines":{"node":">=24.0.0"},"publishConfig":{"access":"public","provenance":true,"registry":"https://registry.npmjs.org/"},"main":"./dist/server/index.cjs","module":"./dist/server/index.mjs","types":"./dist/server/index.d.cts","typesVersions":{"*":{"dist/server/index.d.cts":["./dist/server/index.d.cts","./dist/server/index.d.ts"],"shared":["./dist/shared/index.d.cts","./dist/shared/index.d.ts"],"client":["./dist/client/index.d.cts","./dist/client/index.d.ts"],"react":["./dist/react/index.d.cts","./dist/react/index.d.ts"],"nextjs":["./dist/nextjs/index.d.cts","./dist/nextjs/index.d.ts"]}},"gitHead":"0481007964f3b10717282ee8b8066fa1b51f6288","_id":"@bymax-one/nest-auth@1.4.5","_nodeVersion":"24.19.0","_npmVersion":"11.17.0","dist":{"integrity":"sha512-tWGZ6RY27FIastrqL4UJpW1nfmoXQ+ad5LJvVULPS5lJqUhSgide1kfDFChdzDKT2ZcDLgGbXcg2dDmn/gu3PA==","shasum":"19f6e15efa05fbe00dc4d9aaa60f5a3149cb7d51","tarball":"https://registry.npmjs.org/@bymax-one/nest-auth/-/nest-auth-1.4.5.tgz","fileCount":24,"unpackedSize":3216582,"attestations":{"url":"https://registry.npmjs.org/-/npm/v1/attestations/@bymax-one%2fnest-auth@1.4.5","provenance":{"predicateType":"https://slsa.dev/provenance/v1"}},"signatures":[{"keyid":"SHA256:DhQ8wR5APBvFHLF/+Tc+AYvPOdTpcIDqOhxsBHRwC7U","sig":"MEUCIQD7nBIjrxUQSHKnYW2L6XcMN630BJ5ACXYroc8X3UWdGwIgPs9/5AZ4Tk8oCPVCPKnnvyUAq875uLuhzAHKO5MdRVw="}]},"_npmUser":{"name":"GitHub Actions","email":"npm-oidc-no-reply@github.com","trustedPublisher":{"id":"github","oidcConfigId":"oidc:e43552ab-03a9-4ea4-af81-3abb0463bd7f"}},"directories":{},"maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages-npm-production","tmp":"tmp/nest-auth_1.4.5_1788092682978_0.696705184593676"},"_hasShrinkwrap":false}},"time":{"created":"2026-05-25T20:09:50.737Z","modified":"2026-08-30T12:24:43.640Z","1.0.0":"2026-05-25T20:09:51.132Z","1.0.1":"2026-05-25T20:29:46.282Z","1.0.2":"2026-05-25T21:21:26.999Z","1.0.3":"2026-05-26T00:37:29.313Z","1.0.4":"2026-05-26T01:33:18.043Z","1.0.5":"2026-05-26T14:13:44.739Z","1.0.6":"2026-05-26T16:47:24.521Z","1.0.7":"2026-05-26T18:56:03.319Z","1.0.8":"2026-05-26T20:01:58.696Z","1.0.9":"2026-05-26T20:50:17.489Z","1.0.10":"2026-05-26T21:34:23.595Z","1.0.11":"2026-05-30T18:37:15.434Z","1.1.0":"2026-08-04T15:50:16.273Z","1.1.1":"2026-08-08T13:07:00.981Z","1.2.0":"2026-08-08T13:29:47.691Z","1.3.0":"2026-08-08T16:20:21.068Z","1.3.1":"2026-08-08T22:56:55.613Z","1.3.2":"2026-08-10T17:04:01.856Z","1.4.0":"2026-08-11T11:00:53.810Z","1.4.1":"2026-08-12T20:30:31.985Z","1.4.2":"2026-08-13T17:49:52.510Z","1.4.3":"2026-08-15T11:58:55.772Z","1.4.4":"2026-08-19T20:59:12.691Z","1.4.5":"2026-08-30T12:24:43.266Z"},"bugs":{"url":"https://github.com/bymaxone/nest-auth/issues"},"author":{"name":"Bymax One","email":"support@bymax.one"},"license":"MIT","homepage":"https://github.com/bymaxone/nest-auth#readme","keywords":["nestjs","auth","authentication","authorization","jwt","mfa","totp","oauth","saas","multi-tenant","nextjs","react","session","rbac","brute-force","password-reset","refresh-token"],"repository":{"type":"git","url":"git+https://github.com/bymaxone/nest-auth.git"},"description":"Full-stack authentication and authorization package for NestJS, React and Next.js — JWT, MFA, OAuth, sessions, multi-tenant SaaS ready","maintainers":[{"name":"bymax.one","email":"bymaxone.core@gmail.com"},{"name":"msalvatti","email":"msalvatti@gmail.com"}],"readme":"<p align=\"center\">\n  <img src=\"https://img.shields.io/badge/%40bymax--one-nest--auth-000000?style=for-the-badge&logo=nestjs&logoColor=E0234E\" alt=\"@bymax-one/nest-auth\" />\n</p>\n\n<h1 align=\"center\">@bymax-one/nest-auth</h1>\n\n<p align=\"center\">\n  <strong>Full-stack authentication for NestJS, React & Next.js</strong><br />\n  <sub>JWT · MFA · OAuth · Sessions · Multi-Tenant · Zero External Crypto Dependencies</sub>\n</p>\n\n<p align=\"center\">\n  <a href=\"https://www.npmjs.com/package/@bymax-one/nest-auth\"><img src=\"https://img.shields.io/npm/v/@bymax-one/nest-auth?style=flat-square&colorA=000000&colorB=000000\" alt=\"npm version\" /></a>\n  <a href=\"https://www.npmjs.com/package/@bymax-one/nest-auth\"><img src=\"https://img.shields.io/npm/dm/@bymax-one/nest-auth?style=flat-square&colorA=000000&colorB=000000\" alt=\"npm downloads\" /></a>\n  <a href=\"https://github.com/bymaxone/nest-auth/actions/workflows/ci.yml\"><img src=\"https://img.shields.io/github/actions/workflow/status/bymaxone/nest-auth/ci.yml?branch=main&style=flat-square&colorA=000000&label=CI\" alt=\"CI status\" /></a>\n  <a href=\"https://github.com/bymaxone/nest-auth/actions/workflows/ci.yml\"><img src=\"https://img.shields.io/badge/coverage-100%25-brightgreen?style=flat-square&colorA=000000\" alt=\"coverage\" /></a>\n  <a href=\"https://github.com/bymaxone/nest-auth/blob/main/docs/mutation_testing_results.md\"><img src=\"https://img.shields.io/badge/mutation-100%25-brightgreen?style=flat-square&colorA=000000\" alt=\"mutation score\" /></a>\n  <a href=\"https://scorecard.dev/viewer/?uri=github.com/bymaxone/nest-auth\"><img src=\"https://api.scorecard.dev/projects/github.com/bymaxone/nest-auth/badge?style=flat-square\" alt=\"OpenSSF Scorecard\" /></a>\n  <a href=\"https://github.com/bymaxone/nest-auth/blob/main/LICENSE\"><img src=\"https://img.shields.io/github/license/bymaxone/nest-auth?style=flat-square&colorA=000000&colorB=000000\" alt=\"license\" /></a>\n  <a href=\"https://www.typescriptlang.org/\"><img src=\"https://img.shields.io/badge/TypeScript-strict-3178C6?style=flat-square&logo=typescript&logoColor=white\" alt=\"TypeScript\" /></a>\n  <a href=\"https://nodejs.org/\"><img src=\"https://img.shields.io/badge/Node.js-24%2B-339933?style=flat-square&logo=node.js&logoColor=white\" alt=\"Node.js\" /></a>\n</p>\n\n<p align=\"center\">\n  <a href=\"https://github.com/bymaxone/nest-auth\">GitHub</a> ·\n  <a href=\"https://github.com/bymaxone/nest-auth/issues\">Issues</a> ·\n  <a href=\"#-quick-start\">Quick Start</a> ·\n  <a href=\"#-subpath-exports\">API Reference</a> ·\n  <a href=\"https://github.com/bymaxone/nest-auth-example\">Example App</a>\n</p>\n\n---\n\n## ✨ Overview\n\n`@bymax-one/nest-auth` is a **complete authentication and authorization solution** shipped as a single npm package with **5 subpath exports** — covering everything from NestJS backend guards to React hooks and Next.js route handlers.\n\nInstead of wiring together dozens of packages for JWT, MFA, OAuth, sessions, password reset, and brute-force protection, you install one library and get a production-ready auth system that works across your entire stack.\n\n### Why nest-auth?\n\n- **🎯 One package, full stack** — Backend module, shared types, fetch client, React hooks, and Next.js integration all in a single `pnpm add`. Types and constants are shared automatically between server and client — no manual synchronization.\n- **🔌 Your database, your rules** — The library defines TypeScript interfaces (`IUserRepository`, `IEmailProvider`). You implement them with your ORM of choice (Prisma, TypeORM, Drizzle). No vendor lock-in, no hidden database dependencies.\n- **🔒 Native crypto only** — All security-critical code (password hashing, MFA encryption, TOTP, token generation) runs on `node:crypto` — zero third-party crypto packages, so the most sensitive code paths carry no third-party supply-chain risk.\n- **⚡ Pay for what you use** — Features like MFA, sessions, OAuth, and platform admin are opt-in. When not configured, their controllers and services are never registered — zero overhead in your NestJS container.\n- **🏢 Multi-tenant ready** — Every operation is scoped by `tenantId`. Built for SaaS from day one, not bolted on as an afterthought.\n\n```\npnpm add @bymax-one/nest-auth\n```\n\n---\n\n## 🔥 Features\n\n### 🔐 Core Authentication\n\n- ✅ **Registration & Login** — Email/password with configurable validation\n- ✅ **JWT Access + Refresh Tokens** — Automatic rotation with grace window for concurrent requests\n- ✅ **Multi-Factor Authentication** — TOTP with QR code URI, recovery codes, and challenge flow\n- ✅ **OAuth 2.0** — Google out of the box, extensible via plugin interface\n- ✅ **Password Reset** — Token-based or OTP, configurable per deployment\n- ✅ **Email Verification** — OTP-based with configurable TTL\n\n### 🛡️ Security\n\n- ✅ **Zero External Crypto** — All cryptography via native `node:crypto` (scrypt, AES-256-GCM, HMAC-SHA1, TOTP)\n- ✅ **Brute-Force Protection** — Configurable rate limiting per email + tenant\n- ✅ **Session Management** — Track active sessions with FIFO eviction, and an `onNewSession` hook fired on every session created (alerting on it is yours to decide — see `sendNewSessionAlert`)\n- ✅ **HttpOnly Cookies** — Secure, SameSite, path-scoped refresh tokens by default\n- ✅ **Timing-Safe Comparisons** — All secret comparisons use `crypto.timingSafeEqual`\n- ✅ **JWT Revocation** — Instant access token revocation via Redis JTI blacklist\n- ✅ **Refresh-Token Reuse Detection** — Replaying a consumed token revokes that login's whole lineage, and only that lineage\n- ✅ **Bulk Access-Token Revocation** — A password reset advances a per-user token epoch, invalidating every outstanding access token in one write\n- ✅ **Absolute Session Lifetime** — Optional hard cap on how long one login can be extended by rotation\n- ✅ **Cross-Site Request Refusal** — Cookie-authenticated writes from an untrusted origin are rejected (matters under `SameSite=None`)\n- ✅ **Breached-Password Refusal** — Optional Have I Been Pwned check by k-anonymity range; the password never leaves the process\n- ✅ **Per-IP Rate Limiting** — Enforced by the library over Redis, so the limit holds across instances with no host wiring\n\n### 🏢 Multi-Tenant & Platform\n\n- ✅ **Tenant Isolation** — All operations scoped by `tenantId` with configurable resolver\n- ✅ **Platform Admin Auth** — Separate token context and role hierarchy for super-admins\n- ✅ **User Invitations** — Invite users with role assignment and configurable expiration\n- ✅ **Role-Based Access Control** — Hierarchical roles with `@Roles()` decorator\n\n### 🧩 Developer Experience\n\n- ✅ **Full-Stack TypeScript** — Strict types shared across server and client\n- ✅ **5 Subpath Exports** — Import only what you need, tree-shakeable\n- ✅ **Dynamic Module** — Configure everything via `registerAsync()`, sensible defaults included\n- ✅ **Interface-Driven** — Bring your own database and email provider\n- ✅ **No Passport Required** — Guards validate JWT natively via `@nestjs/jwt`\n\n---\n\n## 📦 Subpath Exports\n\nOne package, five entry points — import only what your app needs:\n\n| Subpath     | Import                        | Purpose                                     |    Dependencies    |\n| ----------- | ----------------------------- | ------------------------------------------- | :----------------: |\n| **Server**  | `@bymax-one/nest-auth`        | NestJS module, guards, decorators, services | NestJS 11, ioredis |\n| **Shared**  | `@bymax-one/nest-auth/shared` | Types, constants, error codes               |        None        |\n| **Client**  | `@bymax-one/nest-auth/client` | Fetch-based auth client                     |        None        |\n| **React**   | `@bymax-one/nest-auth/react`  | Hooks & AuthProvider                        |      React 19      |\n| **Next.js** | `@bymax-one/nest-auth/nextjs` | Proxy, route handlers, JWT helpers          |     Next.js 16     |\n\n```\nshared (zero deps)\n  ↗       ↖\nserver    client\n            ↑\n          react\n            ↑\n         nextjs\n```\n\n---\n\n> [!TIP]\n> Prefer to learn from a working app? See the [nest-auth-example](https://github.com/bymaxone/nest-auth-example) — a full NestJS + Next.js project wired with this library.\n\n## 🚀 Quick Start\n\n### 1. Install\n\n```bash\n# Using pnpm (recommended)\npnpm add @bymax-one/nest-auth\n\n# Using npm\nnpm install @bymax-one/nest-auth\n\n# Using yarn\nyarn add @bymax-one/nest-auth\n```\n\n> [!IMPORTANT]\n> You must also install the required **peer dependencies** for the subpaths you use:\n\n```bash\n# Server subpath (required)\npnpm add @nestjs/common @nestjs/core @nestjs/jwt @nestjs/throttler @nestjs/websockets ioredis class-validator class-transformer reflect-metadata\n\n# React subpath (optional)\npnpm add react\n\n# Next.js subpath (optional)\npnpm add next react server-only\n```\n\n> [!NOTE]\n> `server-only` is what makes importing the Next.js JWT helper from a Client Component a\n> **build error**. That module receives the HS256 secret, and a secret in a client chunk is a\n> secret published to every visitor — with nothing downstream to notice. It is a marker package\n> with no runtime behaviour, and Next.js's own documentation prescribes it for exactly this.\n\n> [!IMPORTANT]\n> Requires `@nestjs/throttler >= 6.0.0` for `AUTH_THROTTLE_CONFIGS` decorators to be honored.\n\n### 2. Implement the Repository Interface\n\nThe package defines **what** it needs — your app provides **how**. The consumer maps the abstract `AuthUser` fields onto its own database schema (column names, indexes, soft-delete columns are entirely up to you). The only invariant is that `passwordHash` MUST be persisted exactly as supplied by the library — it is the output of `node:crypto` scrypt and re-hashing or transforming it will break login.\n\n```typescript\n// user.repository.ts\nimport { Injectable } from '@nestjs/common'\nimport type {\n  AuthUser,\n  CreateUserData,\n  CreateWithOAuthData,\n  FindUserByEmailParams,\n  FindUserByOAuthIdParams,\n  IUserRepository,\n  LinkOAuthParams,\n  TenantScopedUserRef,\n  UpdateEmailParams,\n  UpdateEmailVerifiedParams,\n  UpdateMfaParams,\n  UpdatePasswordParams,\n  UpdateStatusParams\n} from '@bymax-one/nest-auth'\nimport { PrismaService } from './prisma.service'\n\n@Injectable()\nexport class PrismaUserRepository implements IUserRepository {\n  constructor(private readonly prisma: PrismaService) {}\n\n  async findById({ id, tenantId }: TenantScopedUserRef): Promise<AuthUser | null> {\n    // Both halves of the key, always. An id is unique only within a tenant, so `findUnique`\n    // by id alone can answer with another tenant's row.\n    return this.prisma.user.findFirst({ where: { id, tenantId } })\n  }\n\n  async findByEmail({ email, tenantId }: FindUserByEmailParams): Promise<AuthUser | null> {\n    return this.prisma.user.findUnique({\n      where: { email_tenantId: { email: email.toLowerCase(), tenantId } }\n    })\n  }\n\n  async create(data: CreateUserData): Promise<AuthUser> {\n    return this.prisma.user.create({\n      data: {\n        email: data.email.toLowerCase(),\n        name: data.name,\n        passwordHash: data.passwordHash,\n        role: data.role ?? 'user',\n        status: data.status ?? 'pending',\n        tenantId: data.tenantId,\n        emailVerified: data.emailVerified ?? false,\n        mfaEnabled: false\n      }\n    })\n  }\n\n  // Every mutator below uses `updateMany` rather than `update`, for one reason: `update` takes a\n  // UNIQUE where-clause, so it cannot accept `{ id, tenantId }` unless your schema declares that\n  // pair unique — and `update({ where: { id } })` is the tenant-blind write this port exists to\n  // prevent. `updateMany` accepts the compound filter and touches nothing outside the tenant.\n  async updatePassword({ id, tenantId, passwordHash }: UpdatePasswordParams): Promise<void> {\n    await this.prisma.user.updateMany({ where: { id, tenantId }, data: { passwordHash } })\n  }\n\n  async updateMfa({ id, tenantId, data }: UpdateMfaParams): Promise<void> {\n    await this.prisma.user.updateMany({\n      where: { id, tenantId },\n      data: {\n        mfaEnabled: data.mfaEnabled,\n        mfaSecret: data.mfaSecret,\n        mfaRecoveryCodes: data.mfaRecoveryCodes ?? []\n      }\n    })\n  }\n\n  async updateLastLogin({ id, tenantId }: TenantScopedUserRef): Promise<void> {\n    await this.prisma.user.updateMany({\n      where: { id, tenantId },\n      data: { lastLoginAt: new Date() }\n    })\n  }\n\n  async updateStatus({ id, tenantId, status }: UpdateStatusParams): Promise<void> {\n    await this.prisma.user.updateMany({ where: { id, tenantId }, data: { status } })\n  }\n\n  async updateEmailVerified({ id, tenantId, verified }: UpdateEmailVerifiedParams): Promise<void> {\n    await this.prisma.user.updateMany({\n      where: { id, tenantId },\n      data: { emailVerified: verified }\n    })\n  }\n\n  async updateEmail({ id, tenantId, email }: UpdateEmailParams): Promise<void> {\n    await this.prisma.user.updateMany({\n      where: { id, tenantId },\n      data: { email: email.toLowerCase() }\n    })\n  }\n\n  async findByOAuthId({\n    provider,\n    providerId,\n    tenantId\n  }: FindUserByOAuthIdParams): Promise<AuthUser | null> {\n    return this.prisma.user.findFirst({\n      where: { oauthProvider: provider, oauthProviderId: providerId, tenantId }\n    })\n  }\n\n  async linkOAuth({ id, tenantId, provider, providerId }: LinkOAuthParams): Promise<void> {\n    await this.prisma.user.updateMany({\n      where: { id, tenantId },\n      data: { oauthProvider: provider, oauthProviderId: providerId }\n    })\n  }\n\n  async createWithOAuth(data: CreateWithOAuthData): Promise<AuthUser> {\n    return this.prisma.user.create({\n      data: {\n        email: data.email.toLowerCase(),\n        name: data.name,\n        passwordHash: null,\n        role: data.role ?? 'user',\n        status: data.status ?? 'active',\n        tenantId: data.tenantId,\n        emailVerified: data.emailVerified ?? true,\n        oauthProvider: data.oauthProvider,\n        oauthProviderId: data.oauthProviderId,\n        mfaEnabled: false\n      }\n    })\n  }\n}\n```\n\n### 3. Implement the Email Provider Interface\n\nEmail delivery is fully delegated to the consumer — the library never imports a mailer SDK. Implement `IEmailProvider` with your transport of choice (Resend, SendGrid, SES, Nodemailer) and bind it to the `BYMAX_AUTH_EMAIL_PROVIDER` token.\n\n> [!WARNING]\n> Any user-supplied value (display name, tenant name, inviter name) interpolated into HTML email bodies MUST be escaped to prevent stored XSS in notification content. Tokens and OTPs are library-generated and safe, but `inviterName`, `tenantName`, device strings, and any consumer-supplied placeholder are attacker-controllable.\n\n> [!CAUTION]\n> **Never log the error your transport rejects with — it can contain the code you just sent.**\n> A policy, DLP or anti-spam relay answering `550` commonly **quotes the offending message body**,\n> so the error your `send()` throws carries the OTP or token this library rendered into it. Logging\n> that error, or attaching it as a `cause` to one you log, puts a working credential into your log\n> pipeline in clear text until it expires. Measured on a real relay, not hypothesised.\n>\n> This is your half: the library cannot reach inside your provider implementation.\n> **`describeChannelStatus` is exported for it** — the same helper the bundled provider uses on\n> every one of its own log lines, so you get the whole treatment rather than just redaction:\n>\n> ```typescript\n> import { describeChannelStatus } from '@bymax-one/nest-auth'\n>\n> async sendPasswordResetOtp(tenantId: string, email: string, otp: string): Promise<void> {\n>   try {\n>     await this.resend.emails.send({ /* ... */ })\n>   } catch (error: unknown) {\n>     // Never `logger.error(msg, error)` here, and never `new Error(msg, { cause: error })`\n>     // into something that logs — both carry the quoted body.\n>     this.logger.error(`reset OTP delivery failed: ${describeChannelStatus(error)}`)\n>     throw error\n>   }\n> }\n> ```\n>\n> Two functions, not one with a mode: which one you call IS the decision, and there is no\n> permissive default to inherit by forgetting.\n>\n> **`describeChannelStatus(error)` wherever the body rendered something you would withhold.** It\n> takes no secrets, and that is the guarantee rather than an omission — nothing the channel wrote\n> is published, so there is nothing to name. Redaction alone does not close this, and neither does\n> a length cap. A relay may quote the body it rejected in transfer encoding rather\n> than verbatim; base64 is the ordinary case and defeats both at once — substring matching finds\n> nothing because the credential's characters are not in the line, and the cap does not help\n> because the encoding runs from the body's first byte, so the code is in the first sentence.\n> Measured: a reset-code body is 96 base64 characters end to end, and the first 200 characters of\n> the line decode straight back to the OTP. Under `describeChannelStatus` NOTHING the channel wrote\n> reaches the line — not the message, not the `name`, not a status parsed off the front. Each of\n> those was tried and each fell: shape validation admits `MTIzNDU2`, the base64 of OTP `123456`;\n> and a status grammar admits `424-242`, an OTP grouped, publishing `424`. What you keep is which\n> message failed. What you lose is the transient-versus-permanent split, which your mail provider's\n> dashboard has and this library does not.\n>\n> **`describeError(error, [values])` for errors whose text you have a reason to trust**, where the\n> values you name appear the way you wrote them and redaction reaches them. The bundled provider\n> uses it nowhere — every one of its paths uses the opaque form, including the notices that\n> render nothing secret, because a relay may re-encode whatever it quotes and the recipient address\n> is in the message either way. If you can say the same about your channel, prefer\n> `describeChannelStatus` and keep this one for strings you built yourself.\n>\n> Neither reads `stack`, and neither reads the transport's own fields — nodemailer hangs the\n> server's full reply on `response`. Beyond that they differ, and the difference is the point:\n> `describeError` reads `name` and `message`, strips the values you named, caps the length and\n> removes control characters so a relay cannot forge extra records in a line-oriented pipeline.\n> `describeChannelStatus` reads **neither** — the only thing it touches is `cause`, walked to count\n> the links. Both walk that chain and never throw, whatever the transport's error does.\n>\n> `redactSecrets(text, [otp])` is exported too, for a string you built yourself and know contains\n> the literal value. It is **not** a substitute for either description on a transport's error: a\n> substring match cannot see through an encoding, which is the whole reason the bundled provider\n> stopped relying on it.\n>\n> If you use the bundled `DefaultAuthEmailProvider` with `onDeliveryError: 'rethrow'`, the error it\n> re-throws is the channel's original and is still yours to contain the same way.\n\n```typescript\n// email.provider.ts\nimport { Injectable } from '@nestjs/common'\nimport type { IEmailProvider, InviteData, SessionAlertInfo } from '@bymax-one/nest-auth'\nimport { Resend } from 'resend'\n\nconst escapeHtml = (s: string): string =>\n  s\n    .replace(/&/g, '&amp;')\n    .replace(/</g, '&lt;')\n    .replace(/>/g, '&gt;')\n    .replace(/\"/g, '&quot;')\n    .replace(/'/g, '&#x27;')\n\n@Injectable()\nexport class ResendEmailProvider implements IEmailProvider {\n  private readonly client = new Resend(process.env.RESEND_API_KEY!)\n  private readonly from = 'no-reply@example.com'\n  private readonly appUrl = process.env.APP_URL!\n\n  async sendPasswordResetToken(\n    _tenantId: string,\n    email: string,\n    token: string,\n    _locale?: string\n  ): Promise<void> {\n    const url = `${this.appUrl}/reset-password?token=${encodeURIComponent(token)}`\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: 'Reset your password',\n      html: `<p>Click <a href=\"${url}\">here</a> to reset your password.</p>`\n    })\n  }\n\n  async sendPasswordResetOtp(\n    _tenantId: string,\n    email: string,\n    otp: string,\n    _locale?: string\n  ): Promise<void> {\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: 'Your password reset code',\n      html: `<p>Your code is <strong>${otp}</strong>. It expires in 10 minutes.</p>`\n    })\n  }\n\n  async sendEmailVerificationOtp(\n    _tenantId: string,\n    email: string,\n    otp: string,\n    _locale?: string\n  ): Promise<void> {\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: 'Verify your email',\n      html: `<p>Your verification code is <strong>${otp}</strong>.</p>`\n    })\n  }\n\n  // The library does NOT await the three MFA notices — by the time one is sent the factor is\n  // already enabled or removed, so a bounced notice must not answer the caller with an error for\n  // an operation that succeeded. The consequence is here: an inline send like this one can be\n  // lost to a process shutdown or a serverless freeze arriving between the response and the send\n  // completing. Where these alerts matter — the administrative reset most of all, since it is what\n  // makes a support-desk takeover detectable — enqueue durably and resolve instead of sending\n  // inline. Awaiting would not fix it either: a freeze mid-await loses the notice AND the response.\n  async sendMfaEnabledNotification(\n    _tenantId: string,\n    email: string,\n    _locale?: string\n  ): Promise<void> {\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: 'MFA enabled on your account',\n      html: '<p>Two-factor authentication has been enabled. If this was not you, contact support immediately.</p>'\n    })\n  }\n\n  async sendMfaDisabledNotification(\n    _tenantId: string,\n    email: string,\n    _locale?: string\n  ): Promise<void> {\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: 'MFA disabled on your account',\n      html: '<p>Two-factor authentication has been disabled. If this was not you, contact support immediately.</p>'\n    })\n  }\n\n  async sendNewSessionAlert(\n    _tenantId: string,\n    email: string,\n    sessionInfo: SessionAlertInfo,\n    _locale?: string\n  ): Promise<void> {\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: 'New sign-in to your account',\n      html: `\n        <p>New session detected:</p>\n        <ul>\n          <li>Device: ${escapeHtml(sessionInfo.device)}</li>\n          <li>IP: ${escapeHtml(sessionInfo.ip)}</li>\n          <li>Session: ${escapeHtml(sessionInfo.sessionHash)}</li>\n        </ul>\n      `\n    })\n  }\n\n  async sendInvitation(\n    _tenantId: string,\n    email: string,\n    inviteData: InviteData,\n    _locale?: string\n  ): Promise<void> {\n    const url = `${this.appUrl}/accept-invite?token=${encodeURIComponent(inviteData.inviteToken)}`\n    await this.client.emails.send({\n      from: this.from,\n      to: email,\n      subject: `You have been invited to ${inviteData.tenantName}`,\n      html: `\n        <p><strong>${escapeHtml(inviteData.inviterName)}</strong> invited you to join\n           <strong>${escapeHtml(inviteData.tenantName)}</strong>.</p>\n        <p><a href=\"${url}\">Accept invitation</a></p>\n        <p>This link expires on ${inviteData.expiresAt.toUTCString()}.</p>\n      `\n    })\n  }\n}\n```\n\nWire it via `extraProviders` alongside the user repository:\n\n```typescript\nimport { BYMAX_AUTH_EMAIL_PROVIDER } from '@bymax-one/nest-auth'\n\nextraProviders: [{ provide: BYMAX_AUTH_EMAIL_PROVIDER, useClass: ResendEmailProvider }]\n```\n\n### 4. Register the Module\n\nThe user repository and Redis client are provided via NestJS dependency injection tokens — not as direct config fields. This follows the [NestJS custom providers pattern](https://docs.nestjs.com/fundamentals/custom-providers) and ensures the DI container manages all dependencies correctly.\n\n```typescript\n// app.module.ts\nimport { Module } from '@nestjs/common'\nimport {\n  BymaxAuthModule,\n  BYMAX_AUTH_USER_REPOSITORY,\n  BYMAX_AUTH_REDIS_CLIENT\n} from '@bymax-one/nest-auth'\n\n@Module({\n  imports: [\n    BymaxAuthModule.registerAsync({\n      imports: [ConfigModule, DatabaseModule, RedisModule],\n      useFactory: (config: ConfigService) => ({\n        jwt: {\n          secret: config.get('JWT_SECRET'), // min 32 chars, high entropy\n          accessExpiresIn: '15m',\n          refreshExpiresInDays: 7\n        },\n        tokenDelivery: 'cookie', // 'cookie' | 'bearer' | 'both'\n        // Required while the limiter is on, and neither value can be a default:\n        // 'peer' behind a proxy reads the proxy's address for every request, and\n        // 'trusted-proxy' without one trusts a header the client can forge.\n        rateLimit: { clientIpSource: 'trusted-proxy' }, // 'peer' | 'trusted-proxy'\n        roles: {\n          hierarchy: {\n            admin: ['manager', 'user'],\n            manager: ['user'],\n            user: []\n          }\n        }\n      }),\n      inject: [ConfigService],\n      extraProviders: [\n        {\n          provide: BYMAX_AUTH_USER_REPOSITORY,\n          useClass: PrismaUserRepository\n        },\n        {\n          provide: BYMAX_AUTH_REDIS_CLIENT,\n          useFactory: (redis: RedisService) => redis.client,\n          inject: [RedisService]\n        }\n      ]\n    })\n  ]\n})\nexport class AppModule {}\n```\n\n### 5. Protect Routes\n\n```typescript\n// users.controller.ts\nimport { Controller, Get, UseGuards } from '@nestjs/common'\nimport { JwtAuthGuard, RolesGuard, Roles, CurrentUser } from '@bymax-one/nest-auth'\n// `import type` is required for a type used in a decorated signature: with\n// `emitDecoratorMetadata` and `isolatedModules`, a value import would be emitted\n// into the metadata and fail to erase (TS1272).\nimport type { DashboardJwtPayload } from '@bymax-one/nest-auth'\n\n@Controller('users')\n@UseGuards(JwtAuthGuard, RolesGuard)\nexport class UsersController {\n  @Get('me')\n  getProfile(@CurrentUser() user: DashboardJwtPayload) {\n    return { id: user.sub, role: user.role, tenantId: user.tenantId }\n  }\n\n  @Get()\n  @Roles('admin')\n  listUsers() {\n    // Only accessible by admins (and above in hierarchy)\n  }\n}\n```\n\n### 6. Frontend Integration (React)\n\nBuild an `AuthClient` once with `createAuthClient`, then hand it to\n`AuthProvider`. Hooks (`useSession`, `useAuth`, `useAuthStatus`) read\nthe context populated by the provider.\n\n```tsx\n// app/providers.tsx\n'use client'\nimport { AuthProvider } from '@bymax-one/nest-auth/react'\nimport { createAuthClient } from '@bymax-one/nest-auth/client'\n\nconst authClient = createAuthClient({\n  // Same-origin: a relative base sends every call through the Next.js\n  // proxy routes — `'/api'` plus the default `routePrefix` composes\n  // `/api/auth/*`. Use an absolute origin for a cross-origin API.\n  baseUrl: '/api'\n})\n\nexport function Providers({ children }: { children: React.ReactNode }) {\n  return (\n    <AuthProvider client={authClient} onSessionExpired={() => (location.href = '/login')}>\n      {children}\n    </AuthProvider>\n  )\n}\n```\n\n> **Which 401 spends a refresh.** The client's `authFetch` retries through `/refresh` only when\n> the 401 says the access token is the problem — `auth.token_invalid`, or a body carrying no\n> readable code. A route can sit behind the JWT guard _and_ verify a second credential, so\n> `auth.invalid_credentials` from a password change and an expired token arrive at the same URL\n> with the same status; the code separates them, the path never could. Any other 401 is returned\n> to the caller untouched, and `createAuthClient({ onSessionExpired })` fires only when a refresh\n> was warranted and failed. `AuthProvider`'s own `onSessionExpired` prop is a different hook: it\n> reacts to a 401 from the session read itself.\n\n```tsx\n// app/(dashboard)/profile.tsx\n'use client'\nimport { useAuth, useSession } from '@bymax-one/nest-auth/react'\n\nexport function Profile() {\n  const { user, status } = useSession()\n  const { logout } = useAuth()\n\n  if (status === 'loading') return <div>Loading…</div>\n  // `status` and `user` are separate fields, so the status check alone does\n  // not narrow `user` away from null — test the one you are about to read.\n  if (!user) return <div>Please log in</div>\n\n  return (\n    <div>\n      <p>Welcome, {user.name}!</p>\n      <button onClick={() => logout()}>Sign out</button>\n    </div>\n  )\n}\n```\n\n#### Plain SPAs — set `refreshEndpoint`\n\nThe example above is a Next.js app, where the default works. **A Vite/CRA SPA talking straight to\na Nest backend must set `refreshEndpoint`**, because it defaults to `/api/auth/client-refresh` —\na Next.js proxy route this library ships for that framework, and a path a plain SPA serves\nnothing at.\n\n```ts\nconst authClient = createAuthClient({\n  baseUrl: 'https://api.example.com',\n  // Without this, refresh POSTs to the Next proxy route and 404s.\n  refreshEndpoint: 'https://api.example.com/auth/refresh'\n})\n```\n\n**The symptom, because it does not look like a configuration problem:** _if every access-token\nexpiry logs the user out, check `refreshEndpoint` before looking at cookies._ The 404 is silent —\nrefresh fails, the session ends, and it presents as a session bug rather than as a missing route.\n\nAlso note `tenantId` is **optional** on every client input. Whether the server wants it is the\ndeployment's answer, not the type's: it is required when no `tenantIdResolver` is configured and\n**refused** when one is, answering `auth.validation` with a `tenantId` field detail either way.\nSend it, or do not, according to the deployment you talk to.\n\n### 7. Frontend Integration (Next.js 16)\n\nMount the Edge-Runtime auth proxy at the project root and expose the\nthree `/api/auth/*` route handlers. The proxy handles anti-redirect-\nloop protection, RBAC, status blocking, and background-request\ndetection; the route handlers bridge the browser to your NestJS\nbackend.\n\n```typescript\n// proxy.ts — Next.js 16 Edge middleware\nimport { createAuthProxy } from '@bymax-one/nest-auth/nextjs'\n\n// Next 16 scans this file for a function exported as `proxy` (or as the default), and it\n// does not recognise a destructuring pattern: `export const { proxy } = ...` fails the build\n// with \"The file ./proxy.ts must export a function\". Bind first, then export.\nconst authProxy = createAuthProxy({\n  publicRoutes: ['/', '/auth/login', '/auth/register'],\n  publicRoutesRedirectIfAuthenticated: ['/auth/login', '/auth/register'],\n  protectedRoutes: [\n    { pattern: '/dashboard/:path*', allowedRoles: ['admin', 'member'] },\n    { pattern: '/admin/:path*', allowedRoles: ['admin'] }\n  ],\n  loginPath: '/auth/login',\n  getDefaultDashboard: (role) => (role === 'admin' ? '/dashboard/admin' : '/dashboard'),\n  apiBase: process.env.API_BASE_URL!,\n  jwtSecret: process.env.JWT_SECRET!,\n  cookieNames: {\n    access: 'access_token',\n    refresh: 'refresh_token',\n    hasSession: 'has_session'\n  },\n  userHeaders: {\n    userId: 'x-user-id',\n    role: 'x-user-role',\n    tenantId: 'x-tenant-id',\n    tenantDomain: 'x-tenant-domain'\n  },\n  blockedUserStatuses: ['BANNED', 'INACTIVE', 'EXPIRED']\n})\n\nexport const proxy = authProxy.proxy\n\nexport const config = {\n  matcher: ['/((?!_next/static|_next/image|favicon.ico).*)']\n}\n```\n\n```typescript\n// app/api/auth/silent-refresh/route.ts\nimport { createSilentRefreshHandler } from '@bymax-one/nest-auth/nextjs'\n\nexport const GET = createSilentRefreshHandler({\n  apiBase: process.env.API_BASE_URL!,\n  loginPath: '/auth/login',\n  cookieNames: {\n    access: 'access_token',\n    refresh: 'refresh_token',\n    hasSession: 'has_session'\n  }\n})\n```\n\n```typescript\n// app/api/auth/client-refresh/route.ts\nimport { createClientRefreshHandler } from '@bymax-one/nest-auth/nextjs'\n\nexport const POST = createClientRefreshHandler({ apiBase: process.env.API_BASE_URL! })\n```\n\n```typescript\n// app/api/auth/logout/route.ts\nimport { createLogoutHandler } from '@bymax-one/nest-auth/nextjs'\n\nexport const POST = createLogoutHandler({\n  apiBase: process.env.API_BASE_URL!,\n  mode: 'redirect',\n  loginPath: '/auth/login',\n  cookieNames: {\n    access: 'access_token',\n    refresh: 'refresh_token',\n    hasSession: 'has_session'\n  }\n})\n```\n\n---\n\n### WebSocket upgrades\n\nThe browser `WebSocket` API cannot set handshake headers, so a browser client cannot send\n`Authorization: Bearer <token>` at the upgrade. The usual workaround puts the access token in the\nquery string, where it lands in access logs, browser history and proxy caches — a long-lived\ncredential in plaintext. `WsJwtGuard` refuses it.\n\nThe supported path is a single-use ticket:\n\n```typescript\n// 1. Mint from an authenticated session (POST, cookies or bearer as usual).\nconst { ticket, expiresIn } = await fetch('/auth/ws-ticket', {\n  method: 'POST',\n  credentials: 'include'\n}).then((r) => r.json())\n\n// 2. Open the socket with it. The ticket is consumed by the first redemption.\nconst socket = new WebSocket(`wss://api.example.com/socket?ticket=${ticket}`)\n```\n\nThe ticket is opaque, 32 bytes of CSPRNG output, and lives 30 seconds. Only `sha256(ticket)` is\never a Redis key, and the stored value is a verified-identity **snapshot** — no `jti`, no\nsignature, no expiry of its own — so a redeemed ticket authorizes a socket and cannot be turned\nback into a session. Minting requires an authenticated session in good standing that has already\nsatisfied MFA, so a ticket never carries more authority than the request that asked for it.\n\nNon-browser clients that can set headers keep using `Authorization: Bearer` at the handshake;\nboth channels are accepted, and a ticket wins when both are present.\n\nBoth channels live on the client's `handshake`, and only a **Socket.IO** client has one — with\n`@nestjs/platform-ws` the gateway receives the raw `ws` socket, which carries no `handshake` and\ndoes not retain the upgrade request. `WsJwtGuard` refuses such a connection with\n`auth.token_invalid` instead of crashing on it, but it cannot authenticate anyone on that\nadapter. And because `AuthException` extends `HttpException`, which Nest's WebSocket layer does\nnot recognise, a gateway that applies the guard also needs `WsAuthExceptionFilter` for the\nrefusal to reach the client as anything but `Internal server error` — see\n[On a WebSocket, the envelope needs its own filter](#on-a-websocket-the-envelope-needs-its-own-filter).\n\n---\n\n## ⚙️ Configuration\n\nAll options are configurable via `registerAsync()`. Here are the key configuration groups:\n\n| Group                 | Key Options                                                                                                                                         | Default                                   |\n| --------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------- |\n| **jwt**               | `secret` (required), `previousSecrets`, `accessExpiresIn`, `refreshExpiresInDays`, `absoluteSessionLifetimeDays`, `algorithm`, `issuer`, `audience` | `15m`, `7d`, `30d` cap, `HS256`, both off |\n| **environment**       | `'production'` \\| `'development'` \\| `'test'` — the only input that answers \"is this production\"                                                    | `'production'`                            |\n| **password**          | `minLength`, `costFactor`, `blockSize`, `parallelization`                                                                                           | `15`, scrypt N=2¹⁷, r=8, p=1              |\n| **tokenDelivery**     | `'cookie'` \\| `'bearer'` \\| `'both'`                                                                                                                | `'cookie'`                                |\n| **cookies**           | `accessTokenName`, `refreshTokenName`, `sessionSignalName`, `refreshCookiePath`, `sameSite`, `trustedOrigins`, `resolveDomains`                     | `'lax'`, `[]` (see cookie section)        |\n| **mfa**               | `encryptionKey`, `previousEncryptionKeys`, `issuer`, `totpWindow`, `recoveryCodeCount`                                                              | —                                         |\n| **sessions**          | `enabled`, `defaultMaxSessions`, `maxSessionsResolver`                                                                                              | `false`, `5`, —                           |\n| **bruteForce**        | `maxAttempts`, `windowSeconds`                                                                                                                      | `5`, `900`                                |\n| **rateLimit**         | `enabled`, `clientIpSource` (`'peer'` \\| `'trusted-proxy'`) — per-IP limits over Redis                                                              | `true`, **required**                      |\n| **passwordReset**     | `method` (`'token'` \\| `'otp'`), `otpLength`, `otpTtlSeconds`                                                                                       | `'token'`                                 |\n| **platform**          | `enabled`                                                                                                                                           | `false`                                   |\n| **invitations**       | `enabled`, `tokenTtlSeconds`                                                                                                                        | `false`                                   |\n| **roles**             | `hierarchy` (required), `platformHierarchy`                                                                                                         | —                                         |\n| **oauth**             | `google: { clientId, clientSecret, callbackUrl }`                                                                                                   | —                                         |\n| **emailVerification** | `required`, `otpTtlSeconds`                                                                                                                         | `true`, `600`                             |\n| **password** (screen) | `blocklist` — extra words the default screen refuses, on top of the ones it ships                                                                   | `[]`                                      |\n| **controllers**       | Toggle individual controllers on/off                                                                                                                | `auth`, `passwordReset` on; rest opt-in   |\n\n> [!NOTE]\n> When a feature is not configured (e.g., `mfa`, `sessions`, `platform`), its controllers and services are **not registered** in the NestJS container — zero overhead.\n\n> [!IMPORTANT]\n> **`environment` is how the module decides whether this is production, and it defaults to\n> saying yes.** It drives cookie `Secure`, the HTTPS requirement on the OAuth `callbackUrl`, and\n> three redirect validations. It used to be read from `NODE_ENV`, which failed **open** on every\n> near miss — unset, `'staging'`, `'prod'`, or `'production '` with a trailing space each\n> silently took the insecure branch, in all six places at once. Whether a deployment is\n> production is something the deployer knows and the process environment only hints at, so it is\n> passed in. The consequence to plan for: a local or test setup must now say\n> `environment: 'development'` (or `'test'`) explicitly, or it will be held to production rules —\n> an `http://` callback URL is refused, and cookies are marked `Secure` and never sent over\n> plaintext. That failure is loud, which is the point; the old one was silent. Matches\n> `Environment` in rust-auth.\n\n> [!NOTE]\n> **`password.minLength` defaults to 15, not 8.** The DTOs keep a structural floor of 8 — the\n> lowest NIST SP 800-63B-4 §3.1.1.1 permits under any circumstance — and this is the\n> deployment's policy on top of it. §3.1.1.1 allows 8 only for a password used as part of\n> multi-factor authentication and requires 15 for one used as a single factor; MFA here is\n> opt-in per user, so the default deployment **is** single-factor. Configurable to anything in\n> `8..=128`, validated at startup: below 8 changes no outcome (the DTOs refuse the request\n> first), and above 128 is longer than any password the validation layer accepts. It is checked\n> in the service rather than a decorator because a decorator is evaluated when the class is\n> defined, before any configuration exists — and it answers the same `auth.validation` code and\n> the same `{ field, message }[]` details a length failure already produced, so a client\n> handling short passwords sees no new shape.\n\n> [!IMPORTANT]\n> **`rateLimit.clientIpSource` is required** whenever rate limiting is enabled — there is no\n> default. The option group is a discriminated union, so TypeScript refuses the omission at\n> compile time; the module also refuses to start without it, because the type binds TypeScript\n> and nothing else. Set `'peer'` when the application is\n> directly exposed: the limit keys on the socket address, read from the connection and never\n> from a forwarding header. Set `'trusted-proxy'` when it runs behind a proxy and `trust proxy`\n> is configured for the real hop count: the limit keys on `req.ip`, the forwarded client\n> address. Neither can be the default, because each is a working limiter in one deployment and\n> no limiter at all in the other — `'peer'` behind a proxy puts every client in **one** bucket,\n> so a single caller can rate-limit your whole user base with no credential, and\n> `'trusted-proxy'` without a proxy lets the caller choose their own key. Both look like a\n> working limiter at runtime. Pass `rateLimit.enabled: false` if the limits are enforced at the\n> edge instead.\n\n> [!TIP]\n> **Binding tokens to an issuer and an audience.** `jwt.issuer` and `jwt.audience` are off by\n> default. Set either and its value is stamped on every token this backend mints and **required**\n> on every token it verifies — one carrying a different value, or none at all, is rejected.\n> That matters with HS256, where the verifier can also sign: every service holding the secret to\n> check a token can mint one, so audience binding is what stops a token minted for one service\n> being replayed at another that trusts the same secret.\n>\n> Two things to know before switching it on. Both backends of a shared deployment must carry the\n> same pair, or they stop accepting each other's tokens. And enabling it invalidates the access\n> tokens already in flight, since those were minted without the claims — a window of one\n> access-token lifetime, which clients close by refreshing. An empty string reads as unconfigured\n> rather than as \"require the empty issuer\", so an unset environment variable cannot turn the\n> check on by accident.\n\n> **Rotating the signing secret.** `jwt.previousSecrets` lists secrets retired by a rotation,\n> accepted for verification only. Without it, changing `jwt.secret` signs every user out the\n> moment the new configuration rolls out **and** invalidates every stored recovery-code digest —\n> those are keyed by an HMAC derived from the secret, so users lose the codes they printed and\n> filed. With it, both keep working while tokens issued under the old secret drain, and a\n> rotation becomes a rollout. Remove the entry once the longest-lived token signed under it has\n> expired: every entry is a key that still opens the door. `mfa.encryptionKey` rotates the same\n> way, through its own list — see below.\n\n> [!TIP]\n> **Rotating the MFA encryption key.** `mfa.previousEncryptionKeys` lists AES-256 keys retired by\n> a rotation of `mfa.encryptionKey`. The stored ciphertext carries no key identifier, so without\n> the list a change of key makes every enrolled user's TOTP secret undecryptable at once, with no\n> way back — their authenticator simply stops matching. With it, a stored secret that opened\n> under a retired key is **re-encrypted under the current one** on the next successful challenge,\n> so the rotation drains on its own instead of requiring the retired key to stay configured\n> forever. Each entry is validated at startup exactly like the current key (base64, exactly 32\n> bytes, and never equal to the current key or to another entry), because a malformed one would\n> otherwise surface at a user's first challenge rather than at boot. Drop the entry once your\n> enrolled users have had time to authenticate at least once.\n\n> [!IMPORTANT]\n> **The parameters that carry a control's strength are bounded at startup.** `mfa.totpWindow`\n> must be `0..=10`: the window counts 30-second steps on _either_ side of now, so `2n + 1`\n> codes are valid at once — three at the default of 1, but 121 at 60, which makes a six-digit\n> code a hundred times easier to guess while the configuration still reads as \"MFA enabled\".\n> `mfa.recoveryCodeCount` must be `1..=50`, because zero enrols an account with no way back\n> if the authenticator is lost. `password.blockSize` must be at least 8 and\n> `password.parallelization` at least 1: scrypt's memory cost is `128 * N * r`, so a smaller\n> block size divides the hardness that `password.costFactor`'s floor exists to guarantee —\n> invisibly, since the bounded parameter is still intact. `rust-auth` enforces the identical\n> ranges.\n\n> [!IMPORTANT]\n> `jwt.accessExpiresIn` must not exceed **30 days**, the window the store keeps a bumped token\n> epoch readable. The epoch is what makes a stateless access token revocable: a password reset\n> advances it and every token stamped below it stops verifying — but only while the bumped value\n> is still there. A longer-lived access token would outlive it, the lookup would fall back to\n> `0`, and a token the reset revoked would verify again. Startup refuses the configuration\n> rather than letting it fail open, and rejects an unreadable time span or a non-positive\n> lifetime on the same pass.\n\n> [!WARNING]\n> **Do not gate on the access token's `status` claim.** It is **point-in-time, never\n> authoritative**, and which of its three states you get depends on things a client cannot see:\n>\n> | how the token was minted                                                   | `status`                                                                                  |\n> | -------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------- |\n> | login, register, OAuth, MFA challenge                                      | the account's value **at that moment**                                                    |\n> | an ordinary refresh rotation                                               | **empty string** — the session record carries no live status, so there is nothing to copy |\n> | a refresh that re-signs because `role`, `tenantId` or `mfaEnabled` changed | the account's value **at that moment**, read during that request                          |\n>\n> `rust-auth` stamps the same empty string on its rotation path, deliberately and with a test\n> pinning it, so the middle row is a shared contract rather than a defect in either library.\n>\n> Every populated value is stale the instant the account changes, because status can change under\n> an unexpired token and nothing re-stamps it. So a route that reads the claim is wrong in **both**\n> directions: `status !== 'active'` refuses everyone whose session has been refreshed ordinarily,\n> and `status === 'suspended'` refuses nobody, ever. Both fail quietly and hours from the code\n> that caused them — the first looks like a broken login, the second like nothing at all.\n>\n> The exceptional re-stamp is the worst of the three for a reader, not the best: it makes the\n> claim _usually_ wrong instead of _reliably_ empty, which is the failure mode that survives\n> testing.\n>\n> Status is resolved per request or not at all: mount `UserStatusGuard` on the route, and for\n> anything richer read the account **tenant-scoped**, the way that guard does —\n> `findById({ id: request.user.sub, tenantId: request.user.tenantId })`. The tenant argument is required by the\n> port and cannot be dropped: ids may collide across tenants, so a lookup by bare id can resolve\n> another tenant's account. That is what the library's own guards do, which\n> is why the claim can be left as it is. `mfaVerified` behaves the same way and for the same\n> reason — it is always `false` after a rotation, so step-up does not survive a refresh and a\n> user re-acquires it through the MFA challenge.\n>\n> One consequence worth planning for: the guard reads a status cache with a\n> `userStatusCacheTtlSeconds` window (default **60**), so a suspension takes up to that long to\n> bite on a guarded route, and a reactivation the same to restore. Nothing exported invalidates\n> that key for one user today — the only immediate lever is `bumpUserTokenEpoch`, which ends\n> every session the user has rather than refreshing one cached string. Lower the TTL if a faster\n> answer matters more than the repository reads it costs.\n\n`jwt.absoluteSessionLifetimeDays` caps how long one login can be extended by rotation, and is\n**on by default at 30 days** — NIST SP 800-63B-4 §3 makes a definite reauthentication timeout a\nSHALL and puts it at no more than 30 days for AAL1. Without a cap, a client refreshing every\nfifteen minutes keeps a session alive forever, and a refresh token stolen once becomes permanent\naccess. Raise it to a value the product can justify, or set `0` to accept unbounded sessions\ndeliberately.\n\nLowering the value ends sessions that are already older than the new one, at their next rotation;\nraising it or setting `0` ends nothing. Sessions established before the cap existed carry no\nrecorded birth time and are never capped, whatever the value — they age out under\n`refreshExpiresInDays` like any other.\n\n`cookies.trustedOrigins` is deliberately off by default, because switching it on changes\nbehaviour for origins that already exist. It is required as soon as `cookies.sameSite: 'none'`\nis set, and refused otherwise — that posture is the only one where the browser sends the session\ncookie cross-site, and it is the only one where the origin check has anything to authorize.\n\nThe breach check is opt-in for a different reason: it is the only part of the credential path\nthat reaches the network, and a library should not start talking to a third party because it was\nupgraded. Wire it explicitly:\n\n```typescript\nBymaxAuthModule.registerAsync({\n  useFactory: () => ({ ... }),\n  extraProviders: [{ provide: BYMAX_AUTH_BREACH_CHECKER, useClass: HibpBreachChecker }]\n})\n```\n\n---\n\n## 🏗️ Architecture\n\nThe package runs **inside** your NestJS application as a dynamic module — not as a separate service:\n\n```\n┌─────────────────────────────────────────────┐\n│           Your NestJS Application            │\n│                                             │\n│  ┌───────────────────────────────────────┐  │\n│  │       @bymax-one/nest-auth            │  │\n│  │                                       │  │\n│  │  Controllers ←→ Services ←→ Redis     │  │\n│  │  Guards ←→ Crypto (node:crypto)       │  │\n│  │  Decorators ←→ Token Manager (JWT)    │  │\n│  └──────────┬────────────┬───────────────┘  │\n│             │            │                   │\n│     ┌───────▼──┐  ┌──────▼───────┐          │\n│     │ IUser    │  │ IEmail       │          │\n│     │ Repo     │  │ Provider     │          │\n│     │ (yours)  │  │ (yours)      │          │\n│     └──────────┘  └──────────────┘          │\n└─────────────────────────────────────────────┘\n```\n\n### Design Principles\n\n| Principle                  | Description                                                                                                                                  |\n| -------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------- |\n| **🔌 Interface-Driven**    | Define contracts, inject implementations — works with Prisma, TypeORM, Drizzle, or any SQL ORM                                               |\n| **🔒 Secure by Default**   | scrypt hashing, HttpOnly cookies, JWT blacklisting, brute-force protection — all enabled out of the box                                      |\n| **🪶 Zero Runtime Deps**   | `\"dependencies\": {}` — adds no runtime deps of its own; crypto is native `node:crypto`. Required peers (NestJS, ioredis…) come from your app |\n| **🌳 Tree-Shakeable**      | `sideEffects: false`, subpath exports, ESM + CJS dual output                                                                                 |\n| **⚡ Conditional Loading** | Unconfigured features don't register — no wasted memory or startup time                                                                      |\n\n---\n\n## 🔐 Security Model\n\nThe security architecture follows established standards and industry best practices.\n\n### JWT Token Type Discrimination\n\nEvery token carries a `type` claim that guards validate before accepting:\n\n| Token type        | Issued when                               | Accepted by            |\n| ----------------- | ----------------------------------------- | ---------------------- |\n| `'dashboard'`     | Successful login or MFA challenge         | `JwtAuthGuard`         |\n| `'platform'`      | Platform admin login or MFA challenge     | `JwtPlatformGuard`     |\n| `'mfa_challenge'` | Login with MFA enabled (pre-verification) | MFA challenge endpoint |\n\nThis prevents **token type confusion attacks** — a class of vulnerability documented by [OWASP](https://owasp.org/www-project-web-security-testing-guide/latest/4-Web_Application_Security_Testing/06-Session_Management_Testing/10-Testing_JSON_Web_Tokens) where a token issued for one purpose is accepted by another. The same pattern is used by AWS Cognito (`token_use` claim) and recommended by [Curity's JWT best practices guide](https://curity.io/resources/learn/jwt-best-practices/).\n\n`JwtPlatformGuard` returns `PLATFORM_AUTH_REQUIRED` (not the generic `TOKEN_INVALID`) when a dashboard token is submitted to a platform route — so clients can distinguish wrong-context from expired/invalid errors.\n\n### Separate Auth Contexts for Multi-Tenant SaaS\n\nPlatform admins and tenant users are fully isolated stacks — separate repositories, JWT payloads, guards, and routes. A platform admin token cannot access tenant routes, and a tenant token cannot access platform routes, regardless of role. This aligns with the architecture recommended by AWS, Logto, and WorkOS for multi-tenant SaaS platforms.\n\nThe `tenantId` is always extracted from the validated JWT — never from the request body — preventing tenant spoofing at the architecture level.\n\n### Token Revocation via Redis JTI Blacklist\n\nAccess tokens are short-lived (default 15 minutes) and immediately revocable via a Redis JTI blacklist. Refresh tokens rotate on every use with a configurable grace window to handle concurrent requests. This is the industry-standard hybrid approach used by Auth0, Okta, and SuperTokens — combining short lifetimes for low-latency revocation with rotating refresh tokens for session continuity.\n\n### Password Hashing\n\nPasswords are hashed with **scrypt** via `node:crypto`, which is memory-hard and resistant to GPU-based brute-force attacks. All secret comparisons use `crypto.timingSafeEqual` for constant-time evaluation — [a requirement explicitly documented](https://nodejs.org/api/crypto.html#cryptotimingsafeequala-b) in the Node.js crypto documentation.\n\n### No External Cryptographic Dependencies\n\nAll security-critical operations use the OpenSSL-backed `node:crypto` module — no bcrypt, argon2, otpauth, uuid, or nanoid packages. This eliminates the supply chain attack surface for the most sensitive code paths.\n\n### Security Checklist\n\nWhen integrating `@bymax-one/nest-auth` in production, verify each of the following:\n\n- `cookies.resolveDomains` MUST validate against an allowlist of configured domains\n- MFA recovery without TOTP requires admin intervention (no self-service)\n- `@MaxLength(128)` on password DTOs prevents algorithmic-DoS via oversized scrypt inputs\n- JWT algorithm pinning to HS256 prevents algorithm-confusion attacks\n- Constant-time comparisons via `crypto.timingSafeEqual` for all secret comparisons\n- HttpOnly cookies; `Secure` enforced in production; `SameSite=Lax` by default on every auth\n  cookie, so the OAuth provider's cross-site redirect back to your app still carries them.\n  Deployments that do not need that redirect can take the stricter posture with\n  `cookies.sameSite: 'strict'`. CSRF does not rest on this setting — `TrustedOriginGuard` is\n  applied to every controller and runs before authentication.\n\n**The tokens are never readable from JavaScript, and verifying that end-to-end is yours.** Under\ncookie delivery this library never writes a token to `localStorage`, `sessionStorage`, or a\nJS-readable cookie: `access_token` and `refresh_token` are `HttpOnly`, and the only readable\ncookie is `has_session=1`, a hint carrying no credential so a SPA can tell a session probably\nexists without touching a token.\n\nThis library's suite asserts **its half** — that the `Set-Cookie` headers carry those flags — and\nit structurally cannot assert the other half. A token leaking into JS-readable storage is\ninvisible from the server: the API answers identically, the wire looks correct, and every test\nhere passes. Only a browser observes it. **If you run a browser suite, assert there that\n`localStorage` and `sessionStorage` are empty and that `document.cookie` carries neither token**;\nit is the one guarantee cookie delivery exists for and the one no server-side test can reach.\n\n---\n\n## 🛡️ Security Table\n\n| Layer              | Implementation                                                                                         |\n| ------------------ | ------------------------------------------------------------------------------------------------------ |\n| Password Hashing   | `node:crypto` scrypt (N=2¹⁷, r=8, p=1, keyLen=64) — OWASP's recommended minimum                        |\n| MFA Encryption     | AES-256-GCM with 12-byte random IV per call                                                            |\n| TOTP               | HMAC-SHA1 per RFC 4226/6238, ±1 step window                                                            |\n| Token Generation   | `crypto.randomBytes(32)` — 256 bits of entropy                                                         |\n| Secret Comparison  | `crypto.timingSafeEqual` (constant-time)                                                               |\n| JWT                | HS256 via `@nestjs/jwt`, JTI blacklist via Redis                                                       |\n| Cookies            | HttpOnly, Secure, SameSite=Lax (override to `strict`), path-scoped                                     |\n| Brute-Force        | Redis atomic counters per HMAC(email, jwt.secret)                                                      |\n| CSRF (OAuth)       | 64-char hex state nonce, single-use via `getdel()`                                                     |\n| Refresh Rotation   | Single-use tokens with a grace window; a replay past it revokes that login's whole family lineage      |\n| Cross-Site Writes  | `Origin` / `Sec-Fetch-Site` check on cookie-authenticated writes — the gap `SameSite=None` leaves open |\n| Breached Passwords | Optional Have I Been Pwned range check by k-anonymity; only a 5-char SHA-1 prefix leaves the process   |\n| Rate Limiting      | Per-IP fixed-window counters in Redis, keyed by `HMAC(ip)` — enforced by the library, not by the host  |\n| Session Lifetime   | Optional absolute cap on how long one login can be extended by rotation                                |\n\n> [!IMPORTANT]\n> This package uses **zero external cryptographic dependencies**. All operations use Node.js native `node:crypto`, eliminating supply chain attack vectors for critical security code.\n\n---\n\n## 🧱 Tech Stack\n\n<p>\n  <img src=\"https://img.shields.io/badge/NestJS-11-E0234E?style=flat-square&logo=nestjs&logoColor=white\" alt=\"NestJS\" />\n  <img src=\"https://img.shields.io/badge/TypeScript-strict-3178C6?style=flat-square&logo=typescript&logoColor=white\" alt=\"TypeScript\" />\n  <img src=\"https://img.shields.io/badge/React-19-61DAFB?style=flat-square&logo=react&logoColor=black\" alt=\"React\" />\n  <img src=\"https://img.shields.io/badge/Next.js-16-000000?style=flat-square&logo=next.js&logoColor=white\" alt=\"Next.js\" />\n  <img src=\"https://img.shields.io/badge/Node.js-24%2B-339933?style=flat-square&logo=node.js&logoColor=white\" alt=\"Node.js\" />\n  <img src=\"https://img.shields.io/badge/Redis-7%2B-DC382D?style=flat-square&logo=redis&logoColor=white\" alt=\"Redis\" />\n  <img src=\"https://img.shields.io/badge/Jest-29-C21325?style=flat-square&logo=jest&logoColor=white\" alt=\"Jest\" />\n</p>\n\n---\n\n## 🧪 Testing & Quality\n\nAuthentication is critical infrastructure, so the suite is held to a bar beyond \"it runs\" — every behavior is pinned so that a regression **fails a test**.\n\n- ✅ **100% line coverage** — statements, branches, functions, and lines, enforced as a release gate across unit + e2e\n- ✅ **100% mutation score** — verified with [Stryker](https://stryker-mutator.io/): 5,333 seeded faults detected (5,311 killed, 22 timed out), **no survivors and nothing left uncovered**, against a `break` threshold of 100 ([measured cold on 2026-08-15](./docs/mutation_testing_results.md#re-measured-cold--2026-08-15))\n- ✅ **3,971 tests** — 3,721 unit and 250 end-to-end, spanning all five subpaths\n- ✅ **Every equivalent mutant documented** — the 367 mutants that no test can kill (a redundant guard, a dependency array of stable references) each carry an inline `// Stryker disable` with the reason, so the score is an accounting rather than a number\n\n```bash\npnpm test          # unit suite\npnpm test:cov:all  # unit + e2e, 100% coverage gate\npnpm mutation      # Stryker mutation testing\n```\n\n> [!NOTE]\n> Line coverage proves a line _executed_ under test; mutation testing proves a test _would fail_ if that line were wrong. The full methodology and per-area breakdown are in [docs/mutation_testing_results.md](./docs/mutation_testing_results.md).\n\n---\n\n## 📖 API Reference\n\n### HTTP Endpoints\n\nConditionally registered controllers (mfa, sessions, platform, invitations, oauth, password-reset) only mount their endpoints when the corresponding feature is enabled in `BymaxAuthModule.registerAsync()`.\n\n| Method | Path                           | Auth / Guard                       | Description                                                 |\n| ------ | ------------------------------ | ---------------------------------- | ----------------------------------------------------------- |\n| POST   | `/register`                    | Public                             | Register a new dashboard user and issue tokens              |\n| POST   | `/login`                       | Public                             | Authenticate with email/password (may return MFA challenge) |\n| POST   | `/logout`                      | Public (reads both credentials)    | Revoke the session; blacklists the access token it is given |\n| POST   | `/refresh`                     | Public (refresh cookie or body)    | Rotate refresh token, issue new access token                |\n| GET    | `/me`                          | `JwtAuthGuard`                     | Current dashboard user payload                              |\n| POST   | `/ws-ticket`                   | `JwtAuthGuard`                     | Mint a single-use ticket for a WebSocket upgrade            |\n| POST   | `/verify-email`                | Public                             | Verify email with OTP                                       |\n| POST   | `/resend-verification`         | Public                             | Resend email-verification OTP                               |\n| POST   | `/password/forgot-password`    | Public                             | Request password reset (token or OTP)                       |\n| POST   | `/password/reset-password`     | Public                             | Submit new password with reset token                        |\n| POST   | `/password/verify-otp`         | Public                             | Verify password-reset OTP                                   |\n| POST   | `/password/resend-otp`         | Public                             | Resend password-reset OTP                                   |\n| POST   | `/mfa/setup`                   | `JwtAuthGuard`                     | Generate TOTP secret and recovery codes                     |\n| POST   | `/mfa/verify-enable`           | `JwtAuthGuard`                     | Confirm setup and enable MFA                                |\n| POST   | `/mfa/challenge`               | Public + `@SkipMfa()`              | Submit TOTP/recovery code after login                       |\n| POST   | `/mfa/disable`                 | `JwtAuthGuard`                     | Disable MFA for the current user                            |\n| POST   | `/mfa/recovery-codes`          | `JwtAuthGuard`                     | Replace the recovery codes, proving a fresh OTP             |\n| GET    | `/sessions`                    | `JwtAuthGuard`, `UserStatusGuard`  | List active sessions for the current user                   |\n| POST   | `/sessions/revoke-all`         | `JwtAuthGuard`, `UserStatusGuard`  | Revoke every session except the caller's                    |\n| DELETE | `/sessions/:id` ","readmeFilename":"README.md"}