您的位置:首页 > 编程语言 > Python开发

20 Web 编程 - 《Python 核心编程》

2015-08-21 17:41 736 查看
􀁺 引言
􀁺 Python 的Web 应用:简单的Web 客户端
􀁺 urlparse 和 urllib 模块
􀁺 高级的 Web 客户端
􀁺 网络爬虫/蜘蛛/机器人
􀁺 CGI:帮助 Web 服务器处理客户端数据
􀁺 创建 CGI 应用程序
􀁺 在 CGI 中使用Unicode
􀁺 高级 CGI
􀁺 创建 Web 服务器
􀁺 相关模块
20.1 介绍
Web 应用:客户端/服务器计算

#!/usr/bin/env python

# Advanced Web Client: a Web Crawler

from sys import argv
from os import makedirs, unlink, sep
from os.path import dirname, exists, isdir, splitext
from string import replace, find, lower
from htmllib import HTMLParser
from urllib import urlretrieve
from urlparse import urlparse, urljoin
from formatter import DumbWriter, AbstractFormatter
from cStringIO import StringIO

class Retriever(object):# dowload Web pages

def __init__(self, url):
self.url = url
self.file = self.filename(url)
#self.parser = None

def filename(self, url, deffile='index.htm'):
parsedurl = urlparse(url, 'http:', 0) ## parse path
path = parsedurl[1] + parsedurl[2]
ext = splitext(parsedurl[2])
if ext[1] == '': # no file, use default
if path[-1] == '/':
path += deffile
else:
path += '/' + deffile
ldir = dirname(path) # local directory
if sep != '/': # os-indep. path separator
ldir = replace(ldir, '/', sep)
if not isdir(ldir):# create archive dir if nec.
if exists(ldir): unlink(ldir)
try:
makedirs(ldir)
except WindowsError, e:
print (ldir, url, path)
raise e
return path

def download(self): # download Web page
try:
retval = urlretrieve(self.url, self.file)
except IOError:
retval = ('*** ERROR: invalid URL "%s"' %\
self.url,)
return retval

def parseAndGetLinks(self): # parse HTML, save links
self.parser = HTMLParser(AbstractFormatter(\
DumbWriter(StringIO())))
self.parser.feed(open(self.file).read())
self.parser.close()
return self.parser.anchorlist

class Crawler(object): # manage entire crawling process
count = 0 # static downloaded page counter

def __init__(self, url):
self.q = [url]
self.seen = list()
self.dom = urlparse(url)[1]

def getPage(self, url):
r = Retriever(url)
retval = r.download()
if retval[0] == '*': # error situation, do not parse
print retval, '... skipping parse'
return
Crawler.count += 1
print '\n(', Crawler.count, ')'
print 'URL:', url
print 'FILE:', retval[0]
self.seen.append(url)

links = r.parseAndGetLinks() # get and process links
for eachLink in links:
if eachLink[:4] != 'http' and \
find(eachLink, '://') == -1:
eachLink = urljoin(url, eachLink)
print '*', eachLink,

if find(lower(eachLink), 'mailto:') != -1:
print '... discarded, mailto link'
continue

if find(lower(eachLink), 'javascript:') != -1:
print '... discarded, javascript link "%s"' % eachLink
continue

if eachLink not in self.seen:
if find(eachLink, self.dom) == -1:
print '... discarded, not in domain'
else:
if eachLink not in self.q:
self.q.append(eachLink)
print '... new, added to Q'
else:
print '... discarded, already in Q'
else:
print '... discarded, already processed'
def go(self): # process links in queue
while self.q:
url = self.q.pop()
self.getPage(url)

def main():
if len(argv) > 1:
url = argv[1]
else:
try:
url = raw_input('Enter starting URL:')
except (KeyboardInterrupt, EOFError):
url = ''
if not url: return
robot = Crawler(url)
robot.go()

if __name__ == '__main__':
main()


