基于tcp的套接字,关键就是两个循环,一个链接循环,一个通信循环

socketserver模块中分两大类:server类(解决链接问题)和request类(解决通信问题)

一、分析socketserver源码

ftpserver=socketserver.ThreadingTCPServer(('127.0.0.1',8080),FtpServer)
ftpserver.serve_forever()

查找属性的顺序:ThreadingTCPServer->ThreadingMixIn->TCPServer->BaseServer

  1. 实例化得到ftpserver,先找类ThreadingTCPServer的__init__,在TCPServer中找到,进而执行server_bind,server_active
  2. 找ftpserver下的serve_forever,在BaseServer中找到,进而执行self._handle_request_noblock(),该方法同样是在BaseServer中
  3. 执行self._handle_request_noblock()进而执行request, client_address = self.get_request()(就是TCPServer中的self.socket.accept()),然后执行self.process_request(request, client_address)
  4. 在ThreadingMixIn中找到process_request,开启多线程应对并发,进而执行process_request_thread,执行self.finish_request(request, client_address)
  5. 上述四部分完成了链接循环,本部分开始进入处理通讯部分,在BaseServer中找到finish_request,触发我们自己定义的类的实例化,去找__init__方法,而我们自己定义的类没有该方法,则去它的父类也就是BaseRequestHandler中找....

源码分析总结:

基于tcp的socketserver我们自己定义的类中的

  1.   self.server即套接字对象
  2.   self.request即一个链接
  3.   self.client_address即客户端地址

基于udp的socketserver我们自己定义的类中的

  1.   self.request是一个元组(第一个元素是客户端发来的数据,第二部分是服务端的udp套接字对象),如(b'adsf', <socket.socket fd=200, family=AddressFamily.AF_INET, type=SocketKind.SOCK_DGRAM, proto=0, laddr=('127.0.0.1', 8080)>)
  2.   self.client_address即客户端地址

二、socketserver基于(TCP)实现并发

import socketserver

class MyHandler(socketserver.BaseRequestHandler):
def handle(self): #对象的固定方法不能变
#通信循环
while True:
try:
data=self.request.recv(1024) #conn.recv(1024)
if len(data)==0:break
self.request.send(data.upper()) #conn.send(data.upper())
except ConnectionResetError:
break
if __name__ == '__main__':
s=socketserver.ThreadingTCPServer(('127.0.0.1',8080),MyHandler,bind_and_activate=True)
s.serve_forever() #本质就是bind和listen,代表连接循环
# 每建立一个连接就会启动一个线程(服务员),+调用FtpServer类产生一个对象,调用该对像下的handle方法,与刚刚建立好的连接进行通信循环

服务端

import socket

phone=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
phone.connect(('127.0.0.1',8080)) # 指定服务端ip和端口 while True:
# msg=input('>>: ').strip() #msg=''
msg = 'client1111111' # msg=''
if len(msg) == 0:continue
phone.send(msg.encode('utf-8'))
data=phone.recv(1024)
print(data) phone.close()

客户端1

import socket

phone=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
phone.connect(('127.0.0.1',8080)) # 指定服务端ip和端口 while True:
# msg=input('>>: ').strip() #msg=''
msg = 'client22222' # msg=''
if len(msg) == 0:continue
phone.send(msg.encode('utf-8'))
data=phone.recv(1024)
print(data) phone.close()

客户端2

三、socketserver基于(UDP)实现并发

import socketserver         #借助别人写好的模块进行并发的效果
class MyHandler(socketserver.BaseRequestHandler):
def handle(self):
data=self.request[0]
print('客户端消息',data)
self.request[1].sendto(data.upper(),self.client_address)
if __name__ == '__main__':
s=socketserver.ThreadingUDPServer(('127.0.01',8080),MyHandler)
s.serve_forever() #启动一个线程

服务端

import socket
client=socket.socket(socket.AF_INET,socket.SOCK_DGRAM)
while True:
msg='client11111111111'
client.sendto(msg.encode('utf-8'),('127.0.0.1',8080))
data,server_addr=client.recvfrom(1024)
print(data)
client.close()

客户端1

import socket
client=socket.socket(socket.AF_INET,socket.SOCK_DGRAM)
while True:
msg='client22222222222'
client.sendto(msg.encode('utf-8'),('127.0.0.1',8080))
data,server_addr=client.recvfrom(1024)
print(data)
client.close()

客户端2

