8

我们目前在许多边缘站点使用 CloudFront 来提供动态调整为不同大小尺寸的产品图像(接近一百万)。我们的 Cloudfront 发行版使用原始 EC2 php 脚本从 S3 检索原始图像,根据提供的查询字符串标准(宽度、高度、裁剪等)动态转换它,并将其流式传输回 Cloudfront,后者将其缓存在边缘位置。

但是,第一次加载非缓存图像的网站访问者会受到这种相当大的转换的打击。

我们希望能够“预缓存”我们的图像(通过使用请求每个图像 url 的批处理作业),这样最终用户就不会第一个点击特定尺寸的图像,等等。

不幸的是,由于图像仅缓存在分配给预缓存服务的边缘位置上,因此使用另一个边缘位置的网站访问者将无法获得缓存的图像,并且会受到源服务器上大量调整大小的脚本的影响。

我们提出的唯一解决方案是,每个边缘位置都可以在合理的加载时间内检索图像,这是:

我们有一个指向原始 EC2 php 脚本的 Cloudfront 发行版。但是,原始脚本没有进行上述图像转换,而是将请求和查询字符串参数转发到另一个 Cloudfront 分发。此发行版具有执行图像转换的原始 EC2 php 脚本。这样,图像始终缓存在我们的 EC2 实例(爱尔兰)附近的边缘位置,从而避免在从另一个边缘位置请求图像时执行另一次转换。

因此,例如,瑞典的请求命中 /image/stream/id/12345,瑞典边缘位置没有缓存,因此它将请求发送到源,即爱尔兰的 EC2 机器。然后,EC2“流式传输”页面从另一个 Cloudfront 发行版加载 /image/size/id/12345,该发行版到达爱尔兰边缘位置,该边缘位置也没有缓存。然后它向源端发送请求,同样是同一台 EC2 机器,但发送到调整大小的“大小”页面。此后,瑞典和爱尔兰的边缘站点都缓存了图像。

现在,来自法国的请求请求相同的图像。法国边缘位置没有缓存它,因此它调用源,即爱尔兰的 EC2 机器,它调用再次命中爱尔兰边缘位置的第二个 CF 分发。这次它确实缓存了图像,并且可以立即返回。现在法国边缘位置也缓存了图像,但不必调用“调整大小”页面 - 只有在爱尔兰缓存图像的“流媒体”页面。

这也意味着我们在爱尔兰的“预缓存”批处理服务可以对爱尔兰边缘位置进行请求,并在我们的网站访问者请求图像之前预缓存图像。

我们知道这看起来有点荒谬,但我们希望最终用户在调整图像大小时永远不必等待很长时间,这似乎是唯一切实可行的解决方案。

我们是否忽略了另一个/更好的解决方案?对以上内容有何评论?

4

2 回答 2

1

我不确定这会减少加载时间(如果这是您的目标)。

是的,此设置将节省一些“转换时间”,但另一方面,这也会在服务器之间创建额外的通信。

IE客户端调用法语 POP >> 法语 POP 调用爱尔兰 POP = 下载时间(和一些)的两倍,这可能比“转换时间”长...

我为 Incapsula 工作,我们实际上开发了自己独特的行为分析启发式过程来处理动态内容缓存。(在这里简要记录:http: //www.incapsula.com/the-incapsula-blog/item/414-advanced-caching-dynamic-through-learning

我们的场地是:

虽然一个网站可以有数百万个动态对象,但只有其中一些需要重复请求。

按照这个逻辑,我们有一个算法可以学习访问模式,为缓存找到好的“候选人”,然后将它们缓存在冗余服务器上。(从而避免了上述的“双重下载”)

然后每 5 分钟重新扫描一次内容,以保持新鲜度,并且启发式系统保持跟踪,以确保内容仍然受欢迎。

这是一个过于简单的解释,但它展示了核心思想,即:找出你的用户最需要什么。参与所有 POP。跟踪以保持新鲜度并检测趋势。

希望这可以帮助。

于 2012-10-02T14:11:34.730 回答
0

只是一个想法...

运行两个缓存。

  1. 每个边缘位置一个,
  2. 爱尔兰的服务器上的一个(如果有多个服务器,则为 elasticache)。它们不需要被缓存超过几分钟。

将运行的微实例附加到数据管道或队列,

当请求进入源服务器时,返回并服务器缓存图像。还将 url 放到队列中。

然后,让守护程序对每个边缘位置进行多次调用。此时,您的服务器将再次受到攻击(因为其他边缘位置将没有图像)-但它将立即从缓存中提供服务-无需执行昂贵的转换。

如果它不进行转换,并且仅从缓存中提供服务 - 应该没什么大不了的。

所以流程是这样的

Request -> Cloud Front -> EC2 -> Add to cache   -> Response -> CloudFront Cache -> User
     -                        -> Queue new request at each edge location
Request -> Cloud Front -> EC2 -> already cached -> Response -> CloudFront -> User

您需要某种形式的标记来说明它已经被提供和缓存,否则您最终会陷入无限循环。

于 2013-09-06T13:51:14.603 回答