php技巧

关注公众号 jb51net

关闭
首页 > 网络编程 > PHP编程 > php技巧 > php中fsockopen用法

php中fsockopen用法实例

投稿:shichen2014

这篇文章主要介绍了php中fsockopen用法,实例分析了fsockopen的创建、写入及关闭等具体流程,需要的朋友可以参考下

本文实例讲述了php中fsockopen用法。分享给大家供大家参考。

函数说明:fsockopen — 打开一个网络连接或者一个Unix套接字连接

语法:

resource fsockopen ( string $hostname [, int $port = -1 [, int &$errno [, string &$errstr [, float $timeout = ini_get("default_socket_timeout") ]]]] )

参数:

返回值:

fsockopen() 将返回一个文件句柄,之后可以被其他文件类函数调用(例如: fgets() , fgetss() , fwrite() , fclose() 还有 feof() )。如果调用失败,将返回 FALSE 。

php fsockopen使用案例

1、fsockopen 来模拟生成 HTTP 连接 

$url="//www.jb51.net";
$port=80;
$t=30;
/**fsockopen 抓取页面
 * @parem $url 网页地址
 * @parem $port 端口 默认 80
 * @parem $t 设置连接的时间 默认30s
 * */
function fsock($url,$port=80,$t=30)
{   $info=parse_url($url);
    $fp = fsockopen($info['host'],$port,$errno,$errstr,$t);
    if (!$fp)
    {
        echo "$errstr ($errno)<br />\n";
    }
    else
    {
        $out = "GET ".$info['path']." HTTP/1.1".PHP_EOL;     $out .= "Host: ".$info['host'].".PHP_EOL;     $out .= "Connection: Close".PHP_EOL.PHP_EOL;
        fwrite($fp, $out);
        $content = '';
        while (!feof($fp))
        {
            $content .= fgets($fp);
        }
        echo $content;
        fclose($fp);
    }
}// 函数调用
fsock($url, $port,$t);

2、PHP fsockopen模拟POST/GET方法

fsockopen除了像上面实例模拟生成 HTTP 连接之外,还能实现很多功能,比如模拟post 和 get 传送数据的方法。 

$url = "http://localhost/test/test.php"; #url 地址必须 http://xxxxx
$port=80;
$t=30;
$data = array(
    'foo'=>'bar',
    'baz'=>'boom',
    'site'=>'www.jb51.net',
    'name'=>'nowa magic');
/**fsockopen 抓取页面
 * @parem $url 网页地址 host 主机地址  * @parem $port 网址端口 默认80 * @parem $t 脚本请求时间 默认30s
 * @parem $method 请求方式 get/post
 * @parem $data 如果单独传数据为 post 方式
 * @return 返回请求回的数据
 * */
function sock_data($url,$port=80,$t=30,$method='get',$data=null)
{
    $info=parse_url($url);
    $fp = fsockopen($info["host"],$port, $errno, $errstr,$t);
    // 判断是否有数据
    if(isset($data) && !empty($data))
    {
        $query = http_build_query($data); // 数组转url 字符串形式
    }else
    {
        $query=null;
    }
    // 如果用户的$url "//www.jb51.net/";  缺少 最后的反斜杠
    if(!isset($info['path']) || empty($info['path']))
    {
       $info['path']="/index.html";
    }
    // 判断 请求方式
    if($method=='post')
    {
        $head = "POST ".$info['path']." HTTP/1.0".PHP_EOL;
    }else
    {
        $head = "GET ".$info['path']."?".$query." HTTP/1.0".PHP_EOL;
    }
   $head .= "Host: ".$info['host'].PHP_EOL; // 请求主机地址
   $head .= "Referer: http://".$info['host'].$info['path'].PHP_EOL;
    if(isset($data) && !empty($data) && ($method=='post'))
    {
        $head .= "Content-type: application/x-www-form-urlencoded".PHP_EOL;
        $head .= "Content-Length: ".strlen(trim($query)).PHP_EOL;
        $head .= PHP_EOL;
        $head .= trim($query);
    }else
    {
        $head .= PHP_EOL;
    }
    $write = fputs($fp, $head); //写入文件(可安全用于二进制文件)。 fputs() 函数是 fwrite() 函数的别名
    while (!feof($fp))
    {
        $line = fread($fp,4096);
        echo $line;
    }
}
// 函数调用
sock_data($url,$port,$t,'post',$data);

