网络编程
1 几个网络设计模块
Socket模块
套接字实例化需要的三个参数:
socket.socket(family=AF_INET, #地址族
type=SOCK_STREAM, #流或数据报
proto=0, #使用的协议
fileno=None)
使用以下两个方法进行数据传输:send和recv
一个小型服务器 使用bind方法 和linsten方法
import socket
s=socket.socket()
host=socket.gethostname()
port=1234
s.bind((host,port))
s.listen(5)
while True:
c,addr=s.accept()
print('Got connect from',addr)
c.sendall(b'Thank you for connecting')
c.close()
一个小型客户机 使用connect方法联接
import socket
s=socket.socket()
host=socket.gethostname()
port=1234
s.connect((host,port))
print('服务器返回信息',s.recv(1024))
Urllib和urllib2模块 通过网络访问文件
Utllib简单的文件下载
Urllib2可以实现http验证cookie或为自已的协议写扩展程序
#打开远程文件
From utllib import urlopen
Webpage=urlopen(‘http://www.python.org’)
#返回的文件支持close() read() readline() readlines()
#获取远程文件
Urlretrieve(‘http://ww.python.org’)
2 socketServer
服务器框架
baseHTTPServer
SimpleHTTPServer
CGIHTTPServer
SimpleXMLRPCServer
DocXMLRPCServer
SocketServer有四个基本的类
tcpServer
udpServer
unixStreamServer
unixDatagramServer
请求处理程序requestHandler中,通过handle方法来处理,self.request取得客户端套接字,
如果使用的是流,可以使用streamRequestHandler,其中self.rfile用于读取,self.wfile用于写入
一个基于socketServer的小型服务器
//在python3中SocketServer改为 socketserver
from socketserver import TCPServer,StreamRequestHandler
class Handler(StreamRequestHandler):
def handler(self):
addr=self.request.getpeername()
print('got connection from',addr)
self.wfile.write('Thank you for connecting')
server=TCPServer(('',1234),Handler)
server.serve_forever()
3 并发多链接
实现并发的三种方法:
Forking 分叉 windows不支持
Threading 线程
异步io asynchronous IO select模块的select函数
twisited
使用socketserver进行分叉和线程处理
#使用了分叉枝术的服务器
from socketserver import TCPServer,ForkingMixIn,StreamRequestHandler
class Server(ForkingMixIn,TCPServer):pass
class Handler(StreamRequestHandler):
def handle(self):
addr=self.request.getpeername()
print('got connection form',addr)
self.wfile.write('Thank you for connection')
server=Server(('',1234),Handler)
server.serve_forever()
#使用了线程处理的服务器
from socketserver import TCPServer,ThreadingMixIn,StreamRequestHandler
class Server(ThreadingMixIn,TCPServer):pass
class Handler(StreamRequestHandler):
def handler(self):
addr=self.request.getpeername()
print('Got connection from',addr)
self.wfile.write('Thank you for connecting')
server=Server(('',1234),Handler)
server.serve_forever()
带有select 和poll的异步io
#使用select的简单服务器
import socket,select
s=socket.socket()
host=socket.gethostname()
port=1234
s.bind((host,port))
s.listen(s)
inputs=[s]
while True:
rs,ws,es=select.select(inputs,[],[])
for r in rs:
if r is s:
e,addr=s.accept()
print('Got connection from',addr)
inputs.append(c)
else:
try:
data=r.recv(1024)
disconnected=not data
except socket.error:
disconnected=True
if disconnected:
print(r.getpeername(),'disconnected')
inputs.remove(r)
else:
print(data)
#使用pull的简单服务器
import socket,select
s=socket.socket()
host=socket.gethostname()
port=1234
s.bind((host,port))
fdmap=(s.fileno():s)
s.listen(5)
p=select.poll()
p.register(s)
while True:
events=p.poll()
for fd.event in events:
if fd in fdmap:
c,addr=s.accept()
print('Got connection from',addr)
p.register(c)
fdmap(c.fileno())=c
elif event $ select.POLLIN:
data=fdmap[fd].recv(1024)
if not data:#没有数据关闭连接
print(fdmap[fd].getpeername,'disconnected')
p.unregister(fd)
del fdmap[fd]
else:
print(data)
Twisted
是一个事件驱动的python网络框架
#使用twisted的简单服务器
from twisted.internet import reactor
form twisted.internet import Protocol,Factory
class SimpleLogger(Protocol):
def connectionMade(self):
print('Got connection from',self.transport.client)
def connectionLost(self,reason):
print(self.transport.client,'disconnected')
def dataReceived(self,data):
print(data)
factory=Factory()
factory.protocol=SimpleLogger
reactor.listenTCP(1234,factory)
reactor.run()
#一个使用lineReceiver协议改进的记录服务器
from twisted.internet import reactor
from twisted.internet.protocol import Factory
from twisted.protocols.basic import LineReceiver
class SimpleLogger(LineReceiver):
def connectionMade(self):
print('Got connection from',self.transport.client)
def connectionLost(self):
print(self.transport.client,'disconnected')
def lineReceived(self.line):
print(line)
factory=Factory()
factory.protocol=SimpleLogger
reactor.listenTCP(1234,factory)
teactor.run()