codeigniter4 / CodeIgniter4

Open Source PHP Framework (originally from EllisLab)
https://codeigniter.com/
MIT License
5.4k stars 1.9k forks source link

Bug: CRITICAL - 2022-08-30 15:15:34 --> 18 : transfer closed with 73673 bytes remaining to read in SYSTEMPATH/HTTP/CURLRequest.php on line 655 #6455

Closed wuuyun closed 2 years ago

wuuyun commented 2 years ago

PHP Version

8.1

CodeIgniter4 Version

4.2.4

CodeIgniter4 Installation Method

Manual (zip or tar.gz)

Which operating systems have you tested for this bug?

Linux

Which server did you use?

fpm-fcgi

Database

No response

What happened?

CRITICAL - 2022-08-30 15:15:34 --> 18 : transfer closed with 73673 bytes remaining to read
in SYSTEMPATH/HTTP/CURLRequest.php on line 655.
 1 SYSTEMPATH/HTTP/CURLRequest.php(655): CodeIgniter\HTTP\Exceptions\HTTPException::forCurlError()
 2 SYSTEMPATH/HTTP/CURLRequest.php(363): CodeIgniter\HTTP\CURLRequest->sendRequest()
 3 SYSTEMPATH/HTTP/CURLRequest.php(136): CodeIgniter\HTTP\CURLRequest->send()

Steps to Reproduce

$client = \Config\Services::curlrequest();
$response = $client->request('GET', $url, [
 'headers' => ['X-Auth-token' => $token],
 ]);

Expected Output

w want to down load pdf success

Anything else?

No response

kenjis commented 2 years ago

It is a CURL error. It may be because of your network or the remote server. Probably CI4 cannot do anything.

For example,

18.2 Transfer closed with n bytes remaining to read https://curl.se/docs/knownbugs.html#Transfer_closed_with_n_bytes_rem

ddevsr commented 2 years ago

Share response design in your API, anyway u can set header option http_errors to false if u want to get real response from API

Example API :

            if($data){
                $response = [
                    'success'  => true,
                    'status'   => 200,
                    'messages' => 'Data member found!',
                    'data' => $data,
                ];

                return $this->respond($response, 200);
            } else {
                $response = [
                    'success'  => false,
                    'status'   => 400,
                    'messages' => 'Data member not found!',
                    'data' => null
                ];

                return $this->respond($response, 400);
            }

And If http_errors set true, you cant get real response in data member not found result

wuuyun commented 2 years ago

but when i use codes like this: verytime ok

$header = [
                    'X-Auth-token:' . $token,
                    'X-Accel-Buffering:no',
                    'Content-type:application/pdf',
                    'Accept-Ranges:bytes',
                ];
public function my_curl_data($url, $header = [], $timeout = 0)
    {
        $ch = curl_init($url);
        if (substr($url, 0, 8) == "https://") {
            curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
            curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, true);
        }
        // curl_setopt($ch, CURLOPT_HEADER, 0);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        if ($header) {
            curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
        }
        $timeout && curl_setopt($ch, CURLOPT_TIMEOUT, $timeout);
        $data = curl_exec($ch);
        $code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
        $errno = curl_errno($ch);
        if ($errno) {
            return $errno;
        }
        curl_close($ch);
        return $data;
    }
wuuyun commented 2 years ago

It is a CURL error. It may be because of your network or the remote server. Probably CI4 cannot do anything.

For example,

18.2 Transfer closed with n bytes remaining to read https://curl.se/docs/knownbugs.html#Transfer_closed_with_n_bytes_rem

$header = [ 'X-Auth-token:' . $token, 'X-Accel-Buffering:no', 'Content-type:application/pdf', 'Accept-Ranges:bytes', ]; public function my_curl_data($url, $header = [], $timeout = 0) { $ch = curl_init($url); if (substr($url, 0, 8) == "https://") { curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, true); } // curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); if ($header) { curl_setopt($ch, CURLOPT_HTTPHEADER, $header); } $timeout && curl_setopt($ch, CURLOPT_TIMEOUT, $timeout); $data = curl_exec($ch); $code = curl_getinfo($ch, CURLINFO_HTTP_CODE); $errno = curl_errno($ch); if ($errno) { return $errno; } curl_close($ch); return $data; }

kenjis commented 2 years ago

Okay, if you know the correct options for the download, you just set the exactly same options in CURLRequest. It seems your code obviously does not set the headers.