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

使用Fetch API无法获取CloudFront返回的自定义请求头问题

问题描述

我在Flask服务器上接收CloudFront返回的自定义请求头,想提取该头的值并展示在页面上。已经在两端完成CORS配置,响应头包含Access-control-allow-origin: *。

现在的问题是:点击调用CloudFront函数的按钮会触发多个网络请求,但用Fetch API无法获取包含所需自定义头的请求的响应头。

相关代码

1. 前端HTML中的JavaScript代码

<script>
function fibonacci() {
     var n = document.getElementById('fibCFInput').value;
     console.log("testing.." + n)
     //fetch('/fibonacci/' + n) //NOTE: neither fetch command has worked for me.
     fetch("<cloudfront url>/fibonacci/" + n)
     .then(response => {

     response.headers.forEach((value, name) => {
     console.log(`${name}: ${value}`);
     });

     const fibval = response.headers.get("Fibval");
     console.log(`fibval value: ${fibval}`);
     })
}
</script>

2. Flask路由代码

@app.route("/fibonacci/<int:value>", methods=['GET', 'OPTIONS'])
def fibonacci(value):
        url = f"<cloudfront url>/fibonacci/{value}"
        return redirect(url, code=302)

3. CloudFront函数代码

import cf from 'cloudfront';

async function handler(event) {
    const url = event.request;
    const pathSegments = url.uri.split('/')
    console.log(pathSegments)
    const key = pathSegments[2] //returns fib number from input
    console.log(key)
    var result = fibFunc(parseInt(key))
    const mainweburl = "http://fakeURL.com:portnumber/"
    const all = "*"
    var response = {
        statusCode: 302,
        statusDescription: 'Found',
        headers: {
        'access-control-allow-origin': {"value": all},
        "location": { "value": mainweburl},
        'fibval': {'value': result.toString()},
        }
    };
    return response;
}

试过多种打印方式和变量调整,也核对过CORS文档,但问题仍未解决。出于性能要求,不能使用XMLHttpRequest(会重复发送请求影响性能指标)。


解决方法

问题根源

  1. Fetch默认自动跟随重定向:CloudFront返回的是302重定向响应,Fetch默认会自动跳转到Location指定的地址,此时你获取到的是最终跳转页面的响应,而非CloudFront带fibval头的302响应。
  2. 自定义头未暴露给前端:CORS规范中,自定义响应头默认无法被前端JavaScript访问,必须通过Access-Control-Expose-Headers显式声明。

修改步骤

1. 调整前端Fetch配置

添加redirect: 'manual'选项,阻止自动跳转,直接捕获CloudFront的302响应:

function fibonacci() {
     var n = document.getElementById('fibCFInput').value;
     console.log("testing.." + n)
     fetch("<cloudfront url>/fibonacci/" + n, {
         redirect: 'manual' // 关键:不自动跟随重定向
     })
     .then(response => {
         // 现在能拿到CloudFront返回的302响应
         response.headers.forEach((value, name) => {
             console.log(`${name}: ${value}`);
         });

         // HTTP头不区分大小写,Fetch返回的头名统一为小写
         const fibval = response.headers.get("fibval");
         console.log(`fibval value: ${fibval}`);

         // 若需跳转到目标页面,手动处理
         const location = response.headers.get('location');
         if (location) {
             window.location.href = location;
         }
     })
}

2. 更新CloudFront函数响应头

添加Access-Control-Expose-Headers,将fibval头暴露给前端:

import cf from 'cloudfront';

async function handler(event) {
    const url = event.request;
    const pathSegments = url.uri.split('/')
    console.log(pathSegments)
    const key = pathSegments[2] //returns fib number from input
    console.log(key)
    var result = fibFunc(parseInt(key))
    const mainweburl = "http://fakeURL.com:portnumber/"
    const all = "*"
    var response = {
        statusCode: 302,
        statusDescription: 'Found',
        headers: {
        'access-control-allow-origin': {"value": all},
        // 添加此行,暴露自定义fibval头
        'access-control-expose-headers': {"value": "fibval"},
        "location": { "value": mainweburl},
        'fibval': {'value': result.toString()},
        }
    };
    return response;
}

额外说明

  • 若不需要跳转页面,可移除手动跳转的代码;若需要保留跳转逻辑,手动调用window.location.href不会额外增加性能开销,和自动跳转效果一致。
  • HTTP头名称不区分大小写,但Fetch API返回的头字段会统一转为小写,因此用response.headers.get("fibval")更稳妥(原代码的"Fibval"也能生效)。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.27 15:17:12