使用 .NET Core 的 Firebase 身份验证 (JWT)
Posted
技术标签:
【中文标题】使用 .NET Core 的 Firebase 身份验证 (JWT)【英文标题】:Firebase Authentication (JWT) with .NET Core 【发布时间】:2017-07-09 06:47:33 【问题描述】:我正在开发一个简单的 API,用于处理 Firebase 进行的身份验证 - 稍后将用于 android 客户端。
所以在 Firebase 控制台中,我启用了 Facebook 和 Google 登录方法并创建了一个示例 html 页面,我可以使用它来测试登录方法 - 下一个函数由按钮调用:
function loginFacebook()
var provider = new firebase.auth.FacebookAuthProvider();
var token = "";
firebase.auth().signInWithPopup(provider).then(function (result)
var token = result.credential.accessToken;
var user = result.user;
alert("login OK");
user.getToken().then(function (t)
token = t;
loginAPI();
);
).catch(function (error)
var errorCode = error.code;
var errorMessage = error.message;
alert(errorCode + " - " + errorMessage);
);
接下来,我使用令牌并通过 jQuery 的简单 ajax 调用将其发送到我的 API:
function loginAPI()
$.ajax(
url: "http://localhost:58041/v1/Users/",
dataType: 'json',
type: 'GET',
beforeSend: function (xhr)
xhr.setRequestHeader("Accept", "application/json");
xhr.setRequestHeader("Content-Type", "application/json");
xhr.setRequestHeader("Authorization", "Bearer " + token);
,
error: function (ex)
console.log(ex.status + " - " + ex.statusText);
,
success: function (data)
console.log(data);
return data;
);
下一站:API 后端 - 使用 .NET Core 编写。
在 Startup 下我配置了 JwtBearer Auth(包Microsoft.AspNetCore.Authentication.JwtBearer
):
app.UseJwtBearerAuthentication(new JwtBearerOptions
AutomaticAuthenticate = true,
IncludeErrorDetails = true,
Authority = "https://securetoken.google.com/PROJECT-ID",
TokenValidationParameters = new TokenValidationParameters
ValidateIssuer = true,
ValidIssuer = "https://securetoken.google.com/PROJECT-ID",
ValidateAudience = true,
ValidAudience = "PROJECT-ID",
ValidateLifetime = true,
,
);
这是控制器代码 - 带有[Authorize]
属性:
[Authorize]
[Route("v1/[controller]")]
public class UsersController : Controller
private readonly ILogger _logger;
private readonly UserService _userService;
public UsersController(ILogger<UsersController> logger, UserService userService)
_logger = logger;
_userService = userService;
[HttpGet]
public async Task<IList<User>> Get()
return await _userService.GetAll();
API 响应是 200 OK(HttpContext.User.Identity.IsAuthenticated
在控制器内是 true
),但我认为它不应该。我的问题是我不完全确定这是安全的。
这是如何检查 JWT 令牌的签名部分的?我看到很多代码示例提到 x509 或 RS256 算法,它们在哪里适合?不应该使用TokenValidationParameters
类中的IssuerSigningKey
或TokenDecryptionKey
检查某种证书或私钥吗?我错过了什么?
有关该问题的相关知识来源:
https://blog.markvincze.com/secure-an-asp-net-core-api-with-firebase/ SPA - Firebase and .Net WebApi 2 authentication https://stormpath.com/blog/token-authentication-asp-net-core https://jwt.io/ https://firebase.google.com/docs/auth/admin/verify-id-tokens【问题讨论】:
即使不传递Authorization
标头,响应也是200 OK
?那肯定是错的。在app.UseJwtBearerAuthentication()
之前或之后有app.UseMvc()
电话吗?
如果我没有传递Authorization
标头,则响应为401
。 app.UseMvc()
在 app.UseJwtBearerAuthentication()
之后。我只是不确定安全性。我试图破解我的应用程序但无法破解。也许我只是偏执。
嗯,但你说响应“不应该是 200”。为什么?您是否故意在标头中传递了不正确的标记?或者你为什么期望响应不是 200?
由于我没有在我的代码中的任何地方提供私钥,所以我认为这应该行不通,但是在无法破解它之后,我认为我只是偏执。
恐怕您误解了令牌签名在此流程中的工作原理。您的应用程序不应提供(或拥有)私钥(或任何类型的密钥)。我在我的博文中添加了对流程的描述:blog.markvincze.com/secure-an-asp-net-core-api-with-firebase/…
【参考方案1】:
Firebase 使用 RSA256 非对称密钥加密系统,这意味着它具有公钥和私钥。 签名令牌使用私钥进行,而验证令牌使用公钥进行。
下图说明了令牌签名是如何发生的。
在登录和访问安全端点期间,涉及以下步骤。
-
当我们的应用程序启动时(然后也定期启动)
JwtBearerMiddleware
调用https://securetoken.google.com/my-firebase-project/.well-known/openid-configuration
,它可以访问 Google 当前的公钥。
重要的是,当我们使用公钥非对称密码系统时,公钥不会保密,而是公开发布。
客户端通过 Firebase 使用其凭据登录(这些是客户端自己的凭据,它们与用于签署令牌的密钥无关)。
如果登录成功,Firebase 会为客户端构造一个 JWT 令牌。该令牌的一个关键部分是使用密钥对的私钥进行签名。与公钥不同的是,私钥永远不会公开,它在 Google 的基础架构中作为秘密保存。
客户端收到 JWT 令牌。
客户端调用我们 Api 上的安全端点,并将令牌放入 Authorization
标头中。
此时,管道中的JwtBearerMiddleware
会检查此令牌,并验证它是否有效(是否使用 Google 的私钥签名)。这里要意识到的重要一点是,为了进行验证,我们的 Api 不需要访问私钥。只有公钥是必要的。验证后,中间件会相应地填充HttpContext.User
和HttpContext.User.Identity.IsAuthenticated
。
您可以在 RSA Wikipedia page 上找到对此概念的更简单描述,在 my blog post 上找到有关 Firebase + ASP.NET 的更多信息。
【讨论】:
我创建了一个涵盖这个gist.github.com/deeja/c67e6027ca37a8d6a367b8b8bf86d5c6的要点【参考方案2】:对于后端,有一个 Nuget 包可以为您解决问题:
安装包 AspNetCore.Firebase.Authentication
public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
app.UseFirebaseAuthentication("https://securetoken.google.com/MYPROJECTNAME", "MYPROJECTNAME");
它负责受众、发行者、签名和有效性验证
【讨论】:
不确定这是否适用于 ASP .NET Core 2.0。我收到以下错误:无法从程序集“Microsoft.AspNetCore.Authentication.JwtBearer, Version=2.0.0.0 加载类型“Microsoft.AspNetCore.Builder.JwtBearerOptions” @Raphaël ApiKey 有什么用? @TzviGregoryKaidanov 实际上它在 appsettings 中,但未使用,因为中间件仅验证令牌和签名,不需要 ApiKey @Primico 我发布了一个 .netcore2.0 兼容包 嗨@Raphaël,我在.Net Core 2.1 上使用你的nuget 包非常好。但它不适用于 .Net Core 3.1。你能帮我检查一下这个问题吗?【参考方案3】:NuGet 数据包使用旧的 ASP NET Core 1.x 身份验证机制
认证已更改:https://docs.microsoft.com/en-us/aspnet/core/migration/1x-to-2x/identity-2x
【讨论】:
发布了支持.aspnetcore2.0的包AspNetCore.Firebase.Authentication 2.0以上是关于使用 .NET Core 的 Firebase 身份验证 (JWT)的主要内容,如果未能解决你的问题,请参考以下文章
Dora.Interception,为.NET Core度身打造的AOP框架 [2]:以约定的方式定义拦截器
Dora.Interception, 为.NET Core度身打造的AOP框架[4]:演示几个典型应用
Dora.Interception,为.NET Core度身打造的AOP框架 [3]:多样化拦截器应用方式
Dora.Interception,为.NET Core度身打造的AOP框架 [5]:轻松地实现与其他AOP框架的整合