如何在ASP.NET Core Web API中实现Google认证登录与注册?
解决方案步骤
1. 安装依赖包
先安装用于验证Google ID Token的NuGet包,推荐使用Google.Apis.Auth.AspNetCore3,它封装了Google认证的常用操作:
Install-Package Google.Apis.Auth.AspNetCore3
2. 配置Google客户端ID
在appsettings.json中添加和前端一致的Google OAuth客户端ID:
"Authentication": { "Google": { "ClientId": "你的Google客户端ID.apps.googleusercontent.com" } }
3. 修正后端接口参数
前端通过请求体发送token,所以接口要改用[FromBody]接收,先创建一个请求模型:
public class GoogleLoginRequest { public string Token { get; set; } } [HttpPost("google-login")] public async Task<IActionResult> GoogleLogin([FromBody] GoogleLoginRequest request) { // 后续逻辑写在这里 }
4. 验证并解析Google ID Token
使用Google SDK验证token有效性,并提取用户核心信息:
using Google.Apis.Auth; // 从配置读取客户端ID var googleClientId = Configuration["Authentication:Google:ClientId"]; try { // 验证ID Token合法性 var payload = await GoogleJsonWebSignature.ValidateAsync(request.Token, new GoogleJsonWebSignature.ValidationSettings { Audience = new List<string> { googleClientId } }); // 解析出的用户信息 var googleUserId = payload.Subject; var email = payload.Email; var name = payload.Name; var avatarUrl = payload.Picture; var isEmailVerified = payload.EmailVerified; // Google返回的邮箱默认已验证 } catch (InvalidJwtException) { // Token无效时返回401 return Unauthorized("无效的Google认证凭证"); }
5. 处理用户注册/登录逻辑
假设你有自定义的用户实体AppUser和数据库上下文AppDbContext,按以下逻辑处理:
// 检查数据库中是否存在该Google用户 var user = await _context.AppUsers.FirstOrDefaultAsync(u => u.GoogleUserId == googleUserId); if (user == null) { // 不存在则创建新用户 user = new AppUser { GoogleUserId = googleUserId, Email = email, UserName = name, AvatarUrl = avatarUrl, EmailVerified = isEmailVerified, CreatedAt = DateTime.UtcNow }; _context.AppUsers.Add(user); await _context.SaveChangesAsync(); } // 生成自定义JWT令牌(供前端后续API请求使用) var jwtToken = GenerateJwtToken(user); // 返回用户信息和JWT return Ok(new { Id = user.Id, Name = user.UserName, Email = user.Email, AvatarUrl = user.AvatarUrl, Token = jwtToken });
6. 实现JWT生成方法
先在Program.cs中配置JWT服务:
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme) .AddJwtBearer(options => { options.TokenValidationParameters = new TokenValidationParameters { ValidateIssuer = true, ValidateAudience = true, ValidateLifetime = true, ValidateIssuerSigningKey = true, ValidIssuer = builder.Configuration["Jwt:Issuer"], ValidAudience = builder.Configuration["Jwt:Audience"], IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(builder.Configuration["Jwt:Key"])) }; }); // 添加授权服务 builder.Services.AddAuthorization();
在appsettings.json补充JWT配置:
"Jwt": { "Key": "你的JWT密钥(建议用32位以上的随机字符串)", "Issuer": "你的API域名,比如https://yourapi.com", "Audience": "你的前端域名,比如https://yourfrontend.com", "ExpiresInMinutes": 60 }
最后在控制器中实现生成JWT的方法:
using System.IdentityModel.Tokens.Jwt; using System.Security.Claims; using System.Text; private string GenerateJwtToken(AppUser user) { var claims = new[] { new Claim(JwtRegisteredClaimNames.Sub, user.Id.ToString()), new Claim(JwtRegisteredClaimNames.Email, user.Email), new Claim(JwtRegisteredClaimNames.Name, user.UserName), new Claim("GoogleUserId", user.GoogleUserId) }; var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(Configuration["Jwt:Key"])); var signingCreds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256); var token = new JwtSecurityToken( issuer: Configuration["Jwt:Issuer"], audience: Configuration["Jwt:Audience"], claims: claims, expires: DateTime.Now.AddMinutes(Convert.ToDouble(Configuration["Jwt:ExpiresInMinutes"])), signingCredentials: signingCreds); return new JwtSecurityTokenHandler().WriteToken(token); }
关键说明
- Token验证:必须校验
audience字段匹配你的客户端ID,防止恶意伪造请求。 - 用户逻辑:可根据业务需求调整用户创建规则,比如是否需要额外字段。
- JWT使用:前端拿到JWT后,后续请求需放在
Authorization头中(格式为Bearer {token}),后端用[Authorize]特性保护接口。
内容的提问来源于stack exchange,提问作者abus
相关产品推荐
相关产品推荐

