part -- 外挂
1.dubbo借助spring的schema启动和初始化
1.1 spring扫描所有jar下META-INF的spring.handlers和spring.schemas。
1.2 运行spring.handlers下定义的DubboNamespaceHandler的init方法。
1.3 spring加载xml,执行DubboBeanDefinitionParser的parse方法,通过RootBeanDefinition将serviceBean暴露给spring。(实际调用AutowireCapableBeanFactory.registerBeanDefinition)
1.4 serviceBean实现了BeanNameAware接口,自动注入spring中的单例name。

part -- 服务暴露(生产者)
2.dubbo服务暴露
2.1 serviceBean实现了ApplicationListener,在bean初始化时触发onApplicationEvent方法,调用serviceConfig的export方法。
2.2 serviceConfig初始化,先初始化静态变量protocol和proxyFactory。
getExtensionLoader.getExtensionLoader ->getAdaptiveExtension->createAdaptiveExtension->getAdaptiveExtensionClass->getExtensionClasses->loadExtensionClasses
->loadFile->createAdaptiveExtensionClassCode
loadFile采用的是java spi的思想,分别读取META-INF/services/,META-INF/dubbo/,META-INF/dubbo/internal/下文件进行解析。
以protocol为例,其中ProtocolFilterWrapper和ProtocolListenerWrapper是有参数为protocol构造函数的,被放到Set<Class<?>> cachedWrapperClasses(后面会用到)中。
没有protocol构造函数,但是有@Adaptive注解的,被放到Holder<Object> cachedAdaptiveInstance中。
以上都不满足的放到cachedClasses中。
createAdaptiveExtensionClassCode通过javassist字节码技术生成代理类Protocol$Adpative,ProxyFactory$Adpative。
附上两个动态类的源码。可以看到protocol默认的是dubbo,proxy默认的是javassist。
2.3 export判断是否需要延迟暴露,执行暴露方法doExport()。
2.4 doExport检查通过,调用doExportUrls
2.5 doExportUrls根据不同的协议将服务以URL(dubbo)形式暴露。
2.6 如果服务未配置成remote,则本地暴露(exportLocal),如果未配置成local,则注册服务(registryProtocol)
2.7 exportLocal:生成本地protocol(Constants.LOCAL_PROTOCOL = injvm),
proxyFactory.getInvoker StubProxyFactoryWrapper->JavassistProxyFactory.getInvoker。Wrapper.getWrappery获取服务的封装代理类(javassist动态字节码),详细参照ClassGenerator.toClass。
protocol.export ExtensionLoader.getExtension(injvm)->createExtension -> getExtensionClasses(返回cachedClasses对应的值)
接着循环cachedWrapperClasses,层层装饰(装饰模式),InjvmProtocol,ProtocolFilterWrapper,ProtocolListenerWrapper增强服务。
ProtocolFilterWrapper buildInvokerChain建立了filter链,方便开发者根据业务进行扩展。
registryProtocol export ->ProtocolFilterWrapper export-> ProtocolListenerWrapper export->dubboProtocol export。

3.netty启动
3.1 openServer netty server打开侦听服务,并缓存服务。
dubbo -> export() -> openServer() -> createServer() -> Exchangers.bind()(HeaderExchanger) -> NettyTransporter -> NettyServer.open()(编码解码采用exchange)
netty ChannelFactory(boss worker) ChannelPipeline(责任链模式) ChannelHandler(处理器) --- 反应器模式

