是的,您是对的,签名的 URL 可以“共享”,因为它在过期之前一直有效(或者在签名的凭据过期或以其他方式失效之前,以先到者为准)。
一种常见的解决方案是应用程序在呈现页面时使用非常短的过期时间生成签名 URL。
另一种是指向受保护内容的链接实际上是返回应用程序的链接,该链接验证用户访问该对象的权限,然后将 HTTP 重定向返回到新生成的签名 URL,其过期时间很短(例如 5秒)。
HTTP/1.1 302 Found
Location: https://example-bucket.s3.amazonaws.com/...?X-Amz-...
使用当前可行的计算能力无法篡改签名 URL,因此恶意用户不可能修改签名 URL 是不切实际的。
另请注意,签名 URL(适用于 S3 或 CloudFront)只需在下载时尚未过期即可starts。实际下载所需时间finish可以任意长,并且下载不会中断。
以下选项没有现成的服务,但使用 CloudFront Lambda@Edge 触发器和 DynamoDB 的组合,可以创建真正的一次性 URL,该 URL 由存储在 Dynamo 中的随机生成的“令牌”组成表并与目标对象关联。访问 URL 时,您可以在 Lambda 触发器中使用 DynamoDB 条件更新将(例如)“view_count”值从 0 更新为 1。如果令牌不在表中或视图计数不为 0,则条件更新失败,因此访问被拒绝;否则,CloudFront 允许请求继续进行——仅一次。 CloudFront 使用源访问身份访问 S3 内容,这一切都在幕后发生,因此用户无法访问与 CloudFront 和 S3 之间请求的实际身份验证相关的任何内容。 (对于加密质量的随机令牌生成,您还可以使用 KMSGenerateRandom https://docs.aws.amazon.com/goto/WebAPI/kms-2014-11-01/GenerateRandomAPI 操作。)
有许多替代方法,包括使用 Lambda@Edge 触发器来执行诸如检查对应用程序提供的 cookie 的请求,然后查询应用程序服务器以对用户进行身份验证等操作。
CloudFront 还支持它本身解析和解释的签名 cookie,但这些提供了对与特定 URL 和路径匹配的所有资产的基于通配符的访问(例如/images/*
)并且没有什么可以阻止用户共享他们的 cookie,因此这些可能对您的用例没有用处。
CloudFront 签名 URL 确实支持仅当从特定源(客户端)IP 地址使用签名 URL 时才允许访问的选项,但这存在潜在问题,因为无法保证用户和 IP 地址之间存在 1:1 关联。许多用户可能位于同一地址(特别是在公司网络环境中),或者单个用户的地址可能随时更改。
可能的实现的复杂性差异很大,您的需求部分取决于您需要的内容安全程度。在许多情况下,更极端的解决方案只不过是阻止诚实的用户,因为用户仍然可以download资源并通过其他方式共享。