Dubbo是Alibaba开源的分布式服务框架,它最大的特点是按照分层的方式来架构,使用这种方式可以使各个层之间解耦合(或者最大限度地松耦合)。从服务模型的角度来看,Dubbo采用的是一种非常简单的模型,要么是提供方提供服务,要么是消费方消费服务,所以基于这一点可以抽象出服务提供方(Provider)和服务消费方(Consumer)两个角色。
在这里插入图片描述

Dubbo 的RPC 调用流程主要涉及到4个模块:

1、Registry:服务注册,我们一般会采取Zookeeper 作为我们的注册中心

2、Provider:服务提供者(生产者),提供具体的服务实现

3、Consumer:消费者,从注册中心中订阅服务

4、Monitor:监控中心,RPC调用次数和调用时间监控

从上图中我们可以看出RPC 服务调用的过程主要为:

1、生产者发布服务到服务注册中心

2、消费者在服务注册中心中订阅服务

3、消费者调用已注册的服务

1、IDEA下将SpringBoot与dubbo整合

项目结构图
在这里插入图片描述

  1. common: 通用模块
  2. provider: 服务提供者
  3. consumer: 服务调用者

## 最外部springboot-dubbo的pom.xml配置文件如下:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.4.5</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <groupId>com.lcxu</groupId>
    <artifactId>springboot-dubbo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>springboot-dubbo</name>
    <description>Demo project for Spring Boot-Dubbo</description>
    <packaging>pom</packaging>
    <properties>
        <java.version>1.8</java.version>
    </properties>

    <modules>
        <module>common</module>
        <module>provider</module>
        <module>consumer</module>
    </modules>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>

        <!--dubbo-springBoot依赖-->
        <dependency>
            <groupId>com.alibaba.spring.boot</groupId>
            <artifactId>dubbo-spring-boot-starter</artifactId>
            <version>1.0.1</version>
        </dependency>
        <!--zookeeper依赖-->
        <dependency>
            <groupId>org.apache.zookeeper</groupId>
            <artifactId>zookeeper</artifactId>
            <version>3.4.11</version>
        </dependency>
        <!--
            1)zookeeper原生API使用中,经常会遇到session expire这类异常,异常发生后需要进行重新连接,重新建立session,会比较麻烦
            2)zookeeper的watcher机制是一次性的,如果你想订阅节点的状态变化、子节点变化等,每次在处理完变化事件之后,需要重新注册watcher。可想而知这是一件令人绝望的事情。这个特性使得在处理事件和重新加上watcher这段时间发生的节点变化将无法被感知。
            3)zookeeper的API接口中,节点数据默认为二进制byte数组,如果想直接保存对象类型的数据,需要相关的序列化工作。
            以上问题,zkClient可以很好的解决。
         -->

        <dependency>
            <groupId>com.101tec</groupId>
            <artifactId>zkclient</artifactId>
            <version>0.10</version>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.4.5</version>
            </plugin>
        </plugins>
    </build>

</project>

公共pom主要引入了: SpringBoot依赖,dubbo-springBoot依赖,zookeeper依赖,zkClient依赖等。

1、provider模块

  • 项目代码结构:
    在这里插入图片描述

  • pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>com.lcxu</groupId>
        <artifactId>springboot-dubbo</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.example</groupId>
    <artifactId>provider</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>provider</name>
    <description>Demo project for Spring Boot</description>
    <properties>
        <java.version>1.8</java.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>com.lcxu</groupId>
            <artifactId>common</artifactId>
            <version>0.0.1-SNAPSHOT</version>
            <scope>compile</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.4.5</version>
            </plugin>
        </plugins>
    </build>

</project>

  • application.yml
server:
  port: 8081
spring:
  dubbo:
    appname: provider
    registry: zookeeper://127.0.0.1:2181
    protocol: dubbo
    port: 20880

  • ProviderApplication
package com.example.provider;

import com.alibaba.dubbo.config.spring.context.annotation.EnableDubbo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
@EnableDubbo //启动dubbo服务,它整合了 @EnableDubboConfig 和 @DubboComponentScan
public class ProviderApplication {
    public static void main(String[] args) {
        SpringApplication.run(ProviderApplication.class, args);
    }

}

  • BookServiceImpl
package com.example.provider.service.impl;

import com.lcxu.common.api.provider.IBookServiceApi;
import org.springframework.stereotype.Service;

@Service
@com.alibaba.dubbo.config.annotation.Service
public class BookServiceImpl implements  IBookServiceApi {

    @Override
    public String sayHello() {
        return "hello, dubbo!这是一个简单的dubbo-demo!";
    }
}

