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

在JavaScript(Remix框架)中如何同时检查响应状态并获取返回数据?

问题

时隔许久重新在个人项目中使用JavaScript,当前用Remix框架对接独立后端。在发起创建用户这类POST请求时,希望既能验证请求是否成功,又能获取后端返回的响应数据——比如创建记录后,后端会返回带自动分配ID的新记录,方便跳转到对应文档页面。

但现在的实现里响应数据“消失”了。我理解是因为response.ok会处理Promise,之后再尝试访问response.id时,响应已经被“清空”。想问怎么重构代码,先验证状态再分支处理?总觉得先等Promise完成再处理的方式有点繁琐。

代码示例:

export async function action({ request }: ActionArgs) {
  const body = await request.formData();

  // 构造要提交的document对象

  const response = await fetch("http://backend:8000/documents/create", {
    method: "POST",
    headers: { "Content-Type": "application/json" },
    body: JSON.stringify(document)
  });

  if (response.ok) {
    const documentId = response.id;

    return redirect("/documents/" + documentId);
  }
  else if (response.status == 400) {
    errors.document = "Document creation failed";
  }

  return json({ errors });
}

解决方案

核心问题是你误解了response.ok的作用——它只是个布尔值,不会消耗响应体。真正的问题是你直接访问response.id的方式错误,后端返回的JSON数据需要通过response.json()解析,这个方法会返回Promise,且调用后响应体就会被读取(不能重复读取)。

重构思路很直接:先判断响应状态,再按需解析响应体,用await处理完全不繁琐,反而逻辑更清晰。

修正后的代码:

export async function action({ request }: ActionArgs) {
  const body = await request.formData();
  const errors = {}; // 提前初始化errors对象,避免未定义报错

  // 构造要提交的document对象
  const document = { /* 填入你的文档数据 */ };

  const response = await fetch("http://backend:8000/documents/create", {
    method: "POST",
    headers: { "Content-Type": "application/json" },
    body: JSON.stringify(document)
  });

  if (response.ok) {
    // 解析后端返回的JSON响应体,得到完整的创建后文档数据
    const createdDocument = await response.json();
    // 从解析后的对象中取出ID
    const documentId = createdDocument.id;

    return redirect(`/documents/${documentId}`);
  } else if (response.status === 400) {
    errors.document = "Document creation failed";
  } else {
    // 补充处理其他错误状态,比如服务器内部错误
    errors.document = "Server error, please try again later";
  }

  return json({ errors });
}

关键说明:

  • response.ok仅用于判断响应状态码是否在200-299区间,不会触发响应体读取,不存在“清空”问题。
  • 后端返回的JSON数据必须通过await response.json()解析成JavaScript对象后,才能访问id这类属性。
  • 提前初始化errors对象,避免未定义导致的运行时错误。
  • 用模板字符串拼接跳转路径比字符串拼接更简洁易读。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.02 02:05:13