Curl.class.php 7.08 KB
<?php
class Util_Curl
{
   private static $mDefaultOptions = array(
                                            //启用时会将头文件的信息作为数据流输出
                                            CURLOPT_HEADER => 0,                                            
                                             //文件流形式
                                            CURLOPT_RETURNTRANSFER => 1, 
                                            //设置curl允许执行的最长秒数   
                                            CURLOPT_TIMEOUT => 15,
                                            CURLOPT_CONNECTTIMEOUT => 15,
                                             //文件流形式
                                            CURLOPT_RETURNTRANSFER => true, 
                                             /*
                                              *启用时会将服务器服务器返回的"Location: "
                                              * 放在header中递归的返回给服务器,
                                              * 使用CURLOPT_MAXREDIRS可以限定递归返回的数量
                                             */  
                                           // CURLOPT_FOLLOWLOCATION => 1
                                        );
    /** 
     * CURL-get方式获取数据 
     * 
     * @param string $url URL 
     * @param array $options 
     * @param array &$header
     * @return string
     */  
    public static function get($url, $options = array(), &$header = array())
    {     
        $curl = curl_init();  
        curl_setopt($curl, CURLOPT_URL, $url);
        self::_rand_agent();
        $options = $options + self::$mDefaultOptions;  
        $parseUrl = parse_url($url);
        if(!empty($parseUrl['host']))
        {
        	$options = $options+ array( CURLOPT_REFERER => 'http://'.$parseUrl['host']);
        } 
        curl_setopt_array($curl, $options);   
        $response = curl_exec($curl);  
        if(empty($header))
        {
        	$header = curl_getinfo($curl);
        } 
        curl_close($curl);
        return $response;  
    }  
      
    /** 
     * CURL-post方式获取数据 
     * 
     * @param string $url URL 
     * @param array  $data POST数据 
     * @param array $options
     * @return array
     */  
    public static function post($url, $data, $options = array())
    {  
        $curl = curl_init();   
        curl_setopt($curl, CURLOPT_URL, $url);
        self::_rand_agent();
        $options = $options + self::$mDefaultOptions; 
        curl_setopt_array($curl, $options);
        //发送一个常规的post请求              
        curl_setopt($curl, CURLOPT_POST, true);
        //post提交的数据包
        curl_setopt($curl, CURLOPT_POSTFIELDS, $data);    
        $response = curl_exec($curl);  
        curl_close($curl);  
        return $response;  
    }
    
    /**
     * 多线程方式处理/队列方式处理
     * 
     * @param array|string $urls
     * @param string $callback(回调函数)
     * @param array $options 
     * @return array
     */
    public static function queue($urls, $callback = null, $options = array())
    {
        $queue = curl_multi_init();
        $responses = array();
        $map = array();
        $running = false;
        self::_rand_agent();
        if(is_array(current($options))) //多个参数
        {
        	if(is_array($urls))
        	{
        		$url = current($urls);
        	}
        	else
        	{
        		$url = $urls;
        	}
        	$parseUrl = parse_url($url);
        	foreach($options as $key => $option)
        	{
        		$curl = curl_init($url);
        		$option = $option + self::$mDefaultOptions;
        		if(!empty($parseUrl))
        		{
        			$new_option = $option + array( CURLOPT_REFERER => 'http://'.$parseUrl['host']);
        		}
        		else
        		{
        			$new_option = $option;
        		}
        		curl_setopt_array($curl, $new_option);
        		curl_multi_add_handle($queue, $curl);
        		$map[(string) $curl.$key] = $url;
        		$responses[$url.$key] = false;
        	}
        }
        else 
        {
        	$options = $options + self::$mDefaultOptions;
        	foreach($urls as $url)
        	{
        		$curl = curl_init($url);
        		$parseUrl = parse_url($url);
        		if(!empty($parseUrl))
        		{
        			$new_options = $options+ array( CURLOPT_REFERER => 'http://'.$parseUrl['host']);
        		}
        		else
        		{
        			$new_options = $options;
        		}
        		curl_setopt_array($curl, $new_options);
        		curl_multi_add_handle($queue, $curl);
        		$map[(string) $curl] = $url;
        		$responses[$url] = false;
        	}
        }
       do
        {
            
            while (($code = @curl_multi_exec($queue, $running)) == CURLM_CALL_MULTI_PERFORM) ;
            
            if ($code != CURLM_OK) {break;}
            //等待一个请求处理完
            while ($done = curl_multi_info_read($queue)) 
            {
                //得到返回信息
                $info = curl_getinfo($done['handle']);
                $output = curl_multi_getcontent($done['handle']);
                $request = $map[(string) $done['handle']];
                //处理函数
                if (is_callable($callback))
                {
                    @call_user_func($callback, $output, $info, $request);
                }
                $responses[$request] = $output;
                curl_multi_remove_handle($queue, $done['handle']);
                curl_close($done['handle']);
            }
            // 处理失败,选择一下请求
            if ($running > 0) 
            {
                curl_multi_select($queue, 0.5);
            }
        } while ($running);
        curl_multi_close($queue);
        return $responses;
    }  
    
    /**
     * 客户端消息头,防止API被网站封杀...
     */
    private static function _rand_agent()
    {
        $useragents = array(
                                'Mozilla/5.0 (Windows NT 5.1; rv:5.0) Gecko/20100101 Firefox/5.0', 
                                'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US) AppleWebKit/534.15 (KHTML, like Gecko) Chrome/10.0.608.0 Safari/534.15', 
                                'Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 6.1;)', 
                                'Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 6.1;)', 
                                'Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1;)', 
                                'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1;)', 
                                'Mozilla/4.0 (compatible; MSIE 9.0; Windows NT 6.1;)', 
                                'Mozilla/5.0 (Windows NT 5.1) AppleWebKit/534.30 (KHTML, like Gecko) Chrome/12.0.742.122 Safari/534.30', 
                                'Mozilla/5.0 (Windows; U; Windows NT 6.1; zh-CN; rv:1.9.2.12) Gecko/20101026 Firefox/3.6.13', 
                                'Mozilla/5.0 (Windows; U; Windows NT 6.1; zh-CN; rv:1.9.2.12) Gecko/20101026 Firefox/3.6.13'
                         );
      self::$mDefaultOptions[CURLOPT_USERAGENT] = array_rand($useragents, 1);
    }
}