zoukankan      html  css  js  c++  java
  • 博客整理day27

    python day27

    subprocess模块

    subprocess:

    ​ 可以通过代码,去执行系统的终端命令,并返回终端执行命令后的结果

    import subprocess
    
    cmd = input('cmd:')
    obj = subprocess.Popen(
    	cmd,
        #Shell=True
        shell = True
        #返回正确结果参数
        stdout = subprocess.PIPE
        #返回错误结果参数error
        stderr = subprocess.PIPE
    )
    result = obj.stdout.read()+obj.stderr.read()
    print(reault.decode('gbk'))
    

    粘包

    粘包问题:

    ​ 服务端第一次发送的数据,与客户端无法精确一次性接收完毕,下一次发送的数据与上一次数据粘在一起了

    ​ 1.无法预知对方需要接收的数据大小

    ​ 2.多次连续发送数据量小,并且时间间隔短的数据会一次性打包发送

    TCP协议特性:

    ​ tcp是一个流式协议,会将多次连续发送数据量小,并且时间间隔短的数据一次性打包发送

    解决粘包问题:

    struct模块

    必须先定义报头,发送报头,再发送真实数据

    当既想发送文件,又想发送文件的描述信息

    ​ 客户端发送字典给服务端

    ​ send_dic = {

    ​ file_name : 文件名

    ​ file_size : 文件的真实长度

    ​ }

    ​ #通过json模块序列化成bytes数据

    ​ json_data = json.dumps(send_dic)

    ​ bytes_data = json_data.encode('utf8')

    ​ #先获取字典的报头

    ​ headers = struct.pack('i',len(bytes_data))

    ​ #服务端接收到字典,并接收文件的真实数据

    import socket
    import struct
    import subprocess
    
    server = socket.socket()
    
    server.bind(('192.168.13.161',8888))
    server.listen(5)
    while True:
        conn,addr = server.accept()
        while True:
            try:
                cmd = conn.recv(1024).decode('utf8')
                if cmd == 'q':
                    break
                if len(cmd)==0:
                    continue
                print(cmd)
                obj = subprocess.Popen(
                    cmd,
                    shell=True,
                    stdout=subprocess.PIPE,
                    stderr=subprocess.PIPE
                )
                result = obj.stdout.read()+obj.stderr.read()
                headers = struct.pack('i',len(result))
                conn.send(result)
            except Exception as e:
                print(e)
                break
        conn.close()
    

    上传大文件

    客户端往服务端上传大文件:

    #Client
    import socket
    import json
    import struct
    
    client = socket.socket()
    
    client.connect(('192.168.13.202', 9526))
    with open(r'E:	he truth that you leave.mp3','rb') as f:
        music_bytes = f.read()
    send_dic = {
        'file_name':'the truth that you leave.mp3',
        'file_size':len(music_bytes)
    }
    json_data = json.dumps(send_dic)
    bytes_data = json_data.encode('utf8')
    headers = struct.pack('i',len(bytes_data))
    client.send(headers)
    client.send(bytes_data)
    
    init_data = 0
    with open(r'E:	he truth that you leave.mp3','rb') as f:
        while init_data<len(music_bytes):
            send_data = f.read(1024)
            print(send_data)
            client.send(send_data)
            init_data += len(send_data)
    
    client.close()
    
    #Server
    import socket
    import struct
    import json
    
    server = socket.socket()
    server.bind(('192.168.13.202', 9526))
    server.listen(5)
    while True:
        conn, addr = server.accept()
        try:
            headers = conn.recv(4)
    
            data_len = struct.unpack('i', headers)[0]
    
            bytes_data = conn.recv(data_len)
            back_dic = json.loads(bytes_data.decode('utf8'))
    
            file_name = back_dic.get('file_name')
            file_size = back_dic.get('file_size')
            init_data = 0
    
            with open(file_name, 'wb') as f:
                while init_data < file_size:
                    data = conn.recv(1024)
                    f.write(data)
                    init_data += len(data)
    
                print(f'{file_name}接收完毕!')
        except Exception as e:
            print(e)
            break
    conn.close()
    

    UDP

    udp是一种传输协议

    ​ 1.不需要建立双向管道

    ​ 2.不会粘包

    ​ 3.客户端给服务端发送数据,不需要等待服务端返回成功

    ​ 4.数据容易丢失,数据不安全

    TCP : 就好比打电话

    UDP : 就好比发短信

    QQ聊天室(基于UDP)

    #Server
    import socket
    
    server = socket.socket()
    
    server.bind(('192.168.13.202', 9526))
    
    while True:
        msg,addr = server.recvfrom(1024)
        print(addr)
        print(msg.decode('utf-8'))
        send_msg = input('server-->client:').encode('utf8')
    
        server.sendto(send_msg,addr)
    
    #Client
    import socket
    
    client = socket.socket()
    server_port = (('192.168.13.202', 9526))
    
    while True:
        send_msg = input('client -- > server:').encode('utf8')
        msg = client.recv(1024)
    
        print(msg.decode('utf-8'))
    

    socketServer

    ​ python内置模块,可以简化socket套接字服务端的代码

    • 简化TCP与UDP服务端代码
    • 必须要创建一个类
    import socketserver
    
    # 定义类
    # TCP: 必须继承BaseRequestHandler类
    class MyTcpServer(socketserver.BaseRequestHandler):
        # 必须重写父类的handle
        def handle(self):
    
            # 1.接收消息
            print(data)
            # 2.给客户端发送消息
            send_msg = input('服务端: ').encode('utf-8')
            self.request.send(send_msg)
    
    if __name__ == '__main__':
        socketserver.TCPServer.allow_reuse_address = True
        server = socketserver.TCPServer(
            ('192.168.13.202', 9526), MyTcpServer
        )
    
        # 永久执行服务
        server.serve_forever()
    
  • 相关阅读:
    Jenkins pipeline基本结构
    接口测试框架httprunner使用自定义extentreports报告模板遇到的问题小结
    python3中扩展字典类实现用点访问属性
    python3系列五可迭代对象、迭代器和生成器
    vue.js-组件嵌套
    使用Vue-CLI3.x进行vue.js环境搭建
    python系列四反射机制
    vue.js环境搭建踩坑记
    python系列三推导式
    python系列二filter()、map()和reduce()
  • 原文地址:https://www.cnblogs.com/samoo/p/11707454.html
Copyright © 2011-2022 走看看