所有连接的创建工作都由OutgoingConnectionFactory完成
OutgoingConnectionFactory的factory方法为create(EndpointI[] endps,boolean hasMore,EndpointSelectionType selType,CreateConnectionCallback callback)
这是一个异步方法,CreateConnectionCallback为异步的回调对象,连接创建成功后回调该对象。
整个创建过程如下:
1。调用findConnectionByEndpoint方法,看看对应的Endpoint是否创建好的connection可用,如果可用则马上callback
2。没有可用connection,创建ConnectCallback对象,ConnectCallback对象负责后继的connection的创建过程
3。ConnectCallback调用getConnectors()方法,这个方法首先调用_factory.incPendingConnectCount()来计算以免connection还没有创建完成OutgoingConnectionFactory对象就被destory掉。
接下调用ConnectCallback的nextEndpoint()方法,这个方法迭代出一个Endpoint,然后调用Endpoint的connectors_async()方法
connectors_async()方法调用EndpointHostResolver.resolve()方法
EndpointHostResolver是一个单独的线程,线程循环如下:
从resolver队列里面取一个需要resolver的对象出来
调用Endpoint.connectors()方法
调用ConnectCallback.connectors()方法
while(true){
ResolverEntry resolve = (ResolverEntry)_queue.removeFirst();
Endpoint endpoint = resolve.endpoint;
List list = endpoint.connectors(Listaddresses);
ConnectCallback cb = resolve.callback;
cb.connectors(list);
}
这里重点是ConnectCallback的connectors(List cons)方法,这个方法由Resolve线程回调,函数本身迭代cons列表集合,迭代时如果有Endpoint怎继续调用nextEndpoint()方法,如果没有Endpoint则表示迭代完成,这个时候调用getConnection()方法开始尝试获取一个connection
getConnection()方法首先还是委托OutgoingConnectionFactory的getConnection()方法来获取连接,
OutgoingConnectionFactory中的重要数据结构
OutgoingConnectionFactory有下面两个字段:
Map _connections 维护一个ConnectorInfo建立的所有ConnectionI,用于根据ConnectorInfo查找连接
Map _connectionsByEndpoint 维护一个Endpoint建立的所有ConnectionI,用户根据Endpoint查找连接
Map _pending 用户根据ConnectorInfo查找连接,一旦ConnectorInfo的连接建立完成,则回调Set里面的所有对象
OutgoingConnectionFactory的findConnection(List)方法描述
循环迭代List集合{
如果ConnectorInfo在pending列表中,continue;
如果_connections map集合中没有,continue;
迭代_connections map中对应key的value List{
如果ConnectionI是激活的,则返回ConnectionI
}
返回null
OutgoingConnectionFactory的getConnection(List connectors,ConnectCallback cb,BooleanHolder compress)方法描述
这个方法根据传进来的connectors参数找到一条对应连接即可。
while(true){
调用findConnection(List)看看是否有创建好的ConnectionI,找到就返回该ConnectionI
如果在_pending列表里面有,则说明已经有其他线程在创建连接了,返回null,等连接成功了回调ConnectCallback对象
如果_pending列表里面没有,则开始调用ConnectorCallback的nextConnector()创建一条连接。
}
ConnectCallback方法的nextConnector()方法委托OutgoingConnectionFactory的createConnection方法开始真正的连接创建工作。
createConnection方法很简单:
实例化一个ConnectionI对象,然后把ConnectionI对象放到_connections和_connectionsByEndpoint集合
然后调用ConnectionI的start方法
现在来讲讲创建连接都有那些回调吧
首先是ConnectRequestHandler,实现了Reference.GetConnectionCallback接口
GetConnectionCallback
setConnection(ConnectionI connection)
setException(LocalException ex)
这个接口的回调是在连接创建好后被callback setConnection
ConnectRequestHandler的connect方法调用_reference.getConnection(GetConnectionCallback callback)去获取连接,如果没有RouterInfo,reference.getConnection方法则继续调用getConnectionNoRouterInfo(GetConnectionCallback callback)方法,这个方法则继续调用createConnection(Endpoint[],GetConnectionCallback callback)方法,这个方法继续把调用委托给OutgoingConnectionFactory的create(Endpoint[],boolean,int,CreateConnectionCallback)方法,现在又看到了一个新的回调接口
CreateConnectionCallback
setConnection(Ice.ConnectionI)
setException(LocalException ex)
这个接口和GetConnectionCallback一模一样,对ConnectRequestHandler他不负责创建接口,所以叫GetConnectionCallback,而OutgoingConnectionCallback负责创建接口,所以叫CreateConnectionCallback。
这里的CreateConnectionCallback接口实现很简单就是调用GetConnectionCallback的对应接口方法,继续OutgoingConnectionFactory的create方法create(EndpointI[] endpts, boolean hasMore,Ice.EndpointSelectionType selType,CreateConnectionCallback callback),这个方法首先findConnectionByEndpoint去找一个连接,找到就马上回调callback,如果没有找到则实例化一个ConnectCallback对象,这个对象又引用了CreateConnectionCallback,就是说ConnectCallback创建完连接后,再回调CreateConnectionCallback.
整个调用栈如下:
ConnectRequestHandler.connect()
Reference.getConnection(GetConnectionCallback callback)
Reference.getConnectionNoRouterInfo()
Reference.createConnection()
OutgoingConnectionFactory.create()
ConnectCallback.getConnectors()
一个ObjectPrx对应一个Reference但不对应一条连接,一个Endpoint对应一条连接。
多个ObjectPrx可以对应同一个Reference.
一个ObjectPrxy都有一个Delegate,Delegate也需要一个Setup过程,Delegate都有一个RequestHandler对象,RequestHandler则启动链接的创建,具体从Reference.getConnection()函数开始。
Reference.getConnection函数被重载为下面两个函数:
getConnection(boolean comp);
getConnection(GetConnectionCallback callback);
从这两个函数开始,产生了2个分支来创建一条链接
分支一:getConnection(boolean comp);==>createConnection(EndpointI[] allEndpoints,boolean comp);==>(Connection|返回值)OutgoingConnectionFactory.create(EndpointI[] endpts, boolean hasMore,Ice.EndpointSelectionType selType, Ice.BooleanHolder compress)
这条分支创建连接是阻塞的。
分支二:getConnection(GetConnectionCallback callback);==>createConnection(EndpointI[] allEndpoints,GetConnectionCallback callback);==>(void)OutgoingConnectionFactory.create(EndpointI[] endpts, boolean hasMore,Ice.EndpointSelectionType selType, CreateConnectionCallback callback);
这条分支创建连接是非阻塞的,所以需要Callback
但2个分支在创建连接时都会先看看本地有没有对特定的Endpoint已经建立好的连接,如果有的话,则不管你是否设置了CacheConnection都会然会已经建立好的连接,不会去重新创建。
建立好的连接是存放在以Endpoint为key的HashMap里面,所以如果想每次都去创建新的连接的一个技巧就是改变Endpoint,Endpoint的hashcode函数被override,修改Endpoint的connectionId属性就会影响
hashcode值。
Ice3.3.1 First Connection来自哪里
上一篇:假如有这样的异性朋友真不错!下一篇:《暖暖》刘备孔明版

心情分类
推荐日记
分享排行