crawl.py
20.4 CGI:帮助Web 服务器处理客户端数据
CGI 介绍
Web 开发的最初目的是在全球范围内对文档进行存储和归档(大多是教学和科研目的的)。这些 零碎的信息通常产生于静态的文本或者HTML.
服务器接到表单反馈,与外部应用程序 交互,收到并返回新生成的HTML 页面都发生在一个叫做Web 服务器CGI(Common Gateway Interface) 的接口上.
创建HTML 的CGI 应用程序通常是用高级编程语言来实现的,可以接受、处理数据,向服务器端 返回HTML 页面。目前使用的编程语言有Perl, PHP, C/C++,或者Python。



图20-3 CGI 工作概要图。CGI 代表了在一个Web 服务器和能够处理用户表单、生成并返回动态 HTML 页的应用程序间的交互。
典型的Web 应用产品已经不再使用CGI
由于它词义的局限性和允许Web 服务器处理大量模拟客户端数据能力的局限性,CGI 几乎绝迹。
Web 服务的关键使命依赖于遵循像C/C++这样语言的规范。如今的Web 服务器典型的部件有Aphache
和集成的数据库部件(MySQL 或者PostgreSQL),Java(Tomcat),PHP 和各种Perl 模块,Python 模
块,以及SSL/security。然而,如果你工作在私人小型的或者小组织的Web 网站上的话就没有必要
使用这种强大而复杂的Web 服务器, CGI 是一个适用于小型Web 网站开发的工具
Web 应用程序开发框架和内容管理系统,仍旧遵循这CGI 最初提供的模式,可以允许用户输入,根据输入执行拷贝,并提供了一个有效的HTML 做为最终的客户端输出。
CGI 应用程序
CGI 应用程序和典型的应用程序有些不同。主要的区别在于输入、输出以及用户和计算机交互方 面。
当一个CGI 脚本开始执行时,它需要检索用户-支持表单,但这些数据必须要从Web 的客户端才可以
获得,而不是从服务器或者硬盘上获得。
这些不同于标准输出的输出将会返回到连接的Web 客户端,而不是返回到屏幕、CUI 窗口或者硬
盘上。这些返回来的数据必须是具有一系列有效头文件的HTML。否则,如果浏览器是Web 的客户端,
由于浏览器只能识别有效的HTTP 数据(也就是MIME 都问价和HTML),那么返回的也只能是个错误消
息(具体的就是因特网服务器错误)。
最后,可能和你想象的一样,用户不能与脚本进行交互。所有的交互都将发生在Web 客户端(用
户的行为),Web 服务器端和CGI 应用程序间。
cgi 模块
在cgi 模块中有个主要类:FieldStorage 类,它完成了所有的工作。在Python CGI 脚本开始时
这个类将会被实例化,它会从Web 客户端(具有Web 服务器)读出有关的用户信息。一旦这个对象
被实例化,它将会包含一个类似字典的对象,具有一系列的键-值对,键就是通过表单传入的表单条
目的名字,而值则包含相应的数据。
这些值本身可以是以下三种对象之一。它们既可以是FieldStorage 对象(实例)也可以是另一
个类似的名为MiniFieldStorage 类的实例,后者用在没有文件上传或mulitple-part 格式数据的情
况。MiniFieldStorage 实例只包含名字和数据的键-值对。最后,它们还可以是这些对象的列表。这
发生在表单中的某个域有多个输入值的情况下。
对于简单的Web 表单,你将会经常发现所有的MiniFieldStorage 实例。
20.5 建立CGI 应用程序

建立Web 服务器
为了可以用Python 进行CGI 开发,你首先需要安装一个Web 服务器,将其配置成可以处理Python CGI 请求的模式,然后让你的Web 服务器访问CGI 脚本。
如果你需要一个真正的Web 服务器,可以下载并安装Aphache。Aphache 的插件或模块可以处理 Python CGI,但这在我们的例子里并不是必要的。
为了学习的目的或者是建立小型的Web 站点,使用Python 自身带的Web 服务器就已经足够了。
如果你只是想建立一个基于Web 的服务器,你可以直接执行下边的Python 语句。
$ python -m CGIHTTPServer
建立表单页



生成结果页



