php - 缓存结果列表的优化方式?

标签 php laravel caching optimization redis

这是一个针对 PHP/Laravel + Redis 的问题,但我确信它可以外推到其他语言/框架。

我正在开发一个显示结果的应用程序(来自用户启动的搜索或类别列表)。默认情况下,我们每页分页 30 个结果。

我使用 Redis 来缓存所有结果,但我遇到了一些优化问题。起初,我缓存了整个结果集,对象(产品)完全存储在结果集中(因此基本上每个结果列表都是一个包含 30 个数据对象的巨大缓存条目)。这很好,但是随着对象存储在多个不同的缓存对象中,内存使用量激增(一个产品可能出现在多个搜索结果和类别中——然后默认情况下每个对象都会被单独缓存)。

此外,另一个问题是,由于我们允许在不同的计数下进行不同的分页,因此我们也必须在其他对象计数下进行缓存。

然后我接下来尝试的是只缓存每个页面的对象 ID 列表。这显着减少了内存使用量,但是每次加载页面时,我们都必须循环遍历 30 个对象并从缓存中检索它们,然后重新创建它们。每个对象大约 50 毫秒(这看起来很高),页面加载时间最多可增加 1.5 秒。即使我们进一步优化对象创建,页面加载/呈现的具体时间量仍然会增加。

我们的下一个尝试是 HTML 缓存(Cloudflare/Varnish 等),这将要求我们重新设计应用程序的某些方面,这很好。但是,对我来说,我想知道没有 HTML 缓存是他们优化这个的方法(或者做我们正在尝试做的事情的最佳方法是什么?)。另外,我遇​​到的另一个问题是,虽然我知道每次请求都会执行 PHP 脚本,但为什么我们不能在执行之间将对象维护为 POPO(普通旧 PHP 对象)?在这一点上,我们仍在 2017 年序列化和反序列化对象,这对我来说似乎很愚蠢。我希望有一个后台 PHP 应用程序来维护所需的对象,并能够根据需要将它们传递给每个脚本。

例如,一个产品在不同页面加载之间不会有太大变化。为什么每分钟要重新创建同一个 Product 对象数百次——即使它来自缓存?

最佳答案

I'd love to have a background PHP app that maintains the objects required and is able to pass them to each script as required.

你不能这样做,因为单独的应用程序不共享范围(它们甚至不共享内存)。因此,您的后台应用程序需要以某种中间形式传递对象。是的,你猜对了。序列化。

可以做的是分离一些服务或 HTML 生成的部分,以便它们仅与特定对象完全关联。到那时,您可能可以拥有一个运行对象代理的后台应用程序。通过使用对象 ID 调用代理并请求其 HTML 来呈现对象,代理可以根据最佳方式缓存对象或呈现的 HTML。

不需要序列化的HTML,这个方法应该很高效。

您甚至可以通过 AJAX 执行此操作:将对象“预呈现”为具有适当大小的 AJAX 占位符和“请稍候”动画

<div class="Placeholder Product"></div>

然后一系列并行的 jQuery 调用为对象设置动画。

我这样做了(对于分页之类的东西,请看图)并通过一个疯狂的动画获得了非常好的结果,该动画开始时是一个非常不集中的搜索结果,逐渐成为焦点(当然没有循环)。这发生得非常缓慢,同时 AJAX 调用得到解决,并且真实对象被混合。对象是如此相似以至于你很少发现未聚焦的图像和最终对象实际上没有关系,并且用户平均没有注意到前两三个之后的对象还没有呈现——他看到整个结果页面立即出现,并认为所有结果都在那里。这些对象也在本地缓存,因此来回分页不会对服务器造成超过一次的压力。

关于php - 缓存结果列表的优化方式?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42284929/

相关文章:

php - 如何在 magento 中获取订单的总额和净总额?

php - 如何使用 id 和类型名称加载 Laravel 模型?

javascript - 在 Laravel 5.6 中使用自定义 JavaScript 函数

php - 在 Laravel 5 应用程序中将 Redis 配置为缓存接口(interface)

php - 使用 Composer 找不到 Google APIClient 类

php - 如何将 laravel orm 更改为我的查询

laravel - 如何在 `only` 中使用 apiReources 方法?

Linux 文件系统百万符号链接(symbolic link)与百万文件

javascript - 找不到在离线 Web 应用程序中存储用于离线下载的文件的方法

php - face.com API 的替代品