part -- 服务引用(消费者)
4.dubbo服务引用
4.1 referenceBean实现了InitializingBean接口,在afterPropertiesSet后执行getObject()方法,调用referenceConfig的init方法。
4.2 StaticContext.getSystemContext()是dubbo全局的线程安全上下文,存放方法调用的相关信息。
4.2 createProxy,设置invoker,这里的invoker有协议默认的dubbo invoker,cluster invoker(重连机制,默认Failover,重试两次,一共三次)
返回InvokerInvocationHandler(javassist动态字节码改造后的代理,执行方法时,实际执行的是invoker的doinvoke方法)
cluster invoker的doinvoke方法会调用select(),负载均衡,默认RandomLoadBalance
4.3 获取dubbo invoker时,调用dubbo的refer,调用getClients获取ExchangeClient,默认的ExchangeClient是共享的getSharedClient。initClient默认是非延迟的,调用Exchangers.connect,最终调用HeaderExchanger.connect,调用
Transporters.connect,同生产者一样,默认的Transporters是netty。因此最终的ExchangeClient是NettyClient。
4.3 dubbo invoker doinvoke方法,ExchangeClient.request方法,结果通过future的get方法返回,get方法通过lock+while+超时控制。
4.4 ExchageClient.request最终调用的是nettyChannel
1.NettyHandler.messageReceived(ChannelHandlerContext ctx, MessageEvent e)
2.AbstractPeer.received(Channel ch, Object msg)
3.MultiMessageHandler.received(Channel channel, Object message)
4.AllChannelHandler.received(Channel channel, Object message)
5.DecodeHandler.received(Channel channel, Object message)
6.HeaderExchangeHandler.received(Channel channel, Object message)
7.DefaultFuture.received(Channel channel, Response response) //注意是static方法
DefaultFuture future = FUTURES.remove(response.getId());
if (future != null) {
future.doReceived(response);
}

http://blog.csdn.net/a19881029/article/details/51058428

spring
1. 入口ContextLoaderListener监听器,调用contextInitialized方法,ContextLoder的initWebApplicationContext,createWebApplicationContext默认创建ContextLoader.properties里的XmlWebApplicationContext,强制转换成configureAndRefreshWebApplicationContext
最终调用AbstractApplicationContext的refresh方法(前面调用了ApplicationContextInitializer的initialize,这里可以做一些spring默认规则的修改,比如id重复bean处理,spring默认覆盖)
2.

 动态生成的Protocol$Adpative.class

package com.alibaba.dubbo.rpc;

import com.alibaba.dubbo.common.extension.ExtensionLoader;

public class Protocol$Adpative implements com.alibaba.dubbo.rpc.Protocol {
public void destroy() {
throw new UnsupportedOperationException(
"method public abstract void com.alibaba.dubbo.rpc.Protocol.destroy() of interface com.alibaba.dubbo.rpc.Protocol is not adaptive method!");
} public int getDefaultPort() {
throw new UnsupportedOperationException(
"method public abstract int com.alibaba.dubbo.rpc.Protocol.getDefaultPort() of interface com.alibaba.dubbo.rpc.Protocol is not adaptive method!");
} public com.alibaba.dubbo.rpc.Invoker refer(java.lang.Class arg0, com.alibaba.dubbo.common.URL arg1)
throws java.lang.Class {
if (arg1 == null)
throw new IllegalArgumentException("url == null");
com.alibaba.dubbo.common.URL url = arg1;
String extName = (url.getProtocol() == null ? "dubbo" : url.getProtocol());
if (extName == null)
throw new IllegalStateException("Fail to get extension(com.alibaba.dubbo.rpc.Protocol) name from url("
+ url.toString() + ") use keys([protocol])");
com.alibaba.dubbo.rpc.Protocol extension = (com.alibaba.dubbo.rpc.Protocol) ExtensionLoader
.getExtensionLoader(com.alibaba.dubbo.rpc.Protocol.class).getExtension(extName);
return extension.refer(arg0, arg1);
} public com.alibaba.dubbo.rpc.Exporter export(com.alibaba.dubbo.rpc.Invoker arg0)
throws com.alibaba.dubbo.rpc.Invoker {
if (arg0 == null)
throw new IllegalArgumentException("com.alibaba.dubbo.rpc.Invoker argument == null");
if (arg0.getUrl() == null)
throw new IllegalArgumentException("com.alibaba.dubbo.rpc.Invoker argument getUrl() == null");
com.alibaba.dubbo.common.URL url = arg0.getUrl();
String extName = (url.getProtocol() == null ? "dubbo" : url.getProtocol());
if (extName == null)
throw new IllegalStateException("Fail to get extension(com.alibaba.dubbo.rpc.Protocol) name from url("
+ url.toString() + ") use keys([protocol])");
com.alibaba.dubbo.rpc.Protocol extension = (com.alibaba.dubbo.rpc.Protocol) ExtensionLoader
.getExtensionLoader(com.alibaba.dubbo.rpc.Protocol.class).getExtension(extName);
return extension.export(arg0);
}
}

