当前位置 博文首页 > 孤寒者的博客:tornado项目愿景—通过socket实现传统TCP客户端和

    孤寒者的博客:tornado项目愿景—通过socket实现传统TCP客户端和

    作者:[db:作者] 时间:2021-07-25 18:34

    tornado和主流的web服务器框架有明显的区别:
    它是非阻塞式服务器而且速度非常快,得力于其非阻塞的方式和epoll的运用!
    tornado可以每秒处理千计的连接!


    1.项目内容简介:使用tornado服务器框架做一个模仿Instagram的应用!

    • 为什么做一个模仿 Instagram 的应用
      (1)偏后端和后台的开发
      (2)充分利用 tornado 的特点
      (3)积累项目经验,巩固知识点
    • Instagram 主要组成
      (1)发现或最近上传的图片页面
      (2)所关注的用户图片流
      (3)单个图片详情页面
      (4)数据库 Database
      (5)用户档案 User Profile

    在这里插入图片描述
    在这里插入图片描述

    2.本项目如何做成:

    • (1)从最简单开始,迭代增加功能
    • (2)用户,登陆,关注等
    • (3)数据库保存
    • (4)UI 和 Web 界面美化
    • (5)外部连接
    • (6)部署和运行

    3.传统TCP客户端与TCP服务器端

    在这里插入图片描述

    ①传统TCP服务器端步骤及对应代码:

    • 1.创建套接字socket
    • 2.绑定IP和端口号
    • 3.设置接收数
    • 4.处理连接
    • 5.设置接收数据的大小
    • 6.关闭和退出
    import socket
    # 1.服务器对象         socket.AF_INET:使用IPV4;  socket.SOCK_STREAM:创建一个socket套接字。
    server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
    # 2.绑定IP和端口号
    server.bind(("127.0.0.1",8080))
    # 3.监听  设置接收数
    server.listen(128)
    print('服务器开启', 8080)
    # 4.处理连接
    # accept是一个阻塞的方法(你不来我就不动!),等待连接,每建立一个连接就会创建一个单独的通道。
    # conn:通道参数;addr:通道地址(客户端连接服务端的IP和端口号,这个客户端的端口号是随机生成的!)。
    new_cli, addr = server.accept()
    # 打印一下ip和端口号的类型
    print('来自一个新的连接', addr, type(addr))
    # 5.设置接收数据的大小
    data = new_cli.recv(1024)
    print(data)
    # 6.关闭这个连接的通道
    new_cli.close()
    # 关闭整个服务器
    server.close()
    

    ②传统TCP客户端步骤及对应代码:

    • 1.指定服务器的IP和端口号
    • 2.发送数据给服务器
    • 3.指定发送服务器的文件大小
    import socket
    
    # 建立服务器对象      通过打印这个client服务器对象可知:默认使用的是IPV4,协议是TCP。
    client=socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
    # 指定服务器的ip和端口号
    client.connect(('127.0.0.1',8080))
    # 发送数据给服务器
    client.send(b'hello server')
    # 发送给服务器指定的文件大小
    data = client.recv(1024)
    print(data)
    

    运行:

    在这里插入图片描述

    注意上面传统TCP服务器中accept是一个阻塞的方法(你不来我就不动!),这就会产生网络等待的问题,同时这也是多线程中线程切换的问题,会因为阻塞而造成等待!
    而我们知道协程是非阻塞的,所以这里就在tcp服务器中使用协程,引入非阻塞(让服务器接收数据的形式变为非阻塞!)——解决线程之间(服务器和客户端两个线程)的切换问题!!!

    引入非阻塞的TCP服务器端代码编写:

    import socket
    import threading
    
    
    def handle_func(new_sock):
        while True:
            data = new_sock.recv(4)     # 接收数据
            print(data)
            if data is None:
                break
        new_sock.close()
    
    while 1:
        # 服务器对象         socket.AF_INET:使用IPV4;  socket.SOCK_STREAM:创建一个socket套接字。
        server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    
        # 绑定服务器
        server.bind(("127.0.0.1", 8000))
        # 监听
        server.listen(128)
        print('服务器开启', 8000)
    
        # accept是一个阻塞的方法(你不来我就不动!),等待连接,每建立一个连接就会创建一个单独的通道。
        # conn:通道参数;addr:通道地址(客户端连接服务端的IP和端口号,这个客户端的端口号是随机生成的!)。
        new_cli, addr = server.accept()
        # 打印一下ip的类型
        print('来自一个新的连接', addr, type(addr))
        server.setblocking(False)  # 设置套接字为非阻塞     找epoll使用  解决网络的等待问题
        # 注意:协程要依附于线程!
        task = threading.Thread(target=handle_func, args=(new_cli,))
        task.start()
    

    运行:

    在这里插入图片描述

    cs