Dubbo3应用开发—协议(Dubbo协议、REST协议 、gRPC协议、Triple协议)

发布时间 2023-10-05 16:04:35作者: 随机的未知

协议

协议简介

什么是协议

Client(Consumer端)与Server(Provider端)在传输数据时双方的约定。

协议简介

Dubbo3中常见的协议

1.dubbo协议[前面文章中使用的都是dubbo协议]
2.rest协议
3.triple协议
4.grpc协议
5.thirft协议
6.webservice协议
7.rocketmq协议
8.redis协议
9.memacached协议
...等等

不同协议的通信效率对比

dubbo官方提供的不同协议之间通信效率的对比如下:

不同协议的通信效率对比

Dubbo协议

1.Dubbo的默认协议,自己定义的私有协议,基于TCP层,默认的通信方式是Netty4;
2.Dubbo采用单一长连接和NIO异步通讯,适合于小数据量大并发的服务调用,反之,Dubbo缺省协议不适合传送大数据量的服务,比如传文件、传视频等。

官方提供的Dubbo协议结构图:

Dubbo协议结构图

官方提供的Dubbo协议的帧组成图:

Dubbo协议的帧组成

协议构成详见Dubbo2 协议规范 | Apache Dubbo

Dubbo协议的使用

准备——zookeeper的安装

https://archive.apache.org/dist/zookeeper/

下载zk

如果使用windows,可以7z解压缩软件解压缩tar包的形式

https://sparanoid.com/lab/7z/

修改conf/zoo.cfg配置⽂件

dataDir=D:\\zookeeper\\apache-zookeeper-3.6.1\\data

启动服务端

启动服务端

启动客户端

客户端

https://github.com/vran-dev/PrettyZoo/releases
图形化zk的客户端

创建项目

父项目maven文件中对依赖版本进行管理

<properties>
    <maven.compiler.source>8</maven.compiler.source>
    <maven.compiler.target>8</maven.compiler.target>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <dubbo.version>3.2.0</dubbo.version>
    <spring-boot.version>2.7.12</spring-boot.version>
    <spring.version>5.3.25</spring.version>
