使用tornado打造异步高并发的rpc server服务

前段时间自己在家闲着没事干,就整理了以前的没有写完的rpc服务。这是一个用tornado来实现的rpc服务,我们知道tornado最令人诟病的是不能随意的用阻塞模块。 怎么就是阻塞的模块?在现在分布式api开发应用中,很多时候访问速度慢是由于网络io阻塞引起的,而不是因为cpu计算量大引起的。 所以不管是gevent、tornado都让你选择patch后的模块。 

对于安全方面首先加入了浏览器ua标示的过滤,然后在swift_rpc支持最基本的remote_ip过滤,当然也支持前端nginx upstream负载均衡client ip透传解析。 另外还蛋疼的加入基本token认证,当然这功能显得有些鸡肋。我在github中开源的2.5版已经支持加密自定义的AES加密传输,以及base64的转码传输。  其实原本是计划让rpc支持rsa的,但又想到tornado这种单线程的服务端,只能对网络io进行异步的调用,对于非对称加密加密肯定是孤木难支。

对于tornado rpc来说,文章总是没完没了的修改,希望大家到原文查看更新后的原文.


http://xiaorui.cc/2015/11/16/%E4%BD%BF%E7%94%A8tornado%E6%89%93%E9%80%A0%E5%BC%82%E6%AD%A5%E9%AB%98%E5%B9%B6%E5%8F%91%E7%9A%84rpc-server%E6%9C%8D%E5%8A%A1/

项目:

swift_rpc


项目地址:

https://github.com/rfyiamcool/swift_rpc


项目介绍:

swift_rpc是用tornado实现的rpc服务,而且支持多种方式加密传输, 现在swift_rpc有四种注册的调度接口:

register 普通接口调用模式,最纯粹最简单的同步调用

(没啥好介绍的,就是调用, 能想到的优点是不会出现bug,最稳定 !)


register_async 借助于tornado gen.coroutine实现的非堵塞调用

(使用gen.coroutine异步调用,严谨使用不兼容yield gen.Task的网络模块,比如mysql、mongodb、hbase、requests等等)


register_pool 借助于futures.ThreadPoolExecutor实现线程池

(这个是使用python3.0的futures来实现的ThreadPool线程池,在这里可以使用io阻塞模块. 但要注意他的内存泄露问题….坑)


register_mq 通过mq异步调用方法,适合后端长时间运算或耗时的调用 

(这方法有些类似rq 、 celery异步任队列的调用方式,提供了getResult获取结果的接口)

Change Log:

Version: 2.1
1. 解决Nginx针对RPC负载均衡时,无法正常获取remote_ip

Version: 2.2
1. rq enqueue塞入任务队列时的一个bug,已经绕过解决

Version: 2.3
1. 解决了curl调用rq的get_result时出现的0x80 code异常

Version: 2.4
1. 日志及加密模式

Version: 2.5
1. 加入自定义的AES加密算法支持

Future:

1. json web token和rsa组合 2. 完善文档


测试json body的args,kwargs:

curl -H "Content-Type: application/json" -H "User-Agent: swift_rpc" -X GET -d '{"args":"[123,456]","kwargs":{"name":1}}' http://localhost:8080/test_args
curl -H "Content-Type: application/json" -H "User-Agent: swift_rpc" -X GET -d '{"args":"123"}' http://localhost:8080/test

测试选择加密模式:

curl -H "Encryption: base64" -H "Content-Type: application/json" -H "User-Agent: swift_rpc" -X GET -d '{"args": [123, 456], "kwargs": {"name": 1}}'  http://localhost:8080/test_args

测试arguments的args,kwargs:

curl -H "User-Agent: swift_rpc" -X GET -d "args=123" http://localhost:8080/test

Tornado RPC Server Usage:

#blog: xiaorui.cc
#coding:utf-8
import sys
reload(sys)
sys.setdefaultencoding("utf-8") 

import time
from tornado import gen
from swift_rpc.server import RPCServer
from swift_rpc.mq import rq_conn
from swift_rpc.mq import redis_conn
from swift_rpc.mq import fetch
from config import *
from api import *

def test(args):
    return "this is test %s"%(args)

def test_args(a,b,name='xiaorui.cc'):
    print a,b,name
    return "this is test %s %s"%(a,name)

def get_result(job_id):
    return redis_conn.hgetall(job_id)

def test_block(args):
    time.sleep(5)
    return "You said "

@gen.coroutine
def test_async(arg):
    return gen.Return("this is test_async async %s" % arg)

if __name__ == "__main__":
    server = RPCServer()
    server.register(test)
    server.register(test_args)
    server.register(get_result)
    server.register_async(test_async)
    server.register_pool(test_block)
    server.register_mq(test_mq)
    server.register_mq(go)
    server.start(RPC_HOST,RPC_PORT)

swift_rpc client Usage:

from swift_rpc.client import RPCClient

client = RPCClient('localhost:8080')
print client.test('hi')
print client.test_args('welcome','xiaorui.cc',name='nima')

懒得更新rpc的例子了,大家自己看github中的example吧。 至于性能方面?  他的前一版本我在乐视线上应用过,每秒处理1500个请求压根不是问题。 如果在线上部署,推荐使用nginx supervisord tornado (swift_rpc) 方案。其实我以前针对这个rpc开发了一个类似supervisord的服务进程管理程序,有机会也开源了…. 


希望大家多多的star….  有bug提出来…


大家觉得文章对你有些作用! 如果想赏钱,可以用微信扫描下面的二维码,感谢!
另外再次标注博客原地址  xiaorui.cc

发表评论

邮箱地址不会被公开。 必填项已用*标注