动态生成的ProxyFactory$Adpative.class

package com.alibaba.dubbo.rpc;

import com.alibaba.dubbo.common.extension.ExtensionLoader;

public class ProxyFactory$Adpative implements com.alibaba.dubbo.rpc.ProxyFactory {
public java.lang.Object getProxy(com.alibaba.dubbo.rpc.Invoker arg0) throws com.alibaba.dubbo.rpc.Invoker {
if (arg0 == null)
throw new IllegalArgumentException("com.alibaba.dubbo.rpc.Invoker argument == null");
if (arg0.getUrl() == null)
throw new IllegalArgumentException("com.alibaba.dubbo.rpc.Invoker argument getUrl() == null");
com.alibaba.dubbo.common.URL url = arg0.getUrl();
String extName = url.getParameter("proxy", "javassist");
if (extName == null)
throw new IllegalStateException("Fail to get extension(com.alibaba.dubbo.rpc.ProxyFactory) name from url("
+ url.toString() + ") use keys([proxy])");
com.alibaba.dubbo.rpc.ProxyFactory extension = (com.alibaba.dubbo.rpc.ProxyFactory) ExtensionLoader
.getExtensionLoader(com.alibaba.dubbo.rpc.ProxyFactory.class).getExtension(extName);
return extension.getProxy(arg0);
} public com.alibaba.dubbo.rpc.Invoker getInvoker(java.lang.Object arg0, java.lang.Class arg1,
com.alibaba.dubbo.common.URL arg2) throws java.lang.Object {
if (arg2 == null)
throw new IllegalArgumentException("url == null");
com.alibaba.dubbo.common.URL url = arg2;
String extName = url.getParameter("proxy", "javassist");
if (extName == null)
throw new IllegalStateException("Fail to get extension(com.alibaba.dubbo.rpc.ProxyFactory) name from url("
+ url.toString() + ") use keys([proxy])");
com.alibaba.dubbo.rpc.ProxyFactory extension = (com.alibaba.dubbo.rpc.ProxyFactory) ExtensionLoader
.getExtensionLoader(com.alibaba.dubbo.rpc.ProxyFactory.class).getExtension(extName);
return extension.getInvoker(arg0, arg1, arg2);
}
} {class com.alibaba.dubbo.config.spring.extension.SpringExtensionFactory=com.alibaba.dubbo.config.spring.extension.SpringExtensionFactory@5d1275be, class com.alibaba.dubbo.common.compiler.support.JavassistCompiler=com.alibaba.dubbo.common.compiler.support.JavassistCompiler@66f03cae, class com.alibaba.dubbo.common.extension.factory.SpiExtensionFactory=com.alibaba.dubbo.common.extension.factory.SpiExtensionFactory@261ff84e} injvm://127.0.0.1/com.ihome.tf.order.service.IBenefitFoundService?anyhost=true&application=tf-order&default.retries=0&default.timeout=10000&dubbo=2.5.3&interface=com.ihome.tf.order.service.IBenefitFoundService&methods=update,clear,qryBenefitFndOrderList,qryCheckPassedBenefitList,qryBenefitFoundOrderSumInf,verify,qryBenefitFound&owner=tf&pid=1492&revision=0.0.1-SNAPSHOT&side=provider&timestamp=1457518110700

动态生成的Wrapper1.class

package com.alibaba.dubbo.common.bytecode;