核心提示:HTML 头文件是从HTML 中分离出来的
有一点需要向CGI 初学者指明的是,在向CGI 脚本返回结果时,须先返回一个适当的HTTP 头文
件后才会返回结果HTML 页面为了区分这些头文件和结果HTML 页面,需要在friends1.py
的第五行中插入几个换行符
生成表单和结果页面





20.6 在CGI 中使用Unicode 编码



20.7 高级CGI

Mulitipart 表单提交和文件的上传

目前, CGI 特别指出只允许两种表单编码,“ application/x-www-form-urlencoded ” 和 “multipart/form-dat”。
由于前者是默认的,就没有必要像下边那样在FORM 标签里声明编码方式。
<FORM enctype="application/x-www-form-urlencoded" ...>
但是对于multipart 表单,你需要像这样明确给出编码:
<FORM enctype="multipart/form-data" ...>
在表单提交时你可以使用任一种编码,但在目前上传的文件仅能表现为multipart 编码
不论你使用的是默认编码还是multipart 编码,cgi 模块都会以同样的方式来处理它们,在表单 提交时提供键和相应的值,你还可以像以前那样通过FieldStorage 实例来访问数据。
Multipart 编码是由网景在早期开发的,但是已经被微软(开始于IE4 版)和其他的浏览器采用。
多值字段
除了上传文件,我们将会展示如何处理具有多值的字段。最常见的情况就是你有一系列的复选
框允许用户有多个选择。每个复选框都会标上相同的字段名,但是为了区分它们,会有不同的值与
特定的复选框关联。
正如你所知道的,在表单提交时,数据从用户端以键-值对形式发送到服务器端。当提交不止一
个复选框时,就会有多个值对应同一个键。在这种情况下,cgi 模块将会建立一个这类实例的列表,
你可以遍历获得所有的值,而不是为你的数据指定一个MiniFielStorage 实例。
cookie
在客户端获得请 求文件前,Web 服务器向客户端发送“SetCookie”头文件要求客户端存储cookie。
cookie 以分号(;)分隔,每个键-值对中间都 由等号(=)分开。
和multipart 编码一样,cookie 同样起源于网景,他们实现了cookie 并制定出第一个规范并沿 用至今。
使用高级CGI
//TODO

20.8 Web(HTTP)服务器
最流行的一些Web 客户 端: Chrome, Firefox, Mozilla, IE, Opera, Netscape, AOL, Safari, Camino, Epiphany, Galeon 和Lynx
最常用的Web 服务器: Apache,Netscape IIS, thttpd, Zeus,和Zope
用Python 建立Web 服务器
要建立一个Web 服务,一个基本的服务器和一个“处理器” 必备的。
基础的(Web)服务器
基础的(Web)服务器是一个必备的模具。它的角色是在客户端和服务器端完成必要HTTP 交互。
在BaseHTTPServer 模块中你可以找到一个名叫HTTPServer 的服务器基本类。
处理器
处理器是一些处理主要“Web 服务”的简单软件。
它们处理客户端的请求,并返回适当的文件, 静态的文本或者由CGI 生成的动态文件。
处理器的复杂性决定了你的Web 服务器的复杂程度。
Python 标准库提供了三种不同的处理器。
BaseHTTPResquestHandler
最基本,最普通的是 vanilla 处理器,被命名 BaseHTTPResquestHandler,这个可以在基本
Web 服务器的BaseHTTPServer 模块中找到。除了获得客户端的请求外,不再执行其他的处理工作,
因此你必须自己完成它们,这样就导致了出现了myhttpd.py 服务的出现。
SimpleHTTPRequestHandler
用于SimpleHTTPServer 模块中的SimpleHTTPRequestHandler , 建立在 BaseHTTPResquestHandler 基础上,直接执行标准的GET 和HEAD 请求。
CGIHTTPRequestHandler
最后,我们来看下用于CGIHTTPServer 模块中的CGIHTTPRequestHandler 处理器,它可以获取
SimpleHTTPRequestHandler 并为POST 请求提供支持。它可以调用CGI 脚本完成请求处理过程,也可
以将生成的HTML 脚本返回给客户端。





20.9 相关模块













内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: