Apache Dubbo与Nacos整合过程

Dubbo服务发现

Dubbo 提供的是一种 Client-Based 的服务发现机制,依赖第三方注册中心组件来协调服务发现过程,支持常用的注册中心如 Nacos、Consul、Zookeeper 等。

以下是 Dubbo 服务发现机制的基本工作原理图:

服务发现包含提供者、消费者和注册中心三个参与角色,其中,Dubbo 提供者实例注册 URL 地址到注册中心,注册中心负责对数据进行聚合,Dubbo 消费者从注册中心读取地址列表并订阅变更,每当地址列表发生变化,注册中心将最新的列表通知到所有订阅的消费者实例。

Dubbo与Nacos整合
前置条件

● 当Dubbo使用3.0.0及以上版本时,需要使用Nacos 2.0.0及以上版本。

● 注意:目前最新版本Dubbo 3.1.8不支持Spring Boot 3,因此开发环境必须基于Spring Boot 2.x + JDK17/8,对应的Spring Cloud与Spring Cloud Alibaba也要调整为2021.x

java 复制代码
<properties>
    <java.version>17</java.version>
    <spring-cloud.version>2021.0.3</spring-cloud.version>
    <spring-cloud-alibaba.version>2021.0.4.0</spring-cloud-alibaba.version>
</properties>

生产者服务provider-service-dubbo

java 复制代码
<dependency>
  <groupId>org.apache.dubbo</groupId>
  <artifactId>dubbo-spring-boot-starter</artifactId>
  <version>3.1.8</version>
</dependency>

配置文件application.yaml

java 复制代码
server:
  port: 8001
spring:
  application:
    name: provider-service
  cloud:
    nacos:
      server-addr: 192.168.31.231:8848
      username: nacos
      password: nacos
dubbo:
  application:
    name: provider-service-dubbo
  registry:
    address: nacos://192.168.31.231:8848
    username: nacos
    password: nacos
  protocol:
    name: dubbo
    port: 20880
logging:
  level:
    root: info

应用入口增加两个注解,启用Dubbo

● @EnableDubbo

@EnableDubbo是一个注解,用于启用Dubbo的自动配置,将Dubbo服务注册到注册中心。它可以放置在Spring Boot应用程序的主类上。通过使用@EnableDubbo注解,可以避免手动配置Dubbo服务的繁琐工作,只需添加相应的注解和配置参数即可自动配置Dubbo。

● @DubboComponentScan

@DubboComponentScan是一个注解,用于扫描Dubbo服务的实现类。它可以放置在Spring Boot应用程序的主类上。通过使用@DubboComponentScan注解,可以自动扫描指定包及其子包中的Dubbo服务实现类,将它们注册为Dubbo服务。这样,Dubbo框架就能够自动发现和管理Dubbo服务,方便使用和维护。

java 复制代码
package com.itlaoqi.providerservicedubbo;

import org.apache.dubbo.config.spring.context.annotation.DubboComponentScan;
import org.apache.dubbo.config.spring.context.annotation.EnableDubbo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
@EnableDubbo
@DubboComponentScan
public class ProviderServiceDubboApplication {

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

}

实现业务接口

接口

java 复制代码
package com.itlaoqi.providerservicedubbo.dubbo;

import com.itlaoqi.providerservicedubbo.entity.User;
import org.springframework.http.ResponseEntity;

import java.util.List;
import java.util.Map;

public interface ProviderService {
    public Map hello();

    public User createUser(String uid, String username, String password, String nickname);

    public ResponseEntity<List<User>> query(int page, int rows);
}

实现

@DubboService是一个注解,用于标注Dubbo服务的实现类。在Dubbo框架中,服务提供者需要将服务注册到注册中心,以便服务消费者能够发现和调用服务。@DubboService注解可以将标注的服务实现类注册为Dubbo服务,使其能够被Dubbo框架自动管理和发布。

java 复制代码
package com.itlaoqi.providerservicedubbo.dubbo.impl;

import com.itlaoqi.providerservicedubbo.dubbo.ProviderService;
import com.itlaoqi.providerservicedubbo.dto.User;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@DubboService
public class ProviderServiceImpl implements ProviderService {
    public Map hello() {
        Map result = new HashMap();
        result.put("code", "0");
        result.put("message", "hello world~");
        return result;
    }

    public User createUser(String uid, String username , String password , String nickname) {
        return new User(uid,username,password,nickname);
    }

    public ResponseEntity<List<User>> query(int page, int rows) {
        List<User> users = new ArrayList<>();
        for (int i = rows * (page - 1); i < rows * page; i++) {
            String uid = "uid:" + i;
            String username = "username-" + i;
            String password = "password-" + i;
            String nickname = "nickname-" + i;
            User user = new User(uid, username, password, nickname);
            users.add(user);
        }
        return new ResponseEntity<>(users, HttpStatus.OK);
    }
}

注意,需要依赖的DTO对象,必须实现序列化接口Serializable

java 复制代码
package com.itlaoqi.providerservicedubbo.dto;

import lombok.AllArgsConstructor;
import lombok.Data;

import java.io.Serializable;

@Data
@AllArgsConstructor
public class User implements Serializable {

    private String uid;
    private String username;
    private String password;
    private String nickname;
}

启动时要万分注意,JDK17与Dubbo 3.1.8有兼容问题,需要在启动项增加,官方说3.2版本会修正这个问题