3、fsockopen以Socket方式模拟HTTP下载文件

PHP设置脚本最大执行时间的三种方法   
1.php.ini文件中   max_execution_time = 120;
2、通过PHP的ini_set函数设置
ini_set("max_execution_time", "120");
3、通过set_time_limit 函数设置
set_time_limit(120);

以上几个数字设置为0则无限制,脚本会一直执行下去,直到执行结束。

set_time_limit(0);
$url = 'http://localhost/test/img.zip';
$port = '80';
/** sockopen 下载文件
 * @parem $url 访问文件的url 地址
 * @parem $port 默认 80 * @parem $down_name 下载指定路径文件名称 例如 ../aa.zip 
 * */
function sock_down($url,$port=80,$down_name=null)
{
    $info=parse_url($url);
    # 建立连接
    $fp = fsockopen($info["host"],$port,$errno,$errstr,$t);
    /*
     为资源流设置阻塞或者阻塞模式  参数:资源流(),0是非阻塞,1是阻塞
    bool stream_set_blocking ( resource $stream , int $mode )
    阻塞的好处是,排除其它非正常因素,阻塞的是按顺序执行的同步的读取。将会一直等到从资源流里面获取到数据才能返回
    而非阻塞,因为不必等待内容,所以能异步的执行,现在读到读不到都没关系,执行读取操作后会立即返回数据
     * */
    stream_set_blocking($fp, 1);
    if(!$fp)
    {
        echo "$errno : $errstr<br/>";
    }
    else
    {
        # 发送一个HTTP请求信息头
        $request_header="GET ".$info['path']." HTTP/1.1".PHP_EOL;
        # 起始行
        # 头域
        $request_header.="Host: ".$info["host"].PHP_EOL;
        # 再一个回车换行表示头信息结束
        $request_header.=PHP_EOL;
        # 发送请求到服务器
        fputs($fp,$request_header);
        if(!isset($down_name) || empty($down_name))
        {
            $down_name=basename($url); //默认当前文件同目录
        }
        # 接受响应
        $fp2=fopen($down_name,'w'); // 要下载的文件名  下载到指定目录
        $line='';
        while (!feof($fp))
        {
            $line.= fputs($fp2,fgets($fp));
        }
        if(feof($fp))
        {
            echo "<script>alert('已下载到当前目录')</script>";
        }
        # 关闭
        fclose($fp2);
        fclose($fp);
    }
}
//函数调用
sock_down($url,$port);

4、使用 fsockopen 伪造来源网址、路径

https://www.jb51.net/article/93173.htm

下面是其他网友的补充

具体实现方法如下:

实例一

$fp=fsockopen("127.0.0.1",80);     //打开数据流
if(!$fp)           //如果打开出错
{
  echo "unable to openn";       //输出内容
}
else            //如果成功打开
{
  fwrite($fp,"get / http/1.0rnrn");     //向数据流写入内容
  stream_set_timeout($fp,2);       //进行超时设置
  $res=fread($fp,2000);        //读取内容
  $info=stream_get_meta_data($fp);      //获取数据流报头
  fclose($fp);          //关闭数据流
  if($info['timed_out'])        //如果超时
  {
    echo 'connection timed out!';      //输出内容
  }
  else
  {
    echo $res;          //输出读取内容
  }
}

实例二

//创建服务端
$socket=stream_socket_server("tcp://0.0.0.0:8000",$errno,$errstr);
//如果创建失败
if(!$socket)
{
  echo "$errstr ($errno)<br />n";
}
//如果创建成功
else
{
  //接受连接
  while($conn=stream_socket_accept($socket))
  {
    //写入数据
    fwrite($conn,'the local time is '.date('n/j/y g:i a')."n");
    //关闭连接
    fclose($conn);
  }
  //关闭socket
  fclose($socket);
}
//
$file="test.txt";       //定义文件
$fp=fopen($file,"w");      //打开数据流
if($fp)        //如果成功打开
{
  stream_set_write_buffer($fp,0);   //设置缓冲区
  fwrite($fp,$output);      //写入内容
  fclose($fp);       //关闭数据流
}

希望本文所述对大家的php程序设计有所帮助。

您可能感兴趣的文章:
阅读全文