import com.prepay.dto.ShareRulesReq;
import com.prepay.service.IOutShareService;
import java.lang.reflect.InvocationTargetException;
import java.util.Map; public class Wrapper1 extends Wrapper
implements ClassGenerator.DC
{
public static String[] pns;
public static Map pts;
public static String[] mns;
public static String[] dmns;
public static Class[] mts0;
public static Class[] mts1;
public static Class[] mts2; public String[] getPropertyNames()
{
return pns;
} public boolean hasProperty(String paramString)
{
return jdField_pts_of_type_JavaUtilMap.containsKey(paramString);
} public Class getPropertyType(String paramString)
{
return (Class)jdField_pts_of_type_JavaUtilMap.get(paramString);
} public String[] getMethodNames()
{
return mns;
} public String[] getDeclaredMethodNames()
{
return dmns;
} public void setPropertyValue(Object paramObject1, String paramString, Object paramObject2)
{
try
{
IOutShareService localIOutShareService = (IOutShareService)paramObject1;
}
catch (Throwable localThrowable)
{
throw new IllegalArgumentException(localThrowable);
}
throw new NoSuchPropertyException("Not found property \"" + paramString + "\" filed or setter method in class com.ihome.prepay.service.IOutShareService.");
} public Object getPropertyValue(Object paramObject, String paramString)
{
try
{
IOutShareService localIOutShareService = (IOutShareService)paramObject;
}
catch (Throwable localThrowable)
{
throw new IllegalArgumentException(localThrowable);
}
throw new NoSuchPropertyException("Not found property \"" + paramString + "\" filed or setter method in class com.ihome.prepay.service.IOutShareService.");
} public Object invokeMethod(Object paramObject, String paramString, Class[] paramArrayOfClass, Object[] paramArrayOfObject)
throws InvocationTargetException
{
IOutShareService localIOutShareService;
try
{
localIOutShareService = (IOutShareService)paramObject;
}
catch (Throwable localThrowable1)
{
throw new IllegalArgumentException(localThrowable1);
}
try
{
if ((!"queryShareRuleDetail".equals(paramString)) || (paramArrayOfClass.length == 1))
return localIOutShareService.queryShareRuleDetail((String)paramArrayOfObject[0]);
if ((!"queryShareRuleList".equals(paramString)) || (paramArrayOfClass.length == 1))
return localIOutShareService.queryShareRuleList((ShareRulesReq)paramArrayOfObject[0]);
if ((!"querySharePullDownList".equals(paramString)) || (paramArrayOfClass.length == 0))
return localIOutShareService.querySharePullDownList();
}
catch (Throwable localThrowable2)
{
throw new InvocationTargetException(localThrowable2);
}
throw new NoSuchMethodException("Not found method \"" + paramString + "\" in class com.ihome.prepay.service.IOutShareService.");
}
}

<以上内容由同事提供>

如果想了解更多Dubbo源码的知识,请移步 Dubbo源码解读——通向高手之路 的视频讲解:
http://edu.51cto.com/sd/2e565

dubbo工作原理的更多相关文章

  1. 通俗易懂描述dubbo工作原理

    关于dubbo的描述就不再赘述,直接进入主题,那就是dubbo的工作原理.dubbo分为服务提供者和服务消费者,主要的工作内容有以下几点:提供者暴露服务.消费者引入服务.提供者和消费者和注册中心之间的 ...

  2. Dubbo工作原理,集群容错,负载均衡

    Remoting:网络通信框架,实现了sync-over-async和request-response消息机制. RPC:一个远程过程调用的抽象,支持负载均衡.容灾和集群功能. Registry:服务 ...

  3. dubbo工作原理(3)

    dubbo主要核心部件 Remoting:网络通信框架,实现了sync-over-async和request-response消息机制. RPC:一个远程过程调用的抽象,支持负载均衡.容灾和集群功能. ...

  4. 说一下Dubbo 的工作原理?注册中心挂了可以继续通信吗?

    面试题 说一下的 dubbo 的工作原理?注册中心挂了可以继续通信吗?说说一次 rpc 请求的流程? 面试官心理分析 MQ.ES.Redis.Dubbo,上来先问你一些思考性的问题.原理,比如 kaf ...

  5. dubbo的工作原理

    dubbo工作原理 第一层:service层,接口层,给服务提供者和消费者来实现的 第二层:config层,配置层,主要是对dubbo进行各种配置的 第三层:proxy层,服务代理层,透明生成客户端的 ...

  6. 1.说一下的 dubbo 的工作原理?注册中心挂了可以继续通信吗?说说一次 rpc 请求的流程?

    作者:中华石杉 面试题 说一下的 dubbo 的工作原理?注册中心挂了可以继续通信吗?说说一次 rpc 请求的流程? 面试官心理分析 MQ.ES.Redis.Dubbo,上来先问你一些思考性的问题.原 ...

  7. 面试系列22 dubbo的工作原理

    (1)dubbo工作原理 第一层:service层,接口层,给服务提供者和消费者来实现的 第二层:config层,配置层,主要是对dubbo进行各种配置的 第三层:proxy层,服务代理层,透明生成客 ...

  8. 说一下的dubbo的工作原理?注册中心挂了可以继续通信吗?

    (1)dubbo工作原理 第一层:service层,接口层,给服务提供者和消费者来实现的 第二层:config层,配置层,主要是对dubbo进行各种配置的 第三层:proxy层,服务代理层,透明生成客 ...

  9. 分布式的几件小事(二)dubbo的工作原理

    1.dubbo的工作原理 ①整体设计 图例说明: 图中左边淡蓝背景的为服务消费方使用的接口,右边淡绿色背景的为服务提供方使用的接口,位于中轴线上的为双方都用到的接口. 图中从下至上分为十层,各层均为单 ...

