如何解决[警告:fsockopen():无法连接]问题?

4

我想要检查我的服务器Ubuntu Server 14.04 LTS在我的共享主机服务器上是否在线。我的服务器有IP而不是域名,但我的共享主机服务器有域名。为此,我在共享主机服务器上使用了以下代码来检查我的服务器是否在线。

<?php
$site = "XX.XX.XX.XX";
$port = 7550;
$fp = fsockopen($site,$port,$errno,$errstr,10);
if ($fp === false) { 
 print($errno." : ".$errstr); 
}  
if(!$fp)
{
echo "SERVER IS DOWN";
}
else
{
echo "SERVER IS UP ON PORT ".$port." AT ".$site;
fclose($fp);
}
?>

在我的共享托管服务器php文件中添加上述代码后,运行它时我遇到了以下错误。
警告:fsockopen():无法连接到XX.XX.XX.XX:7550(连接超时),位于/home/USERNAME/public_html/index.php的第4110行:连接超时,服务器已停止
现在有人告诉我检查我的共享托管服务器上是否打开了allow_url_fopen = On,然后我检查了我的共享托管服务器php.ini文件,发现它已经打开了。
现在当我四处寻找帮助时,其他人告诉我要检查两个服务器(我的共享托管服务器和我的服务器)是否都开启了fsockopen()。然后我在一个php文件中编写了以下代码,并在两个服务器上运行。
<?php
$fp = fsockopen ("localhost", 80, $errno, $errstr, 10);
if (!$fp) {
echo "$errstr ($errno)
\n";
}else
{
echo "fsockopen Is Working Perfectly.";
}
fclose ($fp);
?>

在两个服务器上运行上述的.php文件后,我得到了以下相同的结果。
重要提示:请注意,我的服务器IP仍然处于活动状态,因为我正在使用该IP上的多台电脑,但我的服务器已关闭。此外,我可以使用代理在Web浏览器中打开http://XX.XX.XX.XX:7550。

“连接超时”通常指防火墙或远程端响应时间过长。 - Gerald Schneider
@Steini 我能够使用代理在我的Web浏览器中打开http://XX.XX.XX.XX:7550 - Muhammad Hassan
@DanFromGermany 我在这个领域是新手。所以你能在回答中分享整个代码吗?我从问题中得到了所有上面的代码。 - Muhammad Hassan
我不会因为在stackoverflow上回答问题而得到报酬。你应该阅读文档并从中学习。 - Daniel W.
@DanFromGermany 感谢您花时间提供链接。 - Muhammad Hassan
显示剩余3条评论
3个回答

6

由于fsockopen函数在主机名不是有效域名时会抛出E_WARNING异常。因此,如果使用离线的IP和端口,则该函数会抛出异常。

您可以通过处理异常或使用@符号来解决问题:

$fp = @fsockopen($site,$port,$errno,$errstr,10);

如果你认为你的端口在线,请检查防火墙并检查外部资源,如http://www.yougetsignal.com/tools/open-ports/
阅读http://php.net/manual/es/function.fsockopen.php
更新:您可以使用socket_create进行测试,它比fsockopen更好。
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
$connection =  @socket_connect($socket, 'XX.XX.XX.XX', 7550);

if( $connection ){
    echo 'ONLINE';
} else {
    echo 'OFFLINE: ' . socket_strerror(socket_last_error( $socket ));
}

您必须设置一个有效的协议,详情请参见:http://php.net/manual/es/function.socket-create.php

11
用 @ 符号抑制错误信息并不能解决问题,反而会产生新的问题。 - Gerald Schneider
不需要在域名中,只需在IP地址中检查端口是否在线,则需要处理异常或使用@。如果您处理异常,则需要使用if条件和try, catch。请阅读http://php.net/manual/es/function.fsockopen.php。在生产环境中显示错误是不好的。 - SnakeDrak
当我加入了$fp = @fsockopen($site,$port,$errno,$errstr,10);之后,我得到了 110:连接超时,服务器已下线。 :( - Muhammad Hassan
@Snake,我是这个领域的新手,所以我没有尝试过其他的代码,问题中上面的所有代码都是从互联网上获取的。您能分享一些新的代码吗? - Muhammad Hassan
@Snake 在你提供的答案代码中将 SOL_TCP 更改为 SOL_UDP 后,我在我的共享托管服务器上运行 PHP 文件后得到了 OFFLINE: Success 文本,即使我的 Ubuntu Server 14.04 LTS 在线。 - Muhammad Hassan
显示剩余9条评论

2
如果您使用 set_error_handler() 覆盖了错误处理程序,那么您需要检查 error_reporting() 是否返回 0,这意味着使用 @ 抑制了错误。
set_error_handler('errorHandler');

function errorHandler($errno, $errstr, $errfile, $errline) {

    if (error_reporting() === 0) 
        return false;

    //handle error
    ...
}

0

通常共享主机会禁止除80端口以外的所有端口,请尝试使用80端口。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接