You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Azure Function(HTTP Trigger)为Angular4实现OAuth用户认证及解决授权问题

嘿,我之前也踩过Azure Functions里[Authorize]属性的坑,它和ASP.NET Core Web API里的用法不太一样,咱们一步步来解决你的问题:

解决Azure Functions中[Authorize]注解不生效的问题

1. 先理清Azure Functions身份验证的核心逻辑

Azure Functions的[Authorize]属性本身不会单独生效,它是依赖于函数应用层面的身份验证/授权配置的。默认情况下,函数应用允许匿名访问,所以就算你加了注解,也拦不住未授权请求。

2. 先开启函数应用的身份验证开关(关键第一步)

你得先在Azure门户里给函数应用配置基础身份验证规则:

  • 进入你的Function App后台,找到左侧菜单的身份验证选项
  • 点击添加身份验证提供程序,选择自定义(因为你要自己用Users表实现令牌验证)
  • 在「请求未经过身份验证时要执行的操作」里选返回HTTP 401未授权,这样匿名请求会被先拦截
  • 保存配置,这时候[Authorize]属性才会真正开始起作用

3. 实现自定义令牌验证的完整流程

既然要基于自己的Users表做类似OAuth的令牌认证,需要分两步走:

第一步:写登录函数生成令牌

先做一个公开的登录接口,接收用户名密码,查询Users表验证身份,然后生成并返回自定义令牌(推荐用JWT,方便携带和验证):

[FunctionName("Login")]
public static async Task<IActionResult> Login(
    [HttpTrigger(AuthorizationLevel.Anonymous, "post", Route = null)] HttpRequest req,
    ILogger log)
{
    var requestBody = await new StreamReader(req.Body).ReadToEndAsync();
    var loginModel = JsonConvert.DeserializeObject<LoginModel>(requestBody);
    
    // 从Azure DB查询用户,验证密码(注意密码要哈希存储,别用明文)
    var user = await GetUserFromDatabase(loginModel.Username);
    if (user == null || !VerifyPassword(loginModel.Password, user.HashedPassword))
    {
        return new UnauthorizedResult();
    }
    
    // 生成JWT令牌,包含用户信息、过期时间等
    var token = GenerateJwtToken(user);
    return new OkObjectResult(new { Token = token });
}

第二步:在受保护函数里验证令牌

给需要授权的函数加上[Authorize],同时手动验证请求头里的令牌(因为是自定义逻辑,需要自己校验合法性):

[FunctionName("GetUserProfile")]
[Authorize]
public static async Task<IActionResult> GetUserProfile(
    [HttpTrigger(AuthorizationLevel.Anonymous, "get", Route = null)] HttpRequest req,
    ILogger log)
{
    // 从请求头提取令牌
    var token = req.Headers["Authorization"].FirstOrDefault()?.Split(" ").Last();
    if (string.IsNullOrEmpty(token))
    {
        return new UnauthorizedResult();
    }
    
    // 验证令牌:检查签名、过期时间,关联到Users表的有效用户
    var isValid = ValidateJwtToken(token);
    if (!isValid)
    {
        return new UnauthorizedResult();
    }
    
    // 执行业务逻辑,返回用户数据
    var userProfile = await GetUserProfileFromDatabase(token);
    return new OkObjectResult(userProfile);
}

如果觉得每个函数都写验证太麻烦,也可以做一个自定义身份验证中间件,把令牌验证逻辑统一抽离出来。

4. Angular端的请求处理

登录成功后把令牌存在本地存储,然后用HTTP拦截器自动给所有请求带上Authorization头:

@Injectable()
export class AuthInterceptor implements HttpInterceptor {
  intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    const authToken = localStorage.getItem('authToken');
    if (authToken) {
      request = request.clone({
        setHeaders: {
          Authorization: `Bearer ${authToken}`
        }
      });
    }
    return next.handle(request);
  }
}

记得把这个拦截器注册到你的Angular模块里,这样所有请求都会自动携带令牌。

常见坑点提醒

  • 别搞混AuthorizationLevel和[Authorize]:HttpTrigger里的AuthorizationLevel要设为Anonymous,因为我们靠函数应用的身份验证拦截请求,而不是Azure内置的Function/Admin级别授权
  • 令牌一定要加过期时间,避免永久有效
  • Users表的密码必须用哈希算法(比如BCrypt)存储,绝对不能存明文

内容的提问来源于stack exchange,提问作者Muhammad Fuzail Zubari

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 08:40:44