zoukankan      html  css  js  c++  java
  • python socket server源码学习

    原文请见:http://www.cnblogs.com/wupeiqi/articles/5040823.html

    这里就是自己简单整理一下:

    #!/usr/bin/env python
    # -*- coding:utf-8 -*-
    import SocketServer
    
    class MyServer(SocketServer.BaseRequestHandler):
    
        def handle(self):
            # print self.request,self.client_address,self.server
            conn = self.request
            conn.sendall('欢迎致电 10086,请输入1xxx,0转人工服务.')
            Flag = True
            while Flag:
                data = conn.recv(1024)
                if data == 'exit':
                    Flag = False
                elif data == '0':
                    conn.sendall('通过可能会被录音.balabala一大推')
                else:
                    conn.sendall('请重新输入.')
    
    
    if __name__ == '__main__':
        server = SocketServer.ThreadingTCPServer(('127.0.0.1',8009),MyServer)
        server.serve_forever()
    

     程序先运行server的一个实例,socket.server.ThreadingTCPServer的构造方法,

    server继承ThreadingMixIn, TCPServer这两个类,构造方法只有TCPServer的类有并且继承其父类BaseServer的构造方法。

    TCPSever的构造方法(这个构造方法会执行bind和listen):

        def __init__(self, server_address, RequestHandlerClass, bind_and_activate=True):
            """Constructor.  May be extended, do not override."""
            BaseServer.__init__(self, server_address, RequestHandlerClass)
            self.socket = socket.socket(self.address_family,
                                        self.socket_type)
            if bind_and_activate:
                try:
                    self.server_bind()
                    self.server_activate()
                except:
                    self.server_close()
                    raise
    

      BaseServer的构造方法:

        def __init__(self, server_address, RequestHandlerClass):
            """Constructor.  May be extended, do not override."""
            self.server_address = server_address
            self.RequestHandlerClass = RequestHandlerClass
            self.__is_shut_down = threading.Event()
            self.__shutdown_request = False
    

      在BaseServer中的构造方法中MyServer类赋给了实例的属性RequestHandlerClass ,相当于server实例有了这个属性。server实例创建完成。

    然后是执行server的server_forever方法,

    接下来就是BaseServer的server_forever方法->BaseServer的_handle_request_noblock方法->ThreadingMixIn的process_request方法(TCPServer和ThreadingMixIn都有这个方法,但ThreadingMixIn优先级高所以是ThreadMixIn的这个方法)->ThreadingMixIn的process_request_thread方法(这时候是多线程中的一个线程的具体处理方法了)

        def process_request_thread(self, request, client_address):
            """Same as in BaseServer but as a thread.
    
            In addition, exception handling is done here.
    
            """
            try:
                self.finish_request(request, client_address)
                self.shutdown_request(request)
            except:
                self.handle_error(request, client_address)
                self.shutdown_request(request)
    

      ->BaseServer的finish_request方法(调用实例的这个方法,这个方法ThreadMixIn中没有BaseServer中有,这时候会执行RequestHandlerClass的构造方法也就是我们写的MyServer的构造方法,但是MyServer中没有需要MyServer的父类中查找)

        def finish_request(self, request, client_address):
            """Finish one request by instantiating RequestHandlerClass."""
            self.RequestHandlerClass(request, client_address, self)
    

      ->BaseRequestHandler的构造方法

        def __init__(self, request, client_address, server):
            self.request = request
            self.client_address = client_address
            self.server = server
            self.setup()
            try:
                self.handle()
            finally:
                self.finish()
    

      这上面finish,setup都是空的,handle是MyServer中定义的,这几个方法都需要我们自定义,

    ->MyServer的handle方法

    ->TcpServer的shutdown_request方法

    ->TcpServer的close_request方法

        def close_request(self, request):
            """Called to clean up an individual request."""
            request.close()
    

      这里request一直是client端的socket,到这里就关闭socket了算是完成了一次处理。

  • 相关阅读:
    机器学习-分类简单介绍
    状态压缩动态规划 -- 旅行商问题
    30 天学习 30 种新技术系列
    Sublime Text3 高亮显示Jade语法 (Windows 环境)
    程序启动缓慢-原来是hbm.xml doctype的原因
    Spring4 Hibernate4 Struts2在WebLogic 10.3.3上面部署
    Spring的 classpath 通配符加载配置文件
    nmp install 异常
    cvc-complex-type.2.4.c: The matching wildcard...
    LazyInitializationException--由于session关闭引发的异常
  • 原文地址:https://www.cnblogs.com/WisWang/p/6131550.html
Copyright © 2011-2022 走看看