Python 2.7 獲取網絡信息(Urllib)

>>> import urllib
>>> google = urllib.urlopen('http://www.google.com')
>>> print 'http header:\n',google.info()
...............(一堆HTTP頭信息)
>>> print 'http status:',google.getcode()
http status: 200
>>> print 'url:',google.geturl()

>>>help(urllib.urlopen)
Help on function urlopen in module urllib:
urlopen(url, data=None, proxies=None)
Create a file-like object for the specified URL to read from.
  • 參數 url 表示遠程數據的路徑,一般是 http 或者 ftp 路徑。
  • 參數 data 表示以 get 或者 post 方式提交到 url 的數據。
  • 參數 proxies 表示用於代理的設置。

urlopen 返回一個類文件對象,它提供瞭如下方法:
  • read() , readline() , readlines(),fileno()和close(): 這些方法的使用與文件對象完全一樣。
  • info():返回一個httplib.HTTPMessage 對象,表示遠程服務器返回的頭信息
  • getcode():返回Http狀態碼,如果是http請求,200表示請求成功完成;404表示網址未找到。
  • geturl():返回請求的url地址。

下例 : 整個html抓取下來:
# 別驚訝,整個程序確實只用了兩行代碼
>>>import urllib
>>>print urllib.urlopen('http://www.google.com').read()

再熟悉一下:
google = urllib.urlopen('http://www.google.com')
print 'http header:/n', google.info()
print 'http status:', google.getcode()
print 'url:', google.geturl()
for line in google: # 就像在操作本地文件
print line,
google.close()

urlopen()
urllib 是 python 自帶的一個抓取網頁信息一個接口,他最主要的方法是 urlopen(),是基於 python 的 open() 方法的。下面是主要說明:
  • 這裏傳入urlopen()的參數有特別說要求 : 要遵循一些網絡協議,比如http,ftp,也就是說,在網址的開頭必須要有 http:// 這樣的說明,如:urllib.urlopen('http://www.baidu.com')。
  • 要麼就是本地文件,本地文件需要使用file關鍵字,比如 urllib.urlopen('file:nowamagic.py'),注意,這裏的hello.py是指的是當前的classpath所指定的內容,如果對hello.py這裏有什麼疑問那一定是python尋找classpath的順序不是很清楚了,當然也可以直接寫全部路徑,urllib.urlopen('file:F:\pythontest\nowamagic.py')。

例如:
import urllib
f = urllib.urlopen('file:F:\pythontest\nowamagic.py')
a = f.read()
print a

urllib 的 代理設置:
import urllib
proxies = {'http':'http://***.***.***.***:1984'}
filehandle = urllib.urlopen('http://www.需要代理才能訪問的網站.com/',proxies = proxies)
a = filehandle.read()
print a
以上是最基本代理,即代理訪問到該網站,並且能夠獲得該網站的內容。但是如果遇到需要登錄,或者需要cookie等的網站呢?

urlretrieve()
下面我們再來看看 urllib 模塊提供的 urlretrieve() 函數。urlretrieve() 方法直接將遠程數據下載到本地
>>> help(urllib.urlretrieve)
Help on function urlretrieve in module urllib:
urlretrieve(url, filename=None, reporthook=None, data=None)
  • 參數 finename 指定了保存本地路徑(如果參數未指定,urllib會生成一個臨時文件保存數據。)
  • 參數 reporthook 是一個回調函數,當連接上服務器、以及相應的數據塊傳輸完畢時會觸發該回調, 我們可以利用這個回調函數來顯示當前的下載進度。
  • 參數 data 指 post 到服務器的數據,該方法返回一個包含兩個元素的(filename, headers)元組,filename 表示保存到本地的路徑,header 表示服務器的響應頭。

下面通過例子來演示一下這個方法的使用,這個例子將 google 的 html 抓取到本地,保存在 D:/google.html 文件中,同時顯示下載的進度。
import urllib
def cbk(a, b, c):
'''回調函數
@a: 已經下載的數據塊
@b: 數據塊的大小
@c: 遠程文件的大小
'''
per = 100.0 * a * b / c
if per > 100:
per = 100
print '%.2f%%' % per


url = 'http://www.google.com'
local = 'd://google.html'
urllib.urlretrieve(url, local, cbk)


