Python公开课 - 网络编程
前言
现在做项目一般都会涉及到网络编程,例如做分布式项目,模块间的彼此调用会用到rest接口,web开发则会涉及到基础的http、https知识。
Python在网络编程这方面,使用起来非常方便。有标准的库可以直接用,也有第三方的强大完善的框架,这些都会在其他章节中进行介绍。
网络模型
首先我们必须了解一下TCP/IP网络模型
在教材里面都喜欢用左边这个OSI模型,因为它很规范,但是在实际项目中TCP/IP使用的更加普遍。我们在这里着重介绍这个。
物理层
不用多说,主要是物理线路,可以是以太网,双绞线,光纤等
数据链路层
主要设备包括网桥、交换机、网卡等,涉及到的主要协议为ARP协议,即可以根据IP解析得到物理设备MAC地址的协议
网络层
这层主要是各种路由器,在该层涉及的协议包括IP、ICMP、IGMP、RIP。
IP协议不用多少,主要是用来将源IP的数据包传输给目的IP。
ICMP控制消息是指网络通不通、主机是否可达、路由是否可用等网络本身的消息。这些控制消息虽然并不传输用户数据,但是对于用户数据的传递起着重要的作用。例如我们经常使用的ping、tracert命令,就是ICMP协议的应用。
IGMP主要用来做分组广播控制,可以控制将报文发送给对该报文感兴趣的主机。
传输层
这里主要的协议就包括TCP和UDP咯,这两个协议一个是面向连接的,另一个是面向无连接的。
应用层
各种HTTP, FTP,DNS等,都属于应用层的协议了
TCP
服务端例子:
import socketserver
class echorequestserver(socketserver.BaseRequestHandler):
def handle(self):
print('服务端启动...')
conn = self.request
print('获得连接:', self.client_address)
while True:
client_data = conn.recv(1024)
if not client_data:
print('断开连接')
break
print(client_data.decode('utf-8'))
print('开始发送...')
conn.sendall(client_data)
if __name__ == '__main__':
server =socketserver.TCPServer(("127.0.0.1", 8002),echorequestserver) # 使用
处理单连接的TCPServer
server.serve_forever()
客户端例子:
import socket,time
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.connect(('127.0.0.1',8002))
while True:
st = input('input command: ')
if not st:
break
s.send(st.encode('utf-8'))
echo_back = s.recv(1024)
print(echo_back.decode('utf-8'))
s.close()
用TCP协议进行Socket编程在Python中十分简单,对于客户端,要主动连接服务器的IP和指定端口,对于服务器,要首先监听指定端口,然后,对每一个新的连接,创建一个线程或进程来处理。通常,服务器程序会无限运行下去。
同一个端口,被一个Socket绑定了以后,就不能被别的Socket绑定了。
UDP
服务端例子:
import socket
BUFSIZE = 1024
ip_port = ('127.0.0.1', 9999)
server = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) # udp协议
server.bind(ip_port)
while True:
data,client_addr = server.recvfrom(BUFSIZE)
print('server收到的数据', data)
server.sendto(data.upper(),client_addr)
server.close()
客户端例子:
import socket
BUFSIZE = 1024
client = socket.socket(socket.AF_INET,socket.SOCK_DGRAM)
while True:
msg = input(">> ").strip()
ip_port = ('127.0.0.1', 9999)
client.sendto(msg.encode('utf-8'),ip_port)
data,server_addr = client.recvfrom(BUFSIZE)
print('客户端recvfrom ',data,server_addr)
client.close()
UDP的使用与TCP类似,但是不需要建立连接。此外,服务器绑定UDP端口和TCP端口互不冲突,也就是说,UDP的9999端口与TCP的9999端口可以各自绑定。
小结
网络编程对所有开发语言都是一样的,Python也不例外。用Python进行网络编程,就是在Python程序本身这个进程内,连接别的服务器进程的通信端口进行通信。
相关阅读
- 上一篇 Python基础教程 - 多线程
- 下一篇 Python基础教程 - 正则表达式