Python中实现远程调用(RPC、RMI)简单例子


Posted in Python onApril 28, 2014

远程调用使得调用远程服务器的对象、方法的方式就和调用本地对象、方法的方式差不多,因为我们通过网络编程把这些都隐藏起来了。远程调用是分布式系统的基础。

远程调用一般分为两种,远程过程调用(RPC)和远程方法调用(RMI)。

RPC

RPC属于函数级别的远程调用,其多是通过HTTP传输数据,数据形式有XML、JSON、序列化数据等。在此,用python做一个xml-rpc的示例。 先给服务器端server.py:

from SimpleXMLRPCServer import SimpleXMLRPCServer   
def add(x, y):
    return x + y    
if __name__ == '__main__':
    s = SimpleXMLRPCServer(('127.0.0.1', 8080))
    s.register_function(add)
    s.serve_forever()
s是一个绑定了本地8080端口的服务器对象,register_function()方法将函数add注册到s中。serve_forever()启动服务器。 再给个客户端client.py:
from xmlrpclib import ServerProxy
if __name__ == '__main__':
    s = ServerProxy("http://127.0.0.1:8080")
    print s.add(3,4)

现在,运行server.py,然后运行client.py,client.py所在的console会输出7。

我们用wireshark看一下这期间传递的数据是什么样子的,请求的数据:

<?xml version='1.0' ?>
<methodCall>
    <methodName>
        add
    </methodName>
    <params>
        <param>
            <value>
                <int> 3 </int>
                </value>
        </param>
        <param>
            <value>
                <int> 4 </int>
            </value>
        </param>
    </params>
</methodCall>

响应的数据:
<?xml version='1.0' ?>
<methodResponse>
    <params>
        <param>
            <value>
                <int> 7 </int>
            </value>
        </param>
    </params>
</methodResponse>

好吧,言简意赅,不做赘述。

RMI

RMI意为远程方法调用,粒度比RPC要大,因为它的基本单位是对象。其大致思路是这样的:创建RMI服务器对象,将实例化的某个对象以指定的服务名称(也可以是多个对象,但是服务名称不应相同)注册到RMI服务器对象中,之后启动RMI服务器。服务器等待客户端发送的数据(包括服务名称、函数名、参数),将处理结果返回给客户端。 Pyro4是一个基于python的RMI实现,下面我们用Pyro4创建一个RMI服务器,请看server2.py:

import Pyro4
class GreetingMaker(object):
    def get_fortune(self, name):
        return "Hello, {0}. \n" .format(name)
greeting_maker=GreetingMaker()
daemon=Pyro4.Daemon()                
uri=daemon.register(greeting_maker)   
print "Ready. Object uri =", uri      
daemon.requestLoop()
uri变量是Pyro4用自己的方法为greeting_maker对象生成的uri,其中包括套接字以及为greeting_maker生成的唯一的id。这个id相当于服务名称,当然也可以指定更易懂的服务名称。下面是客户端client2.py:
import Pyro4
uri=raw_input(" Pyro uri : ").strip()
name=raw_input("Your name: ").strip()
greeting_maker=Pyro4.Proxy(uri)        
print greeting_maker.get_fortune(name)

这其中要输入的uri也就是server2.py生成的uri。通过给Pyro4.Proxy传递greeting_maker的uri,可以认为和服务器端的greeting_maker建立的连接,然后调用greeting_maker的get_fortune()方法。如果name是letian,那么print greeting_maker.get_fortune(name)的结果是Hello, letian.。
Python 相关文章推荐
python生成验证码图片代码分享
Jan 28 Python
Pyhton中单行和多行注释的使用方法及规范
Oct 11 Python
python中reload(module)的用法示例详解
Sep 15 Python
Pandas:Series和DataFrame删除指定轴上数据的方法
Nov 10 Python
详解分布式任务队列Celery使用说明
Nov 29 Python
详解python 3.6 安装json 模块(simplejson)
Apr 02 Python
Python openpyxl读取单元格字体颜色过程解析
Sep 03 Python
pygame实现俄罗斯方块游戏(基础篇1)
Oct 29 Python
调整Jupyter notebook的启动目录操作
Apr 10 Python
python 常见的反爬虫策略
Sep 27 Python
Python监听剪切板实现方法代码实例
Nov 11 Python
Python中super().__init__()测试以及理解
Dec 06 Python
Python的ORM框架SQLObject入门实例
Apr 28 #Python
django自定义Field实现一个字段存储以逗号分隔的字符串
Apr 27 #Python
python监控网卡流量并使用graphite绘图的示例
Apr 27 #Python
python抓取网页图片示例(python爬虫)
Apr 27 #Python
python实现sublime3的less编译插件示例
Apr 27 #Python
python中的实例方法、静态方法、类方法、类变量和实例变量浅析
Apr 26 #Python
Python设计模式之单例模式实例
Apr 26 #Python
You might like
实现树状结构的两种方法
2006/10/09 PHP
php对二维数组按指定键值key排序示例代码
2013/11/26 PHP
JavaScript中的Screen屏幕对象
2008/01/16 Javascript
iframe子父页面调用js函数示例
2013/11/07 Javascript
Nodejs+express+html5 实现拖拽上传
2014/08/08 NodeJs
jQuery实现HTML5 placeholder效果实例
2014/12/09 Javascript
node.js中的require使用详解
2014/12/15 Javascript
javascript笛卡尔积算法实现方法
2015/04/08 Javascript
jQuery实现鼠标滑向当前图片高亮显示并且其它图片变灰的方法
2015/07/27 Javascript
web前端开发JQuery常用实例代码片段(50个)
2015/08/28 Javascript
详解JavaScript时间格式化
2015/12/23 Javascript
基于JS代码实现导航条弹出式悬浮菜单
2016/06/17 Javascript
JS去除重复并统计数量的实现方法
2016/12/15 Javascript
详解Angular路由 ng-route和ui-router的区别
2017/05/22 Javascript
[js高手之路]从原型链开始图解继承到组合继承的产生详解
2017/08/28 Javascript
理解 JavaScript EventEmitter
2018/03/29 Javascript
JavaScript时间与时间戳的转换操作实例分析
2018/12/07 Javascript
vue使用swiper实现左右滑动切换图片
2020/10/16 Javascript
JavaScript大数相加相乘的实现方法实例
2020/10/18 Javascript
分析Python编程时利用wxPython来支持多线程的方法
2015/04/07 Python
python学生管理系统代码实现
2020/04/05 Python
浅谈Pandas中map, applymap and apply的区别
2018/04/10 Python
opencv python 基于KNN的手写体识别的实例
2018/08/03 Python
Python3.5装饰器原理及应用实例详解
2019/04/30 Python
django项目中使用手机号登录的实例代码
2019/08/15 Python
Python使用psutil获取进程信息的例子
2019/12/17 Python
构建高效的python requests长连接池详解
2020/05/02 Python
使用HTML5 Canvas绘制直线或折线等线条的方法讲解
2016/03/14 HTML / CSS
美国知名的网上鞋类及相关服装零售商:Shoes.com
2017/05/06 全球购物
RUIFIER官网:英国奢侈高级珠宝品牌
2020/06/12 全球购物
仓库管理专业个人的自我评价
2013/12/30 职场文书
招聘专员岗位职责
2014/03/07 职场文书
年会主持人开场白台词
2015/05/29 职场文书
地震捐款简报
2015/07/21 职场文书
员工手册董事长致辞
2015/07/29 职场文书
趣味运动会广播稿
2015/08/19 职场文书