选择语言 :

 Module_HttpClient_Driver_Curl::request_urls

支持多线程获取网页

Array Module_HttpClient_Driver_Curl::request_urls( Array/string $urls [, Int $timeout = integer 10 ] )
see
http://cn.php.net/manual/en/function.curl-multi-exec.php#88453

参数列表

参数 类型 描述 默认值
$urls Array/string $urls
$timeout Int $timeout integer 10
返回值
  • Array
File: ./modules/httpclient/driver/curl.class.php
protected function request_urls($urls, $timeout = 10)
{
    # 去重
    $urls = array_unique($urls);

    if (!$urls)return array();

    $mh = curl_multi_init();

    # 监听列表
    $listener_list = array();

    # 返回值
    $result = array();

    # 总列队数
    $list_num = 0;

    # 排队列表
    $multi_list = array();
    foreach ( $urls as $url )
    {
        # 创建一个curl对象
        $current = $this->_create($url, $timeout);

        if ( $this->multi_exec_num>0 && $list_num>=$this->multi_exec_num )
        {
            # 加入排队列表
            $multi_list[] = $url;
        }
        else
        {
            # 列队数控制
            curl_multi_add_handle($mh, $current);
            $listener_list[$url] = $current;
            $list_num++;
        }

        $result[$url] = null;
        $this->http_data[$url] = null;
    }
    unset($current);

    $running = null;

    # 已完成数
    $done_num = 0;

    do
    {
        while ( ($execrun = curl_multi_exec($mh, $running)) == CURLM_CALL_MULTI_PERFORM );
        if ( $execrun != CURLM_OK ) break;

        while ( true==($done = curl_multi_info_read($mh)) )
        {
            foreach ( $listener_list as $done_url=>$listener )
            {
                if ( $listener === $done['handle'] )
                {
                    # 获取内容
                    $this->http_data[$done_url] = $this->get_data(curl_multi_getcontent($done['handle']), $done['handle']);

                    if ( $this->http_data[$done_url]['code'] != 200 )
                    {
                        Core::debug()->error('URL:'.$done_url.' ERROR,TIME:' . $this->http_data[$done_url]['time'] . ',CODE:' . $this->http_data[$done_url]['code'] );
                        $result[$done_url] = false;
                    }
                    else
                    {
                        # 返回内容
                        $result[$done_url] = $this->http_data[$done_url]['data'];
                        Core::debug()->info('URL:'.$done_url.' OK.TIME:' . $this->http_data[$done_url]['time'] );
                    }

                    curl_close($done['handle']);

                    curl_multi_remove_handle($mh, $done['handle']);

                    # 把监听列表里移除
                    unset($listener_list[$done_url],$listener);
                    $done_num++;

                    # 如果还有排队列表,则继续加入
                    if ( $multi_list )
                    {
                        # 获取列队中的一条URL
                        $current_url = array_shift($multi_list);

                        # 创建CURL对象
                        $current = $this->_create($current_url, $timeout);

                        # 加入到列队
                        curl_multi_add_handle($mh, $current);

                        # 更新监听列队信息
                        $listener_list[$current_url] = $current;
                        unset($current);

                        # 更新列队数
                        $list_num++;
                    }

                    break;
                }
            }
        }

        if ($done_num>=$list_num)break;

    } while (true);

    # 关闭列队
    curl_multi_close($mh);

    return $result;
}