ICE connection问答

ICE connection问答

hanlray@hotmail.com

Revision: 1.0 Date: 2005/07/31


对于分布式的应用,人们一般都希望把工作集中的应用本身的逻辑上,而不必关心像连接、数据传输格式这样的细节,最好的效果就是可以把它当成一个非分布式的应用来设计编码,由框架或其他技术来处理应用的分布式问题,这样不仅使分布式应用的开发变得简单,同时也提高了应用的灵活性,正符合Martin Flower所说的:“记住分布式计算机的第一法则:不要分布你的对象”。ICE就是解决这种问题的中间件之一,相比同类技术如CORBA和DCOM,其主要优势在于:

  • 简单。易学易用。
  • 高效。看其测试数据比CORBA要高不少,更不用说Web Service之流了。
  • 开源。代码水平高,值得借鉴。

然而既然牵涉到网络通讯,对网络连接的管理必然是个重要的部分,ICE是怎样管理连接的?下面以问答的方式 作了一些总结,例子当然是ICE版的Hello world,这里暂且只考虑客户端:

Slice:
module Demo
{

interface Hello
{
	nonmutating void sayHello();
	idempotent void shutdown();
};

};

Client:
Ice::CommunicatorPtr communicator = Ice::initialize(argc, argv);
Ice::ObjectPrx base = communicator->stringToProxy(proxy);
HelloPrx hello = HelloPrx::checkedCast(base);
hello->sayHello();

Q:连接在何时建立?

A:在HelloPrx::checkedCast时。这个函数除了建立连接之外,还会向服务器发送一条消息,消息包含目标接口的ID,这里是字符串::Demo::Hello,若对方是正确的服务器,该转换就成功,否则转换失败。

Q:连接可以重用吗?

A:只要有可能,ICE总会重用存在的连接。事实上,ICE没有对外提供创建新连接的接口,其内部通过一个Connection Factory实现了连接的重用,当然重用是有条件的,当为某个proxy建立连接时,如果某个已存在连接满足下列条件,ICE就会重用连接它:

  • 该连接的远程端点匹配proxy的端点之一
  • 该连接被创建这个proxy的Communicator创建
  • 该连接匹配该proxy的配置。timeout值是个重要的匹配项

Q:当连接意外断开后能自动重连吗?

A:能。事实上这是ICE中operation retry机制的side effect。配置属性Ice.RetryIntervals用来配置当一个操作失败时自动重试的次数和重试的间隔时间,对slice中定义的每个非local方法,生成的proxy代码中都会有一个循环,比如这里的sayHello方法,生成的C++实现是:

void
IceProxy::Demo::Hello::sayHello(const ::Ice::Context& __ctx)
{
	int __cnt = 0;
	while(true)
	{
	try
	{
	    ::IceInternal::Handle< ::IceDelegate::Ice::Object> __delBase = __getDelegate();
	    ::IceDelegate::Demo::Hello* __del = dynamic_cast< ::IceDelegate::Demo::Hello*>(__delBase.get());
	    __del->sayHello(__ctx);
	    return;
	}
	catch(const ::IceInternal::NonRepeatable& __ex)
	{
	    __handleException(*__ex.get(), __cnt);
	}
	catch(const ::Ice::LocalException& __ex)
	{
	    __handleException(__ex, __cnt);
	}
	}
}

当连接意外断掉后,__del->sayHello抛出的异常会被第二个catch语句抓住,对该异常的处理会把该Proxy对象内部保存的delegate(类型是::IceDelegate::Ice::Object)指针置0, 这样当循环再次到__getDelegate时,就会重新创建一个delegate,而在创建delegate的过程中就会重新建立连接。对连接次数和连接间隔时间的控制都是在__handleException函数中完成的。

Q:怎么处理长时间不用的连接?

A:如果你希望自动关闭长时间不用的连接来节省资源,可以利用ICE的ACM(Active Connection Management)机制。配置属性Ice.ACM.Client用来设置当一个outgoing连接多长时候没有活动时就关闭它;Ice.ACM.Server用来设置当一个Incoming 连接多长时间没有活动时就关闭它。当然,关闭这样的连接对应用是不会产生影响的,在需要的时候连接会重新建立。ACM对应用是可选的,将那两个属性设置为 0,ACM就不会起作用了。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值