CURL错误:Recv失败:通过对等- PHP CURL重设连接

时间:2022-10-25 21:31:41

I'm having this strange error, CURL ERROR: Recv failure: Connection reset by peer

我有一个奇怪的错误,CURL错误:Recv失败:通过对等连接重置

This is how it happens, if I did not connect to the server and all of a sudden trying to connect to the server via CURL in PHP I get the error. When I run the CURL script again the error disappears and then works well the whole time, if I leave the remote server idle for about 30mins or reboot the remote server and try to connect again, I get the error again. So it seems like the connection is idle and then all of sudden the server wakes up and then works and then sleeps again.

这就是它发生的方式,如果我没有连接到服务器,并且突然试图通过PHP的CURL连接到服务器,我就会得到错误。当我再次运行CURL脚本时,错误消失了,然后整个过程都运行良好,如果我让远程服务器空闲大约30分钟,或者重新启动远程服务器并尝试再次连接,我将再次获得错误。似乎连接是空闲的,然后服务器突然醒来然后工作,然后再睡。

This is how my CURL script looks.

这就是我的CURL脚本的样子。

$url = Yii::app()->params['pdfUrl'];
            $body = 'title='.urlencode($title).'&client_url='.Yii::app()->params['pdfClientURL'].'&client_id='.Yii::app()->params['pdfClientID'].'&content='.urlencode(htmlentities($content));

            $c = curl_init ($url);
            $body = array(
                "client_url"=>Yii::app()->params['pdfClientURL'],
                "client_id"=>Yii::app()->params['pdfClientID'],
                "title"=>urlencode($title),
                "content"=>urlencode($content)

            );
            foreach($body as $key=>$value) { $body_str .= $key.'='.$value.'&'; }
                rtrim($body_str,'&');

            curl_setopt ($c, CURLOPT_POST, true);
            curl_setopt ($c, CURLOPT_POSTFIELDS, $body_str);
            curl_setopt ($c, CURLOPT_RETURNTRANSFER, true);
            curl_setopt ($c, CURLOPT_CONNECTTIMEOUT , 0);
            curl_setopt ($c, CURLOPT_TIMEOUT  , 20);

            $pdf = curl_exec ($c);
            $errorCode = curl_getinfo($c, CURLINFO_HTTP_CODE);
            $curlInfo = curl_getinfo($c);
            $curlError = curl_error($c);

            curl_close ($c);

I'm totally out of ideas and solutions, please help, I'll appreciate it!!!

我完全没有想法和解决办法,请帮忙,我会很感激的!!!

If I verbose the output to see what happens using

如果我详细地输出,看看会发生什么

curl_setopt ($c, CURLOPT_VERBOSE, TRUE);
curl_setopt($c, CURLOPT_STDERR, $fp); 

I get the following

我得到以下