随机推荐

  1. 问题:C++ 删除数组指针实用 delete []变量 汇编怎么实现的?

    问题:C++ 删除数组指针实用  delete []变量    汇编怎么实现的?

  2. SILVERLIGHT 应急卫生模拟演练项目之loading界面实现

    第一次在博客园写文章 俺是菜鸟 有不足之处还请大佬们多多指教 第一次也不知道该写啥 俺就拿自己最近做的一个项目 来细说吧 俺们公司是做医疗卫生方面的  其中有一块涉及到应急卫生模拟演练方面 这块分到我 ...

  3. LPTHW 笨办法学python 33章

    32-33章节 将for-loop和while-loop循环的. 俩种句法就不说了.简单说下个人对于for和while的理解. 我觉得他learn python the hard way这里的写法是, ...

  4. 【转】家庭wifi覆盖指导

    网址:家庭wifi覆盖指导 私以为,目前民用 wifi 路由器市场已经完全走上了邪路.天线越来越大,发射功率越做越高.都敢冒着法律的风险使用大大超过 100mW 的发射功率了.且不论巨大的发射功率可能 ...

  5. Notes of 大数据智能

    资料 刘知远 等. 大数据智能:互联网时代的机器学习和自然语言处理技术. 北京:电子工业出版社. 2016. 1 深度学习--机器大脑的结构 深度学习(Deep Learning)的两个方面: 神经网 ...

  6. MySql 中游标,事务,终止存储过程方法总结

    最近在项目开发中,有段逻辑处理,需要在网站,app,后台分别运行,这样给后期的维护带来了很大的不方便,容易遗漏app端或者后台,所以讲java代码转换成存储过程,把逻辑处理写在了mysql端,其中遇到 ...

  7. 第七章:LED将为我闪烁:控制发光二极管

        在之前章节了解到Linux驱动程序可以控制软硬件,可以实现软硬件之间的交互.在这章我们学习LED驱动的实现原理.Linux内核提供了多个与I/O内存交互的函数可以实现控制硬件.    编写LE ...

  8. git的使用,通过git上传修改工程

    一:下载git,https://git-scm.com/downloads(若下载速度慢,可下载百度下的)接下来,默认配置,一直next 二:在github上注册账号,并新建一个项目test(英文有点 ...

  9. python ABC

    因为项目需要,总是会有各种各样要重命名文件的场合,manual的方法当然不可取,bat的方法又感觉不够强大,所以就从零开始学python,就为了能够自动批量修改文件名,倒腾了一个周六,总算可以了 :) ...

  10. [NOIP2011] 聪明的质检员(二分答案)

    题目描述 小T 是一名质量监督员,最近负责检验一批矿产的质量.这批矿产共有 n 个矿石,从 1到n 逐一编号,每个矿石都有自己的重量 wi 以及价值vi .检验矿产的流程是: 1 .给定m 个区间[L ...