java 复制代码
--add-opens java.base/java.lang=ALL-UNNAMED


消费者服务consumer-service-dubbo

java 复制代码
  <dependency>
      <groupId>org.apache.dubbo</groupId>
      <artifactId>dubbo-spring-boot-starter</artifactId>
      <version>3.1.8</version>
  </dependency>

配置消费者接口

java 复制代码
server:
  port: 8002
spring:
  application:
    name: consumer-service
  cloud:
    nacos:
      server-addr: 192.168.31.231:8848
      username: nacos
      password: nacos
dubbo:
  application:
    name: consumer-service-dubbo
  registry:
    address: nacos://192.168.31.231:8848
    username: nacos
    password: nacos
logging:
  level:
    root: info

启用Dubbo

java 复制代码
package com.itlaoqi.consumerservicedubbo;

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

@SpringBootApplication
@EnableDubbo
public class ConsumerServiceDubboApplication {

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

}

将服务端接口与依赖的类加载到本地

● 复制源代码

● Maven依赖

注意包名是com.itlaoqi.providerservicedubbo.dubbo

java 复制代码
package com.itlaoqi.providerservicedubbo.dubbo;

import com.itlaoqi.providerservicedubbo.dto.User;

import java.util.List;
import java.util.Map;

public interface ProviderService {
    public Map hello();

    public User createUser(String uid, String username, String password, String nickname);

    public List<User> query(int page, int rows);
}
java 复制代码
package com.itlaoqi.providerservicedubbo.dto;

import lombok.AllArgsConstructor;
import lombok.Data;

import java.io.Serializable;

@Data
@AllArgsConstructor
public class User implements Serializable {

    private String uid;
    private String username;
    private String password;
    private String nickname;
}

依赖并远程访问

● @DubboReference

通过在 Spring 容器中标记 @DubboReference 注解,可以让 Dubbo 自动为该属性注入一个代理对象,该对象可以调用远程 Dubbo 服务的方法,使得在使用 Dubbo 服务时可以像调用本地服务一样方便。

java 复制代码
package com.itlaoqi.consumerservicedubbo.controller;

import com.itlaoqi.providerservicedubbo.dubbo.ProviderService;
import com.itlaoqi.providerservicedubbo.dto.User;
import org.apache.dubbo.config.annotation.DubboReference;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

import java.util.List;

@RestController
public class ConsumerController {
    @DubboReference
    private ProviderService providerService;
    @GetMapping("/list")
    public List<User> list(int page, int rows) {
        return providerService.query(page, rows);
    }
}

执行结果

java 复制代码
###
GET http://localhost:8002/list?page=2&rows=10

[
  {
    "uid": "uid:10",
    "username": "username-10",
    "password": "password-10",
    "nickname": "nickname-10"
  },
  {
    "uid": "uid:11",
    "username": "username-11",
    "password": "password-11",
    "nickname": "nickname-11"
  },
  {
    "uid": "uid:12",
    "username": "username-12",
    "password": "password-12",
    "nickname": "nickname-12"
  },
  {
    "uid": "uid:13",
    "username": "username-13",
    "password": "password-13",
    "nickname": "nickname-13"
  },
  {
    "uid": "uid:14",
    "username": "username-14",
    "password": "password-14",
    "nickname": "nickname-14"
  },
  {
    "uid": "uid:15",
    "username": "username-15",
    "password": "password-15",
    "nickname": "nickname-15"
  },
  {
    "uid": "uid:16",
    "username": "username-16",
    "password": "password-16",
    "nickname": "nickname-16"
  },
  {
    "uid": "uid:17",
    "username": "username-17",
    "password": "password-17",
    "nickname": "nickname-17"
  },
  {
    "uid": "uid:18",
    "username": "username-18",
    "password": "password-18",
    "nickname": "nickname-18"
  },
  {
    "uid": "uid:19",
    "username": "username-19",
    "password": "password-19",
    "nickname": "nickname-19"
  }
]

启动时要万分注意,JDK17与Dubbo 3.1.8有兼容问题,需要在启动项增加,官方说3.2版本会修正这个问题

java 复制代码
--add-opens java.base/java.lang=ALL-UNNAMED
相关推荐
Dola_Pan21 小时前
Linux文件IO(一)-open使用详解
java·linux·dubbo
檀越剑指大厂1 天前
开源多场景问答社区论坛Apache Answer本地部署并发布至公网使用
开源·apache
nvd111 天前
Java ETL - Apache Beam 简介
java·apache·etl
兮动人2 天前
错误: 找不到或无法加载主类 org.apache.zookeeper.server.quorum.QuorumPeerMain
分布式·zookeeper·apache
凌晨五点的星2 天前
网络安全-利用 Apache Mod CGI
apache
一 乐4 天前
学习平台|基于java的移动学习平台系统小程序(源码+数据库+文档)
java·数据库·学习·小程序·论文·apache
weixin_436525074 天前
【安全漏洞】Apache Tomcat 高危漏洞版本
java·apache
腾讯云中间件5 天前
基于 TDMQ for Apache Pulsar 的跨地域复制实践
apache
爱吃土豆的程序员5 天前
Apache License 2.0 和 MIT License 区别
apache·开源协议
喜欢猪猪5 天前
Apache Spark Streaming技术深度解析
大数据·spark·apache