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

Flutter用户认证后调用Firebase实时数据库REST API返回404错误

问题原因与修复方案

1. 令牌获取逻辑空安全错误

Auth类的token getter判断顺序错误,先访问了_expiryDate!再判断_expiryDate是否为空,会触发空异常导致返回null令牌:
原有代码:

String? get token {
  if(_token != null && _expiryDate!.isAfter(DateTime.now()) && _expiryDate != null) {
    return _token;
  }
  return null;
}

调整判断顺序修复:

String? get token {
  if(_token != null && _expiryDate != null && _expiryDate!.isAfter(DateTime.now())) {
    return _token;
  }
  return null;
}

2. 数据库请求URL拼接错误,额外携带错误认证头

这是触发404报错的核心原因:
使用Uri.https构造请求时,直接把查询参数?auth=$token拼到了路径参数里,Uri会自动对特殊字符做转义,导致实际请求的路径错误触发404。同时额外加了Basic类型的Authorization头,Firebase实时数据库的REST接口不支持Basic认证,两种认证方式冲突也会导致权限校验失败。
原有请求代码:

final url = Uri.https('form-app-c5343-default-rtdb.firebaseio.com', '/products.json?auth=$token');
final response = await http.get(
    url,
    headers: {
      HttpHeaders.authorizationHeader : "Basic $token"
    }
);

修改后将查询参数放到Uri.https的第三个参数中,删除错误的认证头即可:

final url = Uri.https(
  'form-app-c5343-default-rtdb.firebaseio.com', 
  '/products.json',
  {'auth': token} // 查询参数单独传入避免转义
);
final response = await http.get(url);

如果偏向用请求头传递令牌,也可以改成Bearer类型的头,不需要在URL带参数:

final url = Uri.https('form-app-c5343-default-rtdb.firebaseio.com', '/products.json');
final response = await http.get(
    url,
    headers: {
      HttpHeaders.authorizationHeader : "Bearer $token"
    }
);

3. 缺少响应状态码判断逻辑

原有逻辑拿到响应后没有先判断状态码就直接解码,请求失败时返回的非JSON内容会触发解析异常,建议增加状态码校验:

final response = await http.get(url);
if (response.statusCode >= 400) {
  throw HttpException('请求失败,状态码:${response.statusCode}');
}
final extractedData = json.decode(response.body);

内容的提问来源于stack exchange,提问作者coolhack7

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.07 07:54:02