You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

优化PHP使用file_get_contents请求多JSON接口的慢加载问题

PHP多HTTP请求场景加载速度优化方案

你当前性能瓶颈来自循环内串行发起10次独立HTTP请求,单次file_get_contents请求本身存在DNS查询、TCP握手、TLS校验(如果是HTTPS)的固定开销,串行执行时总耗时是10次请求耗时的累加,自然会导致页面加载速度大幅下降。以下是可落地的优化方案:

1. 改用cURL并发请求(优先级最高)

使用PHP的curl_multi_*系列函数并行发起所有HTTP请求,总耗时仅等于10次请求中最慢的单次请求耗时,通常可以把这部分耗时压缩到原来的1/3~1/10。
示例代码:

<?php 
$site = file_get_contents('website.com/content.json');
$obj = json_decode($site, true);
$idList = [];
for ($i = 0; $i <= 9; $i++) {
    $idList[] = $obj[$i]['id'];
}

// 初始化curl多句柄
$mh = curl_multi_init();
$chList = [];
$infos = [];

// 批量添加请求
foreach ($idList as $id) {
    $ch = curl_init("website.com/info/" . $id . ".json");
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 2);
    curl_setopt($ch, CURLOPT_TIMEOUT, 5);
    curl_multi_add_handle($mh, $ch);
    $chList[$id] = $ch;
}

// 执行并发请求
$running = null;
do {
    curl_multi_exec($mh, $running);
    curl_multi_select($mh);
} while ($running > 0);

// 收集返回结果
foreach ($idList as $id) {
    $content = curl_multi_getcontent($chList[$id]);
    $infos[$id] = json_decode($content, true);
    curl_multi_remove_handle($mh, $chList[$id]);
    curl_close($chList[$id]);
}
curl_multi_close($mh);

// 渲染输出
for ($i = 0; $i <= 9; $i++) {
    $id = $obj[$i]['id'];
    echo '<div class="result-' . $id . '">';
    echo $infos[$id]['content'] ?? '';
    echo '</div>';
} 
?>

2. 增加请求结果缓存

如果对应id的info数据不是实时性要求极高的内容,添加缓存层可以避免重复发起请求,是性能收益最高的方案:

  • 缓存介质可以选择APCu(进程级内存缓存)、Redis(分布式缓存)、本地文件缓存,根据你的部署环境选择即可
  • 缓存过期时间可以根据业务更新频率设置,通常设置5~60分钟即可覆盖绝大多数用户访问场景
    简单本地文件缓存示例:
// 获取info的封装函数
function getInfoById($id) {
    $cachePath = __DIR__ . '/cache/info_' . $id . '.json';
    // 缓存存在且未过期(示例过期时间1小时)
    if (file_exists($cachePath) && (time() - filemtime($cachePath)) < 3600) {
        $content = file_get_contents($cachePath);
    } else {
        $content = file_get_contents("website.com/info/" . $id . ".json");
        // 写入缓存,提前创建cache目录并给写入权限
        file_put_contents($cachePath, $content);
    }
    return json_decode($content, true);
}

3. 优化file_get_contents请求参数

如果不想改用cURL,也可以通过复用HTTP上下文减少file_get_contents的连接开销:

<?php 
// 提前创建上下文,复用连接
$context = stream_context_create([
    'http' => [
        'timeout' => 3, // 设置超时时间,避免请求卡死
        'header' => 'Connection: keep-alive'
    ]
]);

$site = file_get_contents('website.com/content.json', false, $context);
$obj = json_decode($site, true);

for ($i = 0; $i <= 9; $i++) {
    echo '<div class="result-' . $obj[$i]['id'] . '">';
    // 复用同一个上下文发起请求
    $info = json_decode(file_get_contents("website.com/info/" . $obj[$i]['id'] . ".json", false, $context), true);
    echo $info['content'];
    echo '</div>';
} 
?>

4. 前端异步渲染兜底

如果以上优化还是不能满足加载速度要求,可以调整渲染逻辑:

  1. 后端先输出页面框架和所有的result-*空div,不发起info请求
  2. 前端用JS并行发起所有info请求,拿到结果后填充到对应div中
    这样后端页面首屏加载速度完全不受请求影响,用户感知的加载速度会明显提升。

内容的提问来源于stack exchange,提问作者Peter Brightt

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.29 20:36:03