* About to connect() to 196.41.139.168 port 80 (#0)
*   Trying 196.x.x.x... * connected
* Connected to 196.x.x.x (196.x.x.x) port 80 (#0)
> POST /serve/?r=pdf/generatePdf HTTP/1.1
Host: 196.x.x.x
Accept: */*
Content-Length: 7115
Content-Type: application/x-www-form-urlencoded
Expect: 100-continue

* Recv failure: Connection reset by peer
* Closing connection #0
012 20:23:49 GMT
< Server: Apache/2.2.15 (CentOS)
< X-Powered-By: PHP/5.3.3
< Connection: close
< Transfer-Encoding: chunked
< Content-Type: text/html; charset=UTF-8
< 
* Closing connection #0

I've added in the following toe remove the default header and still no luck:

我在下面的脚趾添加了删除默认标题,仍然没有运气:

curl_setopt ($c, CURLOPT_HTTPHEADER, array( 'Expect:' ) );

> Accept: */* Content-Length: 8414 Content-Type:
> application/x-www-form-urlencoded
> 
> * Recv failure: Connection reset by peer
> * Closing connection #0 r: Apache/2.2.15 (CentOS) < X-Powered-By: PHP/5.3.3 < Connection: close < Transfer-Encoding: chunked <
> Content-Type: text/html; charset=UTF-8 < 
> * Closing connection #0

6 个解决方案

#1


84  

Introduction

The remote server has sent you a RST packet, which indicates an immediate dropping of the connection, rather than the usual handshake.

远程服务器向您发送了一个RST包,该包表示连接的立即删除,而不是通常的握手。

Possible Causes

A. TCP/IP

答:TCP / IP

It might be TCP/IP issue you need to resolve with your host or upgrade your OS most times connection is close before remote server before it finished downloading the content resulting to Connection reset by peer.....

可能是TCP/IP问题,您需要与您的主机解决,或升级您的操作系统。大多数时候,连接在远程服务器完成下载内容以连接重置之前关闭。

B. Kannel Bug

b有错误

Note that there are some issues with TCP window scaling on some Linux kernels after v2.6.17. See the following bug reports for more information:

请注意,在v2.6.17之后,一些Linux内核上的TCP窗口扩展存在一些问题。有关更多信息,请参见下面的bug报告:

https://bugs.launchpad.net/ubuntu/+source/linux-source-2.6.17/+bug/59331

https://bugs.launchpad.net/ubuntu/ +源/ linux-source-2.6.17 / +错误/ 59331

https://bugs.launchpad.net/ubuntu/+source/linux-source-2.6.20/+bug/89160

https://bugs.launchpad.net/ubuntu/ +源/ linux-source-2.6.20 / +错误/ 89160

C. PHP & CURL Bug

C. PHP和CURL错误

You are using PHP/5.3.3 which has some serious bugs too ... i would advice you work with a more recent version of PHP and CURL

您使用的是PHP/5.3.3,它也有一些严重的bug……我建议您使用最新版本的PHP和CURL

https://bugs.php.net/bug.php?id=52828

https://bugs.php.net/bug.php?id=52828

https://bugs.php.net/bug.php?id=52827

https://bugs.php.net/bug.php?id=52827

https://bugs.php.net/bug.php?id=52202

https://bugs.php.net/bug.php?id=52202

https://bugs.php.net/bug.php?id=50410

https://bugs.php.net/bug.php?id=50410

D. Maximum Transmission Unit

d .最大传输单元

One common cause of this error is that the MTU (Maximum Transmission Unit) size of packets travelling over your network connection have been changed from the default of 1500 bytes. If you have configured VPN this most likely must changed during configuration

造成此错误的一个常见原因是,在您的网络连接上运行的数据包的MTU(最大传输单元)大小已经从默认的1500字节改变了。如果您已经配置了VPN,那么在配置过程中很可能必须进行更改

D. Firewall : iptables

d .防火墙:iptables

If you don't know your way around this guys they would cause some serious issues .. try and access the server you are connecting to check the following

如果你不了解这些人,他们会给你带来严重的问题。尝试访问正在连接的服务器,检查以下内容

  • You have access to port 80 on that server
  • 您可以在该服务器*问端口80。

Example

例子

 -A RH-Firewall-1-INPUT -m state --state NEW -m tcp -p tcp --dport 80 -j ACCEPT`
  • The Following is at the last line not before any other ACCEPT
  • 以下是在最后一行而不是在任何其他接受之前

Example

例子

  -A RH-Firewall-1-INPUT -j REJECT --reject-with icmp-host-prohibited 
  • Check for ALL DROP , REJECT and make sure they are not blocking your connection

    检查所有的下降,拒绝并确保他们没有阻塞你的连接。

  • Temporary allow all connection as see if it foes through

    暂时允许所有的连接,看它的敌人是否通过。

Experiment

Try a different server or remote server ( So many fee cloud hosting online) and test the same script .. if it works then i guesses are as good as true ... You need to update your system

尝试使用不同的服务器或远程服务器(如此多的收费云托管在线)并测试相同的脚本。如果这是真的,我猜是真的。您需要更新系统

Others Code Related

A. SSL

答:SSL

If Yii::app()->params['pdfUrl'] is a url with https not including proper SSL setting can also cause this error in old version of curl

如果Yii:::app()->params['pdfUrl']是一个具有https的url,不包括适当的SSL设置也会在旧版本的curl中导致此错误

Resolution : Make sure OpenSSL is installed and enabled then add this to your code

解决方案:确保安装并启用了OpenSSL,然后将其添加到代码中

curl_setopt($c, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($c, CURLOPT_SSL_VERIFYHOST, false);

I hope it helps

我希望这有助于

#2


9  

Normally this error means that a connection was established with a server but that connection was closed by the remote server. This could be due to a slow server, a problem with the remote server, a network problem, or (maybe) some kind of security error with data being sent to the remote server but I find that unlikely.

通常,此错误意味着与服务器建立了连接,但是远程服务器关闭了该连接。这可能是由于服务器速度缓慢、远程服务器出现问题、网络问题,或者(可能)数据被发送到远程服务器时出现某种安全错误,但我认为这不太可能。

Normally a network error will resolve itself given a bit of time, but it sounds like you’ve already given it a bit of time.

通常一个网络错误会在一段时间内自行解决,但听起来好像你已经给了它一点时间。

cURL sometimes having issue with SSL and SSL certificates. I think that your Apache and/or PHP was compiled with a recent version of the cURL and cURL SSL libraries plus I don't think that OpenSSL was installed in your web server.

cURL有时会出现SSL和SSL证书的问题。我认为您的Apache和/或PHP是使用最新版本的cURL和cURL SSL库编译的,而且我不认为OpenSSL是安装在web服务器上的。

Although I can not be certain However, I believe cURL has historically been flakey with SSL certificates, whereas, Open SSL does not.

尽管我不能确定,但是我认为cURL在使用SSL证书时一直很不稳定,而Open SSL则不然。

Anyways, try installing Open SSL on the server and try again and that should help you get rid of this error.

无论如何,请尝试在服务器上安装Open SSL并再次尝试,这将帮助您消除此错误。

#3


3  

So what is the URL that Yii::app()->params['pdfUrl'] gives? You say it should be https, but the log shows it's connecting on port 80... which almost no server is setup to accept https connections on. cURL is smart enough to know https should be on port 443... which would suggest that your URL has something wonky in it like: https://196.41.139.168:80/serve/?r=pdf/generatePdf

那么Yii::app()->params['pdfUrl']给出的URL是什么?您说它应该是https,但是日志显示它正在连接端口80……几乎没有服务器设置接受https连接。cURL非常聪明,知道https应该在端口443上……这说明您的URL有一些问题,比如:https://196.41.139.168:80/serve/?r=pdf/generatePdf

That's going to cause the connection to be terminated, when the Apache at the other end cannot do https communication with you on that port.

当另一端的Apache无法在该端口上与您进行https通信时,这将导致连接终止。

You realize your first $body definition gets replaced when you set $body to an array two lines later? {Probably just an artifact of you trying to solve the problem} You're also not encoding the client_url and client_id values (the former quite possibly containing characters that need escaping!) Oh and you're appending to $body_str without first initializing it.

你意识到你的第一个$body定义在两行后将$body设置为数组时被替换了吗?{可能只是您试图解决问题的工件}您也没有对client_url和client_id值进行编码(前者很可能包含需要转义的字符!)噢,你附加到$body_str,而没有先初始化它。

From your verbose output we can see cURL is adding a content-length header, but... is it correct? I can see some comments out on the internets of that number being wrong (especially with older versions)... if that number was to small (for example) you'd get a connection-reset before all the data is sent. You can manually insert the header:

从您的详细输出中,我们可以看到cURL正在添加内容长度的标题,但是……是正确的吗?我可以看到一些关于这个数字的内部评论是错误的(特别是旧版本)……如果这个数字很小(例如),那么在发送所有数据之前就会进行连接重置。你可以手动插入标题:

curl_setopt ($c, CURLOPT_HTTPHEADER, 
   array("Content-Length: ". strlen($body_str))); 

Oh and there's a handy function http_build_query that'll convert an array of name/value pairs into a URL encoded string for you.

噢,还有一个方便的函数http_build_query,它可以将名称/值对数组转换为URL编码的字符串。

All this rolls up into the final code:

所有这些都卷进了最后的代码:

$post=http_build_query(array(
  "client_url"=>Yii::app()->params['pdfClientURL'],
  "client_id"=>Yii::app()->params['pdfClientID'],
  "title"=>$title,
  "content"=>$content));

//Open to URL
$c=curl_init(Yii::app()->params['pdfUrl']);
//Send post
curl_setopt ($c, CURLOPT_POST, true);
//Optional: [try with/without]
curl_setopt ($c, CURLOPT_HTTPHEADER, array("Content-Length: ".strlen($post))); 
curl_setopt ($c, CURLOPT_POSTFIELDS, $post);
curl_setopt ($c, CURLOPT_RETURNTRANSFER, true);
curl_setopt ($c, CURLOPT_CONNECTTIMEOUT , 0);
curl_setopt ($c, CURLOPT_TIMEOUT  , 20);
//Collect result
$pdf = curl_exec ($c);
$curlInfo = curl_getinfo($c);
curl_close($c);

#4


1  

This is a firewall issue, if you are using a VMware application, make sure the firewall on the antivirus is turned off or allowing connections.

这是一个防火墙问题,如果您正在使用VMware应用程序,请确保杀毒软件上的防火墙已关闭或允许连接。

If this server is on a secure network, please have a look at firewall rules of the server.

如果此服务器位于安全网络中,请查看服务器的防火墙规则。

Thanks Ganesh PNS

由于Ganesh pn

#5


0  

In my case there was problem in URL. I've use https://example.com - but they ensure 'www.' - so when i switched to https://www.example.com everything was ok. The proper header was sent 'Host: www.example.com'.

在我的例子中,URL有问题。我使用了https://example.com——但是他们保证了“www.”——所以当我切换到https://www.example.com时一切都很好。正确的标题是“Host: www.example.com”。

You can try make a request in firefox brwoser, persist it and copy as cURL - that how I've found it.

您可以尝试在firefox brwoser中发出一个请求,并将其持久化,并将其复制为cURL——我就是这样找到它的。

#6


0  

I faced same error but in a different way.

我面临着同样的错误,但方式不同。

When you curl a page with a specific SSL protocol.

当您使用特定的SSL协议卷起页面时。

curl --sslv3 https://example.com

If --sslv3 is not supported by the target server then the error will be

如果目标服务器不支持sslv3,那么错误将是

curl: (35) TCP connection reset by peer

curl: (35) TCP连接通过对等重设

With the supported protocol, error will be gone.

有了支持的协议,错误就会消失。

curl --tlsv1.2 https://example.com

#1


84  

Introduction

The remote server has sent you a RST packet, which indicates an immediate dropping of the connection, rather than the usual handshake.

远程服务器向您发送了一个RST包,该包表示连接的立即删除,而不是通常的握手。

Possible Causes

A. TCP/IP

答:TCP / IP

It might be TCP/IP issue you need to resolve with your host or upgrade your OS most times connection is close before remote server before it finished downloading the content resulting to Connection reset by peer.....

可能是TCP/IP问题,您需要与您的主机解决,或升级您的操作系统。大多数时候,连接在远程服务器完成下载内容以连接重置之前关闭。

B. Kannel Bug

b有错误

Note that there are some issues with TCP window scaling on some Linux kernels after v2.6.17. See the following bug reports for more information:

请注意,在v2.6.17之后,一些Linux内核上的TCP窗口扩展存在一些问题。有关更多信息,请参见下面的bug报告:

https://bugs.launchpad.net/ubuntu/+source/linux-source-2.6.17/+bug/59331

https://bugs.launchpad.net/ubuntu/ +源/ linux-source-2.6.17 / +错误/ 59331

https://bugs.launchpad.net/ubuntu/+source/linux-source-2.6.20/+bug/89160

https://bugs.launchpad.net/ubuntu/ +源/ linux-source-2.6.20 / +错误/ 89160

C. PHP & CURL Bug

C. PHP和CURL错误

You are using PHP/5.3.3 which has some serious bugs too ... i would advice you work with a more recent version of PHP and CURL

您使用的是PHP/5.3.3,它也有一些严重的bug……我建议您使用最新版本的PHP和CURL

https://bugs.php.net/bug.php?id=52828

https://bugs.php.net/bug.php?id=52828

https://bugs.php.net/bug.php?id=52827

https://bugs.php.net/bug.php?id=52827

https://bugs.php.net/bug.php?id=52202

https://bugs.php.net/bug.php?id=52202

https://bugs.php.net/bug.php?id=50410

https://bugs.php.net/bug.php?id=50410

D. Maximum Transmission Unit

d .最大传输单元

One common cause of this error is that the MTU (Maximum Transmission Unit) size of packets travelling over your network connection have been changed from the default of 1500 bytes. If you have configured VPN this most likely must changed during configuration

造成此错误的一个常见原因是,在您的网络连接上运行的数据包的MTU(最大传输单元)大小已经从默认的1500字节改变了。如果您已经配置了VPN,那么在配置过程中很可能必须进行更改

D. Firewall : iptables

d .防火墙:iptables

If you don't know your way around this guys they would cause some serious issues .. try and access the server you are connecting to check the following

如果你不了解这些人,他们会给你带来严重的问题。尝试访问正在连接的服务器,检查以下内容

  • You have access to port 80 on that server
  • 您可以在该服务器*问端口80。

Example

例子

 -A RH-Firewall-1-INPUT -m state --state NEW -m tcp -p tcp --dport 80 -j ACCEPT`
  • The Following is at the last line not before any other ACCEPT
  • 以下是在最后一行而不是在任何其他接受之前

Example

例子

  -A RH-Firewall-1-INPUT -j REJECT --reject-with icmp-host-prohibited 
  • Check for ALL DROP , REJECT and make sure they are not blocking your connection

    检查所有的下降,拒绝并确保他们没有阻塞你的连接。

  • Temporary allow all connection as see if it foes through

    暂时允许所有的连接,看它的敌人是否通过。

Experiment

Try a different server or remote server ( So many fee cloud hosting online) and test the same script .. if it works then i guesses are as good as true ... You need to update your system

尝试使用不同的服务器或远程服务器(如此多的收费云托管在线)并测试相同的脚本。如果这是真的,我猜是真的。您需要更新系统

Others Code Related

A. SSL

答:SSL

If Yii::app()->params['pdfUrl'] is a url with https not including proper SSL setting can also cause this error in old version of curl

如果Yii:::app()->params['pdfUrl']是一个具有https的url,不包括适当的SSL设置也会在旧版本的curl中导致此错误

Resolution : Make sure OpenSSL is installed and enabled then add this to your code

解决方案:确保安装并启用了OpenSSL,然后将其添加到代码中

curl_setopt($c, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($c, CURLOPT_SSL_VERIFYHOST, false);

I hope it helps

我希望这有助于

#2


9  

Normally this error means that a connection was established with a server but that connection was closed by the remote server. This could be due to a slow server, a problem with the remote server, a network problem, or (maybe) some kind of security error with data being sent to the remote server but I find that unlikely.

通常,此错误意味着与服务器建立了连接,但是远程服务器关闭了该连接。这可能是由于服务器速度缓慢、远程服务器出现问题、网络问题,或者(可能)数据被发送到远程服务器时出现某种安全错误,但我认为这不太可能。

Normally a network error will resolve itself given a bit of time, but it sounds like you’ve already given it a bit of time.

通常一个网络错误会在一段时间内自行解决,但听起来好像你已经给了它一点时间。

cURL sometimes having issue with SSL and SSL certificates. I think that your Apache and/or PHP was compiled with a recent version of the cURL and cURL SSL libraries plus I don't think that OpenSSL was installed in your web server.

cURL有时会出现SSL和SSL证书的问题。我认为您的Apache和/或PHP是使用最新版本的cURL和cURL SSL库编译的,而且我不认为OpenSSL是安装在web服务器上的。

Although I can not be certain However, I believe cURL has historically been flakey with SSL certificates, whereas, Open SSL does not.

尽管我不能确定,但是我认为cURL在使用SSL证书时一直很不稳定,而Open SSL则不然。

Anyways, try installing Open SSL on the server and try again and that should help you get rid of this error.

无论如何,请尝试在服务器上安装Open SSL并再次尝试,这将帮助您消除此错误。

#3


3  

So what is the URL that Yii::app()->params['pdfUrl'] gives? You say it should be https, but the log shows it's connecting on port 80... which almost no server is setup to accept https connections on. cURL is smart enough to know https should be on port 443... which would suggest that your URL has something wonky in it like: https://196.41.139.168:80/serve/?r=pdf/generatePdf

那么Yii::app()->params['pdfUrl']给出的URL是什么?您说它应该是https,但是日志显示它正在连接端口80……几乎没有服务器设置接受https连接。cURL非常聪明,知道https应该在端口443上……这说明您的URL有一些问题,比如:https://196.41.139.168:80/serve/?r=pdf/generatePdf

That's going to cause the connection to be terminated, when the Apache at the other end cannot do https communication with you on that port.

当另一端的Apache无法在该端口上与您进行https通信时,这将导致连接终止。

You realize your first $body definition gets replaced when you set $body to an array two lines later? {Probably just an artifact of you trying to solve the problem} You're also not encoding the client_url and client_id values (the former quite possibly containing characters that need escaping!) Oh and you're appending to $body_str without first initializing it.

你意识到你的第一个$body定义在两行后将$body设置为数组时被替换了吗?{可能只是您试图解决问题的工件}您也没有对client_url和client_id值进行编码(前者很可能包含需要转义的字符!)噢,你附加到$body_str,而没有先初始化它。

From your verbose output we can see cURL is adding a content-length header, but... is it correct? I can see some comments out on the internets of that number being wrong (especially with older versions)... if that number was to small (for example) you'd get a connection-reset before all the data is sent. You can manually insert the header:

从您的详细输出中,我们可以看到cURL正在添加内容长度的标题,但是……是正确的吗?我可以看到一些关于这个数字的内部评论是错误的(特别是旧版本)……如果这个数字很小(例如),那么在发送所有数据之前就会进行连接重置。你可以手动插入标题:

curl_setopt ($c, CURLOPT_HTTPHEADER, 
   array("Content-Length: ". strlen($body_str))); 

Oh and there's a handy function http_build_query that'll convert an array of name/value pairs into a URL encoded string for you.

噢,还有一个方便的函数http_build_query,它可以将名称/值对数组转换为URL编码的字符串。

All this rolls up into the final code:

所有这些都卷进了最后的代码:

$post=http_build_query(array(
  "client_url"=>Yii::app()->params['pdfClientURL'],
  "client_id"=>Yii::app()->params['pdfClientID'],
  "title"=>$title,
  "content"=>$content));

//Open to URL
$c=curl_init(Yii::app()->params['pdfUrl']);
//Send post
curl_setopt ($c, CURLOPT_POST, true);
//Optional: [try with/without]
curl_setopt ($c, CURLOPT_HTTPHEADER, array("Content-Length: ".strlen($post))); 
curl_setopt ($c, CURLOPT_POSTFIELDS, $post);
curl_setopt ($c, CURLOPT_RETURNTRANSFER, true);
curl_setopt ($c, CURLOPT_CONNECTTIMEOUT , 0);
curl_setopt ($c, CURLOPT_TIMEOUT  , 20);
//Collect result
$pdf = curl_exec ($c);
$curlInfo = curl_getinfo($c);
curl_close($c);

#4


1  

This is a firewall issue, if you are using a VMware application, make sure the firewall on the antivirus is turned off or allowing connections.

这是一个防火墙问题,如果您正在使用VMware应用程序,请确保杀毒软件上的防火墙已关闭或允许连接。

If this server is on a secure network, please have a look at firewall rules of the server.

如果此服务器位于安全网络中,请查看服务器的防火墙规则。

Thanks Ganesh PNS

由于Ganesh pn

#5


0  

In my case there was problem in URL. I've use https://example.com - but they ensure 'www.' - so when i switched to https://www.example.com everything was ok. The proper header was sent 'Host: www.example.com'.

在我的例子中,URL有问题。我使用了https://example.com——但是他们保证了“www.”——所以当我切换到https://www.example.com时一切都很好。正确的标题是“Host: www.example.com”。

You can try make a request in firefox brwoser, persist it and copy as cURL - that how I've found it.

您可以尝试在firefox brwoser中发出一个请求,并将其持久化,并将其复制为cURL——我就是这样找到它的。

#6


0  

I faced same error but in a different way.

我面临着同样的错误,但方式不同。

When you curl a page with a specific SSL protocol.

当您使用特定的SSL协议卷起页面时。

curl --sslv3 https://example.com

If --sslv3 is not supported by the target server then the error will be

如果目标服务器不支持sslv3,那么错误将是

curl: (35) TCP connection reset by peer

curl: (35) TCP连接通过对等重设

With the supported protocol, error will be gone.

有了支持的协议,错误就会消失。

curl --tlsv1.2 https://example.com