</properties>
<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>org.apache.dubbo</groupId>
            <artifactId>dubbo-bom</artifactId>
            <version>${dubbo.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-dependencies</artifactId>
            <version>${spring-boot.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

zk版本和dubbo版本的关系

引入相关依赖

<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>

    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-spring-boot-starter</artifactId>
    </dependency>

    <!--zk注册中心 需要的依赖-->
    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-dependencies-zookeeper-curator5</artifactId>
        <version>${dubbo.version}</version>
        <type>pom</type>
        <exclusions>
            <exclusion>
                <artifactId>zookeeper</artifactId>
                <groupId>org.apache.zookeeper</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>org.apache.zookeeper</groupId>
        <artifactId>zookeeper</artifactId>
        <version>3.8.1</version>
    </dependency>

    <!--lombok-->
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <version>1.18.22</version>
    </dependency>


    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-aop</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-beans</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-context</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-expression</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-jcl</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-test</artifactId>
        <version>${spring.version}</version>
    </dependency>



    <!--<dependency>
            <groupId>org.apache.dubbo</groupId>
            <artifactId>dubbo-rpc-rest</artifactId>
            <version>${dubbo.version}</version>
            <exclusions>
                <exclusion>
                    <artifactId>jackson-core-asl</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>jackson-jaxrs</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>jackson-mapper-asl</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>jackson-xc</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
            </exclusions>
        </dependency>

        <dependency>
            <groupId>org.jboss.resteasy</groupId>
            <artifactId>resteasy-jackson-provider</artifactId>
            <version>${resteasy-version}</version>
            <exclusions>
                <exclusion>
                    <artifactId>jackson-core-asl</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>jackson-jaxrs</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>jackson-mapper-asl</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
                <exclusion>
                    <artifactId>jackson-xc</artifactId>
                    <groupId>org.codehaus.jackson</groupId>
                </exclusion>
            </exclusions>
        </dependency>

        <dependency>
            <artifactId>jackson-core-asl</artifactId>
            <groupId>org.codehaus.jackson</groupId>
            <version>${jackson-version}</version>
        </dependency>

        <dependency>
            <artifactId>jackson-jaxrs</artifactId>
            <groupId>org.codehaus.jackson</groupId>
            <version>${jackson-version}</version>
        </dependency>

        <dependency>
            <artifactId>jackson-mapper-asl</artifactId>
            <groupId>org.codehaus.jackson</groupId>
            <version>${jackson-version}</version>
        </dependency>

        <dependency>
            <artifactId>jackson-xc</artifactId>
            <groupId>org.codehaus.jackson</groupId>
            <version>${jackson-version}</version>
        </dependency>-->

</dependencies>

创建api、provider、consumer包,并编写代码。

provider的application.yml配置文件如下:

spring:
  application:
    name: DUBBO-PROTOCOL-PROVIDER
dubbo:
  protocol:
    name: dubbo
    port: -1
  registry:
    address: zookeeper://127.0.0.1:2181

consumer的application.yml的配置如下:

spring:
  application:
    name: DUBBO-PROTOCOL-CONSUMER
dubbo:
  registry:
    address: zookeeper://127.0.0.1:2181

  application:
    qos-enable: false

REST协议

Rest协议就是我们平时说的Restful,本质上把他称为协议不准确。因为 Restful他是基于Http1.x协议的。 使⽤Rest协议这种⽅式可以让我们的Dubbo服务直接通过url进⾏访问,同时也可以更好的与SpringCloud技术栈进⾏整合。

搭建开发环境

父项目的pom文件核心如下:

<properties>
    <maven.compiler.source>8</maven.compiler.source>
    <maven.compiler.target>8</maven.compiler.target>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <dubbo.version>3.2.0</dubbo.version>
    <spring-boot.version>2.6.11</spring-boot.version>
    <jackson-version>1.9.13</jackson-version>
    <resteasy-version>3.15.6.Final</resteasy-version>
    <tomcat.version>9.0.75</tomcat.version>
    <grpc.version>1.54.1</grpc.version>
    <spring.version>5.3.25</spring.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>

    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-spring-boot-starter</artifactId>
    </dependency>

    <!--zk注册中心 需要的依赖-->
    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-dependencies-zookeeper-curator5</artifactId>
        <version>${dubbo.version}</version>
        <type>pom</type>
        <exclusions>
            <exclusion>
                <artifactId>zookeeper</artifactId>
                <groupId>org.apache.zookeeper</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>org.apache.zookeeper</groupId>
        <artifactId>zookeeper</artifactId>
        <version>3.8.1</version>
    </dependency>

    <!--lombok-->
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <version>1.18.22</version>
    </dependency>


    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-aop</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-beans</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-context</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-core</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-expression</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-jcl</artifactId>
        <version>${spring.version}</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-test</artifactId>
        <version>${spring.version}</version>
    </dependency>


    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-rpc-rest</artifactId>
        <version>${dubbo.version}</version>
        <exclusions>
            <exclusion>
                <artifactId>jackson-core-asl</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
            <exclusion>
                <artifactId>jackson-jaxrs</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
            <exclusion>
                <artifactId>jackson-mapper-asl</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
            <exclusion>
                <artifactId>jackson-xc</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>org.jboss.resteasy</groupId>
        <artifactId>resteasy-jackson-provider</artifactId>
        <version>${resteasy-version}</version>
        <exclusions>
            <exclusion>
                <artifactId>jackson-core-asl</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
            <exclusion>
                <artifactId>jackson-jaxrs</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
            <exclusion>
                <artifactId>jackson-mapper-asl</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
            <exclusion>
                <artifactId>jackson-xc</artifactId>
                <groupId>org.codehaus.jackson</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <artifactId>jackson-core-asl</artifactId>
        <groupId>org.codehaus.jackson</groupId>
        <version>${jackson-version}</version>
    </dependency>

    <dependency>
        <artifactId>jackson-jaxrs</artifactId>
        <groupId>org.codehaus.jackson</groupId>
        <version>${jackson-version}</version>
    </dependency>

    <dependency>
        <artifactId>jackson-mapper-asl</artifactId>
        <groupId>org.codehaus.jackson</groupId>
        <version>${jackson-version}</version>
    </dependency>

    <dependency>
        <artifactId>jackson-xc</artifactId>
        <groupId>org.codehaus.jackson</groupId>
        <version>${jackson-version}</version>
    </dependency>

</dependencies>


<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>org.apache.dubbo</groupId>
            <artifactId>dubbo-bom</artifactId>
            <version>${dubbo.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-dependencies</artifactId>
            <version>${spring-boot.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

provide pom文件引入的依赖:

<dependencies>
    <dependency>
        <groupId>com.sjdwz</groupId>
        <artifactId>dubbo-protocol-api</artifactId>
        <version>1.0-SNAPSHOT</version>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
        <exclusions>
            <exclusion>
                <artifactId>tomcat-embed-core</artifactId>
                <groupId>org.apache.tomcat.embed</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>org.apache.tomcat.embed</groupId>
        <artifactId>tomcat-embed-core</artifactId>
        <version>${tomcat.version}</version>
    </dependency>
</dependencies>

consumer只需要引入api模块即可。

api模块

java编码

@Path("orders")
@Consumes({MediaType.APPLICATION_JSON})
@Produces({ContentType.APPLICATION_JSON_UTF_8})
public interface OrderService {

    @GET
    @Path("{id}")
    Order getOrder(@PathParam("id") Long id);
}

provider模块

application.yml文件

spring:
  application:
    name: DUBBO-PROTOCOL-PROVIDER
dubbo:
  protocol:
    name: rest
    port: 9005
    server: tomcat
    contextpath: sjdwz
  registry:
    address: zookeeper://127.0.0.1:2181
server:
  port: 8090

java代码

@DubboService
public class OrderServiceImpl implements OrderService {
    @Override
    public Order getOrder(Long id) {
        System.out.println("OrderServiceImpl.getOrder id " + id);
        return new Order("1001", 100.0);
    }
}

运行起来

http://localhost:9005/sjdwz/orders/1

在浏览器输入上述url即可访问到。

consumer模块

java代码

@DubboReference(protocol = "rest")
private OrderService orderService;


@Test
public void test2(){
    orderService.getOrder(2L);
}

gRPC协议

  1. gRPC简介

    Dubbo中的gRPC协议就是应⽤gRPC来替换Dubbo的RPC调⽤。本质上把它称为协议不准确,因为gRPC他是Google开源⼀种异构语⾔通信的RPC框
    架。Dubbo引⼊gRPC的⽬的是为了更好的支持云原生的开发。
    
  2. gRPC底层协议

    gRPC底层基于Http2.x协议。Http2.x是双工协议,可以支持流式通信(反应式编程)。所以在通信效率上更高。
    
  3. gRPC开发过程

    1. 通过Protobuf的IDL定义通信数据,及操作。
    2. 通过Maven的插件,根据不同的编程语言生成成对应的代码
    3. 服务端发布RPC服务
    3.1. ⼀元调⽤
    3.2. 服务端流式RPC
    3.3. 客户端流式RPC
    3.4. 双向流式RPC
    4. 客户端进⾏RPC服务的调⽤
    4.1. 通过stub代理进⾏远端RPC的调⽤
    
  4. Dubbo中gRPC协议的开发

    本质上Dubbo对于gRPC协议的⽀持,就是在原有gRPC客户端代码上进行了封装。
    
  5. 父项目依赖设置

    <properties>
            <maven.compiler.source>8</maven.compiler.source>
            <maven.compiler.target>8</maven.compiler.target>
            <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
            <dubbo.version>3.1.10</dubbo.version>
            <spring-boot.version>2.7.12</spring-boot.version>
            <grpc.version>1.54.1</grpc.version>
            <os.detected.classifier>windows-x86_64</os.detected.classifier>
            <spring.version>5.3.25</spring.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>
    
            <dependency>
                <groupId>org.apache.dubbo</groupId>
                <artifactId>dubbo-spring-boot-starter</artifactId>
            </dependency>
    
            <!--zk注册中心 需要的依赖-->
            <dependency>
                <groupId>org.apache.dubbo</groupId>
                <artifactId>dubbo-dependencies-zookeeper-curator5</artifactId>
                <version>${dubbo.version}</version>
                <type>pom</type>
                <exclusions>
                    <exclusion>
                        <artifactId>zookeeper</artifactId>
                        <groupId>org.apache.zookeeper</groupId>
                    </exclusion>
                </exclusions>
            </dependency>
    
            <dependency>
                <groupId>org.apache.zookeeper</groupId>
                <artifactId>zookeeper</artifactId>
                <version>3.8.1</version>
            </dependency>
    
            <!--lombok-->
            <dependency>
                <groupId>org.projectlombok</groupId>
                <artifactId>lombok</artifactId>
                <version>1.18.22</version>
            </dependency>
    
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-aop</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-beans</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-context</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-core</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-expression</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-jcl</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework</groupId>
                <artifactId>spring-test</artifactId>
                <version>${spring.version}</version>
            </dependency>
    
        </dependencies>
    
        <dependencyManagement>
            <dependencies>
                <dependency>
                    <groupId>org.apache.dubbo</groupId>
                    <artifactId>dubbo-bom</artifactId>
                    <version>${dubbo.version}</version>
                    <type>pom</type>
                    <scope>import</scope>
                </dependency>
    
                <dependency>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-dependencies</artifactId>
                    <version>${spring-boot.version}</version>
                    <type>pom</type>
                    <scope>import</scope>
                </dependency>
    
                <dependency>
                    <groupId>io.grpc</groupId>
                    <artifactId>grpc-bom</artifactId>
                    <version>${grpc.version}</version>
                    <type>pom</type>
                    <scope>import</scope>
                </dependency>
            </dependencies>
        </dependencyManagement>
    
    

api模块的开发

pom文件修改

<dependencies>
    <dependency>
        <groupId>io.grpc</groupId>
        <artifactId>grpc-netty</artifactId>
        <exclusions>
            <exclusion>
                <groupId>io.netty</groupId>
                <artifactId>netty-codec-http2</artifactId>
            </exclusion>
            <exclusion>
                <groupId>io.netty</groupId>
                <artifactId>netty-handler-proxy</artifactId>
            </exclusion>
        </exclusions>
    </dependency>
    <dependency>
        <groupId>io.grpc</groupId>
        <artifactId>grpc-netty-shaded</artifactId>
    </dependency>
    <dependency>
        <groupId>io.grpc</groupId>
        <artifactId>grpc-protobuf</artifactId>
        <exclusions>
            <exclusion>
                <groupId>com.google.protobuf</groupId>
                <artifactId>protobuf-java</artifactId>
            </exclusion>
        </exclusions>
    </dependency>
    <dependency>
        <groupId>io.grpc</groupId>
        <artifactId>grpc-stub</artifactId>
    </dependency>

    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-common</artifactId>
    </dependency>

    <dependency>
        <groupId>com.google.protobuf</groupId>
        <artifactId>protobuf-java</artifactId>
        <version>3.21.7</version>
    </dependency>

    <dependency>
        <groupId>com.google.protobuf</groupId>
        <artifactId>protobuf-java-util</artifactId>
        <version>3.21.7</version>
        <exclusions>
            <exclusion>
                <groupId>com.google.protobuf</groupId>
                <artifactId>protobuf-java</artifactId>
            </exclusion>
        </exclusions>
    </dependency>

</dependencies>

<build>
    <plugins>
        <plugin>
            <groupId>kr.motd.maven</groupId>
            <artifactId>os-maven-plugin</artifactId>
            <version>1.7.1</version>
        </plugin>
        <plugin>
            <groupId>org.xolstice.maven.plugins</groupId>
            <artifactId>protobuf-maven-plugin</artifactId>
            <version>0.6.1</version>
            <configuration>
                <protocArtifact>com.google.protobuf:protoc:3.21.7:exe:${os.detected.classifier}</protocArtifact>
                <pluginId>grpc-java</pluginId>
                <pluginArtifact>io.grpc:protoc-gen-grpc-java:${grpc.version}:exe:${os.detected.classifier}
                </pluginArtifact>
                <outputDirectory>${basedir}/src/main/java</outputDirectory>
                <clearOutputDirectory>false</clearOutputDirectory>
                <protocPlugins>
                    <protocPlugin>
                        <id>dubbo-grpc</id>
                        <groupId>org.apache.dubbo</groupId>
                        <artifactId>dubbo-compiler</artifactId>
                        <version>${dubbo.version}</version>
                        <mainClass>org.apache.dubbo.gen.grpc.DubboGrpcGenerator</mainClass>
                    </protocPlugin>
                </protocPlugins>
            </configuration>
            <executions>
                <execution>
                    <id>protobuf-maven-plugin</id>
                    <goals>
                        <goal>compile</goal>
                        <goal>compile-custom</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

maven插件

provider模块的开发

application.yml文件

spring:
  application:
    name: DUBBO-PROTOCOL-PROVIDER
dubbo:
  protocol:
    name: grpc
    port: -1
  registry:
    address: zookeeper://127.0.0.1:2181
#  port: 8081

Java类

provider的ServiceImpl

@DubboService
public class DemoServiceImpl extends DubboDemoServiceGrpc.DemoServiceImplBase {
    @Override
    public void demo(RequestData request, StreamObserver<ResponseData> responseObserver) {
        System.out.println("DemoServiceImpl.demo " + request.getName());
        responseObserver.onNext(ResponseData.newBuilder().setResult("this is result").build());
        responseObserver.onCompleted();
    }
}

consumer模块的开发

测试Java方法

@DubboReference(protocol = "grpc")
private DubboDemoServiceGrpc.IDemoService iDemoService;


@Test
void test3() {
    ResponseData ret = iDemoService.demo(RequestData.newBuilder().setName("xiaohei").build());
    System.out.println("ret.getResult() = " + ret.getResult());

}

Triple协议

  1. Triple协议是什么

    在阿里巴巴,Triple 协议广泛用于跨环境、跨语言、跨生态互通,已有数十万容器生产级使用。
    
    Triple 协议是 Dubbo3设计的基于HTTP的RPC通信协议规范,它完全兼容 gRPC 协议,支持 Request-Response、Streaming流式等通信模型,可同时运行在HTTP/1和 HTTP/2之上。
    核心:
    1.Dubbo3全新设计的基于Http的RPC协议
    2.完全兼容gRPC协议
    3.支持Streaming流式通信【与gRPC类似】
    4.同时支持HTTP1和HTTP2
    5.对比内置的Dubbo协议,更好的支持异构语言通信,且更加适应云原生。
    
  2. Dubbo原有已经支持了gRPC协议,为什么还要做Triple协议?

    生态建设︰
    1.如果只支持gRPC协议,不能够体现Dubbo的价值,毕竟gRPC是Google制定的。
    Triple的优势:
    1.不绑定IDL,支持Java lnterface 定义服务。(gRPC需要使用Protobuf,而Triple可以通过Java接口的方式进行服务的)
    2.同时支持Http1和Http2协议,而gRPC只支持Http2协议。
    3.100%兼容gRPC。从Dubbo3.2.x开始,已经废弃原有的gRPC协议使用Triple协议进行替代。
    

Triple协议的开发

父项目中pom文件,dubbo版本切换到3.2.0

<properties>
    <maven.compiler.source>8</maven.compiler.source>
    <maven.compiler.target>8</maven.compiler.target>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <dubbo.version>3.2.0</dubbo.version>
    <grpc.version>1.54.1</grpc.version>
    <spring-boot.version>2.7.12</spring-boot.version>
    <protoc.version>3.21.7</protoc.version>
	<os.detected.classifier>windows-x86_64</os.detected.classifier>
</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>

    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-spring-boot-starter</artifactId>
    </dependency>

    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo</artifactId>
    </dependency>

    <dependency>
        <groupId>io.grpc</groupId>
        <artifactId>grpc-all</artifactId>
        <version>${grpc.version}</version>
        <exclusions>
            <exclusion>
                <artifactId>grpc-netty</artifactId>
                <groupId>io.grpc</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>com.google.protobuf</groupId>
        <artifactId>protobuf-java</artifactId>
        <version>${protoc.version}</version>
    </dependency>


    <dependency>
        <groupId>org.apache.dubbo</groupId>
        <artifactId>dubbo-dependencies-zookeeper-curator5</artifactId>
        <version>${dubbo.version}</version>
        <type>pom</type>
        <exclusions>
            <exclusion>
                <artifactId>zookeeper</artifactId>
                <groupId>org.apache.zookeeper</groupId>
            </exclusion>
        </exclusions>
    </dependency>

    <dependency>
        <groupId>org.apache.zookeeper</groupId>
        <artifactId>zookeeper</artifactId>
        <version>3.8.1</version>
    </dependency>

    <!--lombok-->
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <version>1.18.22</version>
    </dependency>

</dependencies>

<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>org.apache.dubbo</groupId>
            <artifactId>dubbo-bom</artifactId>
            <version>${dubbo.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-dependencies</artifactId>
            <version>${spring-boot.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>

        <dependency>
            <groupId>io.grpc</groupId>
            <artifactId>grpc-bom</artifactId>
            <version>${grpc.version}</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>
<build>
    <extensions>
        <extension>
            <groupId>kr.motd.maven</groupId>
            <artifactId>os-maven-plugin</artifactId>
            <version>1.7.1</version>
        </extension>
    </extensions>
    <plugins>
        <plugin>
            <groupId>org.xolstice.maven.plugins</groupId>
            <artifactId>protobuf-maven-plugin</artifactId>
            <version>0.6.1</version>
            <configuration>
                <protocArtifact>com.google.protobuf:protoc:3.21.7:exe:${os.detected.classifier}
                </protocArtifact>
                <pluginId>grpc-java</pluginId>
                <pluginArtifact>io.grpc:protoc-gen-grpc-java:${grpc.version}:exe:${os.detected.classifier}
                </pluginArtifact>
                <outputDirectory>${basedir}/src/main/java</outputDirectory>
                <clearOutputDirectory>false</clearOutputDirectory>
                <protocPlugins>
                    <protocPlugin>
                        <id>dubbo</id>
                        <groupId>org.apache.dubbo</groupId>
                        <artifactId>dubbo-compiler</artifactId>
                        <version>${dubbo.version}</version>
                        <mainClass>org.apache.dubbo.gen.tri.Dubbo3TripleGenerator</mainClass>
                    </protocPlugin>
                </protocPlugins>
            </configuration>
            <executions>
                <execution>
                    <goals>
                        <goal>compile</goal>
                        <goal>test-compile</goal>
                        <goal>compile-custom</goal>
                        <goal>test-compile-custom</goal>
                    </goals>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

api模块的开发

proto文件夹

syntax = "proto3";
option java_multiple_files = true;
option java_package = "com.sjdwz.tri";
package com.sjdwz.tri;
// The request message containing the user's name.
message GreeterRequest {
  string name = 1;
}
// The response message containing the greetings
message GreeterReply {
  string message = 1;
}
service Greeter{
  // unary
  rpc greet(GreeterRequest) returns (GreeterReply);
  // serverStream
  rpc greetServerStream(GreeterRequest) returns (stream GreeterReply);
  // bi streaming
  rpc greetStream(stream GreeterRequest) returns (stream GreeterReply);
}

maven命令

在父项目执行上图maven命令。

provider模块的开发

application.yml

spring:
  application:
    name: DUBBO-TRIPLE-PROVIDER

dubbo:
  protocol:
    name: tri
    port: -1
  registry:
    address: zookeeper://127.0.0.1:2181

服务接口的开发

@DubboService
public class GreeterImpl extends DubboGreeterTriple.GreeterImplBase {
    @Override
    public GreeterReply greet(GreeterRequest request) {
        System.out.println("GreeterImpl.greet " + request.getName());
        GreeterReply greeterReply = GreeterReply.newBuilder().setMessage("this is on method").build();
        return greeterReply;
    }

    @Override
    public StreamObserver<GreeterRequest> greetStream(StreamObserver<GreeterReply> responseObserver) {
        System.out.println("GreeterImpl.greetStream");
        responseObserver.onNext(GreeterReply.newBuilder().setMessage("bi stream result").build());
        responseObserver.onCompleted();
        return new StreamObserver<GreeterRequest>() {
            @Override
            public void onNext(GreeterRequest data) {
                System.out.println(" recive request param = " + data.getName());
            }

            @Override
            public void onError(Throwable throwable) {

            }

            @Override
            public void onCompleted() {
                System.out.println("GreeterImpl.onCompleted");
            }
        };
    }

    @Override
    public void greetServerStream(GreeterRequest request, StreamObserver<GreeterReply> responseObserver) {
        System.out.println("GreeterImpl.greetServerStream name " + request.getName());

        responseObserver.onNext(GreeterReply.newBuilder().setMessage("this is result").build());

        responseObserver.onCompleted();
    }
}

consumer模块的开发

测试类的开发

@DubboReference(protocol = "tri")
private Greeter greeter;


@Test
void test2() {
    GreeterRequest request = GreeterRequest.newBuilder().setName("xiaowb").build();
    GreeterReply greeterReply = greeter.greet(request);
    System.out.println("greeterReply.getMessage() = " + greeterReply.getMessage());
}

triple协议——grpc方式的开发

api模块

在api模块的pom文件执行如下命令;

maven命令

consumer模块

gRPC adaptor类

package com.sjdwz;

import io.grpc.stub.StreamObserver;

public class GrpcStreamObserverAdapter<T> implements StreamObserver<T> {

    private final org.apache.dubbo.common.stream.StreamObserver<T> delegate;

    public GrpcStreamObserverAdapter(org.apache.dubbo.common.stream.StreamObserver<T> delegate) {
        this.delegate = delegate;
    }

    @Override
    public void onNext(T value) {
        delegate.onNext(value);
    }

    @Override
    public void onError(Throwable t) {
        delegate.onError(t);

    }

    @Override
    public void onCompleted() {
        delegate.onCompleted();

    }
}

Test类

@Test
void test4() {
    ManagedChannel managedChannel = ManagedChannelBuilder.forAddress("localhost", 50051).usePlaintext().build();
    try {
        //一元操作
        GreeterGrpc.GreeterBlockingStub greeterBlockingStub = GreeterGrpc.newBlockingStub(managedChannel);
        //流式处理
        GreeterGrpc.GreeterStub greeterStub = GreeterGrpc.newStub(managedChannel);
        GreeterRequest request = GreeterRequest.newBuilder().setName("grpc").build();
        greeterStub.greetServerStream(request, new GrpcStreamObserverAdapter<>(new StreamObserver<GreeterReply>() {
            @Override
            public void onNext(GreeterReply data) {
                System.out.println("TestTripleDemo.onNext " + data.getMessage());
            }

            @Override
            public void onError(Throwable throwable) {

            }

            @Override
            public void onCompleted() {
                System.out.println("TestTripleDemo.onCompleted");
            }
        }));

        System.in.read();
    } catch (Exception e) {
        throw new RuntimeException(e);
    } finally {
        managedChannel.shutdown();
    }
}

triple协议——Java Interface的方式

需要记住两个规律:

1. message替换成Java类型
2. StreamObserver也用StreamObserver处理