基于socketserver实现并发的更多相关文章

  1. 模拟ssh远程执行命令,粘包问题,基于socketserver实现并发的socket

    06.27自我总结 1.模拟ssh远程执行命令 利用套接字编来进行远程执行命令 服务端 from socket import * import subprocess server = socket(A ...

  2. 网络编程之基于UDP协议的套接字编程、基于socketserver实现并发的socket

    目录 基于UDP协议的套接字编程 UDP套接字简单示例 服务端 客户端 基于socketserver实现并发的socket 基于TCP协议 server类 request类 继承关系 服务端 客户端1 ...

  3. 基于socketserver实现并发的socket编程

    目录 一.基于TCP协议 1.1 server类 1.2 request类 1.3 继承关系 1.4 服务端 1.5 客户端 1.6 客户端1 二.基于UDP协议 2.1 服务端 2.2 客户端 2. ...

  4. 基于socketserver实现并发的socket套接字编程

    一.基于TCP协议 基于tcp的套接字,关键就是两个循环,一个链接循环,一个通信循环 socketserver模块中分两大类:server类(解决链接问题)和request类(解决通信问题) 1.1 ...

  5. Python中基于socketserver实现并发的socket

    1.基于TCP协议: 服务端: import socketserver class MyHandler(socketserver.BaseRequestHandler): def handle(sel ...

  6. 基于socketserver实现的并发(tcp和udp)

    threading 线程 基于tcp协议:请求建立连接,然后开启进程 基于udp协议:直接开启新进程 基于tcp协议 import socketserver # 导入socketserver模块 # ...

  7. 36、IO模型与socketserver实现并发

    特别声明本随笔copy于egon(林海峰). 一 IO模型介绍 为了更好地了解IO模型,我们需要事先回顾下:同步.异步.阻塞.非阻塞 同步(synchronous) IO和异步(asynchronou ...

  8. 网络编程----socketserver多并发实现、FTP上传多并发、udp协议套接字多并发

    一.socketserver多并发                                                              基于tcp的套接字,关键就是两个循环,一个 ...

  9. Day10 - Python基础10 socketserver 实现并发

    本节内容: 1.实例tcp的并发 2.看源代码继承关系 3.详解:ThreadingTCPServer的过程 4.tcp和udp的request 不同 5.基于udp的并发实现 1.实例tcp并发 s ...

随机推荐

  1. Google, Facebook, Amazon and Microsoft Salaries

    https://blog.step.com/2016/04/08/an-open-source-project-for-tech-salaries/ Step.com Crowdsource your ...

  2. java.lang.verifyerror:bad type on orerand stack

    问题: junit测试的时候报这个错:java.lang.verifyerror:bad type on orerand stack 原因:(多种,自行逐个排查) 1.class not find 引 ...

  3. Hadoop HBase概念学习系列之HBase里的宽表设计概念(表设计)(二十七)

    在下面这篇博文里,我给各位博客们,分享了创建HBase表,但这远不止打好基础. HBase编程 API入门系列之create(管理端而言)(8) 在关系型数据库里,表的高表和宽表是不存在的.在如HBa ...

  4. APUE 12.7 取消选项

  5. 字节(byte)与位(bit)基础回顾

    预估方式:一个uid,String类型,最长约50字节,即50Byte,一天100亿PV,则100亿*50Byte,约500G容量存ES中或Hbase中,无法存日志文件中,一个docker磁盘才50G ...

  6. JavaScript动画

    早期的JS动画 早期的JS循环动画主要是通过setInterval/setTimeout实现的 function jump() { console.log("我跳了一下"); } ...

  7. jquery与json的结合

    通过AJAX异步减少网络内容传输,而JSON则可以把传输内容缩减到纯数据:然后利用jQuery内置的AJAX功能直接获得JSON格式的数据:在客户端直接绑定到数据控件里面,从而达到最优. 1 2 3 ...

  8. python第十六课——ascii码

    2.ascii码 美国设计出来的一张编码表,将涉及的字符都编号了,底层仍然还是进行二进制的运算: 记住:3个范围段 1).'0' --> 码值:48 2).'A' --> 码值:65 3) ...

  9. shell基础--字符串和变量的操作

    一.统计字符串长度 1.wc –L [root@~_~day4]# echo "hello" | wc -L 5 2.expr length string [root@~_~day ...

  10. SVN服务器安装与本地连接

    SVN服务器安装与本地连接 系统环境 Centos7 查看是否安装了低版本SVN [root@svn-server ~]# rpm -qa subversion 卸载旧版本SVN [root@svn- ...