zoukankan      html  css  js  c++  java
  • Python全栈开发:socket代码实例

    客户端与服务端交互的基本流程

    1. 服务端server
      #!/usr/bin/env python
      # -*- coding;utf-8 -*-
      import socket
      
      sk = socket.socket()
      sk.bind(("127.0.0.1", 9999))
      sk.listen(5)
      while True:
          conn, address = sk.accept()
          conn.sendall(bytes("欢迎访问老男孩!",encoding="utf-8"))
          while True:
              ret_bytes = conn.recv(1024)
              ret_str = str(ret_bytes, encoding="utf-8")
              print(ret_str)
              if ret_str == "q":
                  break
              conn.sendall(bytes("答:" + "好!", encoding="utf-8"))
    2. 客户端client
      #!/usr/bin/env python
      # -*- coding;utf-8 -*-
      import socket
      
      obj = socket.socket()
      obj.connect(("127.0.0.1", 9999))
      ret_bytes = obj.recv(1024)
      ret_str = str(ret_bytes, encoding="utf-8")
      print(ret_str)
      while True:
          inp = input("请输入内容:
       问:")
          obj.sendall(bytes(inp, encoding="utf-8"))
          if inp == 'q':
              break
          else:
              ret = str(obj.recv(1024), encoding="utf-8")
              print(ret)
      obj.close()

    粘包问题解决方案:一个类型文件发送完毕之后进行一次确认信息交互。

    1. server(粘包)
      #!/usr/bin/env python
      # -*- coding;utf-8 -*-
      
      
      import socket
      
      sk = socket.socket()
      sk.bind(("192.168.1.107", 9999,))  # 传入元组
      sk.listen(5)  # 监听客户端请求,最多有五个客户端请求等待)
      # 连接,客户端的地址信息(IP,port)
      while True:
          conn, address = sk.accept()  # accept表示阻塞,等待连接请求
          conn.sendall(bytes("欢迎访问老男孩!", encoding="utf-8"))
          file_size = str(conn.recv(1024), encoding="utf-8")
          print(file_size)
          conn.sendall(bytes("开始吧!", encoding="utf-8"))
          total_size = int(file_size)
          has_recv = 0
          with open("c11.py", "wb") as f:
              i = 0
              while True:
                  if total_size == has_recv:
                      print("接收完毕!")
                      break
                  data = conn.recv(1024)
                  f.write(data)
                  has_recv += len(data)
      obj.close()
    2. client(粘包)
      #!/usr/bin/env python
      # -*- coding;utf-8 -*-
      import socket
      import os
      
      obj = socket.socket()
      obj.connect(("192.168.1.107", 9999))
      result_bytes = obj.recv(1024)  # 等待发送消息
      result_str = str(result_bytes, encoding="utf-8")
      print(result_str)
      # 发送当前文件大小
      file_size = os.stat("client(粘包).py").st_size
      print("文件大小:" + str(file_size))
      obj.sendall(bytes(str(file_size), encoding="utf-8"))
      obj.recv(1024)
      with open("client(粘包).py", "rb") as f:
          seed_size = 0
          for i, line in enumerate(f, 1):
              obj.sendall(line)
              seed_size += len(line)
              if seed_size == file_size:
                  print("发送完毕!")
      obj.close()
      

    IO多路复用在socket中的运用:针对老用户和新用户,服务器做出不同的响应

    1. server服务端
      #!/usr/bin/env python
      # -*- coding;utf-8 -*-
      """
      IO多路复用socket实例代码
      """
      import socket
      import select
      
      sk1 = socket.socket()
      sk1.bind(("127.0.0.1", 8001))
      sk1.listen(5)
      inputs = [sk1, ]
      info_sender = []
      message = {}
      
      while True:
          # select自动监听文件描述符,发生变化则放入r_list列表中
          r_list, w_list, e_list = select.select(inputs, info_sender, [], 1)
          # print("正在监听的对象数量:%d" % len(inputs))
          for sk in r_list:
              # sk 表示每个连接对象
              if sk == sk1:
                  # 有新用户建立连接
                  conn, address = sk.accept()
                  conn.sendall(bytes("hello", encoding="utf-8"))
                  inputs.append(conn)
                  message[conn] = []
              else:
                  # 有老用户发送信息
                  try:
                      date = str(sk.recv(1024), encoding="utf-8")
                  except Exception as e:
                      e_list.append(sk)
                  else:
                      if sk not in info_sender:
                          info_sender.append(sk)
                      message[sk].append(date)
      
          for sk in w_list:
              re = message[sk][0]
              del message[sk][0]
              sk.sendall(bytes(re + "hello", encoding="utf-8"))
              # 给我发送信息的对象,我回复了信息就要把它排除,不然前面有while循环,和for循环,就会不断给对方回复消息!
              info_sender.remove(sk)
      
          for sk in e_list:
              inputs.remove(sk)
      
    2. 客户端client(client1,client2,client3):当用户第一次连接时执行相同的操作,支持多用户与服务器交互,客户端断开连接,服务器不受影响
      #!/usr/bin/env python
      # -*- coding;utf-8 -*-
      import socket
      
      sk1 = socket.socket()
      sk1.connect(("127.0.0.1", 8001))
      while True:
          content1 = str(sk1.recv(1024), encoding="utf-8")
          a = []
          print(content1)
          while True:
              inp = input(">>>")
              if inp == "q":
                  a.append(inp)
                  break
              else:
                  sk1.sendall(bytes(inp, encoding="utf-8"))
                  content2 = str(sk1.recv(1024), encoding="utf-8")
                  print(content2)
          if a == ["q"]:
              break
      sk1.close()
      

        

      

  • 相关阅读:
    一种想法
    识别link_text
    识别name
    识别id
    文件的读写
    条件和循环
    网站测试-功能测试小结
    拷贝
    #团队博客作业1-小组成员介绍
    软件测试基础-Homework1
  • 原文地址:https://www.cnblogs.com/nixingguo/p/6494201.html
Copyright © 2011-2022 走看看