Provider模块代码就这么多。

2、Consumer模块

  • 项目代码结构
    在这里插入图片描述

  • pom.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>com.lcxu</groupId>
        <artifactId>springboot-dubbo</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.example</groupId>
    <artifactId>consumer</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>consumer</name>
    <description>Demo project for Spring Boot</description>
    <properties>
        <java.version>1.8</java.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>com.lcxu</groupId>
            <artifactId>common</artifactId>
            <version>0.0.1-SNAPSHOT</version>
            <scope>compile</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.4.5</version>
            </plugin>
        </plugins>
    </build>

</project>

  • application.yml
server:
  port: 8082
spring:
  dubbo:
    appname: provider
    registry: zookeeper://127.0.0.1:2181
    protocol: dubbo
    port: 20880
  • ConsumerApplication
package com.example.consumer;

import com.alibaba.dubbo.config.spring.context.annotation.EnableDubbo;
import com.alibaba.dubbo.spring.boot.annotation.EnableDubboConfiguration;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
@EnableDubbo
public class ConsumerApplication {

    public static void main(String[] args) {
        SpringApplication.run(ConsumerApplication.class, args);
    }

}

  • BookController
package com.example.consumer.controller;

import com.alibaba.dubbo.config.annotation.Reference;
import com.lcxu.common.api.provider.IBookServiceApi;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@RequestMapping("/book")
public class BookController {

    @Reference
    private IBookServiceApi bookService;

    @GetMapping("/book")
    private String getBook() {
        return this.bookService.sayHello();
    }
}

调用provider模块定义的service的时候,必须要加入@Reference注解
@Reference是dubbo的注解,也是注入,他一般注入的是分布式的远程服务的对象,需要dubbo配置使用。

3、common模块
common只是一个基础包,可以放一些接口,或者工具类,一些bean等。

  • 项目结构图

在这里插入图片描述

  • pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.4.5</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.lcxu</groupId>
    <artifactId>common</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>common</name>
    <description>Demo project for Spring Boot</description>
    <properties>
        <java.version>1.8</java.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.4.5</version>
            </plugin>
        </plugins>
    </build>

</project>

  • IBookServiceApi
    只定义了一个公共接口
package com.lcxu.common.api.provider;

public interface IBookServiceApi {
    String sayHello();
}

至此,代码模块编写完成,但是目前还不能运行,因为还没有启动zookeeper。

2、zookeeper的安装,windows为例

1、下载zookeeper
下载地址:
https://zookeeper.apache.org/releases.html

2、解压
在这里插入图片描述

3、复制zoo_simple.cfg,重命名为zoo.cfg
在这里插入图片描述
根据实际情况修改下面配置
在这里插入图片描述
4、启动zookeeper
在这里插入图片描述
zookeeper命令,参照下面链接
zookeeper之 zkServer.sh命令、zkCli.sh命令、四字命令
cnblogs.com/andy6/p/7674028.html

启动zookeeper后,然后启动provider与consumer模块,再浏览器输入http://localhost:8082/book/book,即可实现模块的远程调用。
在这里插入图片描述

3、zookeeper可视化工具 zkui

1、下载zkui源码
源码地址:https://github.com/DeemOpen/zkui.git

2、编译
mvn clean
mvn install

编译成功,此时生成两个jar包,zkui-2.0-SNAPSHOT.jar和zkui-2.0-SNAPSHOT-jar-with-dependencies.jar,使用的是第二个jar包

3、修改配置文件

zkui运行生成的jar包,可以直接运行,在运行该文件之前,我们还需要修改zkui的配置文件config.cfg,config.cfg 文件中配置了zkui需要连接的zookeeper集群的IP地址和端口,访问UI的用户名和密码,以及zkui监听的端口号
在这里插入图片描述
4、启动程序

java -jar zkui-2.0-SNAPSHOT-jar-with-dependencies.jar

注意,需要将config.cfg复制到jar包的同一层目录去,不然启动会报错
在这里插入图片描述
在这里插入图片描述
5、访问页面,输入配置文件里的用户名密码
在这里插入图片描述
在这里插入图片描述
6、登录zkui ,选择导航“Host” 出现错误提示:KeeperErrorCode = NoNode for /appconfig/hosts 如下所示:
在这里插入图片描述
解决方案:

  • 启动zkcli.cmd客户端,然后执行下面命令即可。

在这里插入图片描述

  • 刷新,正常

在这里插入图片描述
至此,完成!
项目代码地址:https://gitee.com/lcxu/springboot-dubbo.git

Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