2

所以我有一个由 AWS Cloudfront 从 AWS S3 提供的 SPA。我已经配置了以下错误页面行为:

404: Not Found->/index.html使用 HTTP 代码200

这需要能够在客户端处理路由。

现在我有一个 Lambda@Edge 函数,它由viewer-responseCloudfront 中的事件触发并设置一些自定义标头,例如 HSTS 和 X-Frame。除了实际的/index.html. 我倾向于认为这是因为它是由 Cloudfront 中的上述错误页面行为处理的,因为对 html 的实际 GET 请求是由 Cloudfront 中的错误页面配置处理的。

解决这个问题的实用方法是什么?

我不确定为什么重定向不会触发 lambda 函数。有没有办法实现与 lambda@edge 中的错误页面配置相同的逻辑?

4

1 回答 1

5

update:服务的行为发生了变化。

https://aws.amazon.com/about-aws/whats-new/2017/12/lambda-at-edge-now-allows-you-to-customize-error-responses-from-your-origin/

下面的答案在发布时是正确的,但不再适用。源错误现在会按源响应触发器(但不是查看器响应触发器)中的预期触发 Lambda@Edge 函数。

请注意,您可以在 Origin Response 触发器中生成自定义响应正文,但您没有编程访问权限来读取从源返回的原始响应正文(如果有的话)。你可以替换它,或者保持原样——不管它是什么。这是因为 Lambda@Edge 源响应触发器不会等待CloudFront 从源接收到整个响应触发——它们似乎会在源完成将完整、有效的响应标头返回给 CloudFront 后立即触发。

当您使用 HTTP 响应时,请注意 Lambda@Edge 不会将源服务器返回的 HTML 正文公开给源响应触发器。您可以通过将其设置为所需的值来生成静态内容主体,或者通过将值设置为空来删除函数内部的主体。如果您不更新函数中的正文字段,则源服务器返回的原始正文将返回给查看器。

https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/lambda-updating-http-responses.html

重要提醒:无论何时您在 CloudFront 上测试更改,请记住,您的更改往往比您预期的更早开始工作 - 在分发状态更改回 之前Deployed,但您可能需要进行缓存失效以使您的更改完全生效并且可见。无效应该包括浏览器实际请求的路径,而不是从源请求的路径(如果不同),或者/*使所有内容无效。查看来自 CloudFront 的响应时,如果有Age:响应标头,则您正在查看缓存的响应。还要记住,错误使用一组不同的计时器来缓存响应。这些是与缓存行为中的 TTL 值分开配置的。查看我对Amazon CloudFront 延迟的回答有关如何更改错误缓存最小 TTL 的说明,默认为 5 分钟并且通常不尊重Cache-Control标头。这是一种保护措施,可防止过多错误到达您的来源(或触发您的 Lambda 函数),但如果您不知道其影响,则在测试和故障排除期间会造成混淆。


(原答案如下)

如果源返回 HTTP 状态代码 400 或更高,CloudFront 不会为源响应和查看器响应事件执行 Lambda 函数。

http://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/lambda-requirements-limits.html

这意味着未处理的错误导致没有响应触发触发。

但是,当自定义错误响应文档处理源错误时,源触发器会在回退请求上触发,包括错误文档成功呈现时的源响应,您可以在此处找到解决方案。

如果您将其实现为源响应触发器而不是查看器响应触发器,则您的代码将运行,因为在获取/index.html(替代错误页面)时,源返回 200,这会调用源响应触发器——但查看器响应触发器仍然没有不开火。此行为似乎没有完整记录,但测试显示 Origin Request 和 Response 触发器在成功获取错误文档时分别触发,只要使用触发器配置了路径与错误文档匹配的缓存行为。

事实上,似乎 Origin Response 触发器对您的应用程序更有意义,因为它能够在响应进入缓存之前修改响应,并且添加的标头将与响应一起缓存 - 这应该会导致总体上减少了触发器实际需要触发的次数。

您可以将其添加为 Origin Response 触发器,等待分发返回到Deployed,然后执行缓存失效/*(这样您就不会提供任何没有添加标头的缓存页面),并且在失效完成后,删除查看器响应触发器。

旁白:我提交了一个功能请求,以支持在错误时触发响应触发器,但我不知道这是否是他们正在考虑添加的内容,显然我不是唯一一个,因为该功能已实现并发布,因为在修改后的答案中描述。

于 2017-09-19T00:03:08.847 回答