我找到了两个可能的解决方案,它们都是相等的,但发生在OIDC中间件的不同时间。在事件中,我提取访问令牌到期时间值并将其存储为声明,稍后可以使用该声明来检查是否可以使用当前访问令牌调用Web API,或者是否应该使用刷新令牌请求新的访问令牌。
如果有人能够给出任何关于哪个事件更可取的意见,我将不胜感激。
var oidcOptions = new OpenIdConnectOptions
{
AuthenticationScheme = appSettings.OpenIdConnect.AuthenticationScheme,
SignInScheme = appSettings.OpenIdConnect.SignInScheme,
Authority = appSettings.OpenIdConnect.Authority,
RequireHttpsMetadata = _hostingEnvironment.IsDevelopment() ? false : true,
PostLogoutRedirectUri = appSettings.OpenIdConnect.PostLogoutRedirectUri,
ClientId = appSettings.OpenIdConnect.ClientId,
ClientSecret = appSettings.OpenIdConnect.ClientSecret,
ResponseType = appSettings.OpenIdConnect.ResponseType,
UseTokenLifetime = appSettings.OpenIdConnect.UseTokenLifetime,
SaveTokens = appSettings.OpenIdConnect.SaveTokens,
GetClaimsFromUserInfoEndpoint = appSettings.OpenIdConnect.GetClaimsFromUserInfoEndpoint,
Events = new OpenIdConnectEvents
{
OnTicketReceived = TicketReceived,
OnUserInformationReceived = UserInformationReceived
},
TokenValidationParameters = new TokenValidationParameters
{
NameClaimType = appSettings.OpenIdConnect.NameClaimType,
RoleClaimType = appSettings.OpenIdConnect.RoleClaimType
}
};
oidcOptions.Scope.Clear();
foreach (var scope in appSettings.OpenIdConnect.Scopes)
{
oidcOptions.Scope.Add(scope);
}
app.UseOpenIdConnectAuthentication(oidcOptions);
这里有一些我可以选择的事件示例:
public async Task TicketReceived(TicketReceivedContext trc)
{
await Task.Run(() =>
{
Debug.WriteLine("TicketReceived");
ClaimsPrincipal p = TransformClaims(trc.Ticket.Principal);
trc.Principal = p;
});
}
我也有UserInformationReceived事件,不确定是否应该使用它来代替TicketReceived事件。
public async Task UserInformationReceived(UserInformationReceivedContext uirc)
{
await Task.Run(() =>
{
Debug.WriteLine("UserInformationReceived");
var identity = uirc.Ticket.Principal.Identity as ClaimsIdentity;
identity.AddClaim(new Claim("expires_in", DateTime.Now.AddSeconds(Convert.ToDouble(uirc.ProtocolMessage.ExpiresIn)).ToLocalTime().ToString()));
});
}