python网络编程的学习笔记
网络通信概述
互联网上计算机之间的信息传递,都是通过网络来实现的,类似于现实生活中的收发快递,当我们需要将包裹寄到另一个地方的时候,我们需要找一家快递公司,并将目的地地址和收件人联系方式告诉快递公司,这时候快递公司才能将你的包裹送达。互联网的网络通信也是如此,网络通信消息,你需要知道对方的ip地址和端口号,才能正确的进行通信。
网络基础
-
IP地址
首先,程序必须要启动,其次,必须有这台机器的地址,我们都知道我们人的地址大概就是国家\省\市\区\街道\楼\门牌号这样字。那么每一台联网的机器在网络上也有自己的地址,它的地址是怎么表示的呢?就是使用一串数字来表示的,例如:100.4.5.6,具体的细节请读者自行查阅资料
-
端口号
在一台电脑里面会有各种各样的程序,那计算机是怎么来标识出这些程序的呢,答案就是通过端口号来识别的,比如电脑中有QQ这个程序,另一台计算机也想通过QQ来发送消息,这时候需要找到发送消息的目的计算机的IP地址,但是这只是找到计算机而已,计算机还需要找到对应的端口号才能找到通信目的程序的QQ,才能发送消息
- 一张图理解IP和端口号的
这里的地址就是通信的IP地址,收件人和联系方式可以理解成通信目的地的端口号,即送到了目的地,还需要找到对应的人才能送包裹
osi七层模型
互联网的核心就是由一堆协议组成,协议就是标准,比如全世界人通信的标准是英语,如果把计算机比作人,互联网协议就是计算机界的英语。所有的计算机都学会了互联网协议,那所有的计算机都就可以按照统一的标准去收发信息从而完成通信了
这些标准都是按照七层模型来定义的
python通信套接字socket
Socket是应用层与TCP/IP协议族通信的中间软件抽象层,它是一组接口。在设计模式中,Socket其实就是一个门面模式,它把复杂的TCP/IP协议族隐藏在Socket接口后面,对用户来说,一组简单的接口就是全部,让Socket去组织数据,以符合指定的协议
基于TCP协议的socket
python当中使用socket 需要import socket
socket.socket(socket.AF_INET,socket.SOCK_STREAM)
其中第一个参数socket.AF_INET表示使用的是ipv4来进行通信,
第二个参数socket.SOCK_STREAM表示使用的是TCP协议进行网络通信
TCP协议通信分为客户端和服务器端,各个流程如下
python TCP服务器端代码简单实现
import socket
def main():
serversocket = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
serversocket.bind(("192.168.131.1",5700)) #绑定端口号 记住这里一定要是元组的形式传入
serversocket.listen() # 服务器监听客户端
while True:
soc,add = serversocket.accept() # 接收客户端
content = soc.recv(1024) # 服务器收到客户端的消息
soc.send("XXXXX") # 服务器向客户端发送消息
print(add)
soc.close()
if __name__ == '__main__':
main()
client 客户端
import socket
def main():
clientsocket = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
clientsocket.connect(("192.168.131.1",5700)) #连接客户端 记住这里一定要是元组的形式传入
while True:
line = input('')
if line is None or line == 'exit':
break
# 将用户的键盘输入内容写入socket
clientsocket.send(line.encode('utf-8'))
if __name__ == '__main__':
main()
大致讲解一下python网络编程中的API
Tcp服务端
Import socket
1 创建套接字
socket (socket_family = AF_INET, socket_type = SOCK_STREAM, proto = 0)
功能 : 创建套接字 参数 : socket_family:选择地址族种类 AF_INET (UNIX) socket_type : 套接字类型 SOCK_STREAM 流式 SOCK_DGRAM 数据报 proto :子协议类型默认为0
返回值 : 返回创建的套接字
例如
serverscoket = socket.socket(family=socket.AF_INET,
type=socket.SOCK_STREAM) # AF_INET表示采用ip4进行连接 SCOK_ STREAM采用tcp协议
2 绑定ip和端口号
socked.bind() 功能 : 绑定IP和端口 参数 : 是一个元组 ,第一项是字符串形式的IP 第二项是端口号 (‘192.168.1.2’,8888)
例如serverscoket.bind(("192.168.131.1", 30000)) # 绑定ip地址和端口号
3 让套接字监听客户端
socked.listen(n) 功能 : 使套接字变为监听套接字,同时创建监听队列 参数 : n 监听队列大小
4等待客户端的连接
sockfd.accept() 功能 : 阻塞等待客户端连接 返回值 : 第一个:返回一个新的套接字用来和客户端通信 第二个:返回连接的客户端的地址
例如 sock, addr = serverscoket.accept()
5 消息的发送和接收
recv(buffer) 功能 : 接收消息 参数 : 一次接收消息的大小 字节 返回值: 接收到的内容
send(data) 功能: 发送消息 参数: 发送的内容 (byte) 返回值 : 发送了多少个字节
6 关闭套接字
close()
功能 : 关闭套接字
Tcp客户端
1 创建套接字和服务器端类似
socketclent = socket.socket(family=socket.AF_INET,type=socket.SOCK_STREAM)
2 发起连接请求
connect() 功能:发起连接 参数 : 一个元组 第一个元素 : 服务器的IP 第二个元素 : 服务器的port
例如 socketclent.connect(("192.168.131.1", 30000))
3 发送和接收消息
recv(buffer) 功能 : 接收消息 参数 : 一次接收消息的大小 字节 返回值: 接收到的内容
send(data) 功能: 发送消息 参数: 发送的内容 (byte) 返回值 : 发送了多少个字节
4 关闭套接字
close()
功能 : 关闭套接字
流程如下图所示
下面是我写的入门程序
Server.py
import socket
import threading
scoket_list = []
def ServerScoket():
try:
serverscoket = socket.socket(family=socket.AF_INET,
type=socket.SOCK_STREAM) # AF_INET表示采用ip4进行连接 SCOK_DGREM采用udp协议
serverscoket.bind(("192.168.131.1", 30000)) # 绑定ip地址和端口号
serverscoket.listen() # 监听来自客户端的连接
while True:
sock, addr = serverscoket.accept()
scoket_list.append(sock)
threading.Thread(target=server_target,args=(sock,)).start()
except Exception as Result:
print(Result)
"""读取客户端信息"""
def read_from_client(s):
try:
return s.recv(2048).decode("utf-8")
except Exception as result:
print(result)
scoket_list.remove(s)
def server_target(s):
try:
# 采用循环不断地从socket中读取客户端发送过来的数据
while True:
content = read_from_client(s)
print(content)
if content is None:
break
for client_s in scoket_list:
client_s.send(content.encode('utf-8'))
except Exception as result:
print(result)
if __name__ == '__main__':
ServerScoket()
Client.py
import socket
import threading
def ClientSocket():
try:
socketclent = socket.socket(family=socket.AF_INET,type=socket.SOCK_STREAM)
socketclent.connect(("192.168.131.1", 30000))
threading.Thread(target=read_from_server,args=(socketclent,)).start()
while True:
line = input('')
if line is None or line == 'exit':
break
# 将用户的键盘输入内容写入socket
socketclent.send(line.encode('utf-8'))
except Exception as Result:
print(Result)
else:
print("成功连接到服务器")
def read_from_server(s):
while True:
print(s.recv(2048).decode('utf-8'))
if __name__ == '__main__':
ClientSocket()