使用Lambda @ Edge的单页应用程序

时间:2017-09-17 08:16:29

标签: aws-lambda amazon-cloudfront aws-lambda-edge

所以我通过AWS Cloudfront从AWS S3提供SPA。我已配置以下错误页面行为:

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

200

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

现在我有一个Lambda @ Edge功能,该功能由Cloudfront中的viewer-response事件触发,并设置了一些自定义标头,如HSTS和X-Frame。正在调用该函数,并且除了实际的/index.html之外,还可以按预期工作。我倾向于认为这是因为它是由Cloudfront中的上述错误页面行为处理的,因为对于html的实际GET请求正由Cloudfront中的错误页面配置处理。

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

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

1 个答案:

答案 0 :(得分:3)

更新:服务的行为已更改。

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 Origin Response触发器不等待 CloudFront收到来自原点的整个响应后触发 - 一旦原点完成返回完整的有效响应头,它们似乎会立即触发CloudFront的。

  

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

     

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

重要提醒:每次在CloudFront上测试更改时,请记住,在分发状态更改回Deployed之前,您的更改往往比预期的更早开始工作,但您可能需要执行缓存失效,以使更改完全生效且可见。失效应该包括浏览器实际请求的路径,而不是原始请求的路径(如果不同),或/*使一切无效。从CloudFront查看响应时,如果存在Age:响应标头,则表示您正在查看缓存的响应。还要记住,错误使用一组不同的计时器来缓存响应。它们与缓存行为中的TTL值分开配置。有关如何更改错误缓存最小TTL的说明,请参阅我对Amazon CloudFront Latency的回答,默认值为5分钟,通常不会考虑Cache-Control标头。这是一种防止过多错误到达原点(或触发Lambda功能)的保护措施,但如果您不了解其影响,则会在测试和故障排除过程中造成混淆。

(原始答案如下)

  

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

     

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

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

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

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

事实上,无论如何,看起来原始响应触发器对您的应用程序更有意义,因为它可以在进入缓存之前修改响应,并且添加的标头将是与响应一起缓存 - 这将导致触发器实际需要触发的次数总体减少。

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

除此之外:我提交了一项功能请求,以支持针对错误的触发响应触发器,但我不知道这是否是他们正在考虑添加的内容,或者不是而且显然我不是& #39;是唯一一个,因为该功能已经实施和发布,如修订后的答案中所述。