我有一个单页应用 - 或多或少基于MVC5 SPA模板 - 使用承载令牌进行身份验证。
该网站还有一些传统的MVC页面,需要加以保护,但使用 cookie身份验证。
在Startup.Auth中我可以启用两种类型的授权:
app.UseCookieAuthentication(new CookieAuthenticationOptions());
app.UseOAuthBearerTokens(OAuthOptions);
但是,这似乎有副作用,因为无论何时从SPA发送AJAX请求,它都会在标题和 Cookie中发送承载令牌。
而我真正想要的行为是仅承载令牌用于WebAPI调用,而只用于MVC调用的cookie。
我还希望MVC调用在未经授权时重定向到登录页面(设置为CookieAuthenticationOption),但显然我不希望在进行API调用时发生这种情况。
有没有办法在一个应用程序中进行这种类型的混合模式身份验证?也许通过路径/路由过滤器?
答案 0 :(得分:46)
我想我是这样做的: -
Startup.Auth正在连接OWIN管道,因此在那里包含Cookie和令牌是正确的。但是对cookie选项的一个更改指定了它应该应用于的身份验证类型:
CookieOptions = new CookieAuthenticationOptions
{
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie
};
然后我需要将WebAPI配置为仅使用令牌:
public static void Configure(HttpConfiguration config)
{
// Configure Web API to use only bearer token authentication.
config.SuppressDefaultHostAuthentication();
config.Filters.Add(new HostAuthenticationFilter(OAuthDefaults.AuthenticationType));
}
这似乎实现了我想要的。 WebAPI只使用承载令牌而不使用cookie,一些常规MVC页面在登录后使用cookie(使用AuthenticationManager)。
答案 1 :(得分:2)
你可以在http-only模式下将jwt标记添加到cookie(这里我的jwt标记cookie名称是“access_token”),并制作这样的中间件
public class JwtCookieMiddleware
{
private readonly RequestDelegate _next;
public JwtCookieMiddleware(RequestDelegate next)
{
_next = next;
}
public Task Invoke(HttpContext ctx)
{
if (ctx.Request.Cookies.TryGetValue("access_token", out var accessToken))
{
if (!string.IsNullOrEmpty(accessToken))
{
string bearerToken = String.Format("Bearer {0}", accessToken);
ctx.Request.Headers.Add("Authorization",bearerToken);
}
}
return this._next(ctx);
}
}
public static class JwtCookieMiddlewareExtensions
{
public static IApplicationBuilder UseJwtCookie(this IApplicationBuilder build)
{
return build.UseMiddleware<JwtCookieMiddleware>();
}
}
你需要在启动时使用这样的中间件:
app.UseJwtCookie();
app.UseAuthentification();
app.UseMvc();
如果此请求带有令牌cookie,则上面的代码会将jwt令牌添加到http请求头;