Aws lambda Lambda函数向CloudFront返回了无效的请求或响应
我正在尝试按照这里的说明进行操作 我已经成功地将CloudFront放在一个静态S3“hello world”HTML文件前面,我想使用lambda edge设置额外的头文件,但是我得到了一个错误。真正令人沮丧的是,我找不到任何错误日志来调试出错的地方。以下是浏览器显示的内容Aws lambda Lambda函数向CloudFront返回了无效的请求或响应,aws-lambda,amazon-cloudfront,amazon-cloudwatch,Aws Lambda,Amazon Cloudfront,Amazon Cloudwatch,我正在尝试按照这里的说明进行操作 我已经成功地将CloudFront放在一个静态S3“hello world”HTML文件前面,我想使用lambda edge设置额外的头文件,但是我得到了一个错误。真正令人沮丧的是,我找不到任何错误日志来调试出错的地方。以下是浏览器显示的内容 ERROR The request could not be satisfied. The Lambda function returned an invalid request or response to Clou
ERROR
The request could not be satisfied.
The Lambda function returned an invalid request or response to CloudFront.
Generated by cloudfront (CloudFront)
Request ID: 2Cqex7euzH0Iigps58i9tMVxdqAaLznL2ZjwqR1sW1AZHz6x2EwfMA==
下面是我的简单lambda的代码:
exports.handler = (event, context, callback) => {
console.log(event)
callback(null, 'Hello from Lambda');
};
触发器类型为viewerresponse
,并附加到我的CloudFront发行版(如果有必要,使用缓存行为:
)。lambda有一个与AWSLambdaBasicExecutionRole
相对应的角色,该角色允许对Cloudwatch进行写访问
一旦启用触发器,对web请求的响应就会从我的“Hello world”HTML更改为上面的错误,因此我知道它正在触发lambda。但在lambda仪表板中,它没有显示任何调用或错误。Cloudwatch中未显示任何日志。CloudFront仪表板显示错误(5xx
),但lambda没有显示任何错误
然后,如果我通过单击部署的函数,将测试事件配置为“CloudFront Modify Response Header”,并点击test,在lambda控制台中测试我的函数,那么它是成功的。Cloudwatch显示测试的日志和控制台输出!但在实时调用的日志中仍然没有任何内容
我唯一的理论是权限有问题,CloudFront实际上无法调用lambda(解释了为什么lambda仪表板中没有任何内容)。最后一件事是CloudFront日志(在S3中)显示带有502错误的web请求和
LambdaValidationError
,但我不知道这是否有帮助。您在博客文章中看到的示例在Lambda@Edge仍在预览中(在正式推出之前,对特定客户的访问有限),但这不再正确。在服务推出前不久,数据结构发生了变化
响应头数据结构以前是这样的:
headers['Strict-Transport-Security'] = "max-age=31536000; includeSubdomains; preload";
headers['Content-Security-Policy'] = "default-src 'none'; img-src 'self'; script-src 'self'; style-src 'self'; object-src 'none'";
headers['X-Content-Type-Options'] = "nosniff";
headers['strict-transport-security'] = [{
key: 'Strict-Transport-Security',
value: "max-age=31536000; includeSubdomains; preload"
}];
headers['content-security-policy'] = [{
key: 'Content-Security-Policy',
value: "default-src 'none'; img-src 'self'; script-src 'self'; style-src 'self'; object-src 'none'"
}];
headers['x-content-type-options'] = [{
key: 'X-Content-Type-Options',
value: "nosniff"
}];
新结构如下所示:
headers['Strict-Transport-Security'] = "max-age=31536000; includeSubdomains; preload";
headers['Content-Security-Policy'] = "default-src 'none'; img-src 'self'; script-src 'self'; style-src 'self'; object-src 'none'";
headers['X-Content-Type-Options'] = "nosniff";
headers['strict-transport-security'] = [{
key: 'Strict-Transport-Security',
value: "max-age=31536000; includeSubdomains; preload"
}];
headers['content-security-policy'] = [{
key: 'Content-Security-Policy',
value: "default-src 'none'; img-src 'self'; script-src 'self'; style-src 'self'; object-src 'none'"
}];
headers['x-content-type-options'] = [{
key: 'X-Content-Type-Options',
value: "nosniff"
}];
外部对象中的键必须是内部对象每个成员中的key
值的小写等价物。为了更准确地反映HTTP头的处理方式,很可能需要对数据结构进行此更改,因为在HTTP/1.x中,它们不区分大小写,但在Javascript对象中密钥区分大小写
如果代码返回的结构不符合CloudFront的要求Lambda@Edge返回时,您看到的错误确实会被抛出。没有生成日志,因为日志没有地方可去——此错误发生在Lambda之外,位于Lambda和CloudFront之间接口边界的CloudFront一侧,而ch不生成任何用户可访问的日志
请参阅文档以了解。有一些常见的“陷阱”Lambda@Edge和CloudFront。您需要:
- 发布Lambda函数的新版本
- 将CloudFront Lambda关联更新到您的新版本,例如:arn:aws:Lambda:us-east-1:572007530218:function:gofaas WebAuthFunction:45
- 寻找Lambda@Edge请求者所在区域的日志
请看一看自动部署a的情况,这需要花费大量的设置时间。如果我下面的答案不能解决您的问题,请将您的代码压缩为a并编辑成问题。您的答案确实解决了我的问题,@sqlbot。我剩下的担心是,在我更改函数时,我无法运行它们每次都是你!我的例子中的问题是返回一个字符串,但是我怎么能从CF和Lambda生成的错误/日志中知道呢?嗯,你知道……你可以随时由我运行它们,只要你有一个资金充足的paypal帐户。:)不过,说真的,你是对的——你没有办法知道,因为当没有节点错误时,CloudFront拒绝Lambda响应,日志就没有地方可去,当然,将错误返回到浏览器不是一个好的做法。但是在文档和示例之间,没有任何东西是无法解决的。确保你检查了所有的“蓝图”。它们生成的有效响应格式完全符合CloudFront喜欢的格式。在AWS论坛上继续使用@michael sqlbot,根据新规范修复了响应事件结构,为我解决了问题。我仍然无法使其正常工作。有人发现了问题吗?@JoeBruno发现了哪个问题?@sqlbot抱歉,我尝试粘贴的代码太长,然后我无法删除我的注释=)今天早上,我通过使用此github repo的“源响应”事件类型实现了这一点: