Socket编程
一、Socket是什么
Socket本身不是一个协议,是一个套接字,操作系统为了方便大家直接使用tcp协议而存在的一个抽象层,它把复杂的TCP/IP协议隐藏在接口后面。

二、Socket编程

三、socket编程实例
socket通信实例一:
程序结构:

socket_server.py
#socket服务端
import socket
server_socket = socket.socket()
#绑定到0.0.0.0 8000端口
server_socket.bind(('0.0.0.0',8000))
server_socket.listen()
#阻塞等待连接
socket,add=server_socket.accept()
print(socket)
print(add)
data=bytes('','utf-8')
while True:
tmp_data=socket.recv(1024)
print(tmp_data)
if tmp_data:
data+=tmp_data
else:
break;
print(data)
socket.close()
socket_client.py
#socket客户端
import socket
client = socket.socket()
client.connect(('localhost', 8000))
#client.send(b'Hello World')
client.send('Hello World'.encode('utf-8'))
client.close()
分别设置server、client程序并行执行

更改选项,设置并行执行

先执行server,后执行client,执行结果如下,可以看到client已经将数据传到server上了

socket通信实例二:(改了客户端输出)
socket_server.py
#socket服务端
import socket
server_socket = socket.socket()
#绑定到0.0.0.0 8000端口
server_socket.bind(('0.0.0.0',8000))
server_socket.listen()
#阻塞等待连接
socket,add=server_socket.accept()
print(socket)
print(add)
data=bytes('','utf-8')
while True:
tmp_data=socket.recv(1024)
print(tmp_data)
if tmp_data:
data+=tmp_data
if tmp_data.decode("utf-8").endswith("#"):
break
else:
break;
print(data)
socket.close()
socket_client.py #号键输出程序结束
#socket客户端
import socket
client = socket.socket()
client.connect(('localhost', 8000))
#当输出完成后,以#号结尾,即为完成
while True:
data = input()
client.send(data.encode('utf-8'))
client.close()
程序运行结果:


socket通信实例三:
socket_server.py
#socket服务端
import socket
import threading
server_socket = socket.socket()
#绑定到0.0.0.0 8000端口
server_socket.bind(('0.0.0.0',8000))
server_socket.listen()
#获取客户端连接并启动线程去处理
def handle_client(server_socket,addr):
while True:
tmp_data = socket.recv(1024)
print(tmp_data.decode("utf-8"))
input_data=input()
socket.send(input_data.encode("utf-8"))
while True:
# 阻塞等待连接
socket, add = server_socket.accept()
#启动一个线程去处理新的用户连接
client_thread=threading.Thread(target=handle_client,args=(socket,add))
client_thread.start()
socket_client.py
#socket客户端
import socket
client = socket.socket()
client.connect(('localhost', 8000))
#当输出完成后,以#号结尾,即为完成
while True:
data = input()
client.send(data.encode('utf-8'))
server_data = client.recv(1024)
if server_data:
if server_data.decode("utf-8").endswith("#"):
break
else:
break;
print("server response:{}".format(server_data.decode("utf-8")))
client.close()
程序运行结果:


socket通信实例四:qq聊天通讯
程序结构

