从0到1,记一次dubbo服务的demo创建历程

  新公司新气象,刚来一个周,捋了捋代码发现技术和之前的项目基本不相同,微服务用的dubbo,为了尽快上手,自己在看文档的同时模仿公司的框架写了个demo,结果问题百出,从0到1的过程走的很艰难,记下来以次为鉴。

先说下框架构成:

   分为消费者和生产者两个项目,消费者为一个web项目,通过tomcat启动,生产者为java项目,通过jar包启动。

  为了让结构更加清晰,消费者命名api,写controller层代码,生产者项目将接口和实现类分开,接口和实体类写在customer里,实现类写在producer里,并且通过一个父级项目关联,结构如下:

消费者:

生产者:

OK项目建完,开始写代码,模拟一个业务场景,通过顾客Id查询顾客姓名,所以在customer中建立一个类Customer,赋予两个属性customerId和customerName,consumer里写service接口,provider里写serviceImpl和dao,并且provider中也需要实体类,所以记得在provider的pom文件中引入consumer,结构如下

consumer项目:

Customer类代码:

public class Customer implements Serializable {

    private static final long serialVersionUID = -8252366926456004984L;

    private  Integer customerId;

    private  String  customerName;

    public Integer getCustomerId() {
        return customerId;
    }

    public void setCustomerId(Integer customerId) {
        this.customerId = customerId;
    }

    public String getCustomerName() {
        return customerName;
    }

    public void setCustomerName(String customerName) {
        this.customerName = customerName;
    }
}

QueryCustomerService接口代码:

public interface QueryCustomerService {
        /**
         * 查询姓名
         * @param customer
         * @return
         */
        public String queryCustomerNameByCustomerId(Customer customer);

}

provider:

QueryCustomerImpl代码:

@Service("queryCustomerImpl")
public class QueryCustomerImpl implements QueryCustomerService {

    @Autowired
    QueryCustomerDao queryCustomerDao;

    @Override
    public String queryCustomerNameByCustomerId(Customer customer) {
        String customerName=queryCustomerDao.queryCustomer(customer.getCustomerId());
        return customerName+"====over";
    }

}

住:@Service用的是Spring的注解

QueryCustomerDao代码:

@Repository("queryCustomerDao")
public class QueryCustomerDao {
    public static Map<Integer,String> map=new HashMap<>();
    static {
           map.put(1,"wahaha");
           map.put(2,"xiaoxixi");
    }
    public String queryCustomer(Integer customerId){
        return map.get(customerId);
    }

dao在map里存放了两个数据,模拟数据库。

这样一来,生产者端代码写完了,接下来就是添加配置文件。

首先是consumer项目,配置文件很简单,就一个consumer.xml。

<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
       http://code.alibabatech.com/schema/dubbo http://code.alibabatech.com/schema/dubbo/dubbo.xsd">
    <dubbo:application name="dubbo-consumer"/>
    <!--向 zookeeper 订阅 provider 的地址,由 zookeeper 定时推送-->
    <dubbo:registry protocol="zookeeper" address="127.0.0.1:2181"/>
    <!--使用 dubbo 协议调用定义好application.xml的QueryCustomerService 接口-->
    <dubbo:reference id="queryCustomerService" interface="com.jk.xym.service.QueryCustomerService"/>
</beans>

provider里面的配置文件稍微多一点,因为还需要spring的配置文件:

dubbo项目中的spring配置文件和provider的配置文件要写在resources/META-INF下,dubbo会默认读取该路径下的配置。

application.xml:主要配置一下扫描的包路径,还有需要读取的dubbo的配置文件路径。

<context:component-scan base-package="com.jk.xym" />

