1

我们有一个高交易量的 PHP 网站,总体上表现良好,但薄弱环节是搜索结果缓慢。原因是我们汇总了来自众多来源的数据。例如:

用户点击搜索 > 从本机数据库获取结果 1 > 从 API 2 获取结果 2 > 从 API 3 获取结果 3 > 从 API 4 获取结果 4 > 聚合和排序 > 输出到浏览器。

数据来自各种来源,一些来自我们自己的 PostgreSQL 数据库,但其余来自各种外部 API。

如您所见,这种顺序访问是一个真正的杀手。我一直在研究使用线程的各种方法,因此我可以将每个请求分配给它自己的线程并执行最终聚合。

到目前为止,我倾向于编写一个专门用于搜索的基于 Java 的层。我的想法是我向 Java 服务发送一条消息,它处理线程池和聚合。我正在考虑使用node.js,但我认为可能很难达到最终结果。

有没有人有任何想法或建议?我愿意使用任何语言或技术。

4

2 回答 2

0

看起来您的请求执行时间不能小于最小 API 请求执行时间,即使您使所有子请求在异步模式下同时运行。如果您需要对所有 API 和 DB 数据应用聚合函数,这是正确的。但是,如果您不需要它,请尝试将请求分成小部分。你也可以尝试使用像 Gearman 这样的任务队列。

已编辑您还可以在此处考虑任何类型的异步调用。尝试在 Gearman中为每个 api 调用异步启动任务,然后在主请求过程中从您的数据库中获取数据并开始检查异步任务执行结果(您可以在 memcache 或 redis ie 中共享它)。这样您就可以并行化一部分聚合工作。

于 2013-07-17T02:28:12.407 回答
0

这只是一个尚未提及的替代选项。

您可以坚持使用纯 php - 只需编写 4 个作为守护进程运行的新进程,以侦听本地套接字连接。您的搜索脚本可以与每个守护进程建立套接字连接并将搜索参数发送给它们,然后等待结果。您可以使用 有效地等待套接字上的结果select(),但即使只是在所有 4 个套接字上按顺序使用阻塞调用的天真解决方案fgets()也会为您提供良好的并发性,只要您在尝试读取结果之前将消息发送到所有 4 个守护程序任何。

但是,当 10 个不同的用户同时执行搜索时,这不会自动提供良好的并发性。守护进程可能能够一次有效地服务多个套接字连接。对于本机数据库查询,您的驱动程序将需要支持异步查询。并且那些 apis 调用可能正在使用 sockets/http。套接字 /http 请求很容易通过使用select()或考虑并行化curl_multi

但是...使用良好的语言支持的线程在一天结束时可能会更简单。

于 2013-07-24T03:34:27.163 回答