Dart http:在获取新的访问令牌后重试 http.Request 时“状态错误:无法完成最终请求”

2023-12-21

我目前正在尝试访问 Flutter 中的 Web API,该 API 需要 JWT 访问令牌进行授权。访问令牌会在一段时间后过期。

可以使用单独的刷新令牌来请求新的访问令牌。现在,一旦请求返回 401 响应,就会执行此访问令牌刷新。之后,应使用新的访问令牌重试失败的请求.

我在最后一步遇到了麻烦。这似乎是一个http.BaseRequest只能发送一次。如何使用新令牌重试 http 请求?


正如建议的飞镖 http 自述文件 https://github.com/dart-lang/http#using,我创建了一个子类http.BaseClient添加授权行为。这是一个简化版本:

import 'dart:async';

import 'package:http/http.dart' as http;

class AuthorizedClient extends http.BaseClient {
  AuthorizedClient(this._authService) : _inner = http.Client();

  final http.Client _inner;
  final AuthService _authService;

  Future<http.StreamedResponse> send(http.BaseRequest request) async {
    final token = await _authService.getAccessToken();
    request.headers['Authorization'] = 'Bearer $token';

    final response = await _inner.send(request);

    if (response.statusCode == 401) {
      final newToken = await _authService.refreshAccessToken();
      request.headers['Authorization'] = 'Bearer $newToken';

      // throws error: Bad state: Can't finalize a finalized Request
      final retryResponse = await _inner.send(request);

      return retryResponse;
    }

    return response;
  }
}

abstract class AuthService {
  Future<String> getAccessToken();
  Future<String> refreshAccessToken();
}

这是我到目前为止根据理查德·希普的回答得出的结论:要重新发送请求,我们必须复制它。

到目前为止我还无法找到流请求的解决方案!