URL編碼解碼
url 中是不能出現一些特殊的符號的,有些符號有特殊的用途。比如以 get 方式提交數據的時候,會在 url 中添加 key=value 這樣的字符串,所以在 value 中是不允許有 '=',因此要對其進行編碼 ,比如 :
1.+ URL 中+號表示空格 %2B
2.空格 URL中的空格可以用+號或者編碼 %20
3./ 分隔目錄和子目錄 %2F
4.? 分隔實際的 URL 和參數 %3F
5.% 指定特殊字符 %25
6.# 表示書籤 %23
7.& URL 中指定的參數間的分隔符 %26
8.= URL 中指定參數的值 %3D

與此同時服務器接收到這些參數的時候,要進行解碼,還原成原始的數據。這個時候,這些輔助方法會很有用:
  • urllib.quote(string[, safe]):對字符串進行編碼。參數 safe 指定了不需要編碼的字符;
  • urllib.unquote(string) :對字符串進行解碼;
  • urllib.quote_plus(string [ , safe ] ) :與 urllib.quote 類似,但這個方法用'+'來替換' '(空格),而 quote 用'%20'來代替' '
  • urllib.unquote_plus(string ) :解碼;
  • urllib.urlencode(query[, doseq]):將dict或者包含兩個元素的元組列表轉換成url參數。 例如 字典{'name': 'dark-bull', 'age': 200}將被轉換爲"name=dark-bull&age=200"
  • urllib.pathname2url(path):將本地路徑轉換成 url 路徑;
  • urllib.url2pathname(path):將url路徑轉換成本地路徑;

Python 2.7.5
>>> import urllib>>> data = 'name = ~nowamagic+5'>>> data1 = urllib.quote(data)>>> print data1name%20%3D%20%7Enowamagic%2B5>>> print urllib.unquote(data1)name = ~nowamagic+5>>> data2 = urllib.quote_plus(data)>>> print data2name+%3D+%7Enowamagic%2B5>>> print urllib.unquote_plus(data2)name = ~nowamagic+5>>> data3 = urllib.urlencode({ 'name': 'nowamagic-gonn', 'age': 200 })>>> print data3age=200&name=nowamagic-gonn>>> data4 = urllib.pathname2url(r'd:/a/b/c/23.php')>>> print data4///D://a/b/c/23.php>>> print urllib.url2pathname(data4)D:\a\b\c\23.php


urllib 2
python 發展過程中,guido 越來越看不慣 urllib 的混亂結構了,但是很多人已經習慣 import urllib 了,並且用的還可以,所以 urllib 不管代碼裏多麼混亂,但他能運行。很好,於是 guido 只能在urllib 外在開發了 urllib2,來滿足一個有“潔癖”的程序員的心理需求。
import urllib2content = urllib2.urlopen('http://www.google.com/')c = content.read()print c


urlib2 是使用各種協議完成打開 url 的一個擴展包。最簡單的使用方式是調用 urlopen() 方法,比如:

import urllib2content_stream = urllib2.urlopen('http://www.google.com/')content = content_stream.read()print content

即可以接受一個字符串型的 url 地址或者一個 Request 對象。將打開這個 url 並返回結果爲一個像文件對象一樣的對象。\

接下來是 OpenerDirector 操作類。這是一個管理很多處理類(Handler)的類。而所有這些 Handler 類都對應處理相應的協議,或者特殊功能。分別有下面的處理類:
  • BaseHandler
  • HTTPErrorProcessor
  • HTTPDefaultErrorHandler
  • HTTPRedirectHandler
  • ProxyHandler
  • AbstractBasicAuthHandler
  • HTTPBasicAuthHandler
  • ProxyBasicAuthHandler
  • AbstractDigestAuthHandler
  • ProxyDigestAuthHandler
  • AbstractHTTPHandler
  • HTTPHandler
  • HTTPCookieProcessor
  • UnknownHandler
  • FileHandler
  • FTPHandler
  • CacheFTPHandler

是不是很多?是不是和我說的結構簡單不一致?不是的,他們都是遵循相應的規則,需求創建的類,甚至是相似的。你何必一口想吃成個胖子,全部都要會,先只管最最基本的需求吧,http 協議的處理類。
剛纔我們說的最簡單的 urlib2 的使用,也就是源碼中給出的使用方式:




發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章