Срок действия обновления токена истёк, как только токен доступа
Я реализую токен обновления JWT и задаю другое время истечения для токена обновления, но оно истекает так же, как токен доступа
var refreshTokenId = Guid.NewGuid().ToString("n");
DateTime refreshTokenLifeTime = context.OwinContext.Get<DateTime>("as:clientRefreshTokenLifeTime");
Сохранить в базе данных
RefreshToken refreshToken = new RefreshToken();
refreshToken.Token = refreshTokenId;
refreshToken.PrivateKey = context.SerializeTicket();
refreshToken.ExpiryDate = refreshTokenLifeTime;
Конец сохранения Db
context.Ticket.Properties.IssuedUtc = DateTime.Now;
context.Ticket.Properties.ExpiresUtc = refreshTokenLifeTime;
context.SetToken(refreshTokenId);
context.SetToken(context.SerializeTicket());
Любая помощь, что я делаю не так?
2 ответа
Токен обновления не продлевает время истечения, это называется скользящим истечением, и вы не можете сделать это с токенами доступа. Я использовал токен обновления для обновления ролей пользователя, а не для срока действия. Проверьте эту ссылку на SlidingExpiration. Я использовал приведенный ниже код, чтобы обновить токен и сохранить его.
public class SimpleRefreshTokenProvider : IAuthenticationTokenProvider
{
public async Task CreateAsync(AuthenticationTokenCreateContext context)
{
var clientid = context.Ticket.Properties.Dictionary["as:client_id"];
if (string.IsNullOrEmpty(clientid))
{
return;
}
var refreshTokenId = Guid.NewGuid().ToString("n");
using (AuthRepository _repo = new AuthRepository())
{
var refreshTokenLifeTime = context.OwinContext.Get<string>("as:clientRefreshTokenLifeTime");
var token = new RefreshToken()
{
Id = Helper.GetHash(refreshTokenId),
ClientId = clientid,
Subject = context.Ticket.Identity.Name,
IssuedUtc = DateTime.UtcNow,
ExpiresUtc = DateTime.UtcNow.AddMinutes(Convert.ToDouble(refreshTokenLifeTime))
};
context.Ticket.Properties.IssuedUtc = token.IssuedUtc;
context.Ticket.Properties.ExpiresUtc = token.ExpiresUtc;
token.ProtectedTicket = context.SerializeTicket();
var result = await _repo.AddRefreshToken(token);
if (result)
{
context.SetToken(refreshTokenId);
}
}
}
public async Task ReceiveAsync(AuthenticationTokenReceiveContext context)
{
var allowedOrigin = context.OwinContext.Get<string>("as:clientAllowedOrigin");
context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { allowedOrigin });
string hashedTokenId = Helper.GetHash(context.Token);
using (AuthRepository _repo = new AuthRepository())
{
var refreshToken = await _repo.FindRefreshToken(hashedTokenId);
if (refreshToken != null )
{
//Get protectedTicket from refreshToken class
context.DeserializeTicket(refreshToken.ProtectedTicket);
var result = await _repo.RemoveRefreshToken(hashedTokenId);
}
}
}
}
Теперь контекст запроса содержит все заявки, сохраненные ранее для этого пользователя, и вам нужно добавить логику, которая позволяет выдавать новые заявки или обновлять существующие заявки и содержать их в новый токен доступа, сгенерированный до того, как вам потребуется добавить приведенный ниже код в классе AuthorizationServerProvider у вас есть.
public override Task GrantRefreshToken(OAuthGrantRefreshTokenContext context)
{
var originalClient = context.Ticket.Properties.Dictionary["as:client_id"];
var currentClient = context.ClientId;
if (originalClient != currentClient)
{
context.SetError("invalid_clientId", "Refresh token is issued to a different clientId.");
return Task.FromResult<object>(null);
}
// Change auth ticket for refresh token requests
var newIdentity = new ClaimsIdentity(context.Ticket.Identity);
newIdentity.AddClaim(new Claim("newClaim", "newValue"));
var newTicket = new AuthenticationTicket(newIdentity, context.Ticket.Properties);
context.Validated(newTicket);
return Task.FromResult<object>(null);
}
Это не верно
DateTime refreshTokenLifeTime = context.OwinContext.Get<DateTime>("as:clientRefreshTokenLifeTime");
вы читаете время жизни, а не устанавливаете для него какое-либо новое значение.