   <context:property-placeholder location="classpath*:dubbo.properties" ignore-unresolvable="true" file-encoding="UTF-8"/>
   <!--<context:property-placeholder location="classpath*:*.properties,classpath:redis.properties" ignore-unresolvable="true" />-->

<!-- 启用 aspectj 动 态代理 -->
<aop:aspectj-autoproxy proxy-target-class="true" />

provider.xml:dubbo关键配置之一。

<!--定义了提供方应用信息,用于计算依赖关系;在 dubbo-provider会显示这个名字,方便辨识-->
<dubbo:application name="dubbo-provider" owner="programmer" organization="dubbo" />
<!--使用 zookeeper 注册中心暴露服务,注意要先开启 zookeeper,这里配置的address是集群模式,个人用修改为本地:localhost:2181-->
<dubbo:registry port="8086" protocol="zookeeper" address="localhost:2181"/>
<!-- 用dubbo协议在20880端口暴露服务 -->
<dubbo:protocol name="dubbo" port="20880" />
<!--使用 dubbo 协议实现定义好的 QueryCustomerService 接口,黑色字体部分修改为创建类的包目录 -->
<dubbo:service interface="com.jk.xym.service.QueryCustomerService" ref="queryCustomerImpl" protocol="dubbo" >
    <dubbo:method name="queryCustomerNameByCustomerId" retries="0"/>
</dubbo:service>

dubbo.properties :dubbo的关键配置之一。

#超时时间(ms)
dubbo.service.timeout=10000
#名称
dubbo.application.name=dubbo-demo
dubbo.application.owner=programmer
#链接zk地址
dubbo.registry.address=zookeeper://localhost:2181

#监控协议
dubbo.monitor.protocol=registry
#协议名称
dubbo.protocol.name=dubbo
#协议端口
dubbo.protocol.port=20880
#负载方式
dubbo.service.loadbalance=roundrobin

#以下是jvm启动参数配置
java_class=com.alibaba.dubbo.container.Main
java_mem_opts= -server -Xmx2g -Xms2g -Xmn256m -XX:PermSize=128m -Xss256k -XX:+DisableExplicitGC -XX:+UseConcMarkSweepGC -XX:+CMSParallelRemarkEnabled -XX:+UseCMSCompactAtFullCollection -XX:LargePageSizeInBytes=128m -XX:+UseFastAccessorMethods -XX:+UseCMSInitiatingOccupancyOnly -XX:CMSInitiatingOccupancyFraction=70
java_opts= -Djava.awt.headless=true -Djava.net.preferIPv4Stack=true

logback.xml为输出日志配置,非必须配置。这里我就不附图了。

配置文件结束,那么最后还剩pom文件,pom文件就不附图了,说下关键的配置吧。

provider模块:

1.spring相关配置

2.dubbo相关配置(com.alibaba.dubbo)

3.zookeeper相关配置 (包含com.101tec.zkclient ,org.apache.zookeeper)

4.处理java字节码的类库 (org.javassist,如果没有该jar包,在消费端拿不到生产端注入的实体类)

5.maven插件配置(maven-jar-plugin,maven-shade-plugin这个插件很好用,会自动的给你把依赖包打上,并且重名的配置会自动追加,省去了很多麻烦,具体的使用方法很多博客里都有,这就不写了,里面有个mainclass这个标签一定要写,这里做个铺垫,等不及的同学可以直接划到结尾。)

6.netty(dubbo底层用了netty框架)

其他的就缺什么配什么吧

consumer模块:

这个就比较简单,配置一下spring就好了。

到此,我们的生产者端就配置完了,接下来去搞消费者端。

=======================================分割线

消费者端:

作为一个消费者,目的就是消费生产者端提供的数据,所以消费者端写一个controller就好了,代码如下:

@Controller
public class QueryCustomerController {

    @Autowired
    QueryCustomerService queryCustomerService;

    @RequestMapping("/queryCustomerName")
    @ResponseBody
    public String queryCustomerName(Integer customerId){
        Customer customer=new Customer();
        customer.setCustomerId(customerId);
       String CustomerName= queryCustomerService.queryCustomerNameByCustomerId(customer);
       System.out.println("123");
       return CustomerName;
    }
}

之后是配置相关的文件,因为消费者端是个web项目,所以就按照web项目来配置,除了web.xml,主要配置文件还有一下这些

我们一个一个来,首先是

dubbo.properties:这个简单配置一下链接zk的地址就好了

dubbo.registry.address=zookeeper://localhost:2181

dubbo-api:dubbo主要配置之一

<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:dubbo="http://code.alibabatech.com/schema/dubbo"
       xmlns="http://www.springframework.org/schema/beans"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
      http://code.alibabatech.com/schema/dubbo http://code.alibabatech.com/schema/dubbo/dubbo.xsd">

    <!--dubbo服务相关配置-->
    <dubbo:application name="dubbo-api" owner="xym-web" organization="dubbox"/>
    <dubbo:registry address="${dubbo.registry.address}"/>
    <dubbo:protocol name="dubbo" />

    <!--配置需要调用的接口,这个可以参考上面consumer里面的配置-->
   <dubbo:reference id="queryCustomerService" interface="com.jk.xym.service.QueryCustomerService" check="false"  timeout="30000" />

</beans>

spring-context.xml 和spring-mvc.xml:spring常规配置,因为懒,就不附图了,需要的小伙伴可以自行百度

有一点需要注意的是在spring-context.xml里面引入其他的配置文件记得用import标签,ex:

<import resource="dubbo-api.xml"/>

接下来是web.xml,也是常规配置。

最后就是pom文件,这里用到的pom 与我上面提到的关键pom保持一致即可。

最后附上一张api的目录图:

接下来就是分别打成jar包和war包,启动就\(^o^)/~了~~~

等等,这就完事了?好像少了点什么

=======================================分割线

让我们把目光拉回到生产者端

整个项目里面好像没有main方法,这里也是我纳闷了很久的地方,之前用springboot也好,或者普通的java项目也好,打成jar包,那肯定得需要一个程序的入口,仔细查了查dubbo的启动方式,发现dubbo除了可以通过web启动,main方法启动外,框架里面还有一个人家已经准备好的Main类,

com.alibaba.dubbo.container.Main

这个类里面已经写好了调用spring的方法,所以打成jar包之后,如果我们之前配置了mainclass的话直接java -jar xxx.jar就好了

如果没有配置,那我们指定一下main方法所在的类,启动指令为:

java -cp xxx.jar com.alibaba.dubbo.container.Main

这样就能成功启动了。

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值