http.BaseRequest _copyRequest(http.BaseRequest request) {
  http.BaseRequest requestCopy;

  if(request is http.Request) {
    requestCopy = http.Request(request.method, request.url)
      ..encoding = request.encoding
      ..bodyBytes = request.bodyBytes;
  }
  else if(request is http.MultipartRequest) {
    requestCopy = http.MultipartRequest(request.method, request.url)
      ..fields.addAll(request.fields)
      ..files.addAll(request.files);
  }
  else if(request is http.StreamedRequest) {
    throw Exception('copying streamed requests is not supported');
  }
  else {
    throw Exception('request type is unknown, cannot copy');
  }

  requestCopy
    ..persistentConnection = request.persistentConnection
    ..followRedirects = request.followRedirects
    ..maxRedirects = request.maxRedirects
    ..headers.addAll(request.headers);

  return requestCopy;
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Dart http:在获取新的访问令牌后重试 http.Request 时“状态错误:无法完成最终请求” 的相关文章

随机推荐

  • maven程序集,避免zip文件中的完整路径?

    我有一个多模块项目 其中包含 2 个模块 每个模块都有自己的 pom xml 和指向这些模块的父 pom xml 当我在父 pom 上运行 mvn clean package 时 每个项目最终都会在其自己的目标文件夹下生成一个 zip 文件
  • 无法将图像上传到 WCF Rest 服务

    我正在创建 WCF Rest 服务以从移动应用程序上传图像 但我得到了 远程服务器返回错误 400 错误请求 任何人都可以指出我做错了什么吗 以下是我的定义 OperationContract WebInvoke BodyStyle Web
  • Vim 和 Java:自动添加 java import 语句

    The tip http vim wikia com wiki Add Java import statements automatically错误是 E349 光标下没有标识符 E433 没有标签文件 和 E426 找不到标签 公共 我觉
  • SQL 查询 - 跨多个字段搜索

    我正在尝试实现一种搜索 您可以在其中输入多个搜索词来形成 AND 条件 它还应该在数据库的不同字段中进行搜索 例如 当你进入时的你 比尔 西雅图 你应该得到一个记录NAME火柴Bill and CITY火柴Seattle 你不应该得到任何只
  • 使用 JAXB 解组 XML,无需取消转义字符

    想象一下以下情况 我们从某些外部工具收到一个 xml 文件 最近 在此 xml 中 节点名中或其 richcontent 标记中可能存在一些转义字符 如以下示例 简化 所示
  • NSMutableData 消失

    在我的程序中 我有一个 NSMutableData 变量 用于收集信息http www nhara org scored races 2013 htm http www nhara org scored races 2013 htm 大约第
  • peewee - 与 Database() 初始化分开定义模型

    我需要使用一些 ORM 引擎 比如peewee 用于在我的 python 应用程序中处理 SQLite 数据库 然而 大多数此类库都提供这样的语法来定义models py import peewee db peewee Database h
  • React:无法导入 .tsx 文件

    刚开始将 TypeScript 与 React 结合使用 当我导入来自 tsx 文件的组件时 默认情况下它假定它是 js 文件 该错误表明该目录中没有 About js 文件或 Contact js 文件 此外 TS linter 不允许我
  • MongoError:没有经过身份验证的用户

    我正在尝试编写一个脚本来使用以下命令将管理员用户和通用用户添加到 MongoDB 数据库mongodbNodeJS 驱动程序 版本3 0 1 我可以创建数据库的管理员用户 但不能创建普通用户 我总是得到MongoError there ar
  • 带子域和 url 模式的 mod_rewrite

    我想使用子域作为 mod rewrite 的获取变量并使用一些参数 eg page language site counter gt index php o operator lg language s arg1 c arg2 如何使用 m
  • 解决 XCode 7 崩溃报告器中的问题

    我最近发布了我的应用程序的 2 0 版本 https itunes apple com app neo virtual reality for reddit id1013650716 https itunes apple com app n
  • 如何从 Android 设备屏幕制作 GIF

    我可以捕获 Android 设备屏幕 adb shell screencap p perl pe s x0D x0A x0A g gt adb screenshot date Y m d H M S png 如何将所有这些图像压缩成单个 G
  • FormContext 在本地 SimpleForm 内返回“null”

    希望有人能指出我正确的方向来尝试调试这个问题 我正在将使用react admin构建的应用程序重构为版本4 0 0 beta 3 但我的自定义表单都无法正常工作 也就是说 当我调用任何新的react hook form方法 例如 useFo
  • CArray 不会在内存重新分配时调用复制构造函数,现在怎么办?

    假设我有一个类需要调用复制构造函数来制作正确的副本 struct CWeird CWeird number 47 target number CWeird const CWeird other number other number tar
  • 如何让两个多播套接字监听具有相同端口的两个多播通道

    我大致有以下多播套接字代码 效果很好 现在我需要在同一台机器上加入两个多播频道 例如 224 10 13 18 55001 224 10 13 34 55001 根据它来自哪个 IP 地址 我需要以不同的方式处理该消息 问题是如何为端口值相
  • 连接到 Joomla 中的第 3 方数据库?

    我需要连接到 Joomla 中的另一个数据库 那是在另一台服务器上 这是一个插件 我需要从表中提取一些数据 现在我不想用这个数据库来运行Joomla 我已经有了Joomla 在其服务器上的自己的数据库上安装并运行 但我想连接到另一个数据库
  • 客户端中未正确捕获 WCF 自定义错误异常

    我正在尝试创建一些自定义的FaultException 我做了一个DataContract类称为CreateFault DataContract public class CreateFault private string report
  • Flask Admin Model查看CREATE和EDIT之间的不同字段

    在使用 Flask Admin 的 Flask 应用程序中 我希望能够在 ModelView 的编辑部分中定义与创建部分中不同的表单字段 The form columns设置适用于创建和编辑 但我似乎找不到一种方法来为每个部分提供不同的列集
  • 仅公开 Rust 库中通用私有类型的具体变体

    我有一个 Rust 库箱 其代码结构如下 pub struct Foo
  • Dart http:在获取新的访问令牌后重试 http.Request 时“状态错误:无法完成最终请求”

    我目前正在尝试访问 Flutter 中的 Web API 该 API 需要 JWT 访问令牌进行授权 访问令牌会在一段时间后过期 可以使用单独的刷新令牌来请求新的访问令牌 现在 一旦请求返回 401 响应 就会执行此访问令牌刷新 之后 应使