标签 file_get_contents 下的文章

前端看没有报错,但file_get_contents()返回了 null, 看服务端日志才发现这个提示。

以前也遇到过,备忘一下。当然改用 curl 也是不错的选择。

//$json_token = file_get_contents($url_accesstoken); //ssl报错
//修改方案,构造一个context参数,不验证ssl
$context = stream_context_create([
    'ssl' => [
        'verify_peer'      => false,
        'verify_peer_name' => false
        ]
]);
$json_token = file_get_contents($url_accesstoken,false,$context); //忽略报错,正确返回内容

参考来源:https://qiita.com/mindwood/items/fd23ddcb94fb4eefa99c

这个问题其实早在2016年已经遇到,在2018年知道原因盖棺定论。近日项目重新触及,备忘一下。

从jssdk或scope接口获得用户信息内的头像链接,如果直接用php的 file_get_contents 请求的话,通常会非常的慢,脚本运行大约30秒之后才能加载出图像。如果请求量大非常容易造成服务器的堵塞。

原因

摘录另一网友的日志:
https://www.cnblogs.com/mysic/p/5421754.html

微信的服务器对头像的资源请求返回的头信息是 Connection: keep-alive ,于是请求传输完数据后就一直在干等超时。
网上对这个问题求助的也不在少数,不知道腾讯是故意为之还是装作不知道,反正问题存在至今没有主动解决。

解决办法:

自欺欺人的解决办法:
这是我最早期的解决思路,在发起请求或者获得用户头像资源的最初即在后台预载这个资源到本地缓存,降低用户对等待延迟的感知。

老实人的解决办法:
改用curl请求到本地缓存处理,加上header,下载完主动截断链接。代码演示略

无效的解决办法:
给file_get_contents() 设置第三参数 context 指定关闭链接,设置了参数后,腾讯返回过来的是0字节的数据。我觉得它们故意的嫌疑更大了!

//实验证明 context 无效,会导致返回0字节
$context = stream_context_create(
    array("http" => 
        array(
            'method'=>'get',
            'header'=>'Connection: close\r\n'
        )
    )
);
$tmp_face_data = file_get_contents($face_url, false, $context);

目前在用的解决办法:

ini_set('default_socket_timeout', 1);
$tmp_face_data = file_get_contents($face_url);

也不是没有缺点,一个小小的瑕疵是要浪费额外的1秒等timeout,不过还可以接受。
另外有一个优点,这个参数不但对 file_get_contents 有效,对于 getimagesize 这个没有context参数的方法也有帮助
所以,一劳永逸。

结论:

腾信真TM会恶心人!