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

时间:2015-06-10 20:52:42

标签: apache amazon-web-services nginx amazon-s3

这个问题的目的是在设计服务器端架构时理解策略。

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

所有内容都将存储在AWS S3存储桶中。应该从用户屏蔽关于S3桶的信息,即桶名称/认证头。由于S3存储桶有多个访问控制选项(AWS-ACL),因此最好不要为All_Users(经过身份验证的用户和匿名用户)提供存储桶。我不想在公共领域公开内容。

查询

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

  • 将访问控制级别设置为S3存储桶到ALL_USERS(到 经过身份验证和匿名用户)对数据隐私妥协?如果我 使用反向代理,用户无法确定S3存储桶 网址。数据安全且私密吗?

  • 但是,如果S3存储桶仅供经过身份验证的用户使用, 将nginx反向代理工作?我经历过Nginx Reverse Proxy for S3。为了使Nginx能够作为反向代理,a 需要准备预签名网址。预签署的到期时间 网址再次是一个棘手的决定。是否设置了一个巨大的到期时间 预先签名的网址有意义吗?它在安全性方面是否妥协? 数据隐私(类似于对ALL_USERS的s3访问控制)?如是, 有没有办法将请求反向代理动态生成 仅通过nginx预先签名的网址(有效期短)?

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

1 个答案:

答案 0 :(得分:2)

  

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

绝对。不要这样做。

  

如果我使用反向代理,则用户无法确定S3存储桶网址。数据安全且私密吗?

理论上,他们无法确定它,但是如果错误消息或错误配置泄漏信息怎么办?这是security through obscurity,它只给你一种虚假的安全感。总是有更好的方式。

  

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

带有签名URL的S3的身份验证机制是设计,因此将其公开给用户没有任何害处。唯一的秘密是您的AWS密钥,您注意到它不会在签名的URL中公开。它也不能合理地进行逆向工程,并且签名的URL仅适用于签名允许的资源和操作。

签署URL并将其呈现给用户不会带来安全风险,但是,不可否认,还有其他原因可能导致您不想这样做。我经常这样做 - 在呈现页面时签署URL,使用相对较长的到期时间,或签署URL并在用户点击返回我的应用程序服务器的链接时将用户重定向到签名URL(验证他们的授权访问资源,然后返回一个签名的URL,其中包含非常短的过期时间,例如5到10秒;过期可以在下载过程中发生而不会导致问题 - 签名只需要避免在到期之前到期接受对S3的请求。)

但是,如果你想进入代理路由(除了上述内容之外,我也在我的系统中执行此操作),这比你想象的要容易得多: bucket policy可以配置为允许根据服务器的源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 to,除非提供备用凭据,例如使用签名URL。这项政策并没有拒绝"任何直接的,因为否定是隐含的。重要的是,不要使用public-read ACL上传您的对象,因为这样可以让任何人下载对象。默认的private ACL非常适合此应用程序。

S3可以根据其他条件(例如Referer:标题)授予此类权限,您可以在线找到该示例,但不要这样做。信任浏览器报告的引用页面是一种极其脆弱和原始的安全机制,几乎不提供真正的保护 - 标头非常容易欺骗。这种过滤实际上只对那些与您的内容进行热链接的烦人懒人有用。源IP地址完全不同,因为它不是在第7层报头中携带的,并且不容易被欺骗。

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

请注意,此解决方案无法与Amazon VPC endpoints的S3 recently announced一起使用,因为使用S3 VPC端点,您的源IP地址(由S3看到)将是私有地址,即#39; t对您的VPC来说是独一无二的......但这应该不是问题。我只是为了彻底而提到这个警告。 S3 VPC端点不是必需的,默认情况下不启用,如果启用,则可以基于每个子网进行配置。