myqq_server.py
#qq服务器
#1、转发消息
#2、处理登陆
#3、处理退出
#4、维护历史消息,维护在线用户和维护用户的链接
import json
import socket
import threading
from collections import defaultdict
def init_user():
return {
"name": "boddy",
"sock": "sock"
}
#1、维护用户的连接
online_users = defaultdict(init_user)
# online_users["boddy"]["name"]="boddy"
# print(online_users)
#2、维护用户的历史消息
user_msgs = defaultdict(list)
server = socket.socket()
#绑定IP
server.bind(('0.0.0.0', 8000))
server.listen()
def handle_sock(server_socket, addr, user=None):
while True:
data = server_socket.recv(1024)
json_data = json.loads(data.decode("utf-8"))
action = json_data.get("action", "")
if action == "login":
online_users[json_data["user"]] = server_socket
server_socket.send("登陆成功".encode("utf-8"))
elif action == "list_user":
#获取当前在线用户
all_users = [user for user, socket in online_users.items()]
server_socket.send(json.dumps(all_users).encode("utf-8"))
elif action == "history_msg":
server_socket.send(json.dumps(user_msgs.get(json_data["user"], [])).encode("utf-8"))
elif action == "send_msg":
if json_data["to"] in online_users:
online_users[json_data["to"]].send(json.dumps(json_data).encode("utf-8"))
user_msgs[json_data["to"]].append(json_data)
elif action == "exit":
del online_users[json_data["user"]]
server_socket.send("退出成功".encode("utf-8"))
while True:
#阻塞等待连接
socket, add = server.accept()
# 启动一个线程去处理新的用户连接
client_thread = threading.Thread(target=handle_sock, args=(socket, add))
client_thread.start()
#1、多线程处理每个用户连接,防止主线程阻塞
#2、自定义了消息协议并且自己完成消息协议解析
myqq_client.py
import json
import socket
import threading
client=socket.socket()
client.connect(('127.0.0.1',8000))
user="boddy1"
#1、登录
login_template={
"action":"login",
"user":user
}
client.send(json.dumps(login_template).encode("utf-8"))
res=client.recv(1024)
print(res.decode("utf-8"))
#2、获取在线用户
get_user_template={
"action":"list_user",
}
client.send(json.dumps(get_user_template).encode("utf-8"))
res=client.recv(1024)
print("当前在线用户:{}".format(res.decode("utf-8")))
#3、获取历史消息
offline_msg_template={
"action":"history_msg",
"user":user
}
client.send(json.dumps(offline_msg_template).encode("utf-8"))
res=client.recv(1024)
print("历史消息:{}".format(res.decode("utf-8")))
exit=False
def handle_receive():
#处理接收请求
while True:
if not exit:
try:
res=client.recv(1024)
except:
break
res=res.decode("utf-8")
try:
res_json=json.loads(res)
msg=res_json["data"]
from_user=res_json["from"]
print(" ")
print("收到来自({})的消息:{}".format(from_user,msg))
except:
print(" ")
print(res)
else:
break
def handle_send():
while True:
# 1、随时可以发送消息
# 2、有新消息随时可以接收到
op_type=input("请你输入要进行的操作:1、发送消息,2、退出,3、获取在线用户")
if op_type not in ["1","2","3"]:
print("不支持该操作!!")
op_type=input("请输入你要进行的操作:1、发送消息,2、退出,3、获取在线用户")
elif op_type == "1":
to_user=input("请输入你要发送的用户:")
msg=input("请输入你要发送的消息")
send_data_template={
"action": "send_msg",
"to": to_user,
"from": user,
"data": msg
}
client.send(json.dumps(send_data_template).encode("utf-8"))
elif op_type == "2":
exit_template = {
"action": "exit",
"user": ""
}
client.send(json.dumps(exit_template).encode("utf-8"))
exit=True
client.close()
break
elif op_type == "3":
get_user_template = {
"action": "list_user",
}
client.send(json.dumps(get_user_template).encode("utf-8"))
if __name__ == '__main__':
send_thread = threading.Thread(target=handle_send)
receive_thread=threading.Thread(target=handle_receive)
send_thread.start()
receive_thread.start()
myqq_client2.py
import json
import socket
import threading
client=socket.socket()
client.connect(('127.0.0.1',8000))
user="boddy2"
#1、登录
login_template={
"action":"login",
"user":user
}
client.send(json.dumps(login_template).encode("utf-8"))
res=client.recv(1024)
print(res.decode("utf-8"))
#2、获取在线用户
get_user_template={
"action":"list_user",
}
client.send(json.dumps(get_user_template).encode("utf-8"))
res=client.recv(1024)
print("当前在线用户:{}".format(res.decode("utf-8")))
#3、获取历史消息
offline_msg_template={
"action":"history_msg",
"user":user
}
client.send(json.dumps(offline_msg_template).encode("utf-8"))
res=client.recv(1024)
print("历史消息:{}".format(res.decode("utf-8")))
exit=False
def handle_receive():
#处理接收请求
while True:
if not exit:
try:
res=client.recv(1024)
except:
break
res=res.decode("utf-8")
try:
res_json=json.loads(res)
msg=res_json["data"]
from_user=res_json["from"]
print(" ")
print("收到来自({})的消息:{}".format(from_user,msg))
except:
print(" ")
print(res)
else:
break
def handle_send():
while True:
# 1、随时可以发送消息
# 2、有新消息随时可以接收到
op_type=input("请你输入要进行的操作:1、发送消息,2、退出,3、获取在线用户")
if op_type not in ["1","2","3"]:
print("不支持该操作!!")
op_type=input("请输入你要进行的操作:1、发送消息,2、退出,3、获取在线用户")
elif op_type == "1":
to_user=input("请输入你要发送的用户:")
msg=input("请输入你要发送的消息")
send_data_template={
"action": "send_msg",
"to": to_user,
"from": user,
"data": msg
}
client.send(json.dumps(send_data_template).encode("utf-8"))
elif op_type == "2":
exit_template = {
"action": "exit",
"user": ""
}
client.send(json.dumps(exit_template).encode("utf-8"))
exit=True
client.close()
break
elif op_type == "3":
get_user_template = {
"action": "list_user",
}
client.send(json.dumps(get_user_template).encode("utf-8"))
if __name__ == '__main__':
send_thread = threading.Thread(target=handle_send)
receive_thread=threading.Thread(target=handle_receive)
send_thread.start()
receive_thread.start()
myqq_client3.py
import json
import socket
import threading
client=socket.socket()
client.connect(('127.0.0.1',8000))
user="boddy3"
#1、登录
login_template={
"action":"login",
"user":user
}
client.send(json.dumps(login_template).encode("utf-8"))
res=client.recv(1024)
print(res.decode("utf-8"))
#2、获取在线用户
get_user_template={
"action":"list_user",
}
client.send(json.dumps(get_user_template).encode("utf-8"))
res=client.recv(1024)
print("当前在线用户:{}".format(res.decode("utf-8")))
#3、获取历史消息
offline_msg_template={
"action":"history_msg",
"user":user
}
client.send(json.dumps(offline_msg_template).encode("utf-8"))
res=client.recv(1024)
print("历史消息:{}".format(res.decode("utf-8")))
exit=False
def handle_receive():
#处理接收请求
while True:
if not exit:
try:
res=client.recv(1024)
except:
break
res=res.decode("utf-8")
try:
res_json=json.loads(res)
msg=res_json["data"]
from_user=res_json["from"]
print(" ")
print("收到来自({})的消息:{}".format(from_user,msg))
except:
print(" ")
print(res)
else:
break
def handle_send():
while True:
# 1、随时可以发送消息
# 2、有新消息随时可以接收到
op_type=input("请你输入要进行的操作:1、发送消息,2、退出,3、获取在线用户")
if op_type not in ["1","2","3"]:
print("不支持该操作!!")
op_type=input("请输入你要进行的操作:1、发送消息,2、退出,3、获取在线用户")
elif op_type == "1":
to_user=input("请输入你要发送的用户:")
msg=input("请输入你要发送的消息")
send_data_template={
"action": "send_msg",
"to": to_user,
"from": user,
"data": msg
}
client.send(json.dumps(send_data_template).encode("utf-8"))
elif op_type == "2":
exit_template = {
"action": "exit",
"user": ""
}
client.send(json.dumps(exit_template).encode("utf-8"))
exit=True
client.close()
break
elif op_type == "3":
get_user_template = {
"action": "list_user",
}
client.send(json.dumps(get_user_template).encode("utf-8"))
if __name__ == '__main__':
send_thread = threading.Thread(target=handle_send)
receive_thread=threading.Thread(target=handle_receive)
send_thread.start()
receive_thread.start()
运行结果:




浙公网安备 33010602011771号