php請求遠程url內容有兩個方法fopen/file_get_contents和curl。
1,fopen/file_get_contents與curl的差異
(1)fopen /file_get_contents 每次請求都會重新做DNS查詢,並不對DNS信息進行緩存。但是CURL會自動對DNS信息進行緩存。對同一域名下的網頁或者圖片的請求只需要一次DNS查詢。這大大減少了DNS查詢的次數。所以CURL的性能比fopen /file_get_contents 好很多。
(2)fopen /file_get_contents在請求HTTP時,使用的是http_fopen_wrapper,不會keeplive。而curl卻可以。這樣在多次請求多個鏈接時,curl效率會好一些。
(3)curl可以模擬多種請求,例如:POST數據,表單提交等,用戶可以按照自己的需求來定制請求。而fopen / file_get_contents只能使用get方式獲取數據。
2,如果遠程服務器關閉,file_get_contents處理方法,可以參考這篇文章,http://www.cnblogs.com/scofi/articles/3607529.html
公司里有經常有這樣的業務,需要調用第三方公司提供的HTTP接口,在把接口提供的信息顯示到網頁上,代碼是這樣寫的: file_get_contents("http://example.com/") 。
$opts = array(
'http'=>array(
'method'=>"GET",
'timeout'=>10,
)
);
$context = stream_context_create($opts);
$html =file_get_contents('http://www.example.com', false, $context);
echo $html;
代碼中的timeout就是file_get_contents讀取url的超時時間。
上篇說到我們說到設置file_get_contents超時時間用到了 stream_context_create方法,那么這個方法到底是什么呢?
<?php
$data = array("name" => 'test_name',"content" => 'test_con');
$data = http_build_query($data);
$opts = array(
'http'=>array(
'method'=>"POST",
'header'=>"Content-type: application/x-www-form-urlencoded\r\n".
"Content-length:".strlen($data)."\r\n" .
"Cookie: foo=bar\r\n" .
"\r\n",
'content' => $data,
)
);
$cxContext = stream_context_create($opts);
$sFile = file_get_contents("http://127.0.0.1/reponse.php", false, $cxContext);
echo $sFile;
?>
reponse.php被請求的頁面:
<?php var_dump($_POST); var_dump($_COOKIE); ?>
運行之后的結果為:
<?php $url = 'http://www.example.com'; //初始化一個 cURL 對象 $ch = curl_init(); //設置你需要抓取的URL curl_setopt($ch, CURLOPT_URL, $url); // 設置cURL 參數,要求結果保存到字符串中還是輸出到屏幕上。 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); //是否獲得跳轉后的頁面 curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1); $data = curl_exec($ch); curl_close($ch); echo $data; ?>
(2)使用curl。post獲取數據
<?php
function curl_post($url, $arr_data){
$post_data = http_build_query($url_data);
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFLELDS, $post_data);
$data = curl_exec($ch);
curl_close($ch);
echo $data;
}
$arr_post = array(
'name'=>'test_name',
'age' => 1
);
curl_post("http://www.explame.com/", $arr_post);
?>
(3)使用代理抓取頁面,什么要使用代理進行抓取呢?以google為例吧,如果去抓google的數據,短時間內抓的很頻繁的話,你就抓取不到了。google對你的ip地址做限制這個時候,你可以換代理重新抓。
<?php $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, "http://google.com"); curl_setopt($ch, CURLOPT_HEADER, false); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); //是否通過http代理來傳輸 curl_setopt($ch, CURLOPT_HTTPPROXYTUNNEL, TRUE); curl_setopt($ch, CURLOPT_PROXY, 125.21.23.6:8080); //url_setopt($ch, CURLOPT_PROXYUSERPWD, 'user:password');如果要密碼的話,加上這個 $result=curl_exec($ch); curl_close($ch); ?>
(4)繼續保持本站session調用,在實現用戶同步登錄的情況下需要共享session,如果要繼續保持本站的session,那么要把sessionid放到http請求中。
<?php $session_str = session_name().'='.session_id().'; path=/; domain=.explame.com'; session_write_close(); //將數據寫入文件並且結束session $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_HEADER, false); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_COOKIE, $session_str); $ret = curl_exec($ch); curl_close($ch); ?>
