EasyReasy.Auth
1.0.0
See the version list below for details.
dotnet add package EasyReasy.Auth --version 1.0.0
NuGet\Install-Package EasyReasy.Auth -Version 1.0.0
<PackageReference Include="EasyReasy.Auth" Version="1.0.0" />
<PackageVersion Include="EasyReasy.Auth" Version="1.0.0" />
<PackageReference Include="EasyReasy.Auth" />
paket add EasyReasy.Auth --version 1.0.0
#r "nuget: EasyReasy.Auth, 1.0.0"
#:package EasyReasy.Auth@1.0.0
#addin nuget:?package=EasyReasy.Auth&version=1.0.0
#tool nuget:?package=EasyReasy.Auth&version=1.0.0
EasyReasy.Auth
A lightweight .NET library for internal JWT authentication and claims handling, designed for simplicity and security.
Overview
EasyReasy.Auth makes it easy to issue, validate, and work with JWT tokens in your .NET applications, with built-in support for roles, custom claims, and progressive brute-force protection.
Why Use EasyReasy.Auth?
- Simple JWT issuing: Create signed tokens with standard and custom claims
- Claims injection: Access user and tenant IDs easily in your controllers
- Role access: Retrieve all roles for the current user with a single call
- Claim access: Retrieve any claim value by key or enum with a single call
- Progressive delay: Built-in middleware to slow down brute-force attacks (enabled by default)
- Flexible configuration: Optional issuer validation, easy integration with ASP.NET Core
- Clear error messages: Enforces minimum secret length for security
Quick Start
1. Add to your project
Install via NuGet:
# In your web/API project
dotnet add package EasyReasy.Auth
dotnet add package Microsoft.IdentityModel.JsonWebTokens
Important note! You will always get 401 Unauthorized if you forget to install
Microsoft.IdentityModel.JsonWebTokens
2. Configure in Program.cs
string jwtSecret = Environment.GetEnvironmentVariable("JWT_SIGNING_SECRET")!;
builder.Services.AddEasyReasyAuth(jwtSecret, issuer: "my-issuer");
var app = builder.Build();
app.UseEasyReasyAuth(); // Progressive delay enabled by default
3. Issue tokens
Option A: Manual Token Creation (Not recommended, see Option B for recommended way)
You probably want to get an instance of IJWtTokenService via dependency injection in your controller class and create an endpoint in that is responsible for issuing tokens if they should be issued.
IJwtTokenService tokenService = new JwtTokenService(jwtSecret, issuer: "my-issuer");
string token = tokenService.CreateToken(
subject: "user-123",
authType: "apikey",
additionalClaims: new[] { new Claim("tenant_id", "tenant-42") },
roles: new[] { "admin", "user" },
expiresAt: DateTime.UtcNow.AddHours(1));
Option B: Automatic Auth Endpoints (Recommended)
The library can automatically create authentication endpoints for you. First, implement the validation service:
public class MyAuthService : IAuthRequestValidationService
{
public async Task<AuthResponse?> ValidateApiKeyRequestAsync(ApiKeyAuthRequest request, IJwtTokenService jwtTokenService)
{
// Validate API key (e.g., check database, external service, etc.)
var user = await _userRepository.GetByApiKeyAsync(request.ApiKey);
if (user == null) return null;
// Create JWT token
DateTime expiresAt = DateTime.UtcNow.AddHours(1);
string token = jwtTokenService.CreateToken(
subject: user.Id,
authType: "apikey",
additionalClaims: new[] { new Claim("tenant_id", user.TenantId) },
roles: user.Roles.ToArray(),
expiresAt: expiresAt);
return new AuthResponse(token, expiresAt.ToString("o"));
}
public async Task<AuthResponse?> ValidateLoginRequestAsync(LoginAuthRequest request, IJwtTokenService jwtTokenService)
{
// Validate username/password (e.g., check database, hash password, etc.)
var user = await _userRepository.GetByUsernameAsync(request.Username);
if (user == null || !VerifyPassword(request.Password, user.PasswordHash))
return null;
// Create JWT token
DateTime expiresAt = DateTime.UtcNow.AddHours(1);
string token = jwtTokenService.CreateToken(
subject: user.Id,
authType: "user",
additionalClaims: new[] { new Claim("tenant_id", user.TenantId) },
roles: user.Roles.ToArray(),
expiresAt: expiresAt);
return new AuthResponse(token, expiresAt.ToString("o"));
}
}
Then register the service and add endpoints in Program.cs:
// Register your validation service
builder.Services.AddAuthValidationService(new MyAuthService());
// ... other configuration ...
var app = builder.Build();
// ... other configuration ...
// Add auth endpoints (choose which ones you want)
app.AddAuthEndpoints(
app.Services.GetRequiredService<IAuthRequestValidationService>(),
allowApiKeys: true,
allowUsernamePassword: true);
// Or add specific endpoints individually:
// app.AddApiAuthEndpoint(app.Services.GetRequiredService<IAuthRequestValidationService>());
// app.AddLoginAuthEndpoint(app.Services.GetRequiredService<IAuthRequestValidationService>());
app.MapControllers(); // This is probably here already
// app.MapControllers(); is not specifically required by the auth library
// it's just to show how the layout would probably look in Program.cs
This will automatically create:
POST /api/auth/apikey- For API key authenticationPOST /api/auth/login- For username/password authentication
Both endpoints return:
200 OKwithAuthResponse(token + expiration) on success401 Unauthorizedon invalid credentials
4. Access claims and roles in controllers
string? userId = HttpContext.GetUserId();
string? tenantId = HttpContext.GetTenantId();
IEnumerable<string> roles = HttpContext.GetRoles();
string? email = HttpContext.GetClaimValue("email");
// Type-safe claim access using the EasyReasyClaim enum
string? userId2 = HttpContext.GetClaimValue(EasyReasyClaim.UserId);
string? tenantId2 = HttpContext.GetClaimValue(EasyReasyClaim.TenantId);
string? issuer = HttpContext.GetClaimValue(EasyReasyClaim.Issuer);
Advanced Configuration
Opting Out of Automatic Service Registration
If you need more control over the IJwtTokenService registration (e.g., for testing, custom implementations, or multiple configurations), you can opt out of automatic registration:
// Register authentication without automatic IJwtTokenService registration
builder.Services.AddEasyReasyAuth(jwtSecret, issuer: "my-issuer", registerJwtTokenService: false);
// Manually register your own implementation
builder.Services.AddSingleton<IJwtTokenService>(new MyCustomJwtTokenService(jwtSecret, issuer));
This is useful for:
- Testing scenarios: Mock the service in unit tests
- Custom implementations: Use your own
IJwtTokenServiceimplementation - Multiple configurations: Register different JWT services for different purposes
- Performance optimization: Control the service lifetime (singleton vs scoped vs transient)
Progressive Delay Middleware
The progressive delay middleware helps protect your API from brute-force attacks by introducing a delay for repeated unauthorized requests from the same IP address.
- How it works:
- The first 10 failed (401 Unauthorized) requests from an IP have no delay.
- After that, each additional failed request adds a 500ms delay (e.g., 11th failure = 500ms, 12th = 1000ms, etc.).
- The delay is reset after a successful (non-401) request.
- Enabled by default:
- The middleware is included automatically when you call
app.UseEasyReasyAuth().
- The middleware is included automatically when you call
- How to disable:
- Pass
enableProgressiveDelay: falsetoUseEasyReasyAuth:app.UseEasyReasyAuth(enableProgressiveDelay: false);
- Pass
- How to enable:
- Omit the parameter or set it to
true(default):app.UseEasyReasyAuth(); // or app.UseEasyReasyAuth(enableProgressiveDelay: true);
- Omit the parameter or set it to
Core Features
- JWT token service: Issue tokens with custom claims, roles, and optional issuer
- Automatic auth endpoints: Create API key and username/password authentication endpoints with minimal code
- Flexible validation: Implement
IAuthRequestValidationServiceto handle any authentication logic (database, external APIs, etc.) - Claims injection middleware: Makes user/tenant IDs available in
HttpContext.Items - Role access: Retrieve all roles for the current user via
GetRoles() - Claim access: Retrieve any claim value by key or enum via
GetClaimValue() - Progressive delay middleware: Slows repeated unauthorized requests from the same IP (first 10 have no delay, then 500ms per failure)
- Configurable issuer validation: Pass
issuer: nullto disable - Secret length enforcement: Secret must be at least 32 bytes (256 bits) for HS256
- Async support: All validation methods are async for database lookups and external API calls
Error Handling
- If the JWT secret is too short,
JwtTokenServicethrows anArgumentExceptionwith a clear message. - Progressive delay is enabled by default; opt out with
app.UseEasyReasyAuth(enableProgressiveDelay: false);
Best Practices
- Use a strong, unique secret: At least 32 bytes (256 bits)
- Set issuer for extra validation: Use the same value when issuing and validating tokens
- Enable progressive delay: Protects against brute-force attacks by default
- Access claims and roles via extension methods: Use
GetUserId(),GetTenantId(),GetRoles(), andGetClaimValue()for convenience
For more details, see XML comments in the code or explore the source. This library is designed to be easy to use and secure enough for most uses cases by default.
⚠️ Security Disclaimer: This library implements a simple token-based authentication system suitable for internal or low-risk applications. It does not follow full OAuth2/OIDC standards and lacks advanced features like key rotation, token introspection, consent management, and third-party identity federation. For production systems with complex threat models, consider using a mature identity provider such as IdentityServer, OpenIddict, or a cloud-based solution.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net8.0 is compatible. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 was computed. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 was computed. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net8.0
- Microsoft.AspNetCore.Authentication (>= 2.3.0)
- Microsoft.AspNetCore.Authentication.JwtBearer (>= 8.0.18)
- Microsoft.AspNetCore.Authorization.Policy (>= 2.3.0)
- Microsoft.AspNetCore.Http.Abstractions (>= 2.3.0)
- Microsoft.IdentityModel.Tokens (>= 8.12.1)
NuGet packages (1)
Showing the top 1 NuGet packages that depend on EasyReasy.Auth:
| Package | Downloads |
|---|---|
|
EasyReasy.Auth.Google
Google Sign-In integration for EasyReasy.Auth JWT authentication |
GitHub repositories
This package is not used by any popular GitHub repositories.
| Version | Downloads | Last Updated |
|---|---|---|
| 5.3.0 | 1,214 | 6/16/2026 |
| 5.2.0 | 390 | 6/11/2026 |
| 5.1.0 | 149 | 6/10/2026 |
| 5.0.0 | 221 | 6/8/2026 |
| 4.1.0 | 269 | 5/30/2026 |
| 4.0.0 | 528 | 4/19/2026 |
| 3.1.0 | 126 | 4/2/2026 |
| 3.0.0 | 623 | 3/21/2026 |
| 2.0.0 | 1,365 | 2/18/2026 |
| 1.4.0 | 117 | 2/18/2026 |
| 1.3.1 | 1,079 | 9/11/2025 |
| 1.3.0 | 298 | 8/7/2025 |
| 1.2.0 | 164 | 8/3/2025 |
| 1.1.0 | 182 | 8/3/2025 |
| 1.0.0 | 211 | 7/30/2025 |