aboutsummaryrefslogtreecommitdiff
path: root/BackEnd/Timeline/Services
diff options
context:
space:
mode:
Diffstat (limited to 'BackEnd/Timeline/Services')
-rw-r--r--BackEnd/Timeline/Services/Token/JwtUserTokenBadFormatException.cs (renamed from BackEnd/Timeline/Services/JwtUserTokenBadFormatException.cs)3
-rw-r--r--BackEnd/Timeline/Services/Token/TokenServiceColletionExtensions.cs18
-rw-r--r--BackEnd/Timeline/Services/Token/UserTokenException.cs (renamed from BackEnd/Timeline/Services/UserTokenException.cs)2
-rw-r--r--BackEnd/Timeline/Services/Token/UserTokenHandler.cs (renamed from BackEnd/Timeline/Services/UserTokenHandler.cs)21
-rw-r--r--BackEnd/Timeline/Services/Token/UserTokenManager.cs (renamed from BackEnd/Timeline/Services/UserTokenManager.cs)25
5 files changed, 46 insertions, 23 deletions
diff --git a/BackEnd/Timeline/Services/JwtUserTokenBadFormatException.cs b/BackEnd/Timeline/Services/Token/JwtUserTokenBadFormatException.cs
index c528c3e3..4d7300a1 100644
--- a/BackEnd/Timeline/Services/JwtUserTokenBadFormatException.cs
+++ b/BackEnd/Timeline/Services/Token/JwtUserTokenBadFormatException.cs
@@ -2,7 +2,7 @@
using System.Globalization;
using static Timeline.Resources.Services.Exception;
-namespace Timeline.Services
+namespace Timeline.Services.Token
{
[Serializable]
public class JwtUserTokenBadFormatException : UserTokenBadFormatException
@@ -13,6 +13,7 @@ namespace Timeline.Services
IdClaimBadFormat,
NoVersionClaim,
VersionClaimBadFormat,
+ NoExp,
Other
}
diff --git a/BackEnd/Timeline/Services/Token/TokenServiceColletionExtensions.cs b/BackEnd/Timeline/Services/Token/TokenServiceColletionExtensions.cs
new file mode 100644
index 00000000..d3219ec4
--- /dev/null
+++ b/BackEnd/Timeline/Services/Token/TokenServiceColletionExtensions.cs
@@ -0,0 +1,18 @@
+using Microsoft.Extensions.Configuration;
+using Microsoft.Extensions.DependencyInjection;
+using Timeline.Configs;
+
+namespace Timeline.Services.Token
+{
+ public static class TokenServiceColletionExtensions
+ {
+ public static IServiceCollection AddTokenService(this IServiceCollection services, IConfiguration configuration)
+ {
+ services.Configure<TokenOptions>(configuration.GetSection("Token"));
+ services.Configure<JwtOptions>(configuration.GetSection("Jwt"));
+ services.AddScoped<IUserTokenHandler, JwtUserTokenHandler>();
+ services.AddScoped<IUserTokenManager, UserTokenManager>();
+ return services;
+ }
+ }
+}
diff --git a/BackEnd/Timeline/Services/UserTokenException.cs b/BackEnd/Timeline/Services/Token/UserTokenException.cs
index 398da41f..d666ba10 100644
--- a/BackEnd/Timeline/Services/UserTokenException.cs
+++ b/BackEnd/Timeline/Services/Token/UserTokenException.cs
@@ -1,6 +1,6 @@
using System;
-namespace Timeline.Services
+namespace Timeline.Services.Token
{
[Serializable]
diff --git a/BackEnd/Timeline/Services/UserTokenHandler.cs b/BackEnd/Timeline/Services/Token/UserTokenHandler.cs
index c24a8d47..2eaea57e 100644
--- a/BackEnd/Timeline/Services/UserTokenHandler.cs
+++ b/BackEnd/Timeline/Services/Token/UserTokenHandler.cs
@@ -8,13 +8,13 @@ using System.Security.Claims;
using Timeline.Configs;
using Timeline.Entities;
-namespace Timeline.Services
+namespace Timeline.Services.Token
{
public class UserTokenInfo
{
public long Id { get; set; }
public long Version { get; set; }
- public DateTime? ExpireAt { get; set; }
+ public DateTime ExpireAt { get; set; }
}
public interface IUserTokenHandler
@@ -28,7 +28,7 @@ namespace Timeline.Services
string GenerateToken(UserTokenInfo tokenInfo);
/// <summary>
- /// Verify a token and get the saved info.
+ /// Verify a token and get the saved info. Do not validate lifetime!!!
/// </summary>
/// <param name="token">The token to verify.</param>
/// <returns>The saved info in token.</returns>
@@ -44,13 +44,13 @@ namespace Timeline.Services
{
private const string VersionClaimType = "timeline_version";
- private readonly IOptionsMonitor<JwtConfiguration> _jwtConfig;
+ private readonly IOptionsMonitor<JwtOptions> _jwtConfig;
private readonly IClock _clock;
private readonly JwtSecurityTokenHandler _tokenHandler = new JwtSecurityTokenHandler();
private SymmetricSecurityKey _tokenSecurityKey;
- public JwtUserTokenHandler(IOptionsMonitor<JwtConfiguration> jwtConfig, IClock clock, DatabaseContext database)
+ public JwtUserTokenHandler(IOptionsMonitor<JwtOptions> jwtConfig, IClock clock, DatabaseContext database)
{
_jwtConfig = jwtConfig;
_clock = clock;
@@ -83,7 +83,7 @@ namespace Timeline.Services
Audience = config.Audience,
SigningCredentials = new SigningCredentials(_tokenSecurityKey, SecurityAlgorithms.HmacSha384),
IssuedAt = _clock.GetCurrentTime(),
- Expires = tokenInfo.ExpireAt.GetValueOrDefault(_clock.GetCurrentTime().AddSeconds(config.DefaultExpireOffset)),
+ Expires = tokenInfo.ExpireAt,
NotBefore = _clock.GetCurrentTime() // I must explicitly set this or it will use the current time by default and mock is not work in which case test will not pass.
};
@@ -127,17 +127,14 @@ namespace Timeline.Services
var decodedToken = (JwtSecurityToken)t;
var exp = decodedToken.Payload.Exp;
- DateTime? expireAt = null;
- if (exp.HasValue)
- {
- expireAt = EpochTime.DateTime(exp.Value);
- }
+ if (exp is null)
+ throw new JwtUserTokenBadFormatException(token, JwtUserTokenBadFormatException.ErrorKind.NoExp);
return new UserTokenInfo
{
Id = id,
Version = version,
- ExpireAt = expireAt
+ ExpireAt = EpochTime.DateTime(exp.Value)
};
}
catch (Exception e) when (e is SecurityTokenException || e is ArgumentException)
diff --git a/BackEnd/Timeline/Services/UserTokenManager.cs b/BackEnd/Timeline/Services/Token/UserTokenManager.cs
index 898e4d6d..00bc2cf7 100644
--- a/BackEnd/Timeline/Services/UserTokenManager.cs
+++ b/BackEnd/Timeline/Services/Token/UserTokenManager.cs
@@ -1,11 +1,13 @@
using Microsoft.Extensions.Logging;
+using Microsoft.Extensions.Options;
using System;
using System.Threading.Tasks;
+using Timeline.Configs;
using Timeline.Entities;
using Timeline.Helpers;
using Timeline.Services.Exceptions;
-namespace Timeline.Services
+namespace Timeline.Services.Token
{
public class UserTokenCreateResult
{
@@ -44,14 +46,16 @@ namespace Timeline.Services
public class UserTokenManager : IUserTokenManager
{
private readonly ILogger<UserTokenManager> _logger;
+ private readonly IOptionsMonitor<TokenOptions> _tokenOptionsMonitor;
private readonly IUserService _userService;
private readonly IUserCredentialService _userCredentialService;
private readonly IUserTokenHandler _userTokenService;
private readonly IClock _clock;
- public UserTokenManager(ILogger<UserTokenManager> logger, IUserService userService, IUserCredentialService userCredentialService, IUserTokenHandler userTokenService, IClock clock)
+ public UserTokenManager(ILogger<UserTokenManager> logger, IOptionsMonitor<TokenOptions> tokenOptionsMonitor, IUserService userService, IUserCredentialService userCredentialService, IUserTokenHandler userTokenService, IClock clock)
{
_logger = logger;
+ _tokenOptionsMonitor = tokenOptionsMonitor;
_userService = userService;
_userCredentialService = userCredentialService;
_userTokenService = userTokenService;
@@ -69,7 +73,13 @@ namespace Timeline.Services
var userId = await _userCredentialService.VerifyCredential(username, password);
var user = await _userService.GetUser(userId);
- var token = _userTokenService.GenerateToken(new UserTokenInfo { Id = user.Id, Version = user.Version, ExpireAt = expireAt });
+
+ var token = _userTokenService.GenerateToken(new UserTokenInfo
+ {
+ Id = user.Id,
+ Version = user.Version,
+ ExpireAt = expireAt ?? _clock.GetCurrentTime() + TimeSpan.FromSeconds(_tokenOptionsMonitor.CurrentValue.DefaultExpireSeconds)
+ });
return new UserTokenCreateResult { Token = token, User = user };
}
@@ -82,12 +92,9 @@ namespace Timeline.Services
var tokenInfo = _userTokenService.VerifyToken(token);
- if (tokenInfo.ExpireAt.HasValue)
- {
- var currentTime = _clock.GetCurrentTime();
- if (tokenInfo.ExpireAt < currentTime)
- throw new UserTokenTimeExpiredException(token, tokenInfo.ExpireAt.Value, currentTime);
- }
+ var currentTime = _clock.GetCurrentTime();
+ if (tokenInfo.ExpireAt < currentTime)
+ throw new UserTokenTimeExpiredException(token, tokenInfo.ExpireAt, currentTime);
try
{