了解服务器体系结构:使用Nginx反向代理或Apache服务器从AWS S3提供内容

这个问题的目的是在devise服务器端体系结构时理解策略。

使用案例:我想为应用程序构build一个http服务器,允许用户上传和下载多媒体内容(图像,video等)。大量的并发用户(比如约50k)预计会上传/下载内容。

所有内容将存储在AWS S3存储桶中。 有关S3存储桶的信息,即存储桶名称/authentication标题应该由用户屏蔽。 由于S3存储桶有多个访问控制选项( AWS-ACL ),因此最好不要让所有用户(authentication用户和匿名用户)都可用。 我不想在公共领域公开内容。

查询

  • 由于我想从用户屏蔽AWS S3,我将需要使用Web服务器或反向代理。 我已经通过比较Apache Vs Nginx的多个资源。 由于服务器需要将S3中的静态内容传递给大量的并发用户,所以Nginx似乎是一个更好的select。 不是吗?

  • 是否将访问控制级别设置为S3存储桶给ALL_USERS(对于通过身份validation的用户和匿名用户)是否会损害数据隐私? 如果我使用反向代理,用户无法确定S3存储桶地址。 数据是否安全和私密?

  • 但是,如果S3存储桶只对authentication的用户可用,nginx会反向代理工作吗? 我已经通过Nginx反向代理S3 。 为了让Nginx成为一个反向代理,需要准备一个预先签名的URL 。 预先签名的URL的到期时间又是一个棘手的决定。 为预先签名的url设置一个巨大的失效时间是否合理? 它会影响数据的安全性或隐私性(类似于对ALL_USERS的s3访问控制)? 如果是的话,有没有办法通过nginx将代理请求dynamic生成预先签名的url(短到期时间)?

任何信息和资源巩固我的理解将是非常有益的。

是否将访问控制级别设置为S3存储桶给ALL_USERS(对于通过身份验证的用户和匿名用户)是否会损害数据隐私?

绝对。 不要这样做。

如果我使用反向代理,用户无法确定S3存储桶地址。 数据是否安全和私密?

理论上,他们不能确定它,但如果错误信息或配置错误会泄漏信息呢? 这是通过默默无闻的安全 ,这只能给你一种虚假的安全感。 总有一个更好的方法。

有关S3存储桶的信息,即存储桶名称/认证标题应该由用户屏蔽。

S3的身份验证机制(带有签名的URL)的设计为了将其暴露给用户没有任何伤害。 唯一的秘密就是您的AWS Secret Key,您将会注意到它不会在签名的URL中公开。 它也不能被合理地反向设计,并且签名的URL仅适用于签名所允许的资源和行为。

签名URL并将其呈现给用户并不构成安全风险,但是,诚然,还有其他原因可能导致您不想这样做。 我经常这样做 – 在呈现页面的同时签署URL,过期时间相对较长,或者签名URL,并在用户点击链接时将用户重定向到签名的URL(这验证了他们的身份授权访问资源,然后返回一个很短的到期时间(如5到10秒)的签名URL;到期时可以在下载过程中发生而不会导致问题 – 签名只需要避免在对S3的请求被接受)。

但是,如果您想要使用代理路由(除了上述以外,我也可以在系统中执行此操作),则比您想象的要简单得多:可以将存储桶策略配置为允许根据您的服务器的源IP地址授予特定的权限。

这是从我的一个桶里直接采取的(消毒)政策。 IP地址来自RFC-5737,以避免这个例子中私有IP地址造成的混乱。

这些IP地址是公共IP地址…它们是连接到您的Web服务器的弹性IP地址,或者,最好是Web服务器用于传出请求的NAT实例。

{ "Version": "2008-10-17", "Id": "Policy123456789101112", "Statement": [ { "Sid": "Stmt123456789101112", "Effect": "Allow", "Principal": { "AWS": "*" }, "Action": "s3:GetObject", "Resource": "arn:aws:s3:::example-bucket/*", "Condition": { "IpAddress": { "aws:SourceIp": [ "203.0.113.173/32", "203.0.113.102/32", "203.0.113.52/32", "203.0.113.19/32" ] } } } ] } 

这是做什么的? 如果请求从其中一个IP地址到达S3, GetObject权限将被授予请求者。 使用代理服务器,您的代理服务器的IP地址将是S3所看到的IP地址,如果该请求与存储桶策略匹配,则允许您的代理从S3获取对象,而不允许其余的Internet访问,除非备用显示证书,例如带有签名的URL。 这个政策不直接“否认”任何东西,因为否定是隐含的。 重要的是,不要使用public-read ACL来上传对象,因为这样可以让任何人下载对象。 默认的private ACL完美适用于这个应用程序。

S3可以根据其他标准(如Referer:标题)授予这样的权限,您可以在线查找示例,但不要这样做 。 信任浏览器作为引用页面报告的是一个极其微弱和原始的安全机制,它几乎没有提供真正的保护 – 头文件非常简单地被欺骗。 这种过滤方式对于烦人的懒惰的人们来说是非常有用的。 源IP地址是完全不同的事情,因为它不是在第7层报头中携带的,并且不容易被欺骗。

因为S3只通过TCP协议与互联网交互,所以你的源地址 – 即使它已经知道你是如何启用存储桶来信任这些地址的 – 不能以任何实际的方式被欺骗,因为这样做意味着违反AWS核心IP网络基础架构的安全性 – TCP要求始发机器通过其所使用的源IP地址跨子网边界可达,而AWS网络只会将这些响应路由回您合法分配的IP地址,除了重置或丢弃连接之外别无选择,因为它们不是由您发起的。

请注意,此解决方案不能与Amazon 最近宣布的 S3 VPC端点一起使用,因为使用S3 VPC端点,您的源IP地址(由S3看到)将是私有地址,这不是您的VPC唯一的地址…但这不应该是一个问题。 我只是为了彻底才提到这个警告。 S3 VPC端点不是必需的,默认情况下不启用,如果启用,可以按每个子网进行配置。