openstack 源码分析之swift proxy 服务启动 2

接上篇 

通过wift-proxy-server 脚本,swift调用swift.common.wsgi中的run_wsgi(conf_file, 'proxy-server', default_port=8080, **options) 启动 wsgi服务

def run_wsgi(conf_path, app_section, *args, **kwargs):
    """
    Runs the server using the specified number of workers.

    :param conf_path: Path to paste.deploy style configuration file/directory
    :param app_section: App name from conf file to load config from
    """
    # Load configuration, Set logger and Load request processor
    try:
        (conf, logger, log_name) = \
            _initrp(conf_path, app_section, *args, **kwargs)
    except ConfigFileError, e:
        print e
        return

    # bind to address and port
    sock = get_socket(conf, default_port=kwargs.get('default_port', 8080)) #socket 绑定端口和conf中的ip地址得到socket
    # remaining tasks should not require elevated privileges
    drop_privileges(conf.get('user', 'swift'))

    # Ensure the application can be loaded before proceeding.
    loadapp(conf_path, global_conf={'log_name': log_name})

    # set utils.FALLOCATE_RESERVE if desired
    reserve = int(conf.get('fallocate_reserve', 0))
    if reserve > 0:
        utils.FALLOCATE_RESERVE = reserve
    # redirect errors to logger and close stdio
    capture_stdio(logger)

    worker_count = int(conf.get('workers', '1'))
    # Useful for profiling [no forks].
    if worker_count == 0:
        run_server(conf, logger, sock) #使用得到的socket,logger日志, 和配置运行server
        return


下来转入 run_server()函数 真正启动wsgi 服务 使用基于eventlet的并发多线程网络IO库,实现了 协程 (博大精深,要慢慢学习)

def run_server(conf, logger, sock):
    # Ensure TZ environment variable exists to avoid stat('/etc/localtime') on
    # some platforms. This locks in reported times to the timezone in which
    # the server first starts running in locations that periodically change
    # timezones.
    os.environ['TZ'] = time.strftime("%z", time.gmtime())

    wsgi.HttpProtocol.default_request_version = "HTTP/1.0" #以下都设置此wsgi服务的http协议
    # Turn off logging requests by the underlying WSGI software.
    wsgi.HttpProtocol.log_request = lambda *a: None
    # Redirect logging other messages by the underlying WSGI software.
    wsgi.HttpProtocol.log_message = \
        lambda s, f, *a: logger.error('ERROR WSGI: ' + f % a)
    wsgi.WRITE_TIMEOUT = int(conf.get('client_timeout') or 60)

    eventlet.hubs.use_hub(get_hub())
    eventlet.patcher.monkey_patch(all=False, socket=True)
    eventlet_debug = config_true_value(conf.get('eventlet_debug', 'no'))
    eventlet.debug.hub_exceptions(eventlet_debug)
    # utils.LogAdapter stashes name in server; fallback on unadapted loggers
    if hasattr(logger, 'server'):
        log_name = logger.server
    else:
        log_name = logger.name
    app = loadapp(conf['__file__'], global_conf={'log_name': log_name})#loadapp方法加载conf文件中的app的app_factory实例化这些app
    max_clients = int(conf.get('max_clients', '1024'))
    pool = RestrictedGreenPool(size=max_clients) #RestrictedGreenPool线程池用来实现协程,保证并行
    try:
        wsgi.server(sock, app, NullLogger(), custom_pool=pool) #使用eventlet库中的wsgi.server实现携程(多线程的并发运行app并管理socket,实现对请求的非阻塞IO)
    except socket.error, err:
        if err[0] != errno.EINVAL:
            raise
    pool.waitall()

上述的app就是 配置文件中 wsgi管道中的app 他们都要实现__call__方法保证是callable的,这些wsgi app 响应请求的操作就在__call__方法中实现(以后会说到) 并且服务的启动顺序和响应顺序应该是相反的。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值