访问受限于 VPC 端点的 S3 网站从 VPC 内部获得 403
Posted
技术标签:
【中文标题】访问受限于 VPC 端点的 S3 网站从 VPC 内部获得 403【英文标题】:S3 website with access restricted to VPC endpoint is getting 403 from inside the VPC 【发布时间】:2020-01-07 18:25:48 【问题描述】:我想创建一个配置为用作网站的 S3 存储桶,并且我想仅限来自特定 VPC 内部的请求访问 S3 网站。 p>
我正在使用 Cloudformation 来设置存储桶和存储桶策略。
bucket CF 启用了WebsiteConfiguration
,并将AccessControl
设置为PublicRead
。
ContentStorageBucket:
Type: AWS::S3::Bucket
Properties:
AccessControl: PublicRead
BucketName: "bucket-name"
WebsiteConfiguration:
IndexDocument: index.html
ErrorDocument: error.html
存储桶策略包括两个条件:一个条件授予访问办公室 IP 时对存储桶的完全访问权限,另一个条件授予通过 VPC 端点访问。代码如下:
ContentStorageBucketPolicy:
Type: AWS::S3::BucketPolicy
Properties:
Bucket: !Ref ContentStorageBucket
PolicyDocument:
Id: BucketPolicy
Version: '2012-10-17'
Statement:
- Sid: FullAccessFromParticularIP
Action:
- s3:*
Effect: "Allow"
Resource:
- !GetAtt [ ContentStorageBucket, Arn ]
- Fn::Join:
- '/'
- - !GetAtt [ ContentStorageBucket, Arn ]
- '*'
Principal: "*"
Condition:
IpAddress:
aws:SourceIp: "x.x.x.x"
- Sid: FullAccessFromInsideVpcEndpoint
Action:
- s3:*
Effect: "Allow"
Resource:
- !GetAtt [ ContentStorageBucket, Arn ]
- Fn::Join:
- '/'
- - !GetAtt [ ContentStorageBucket, Arn ]
- '*'
Principal: "*"
Condition:
StringEquals:
aws:sourceVpce: "vpce-xxxx"
为了测试上述政策条件,我做了以下工作:
我已将一个名为json.json
的文件添加到 S3 存储桶;
我创建了一个 EC2 实例并将其放置在存储桶中引用的 VPC 中。
我已从白名单 IP 地址内向文件端点 http://bucket-name.s3-website-us-east-1.amazonaws.com/json.json
发出 curl 请求,请求成功;
我已从 EC2 实例(放置在 VPC 中)内部向文件端点发出 curl 请求,但请求失败并显示 403 Access Denied
注意事项:
我已确保 EC2 实例位于正确的 VPC 中。aws:sourceVpce
不是使用 VPC ID 的值,而是使用对应 VPC 的 Endpoint ID 的值。
我还使用了带有 VPC ID 的 aws:sourceVpc
,而不是使用带有端点 ID 的 aws:sourceVpce
,但这产生了与上述相同的结果。
鉴于此,我目前不确定如何继续进行进一步调试。您对可能出现的问题有什么建议吗?如果问题不清楚或有任何需要澄清的地方,请告诉我。感谢您的帮助!
【问题讨论】:
您是否检查了您的 EC2 实例所在子网的路由表?您需要一条代表 S3 端点到 vpc 端点的前缀列表的路由(会有一条路由说 pl-XXXXXXXX 到 vpce-XXXXXXXX)。如果此路由不存在,您的请求将通过公共 Internet 并被拒绝,除非它在白名单 IP 上。 对于全新的Managing Data Access with Amazon S3 Access Points 来说,这听起来像是一个很棒的用例。 如果您通过 awscli 使用 IAM 凭据而不是没有凭据和 curl,访问是否有效?另外,可能的调试帮助:aws.amazon.com/premiumsupport/knowledge-center/… @TopherIsSwell 感谢您标记此内容。目前我在路由表中没有该路由,所以这很可能是问题所在。如果它工作,我会调查并报告。感谢您的帮助。还要感谢 jarmod 提到的调试链接,这似乎也让我找到了丢失的路线。 @RafaelMarques 您的存储桶策略对我有效,没有任何更改,因此显然是路由或 VPC 端点策略。 【参考方案1】:为了让资源将 VPC 终端节点用于 S3,VPC 路由器必须将所有发往 S3 的流量指向 VPC 终端节点。 AWS 允许您使用 BGP 前缀列表,这是 AWS 中的一流资源,而不是您自己维护所有特定于 S3 的 CIDR 块的列表。
要查找 S3 的前缀列表,请运行以下命令(您的输出应该与我的输出匹配,因为这应该是所有帐户的相同区域,但最好检查一下)。使用您的 VPC 的区域。
aws ec2 describe-prefix-lists --region us-east-1
我得到以下输出:
"PrefixLists": [
"Cidrs": [
"54.231.0.0/17",
"52.216.0.0/15"
],
"PrefixListId": "pl-63a5400a",
"PrefixListName": "com.amazonaws.us-east-1.s3"
,
"Cidrs": [
"52.94.0.0/22",
"52.119.224.0/20"
],
"PrefixListId": "pl-02cd2c6b",
"PrefixListName": "com.amazonaws.us-east-1.dynamodb"
]
对于 com.amazonaws.us-east-1.s3,前缀列表 id 为 pl-63a5400a,
这样您就可以在为相关子网提供服务的任何路由表中创建路由。 Destination 应该是前缀列表 (pl-63a5400a),target 应该是 VPC 终端节点 ID (vpce-XXXXXXXX)(您可以通过 aws ec2 describe-vpc-endpoints
找到它)。
这在控制台中是微不足道的。我不记得如何从命令行执行此操作,我认为您必须发送带有以下内容的 cli-input-json,但我尚未测试。这留给读者作为练习。
"DestinationPrefixListId": "pl-63a5400a",
"GatewayId": "vpce-12345678",
"RouteTableid": "rt-90123456"
【讨论】:
我相信这是一个非常有用的答案,我会对其进行测试。不过我有一个问题:应该在 VPC 的路由表上设置路由,还是在设置 EC2 实例的子网的路由表上设置路由。谢谢! @TopherIsSwell 这个答案是正确的,并为我指明了正确的方向。我能够将子网路由表添加到 VPC 终端节点,并且将存储桶策略设置为允许此终端节点,请求现在成功。 好的,很高兴听到。为了向阅读本文的其他人澄清,VPC 将有一个主/默认路由表,适用于所有没有分配路由表的子网。因此,我指的是明确分配给子网的路由表,或者如果没有其他路由表适用,则指主 VPC 路由表。如果您发现此答案有帮助,如果您将其标记为已接受,它将帮助我和其他人解决此问题。谢谢,祝你好运!以上是关于访问受限于 VPC 端点的 S3 网站从 VPC 内部获得 403的主要内容,如果未能解决你的问题,请参考以下文章