網絡新聞
什麼是Usenet 與新聞組
usenet新聞系統是一個全球存檔的‘’電子公告版”。各種主題新聞組一應俱全,從詩歌到政治,從自然語言學到計算機語言,從軟件到硬件,從種植到烹飪、招聘/應聘、音樂、 魔術、相親等。新聞組可以面向全球,也可以只面向某個特定區域。
每個系統是一個由大量計算機組成的全球網絡,計算機之間共享Usenet上的帖子,如果某個用戶發了一個帖子到本地的 Usenet 計算機上,這個帖子會被傳播到其他相連 的計算機上,再由這些計算機傳到與它們相連的計算機上,直到這個帖子傳播到了全世界, 每個人都收到這個帖子爲止。帖子在 Usenet 上的存活時間是有限的,這個時間可以由 Usenet 系統管理員來指定,也可以爲帖子指定一個過期的日期/時間。
每個系統都有一個已“訂閱”的新聞組列表,系統只接收感興趣的新聞組裏的帖子,而不是 接收服務器上所有新聞組的帖子。Usenet 新聞組的內容由提供者安排,很多服務都是公開的。但 也有一些服務只允許特定用戶使用,例如付費用戶、特定大學的學生等。Usenet 系統管理員可能 會進行一些設置來要求用戶輸入用戶名和密碼,管理員也可以設置是否只能上傳或只能下載
網絡新聞傳輸協議—NNTP
用戶使用網絡新聞傳輸協議(NNTP)在新聞組中下載或發表帖子。該協議由Brain Kantor (加州大學聖地亞哥分校)和 Phil Lapsley(加州大學伯克利分校)創建,於 1986 年 2 月公佈。其後在 2000 年 10 月公佈的 RFC 2980 中對該協議進行了更新。
作爲客戶端/服務器架構的另一個例子,NNTP 與 FTP 的操作方式相似,但更簡單。在 FTP 中,登錄、傳輸數據和控制需要使用不同的端口,而 NNTP 只使用一個標準端口 119 來 通信。用戶向服務器發送一個請求,服務器就做出相應的響應,如圖 所示。
FTP傳輸協議 如下
NNTP傳輸協議如下
Python 和 NNTP
NNTP大致的工作流程如下;
- 連接到服務器。
- 登陸(根據需求)。
- 發出服務請求。
- 退出
NNTP類方法
這裏列舉出一些常用的方法,詳細內容建議參考Python庫手冊
客戶端程序 NNTP 示例
import nntplib
import socket
HOST = 'your.nntp.server'
GRNM = 'comp.lang.python'
USER = 'wesley'
PASS = "you'llNeverGuess"
def main():
try:
n = nntplib.NNTP(HOST) #, user=USER, password=PASS)
except socket.gaierror as e:
print ('ERROR: cannot reach host "%s"' % HOST)
print (' ("%s")' % eval(str(e))[1])
return
except nntplib.NNTPPermanentError as e:
print ('ERROR: access denied on "%s"' % HOST)
print (' ("%s")' % str(e))
return
print ('*** Connected to host "%s"' % HOST)
try:
rsp, ct, fst, lst, grp = n.group(GRNM)
except nntplib.NNTPTemporaryError as e:
print ('ERROR: cannot connect to group "%s"' % GRNM)
print (' ("%s")' % str(e))
print (' Server may require authentication')
print (' Uncomment/edit login line above')
n.quit()
return
except nntplib.NNTPTemporaryError as e:
print ('ERROR: group "%s" unavailable' % GRNM)
print (' ("%s")' % str(e))
n.quit()
return
print ('*** Found newsgroup "%s"' % GRNM)
rng = '%s-%s' % (lst, lst)
rsp, frm = n.xhdr('from', rng)
rsp, sub = n.xhdr('subject', rng)
rsp, dat = n.xhdr('date', rng)
print ('''*** Found last article (#%s):\n
From: %s
Subject: %s
Date: %s
'''% (lst, frm[0][1], sub[0][1], dat[0][1]))
rsp, anum, mid, data = n.body(lst)
displayFirst20(data)
n.quit()
def displayFirst20(data):
print ('*** First (<= 20) meaningful lines:\n')
count = 0
lines = (line.rstrip() for line in data)
lastBlank = True
for line in lines:
if line:
lower = line.lower()
if (lower.startswith('>') and not \
lower.startswith('>>>')) or \
lower.startswith('|') or \
lower.startswith('in article') or \
lower.endswith('writes:') or \
lower.endswith('wrote:'):
continue
if not lastBlank or (lastBlank and line):
print (' %s' % line)
if line:
count += 1
lastBlank = False
else:
lastBlank = True
if count == 20:
break
if __name__ == '__main__':
main()