栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

SpringBoot基础(二)

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

SpringBoot基础(二)

SpringBoot基础(二)

spring官网:https://spring.io/

https://mp.weixin.qq.com/mp/homepage?__biz=Mzg2NTAzMTExNg==&hid=1&sn=3247dca1433a891523d9e4176c90c499

该笔记记录的是SpringBoot2,更新的SpringBoot3版本需要参考最新官方文档

文章目录
  • SpringBoot基础(二)
  • 7、连接数据库
    • 7.0 SpringData
    • 7.1 整合JDBC
    • 7.2 整合Druid
    • 7.3 整合Mybatis
      • 使用例
  • 8、信息安全
    • 8.1 spring Security
      • 8.1.1 环境搭建
      • 8.1.2 认证和授权
      • 8.1.3 权限控制和注销
      • 8.1.4 记住我功能
      • 8.1.5 定制登录页
      • SecurityConfig完整代码
    • 8.2 Shiro
      • 8.2.0 Shiro外部架构
      • 8.2.1 使用例
      • 8.2.2 springboot整合shiro
        • 实现登录拦截
        • 实现用户认证
        • 整合Mybatis
        • 请求授权实现
        • 整合thymeleaf
  • 9、Swagger
    • 前后端分离
    • 9.1 springboor集成Swagger
    • 9.2 配置swagger
    • 9.3 Swagger配置扫描接口
    • 9.4 API文档的分组和接口注释
    • 小结
  • 10、任务
    • 10.1 异步任务
    • 10.2 邮件任务
    • 10.3 定时任务
  • 11、Redis
    • 11.1 使用例
    • 11.2 自定义RedisTemplate
  • 12、分布式(待完善)
    • 12.1 分布式(待完善)
      • 前置内容
      • Dubbo概念
      • zookeeper
      • 安装dubbo-admin
    • 12.2 分布式Dubbo+Zookeeper+SpringBoot
      • 步骤
      • 步骤

7、连接数据库 7.0 SpringData

对于数据访问层,无论是 SQL 还是 NoSQL,Spring Boot 底层都是采用 Spring Data 的方式进行统一处理。

SpringData官网:https://spring.io/projects/spring-data

数据库相关启动器:https://docs.spring.io/spring-boot/docs/2.2.5.RELEASE/reference/htmlsingle/#using-boot-starter

7.1 整合JDBC

创建一个springboot项目,引入JDBC相关依赖

自动生成的pom.xml依赖


    org.springframework.boot
    spring-boot-starter-jdbc


    org.springframework.boot
    spring-boot-starter-web



    mysql
    mysql-connector-java
    runtime


    org.springframework.boot
    spring-boot-starter-test
    test

编写application.yml配置文件连接数据库

spring:
  datasource:
    username: root
    password: 密码
    #?serverTimezone=UTC用于解决时区报错
    url: jdbc:mysql://localhost:3306/springboot?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8
    driver-class-name: com.mysql.cj.jdbc.Driver

springboot底层会处理这些配置内容。接下来可以直接使用jdbc

@SpringBootTest
public class SpringbootDataJdbcTest {
    //注入数据源。配置文件完成后,底层会构造出dataSource对象
    @Resource
    DataSource dataSource;

    @Test
    public void contextLoads() throws SQLException{
        //查看默认的数据源
        System.out.println(dataSource.getClass());
        //获取连接
        Connection connection = dataSource.getConnection();
        System.out.println(connection);
        //关闭连接
        connection.close();
    }
}

注:项目创建后会生成一个总测试类,自己写的测试类要和这个总测试类处于同级目录

输出

由输出可以看到,默认配置的数据源是class com.zaxxer.hikari.HikariDataSource。

数据源的自动配置写在DataSourceAutoConfiguration类中,打开它的源码,源码中有一处默认数据源配置相关的内部类

@Configuration(
    proxyBeanMethods = false
)
@Conditional({DataSourceAutoConfiguration.PooledDataSourceCondition.class})
@ConditionalOnMissingBean({DataSource.class, XADataSource.class})

@Import({Hikari.class, Tomcat.class, Dbcp2.class, OracleUcp.class, Generic.class, DataSourceJmxConfiguration.class})
protected static class PooledDataSourceConfiguration {
    protected PooledDataSourceConfiguration() {
    }
}

源码中通过@Import注解导入了Hikari.class,即前面打印的默认配置数据源。

可以在配置文件中设置spring.datasources.type的值来配置数据源类型(mysql、oracle…)。

JDBCTemplate

目的和MyBatis差不多,都是为了简化数据库相关的代码书写。JDBCTemplate也是springboot底层的一个默认配置。

相关配置类是JdbcTemplateConfiguration。

常用方法:

  • excute:执行sql语句
  • update、batchUpdate:前者执行增删改语句,后者执行批处理相关语句
  • query、queryForXXX:执行查询语句
  • call:执行存储过程、函数相关的语句

使用例

编写一个Controller,注入 jdbcTemplate,编写测试方法进行访问测试.

@RestController
@RequestMapping("/jdbc")
public class JdbcController {

    //使用默认配置的JdbcTemplate
    @Autowired
    JdbcTemplate jdbcTemplate;

    //查
    //List 中的一个 Map 对应数据库的一行数据
    //Map 中的 key 对应数据库的字段名,value 对应数据库的字段值
    @GetMapping("/list")
    public List> userList(){
        String sql="select * from user";
        List> maps = jdbcTemplate.queryForList(sql);
        return maps;
    }

    //增
    @GetMapping("/add")
    public String addUser(){
        String sql="insert into user(id,name,pwd) values(5,'田七',888888)";
        jdbcTemplate.update(sql);
        return "addOk";
    }

    //删
    @GetMapping("/del/{id}")
    public String delUser(@PathVariable("id")int id){
        String sql="delete from user where id=?";
        jdbcTemplate.update(sql,id);
        return "deleteOk";
    }

    //改
    @GetMapping("/update/{id}")
    public String updateUser(@PathVariable("id")int id){
        String sql="update user set name=?,pwd=? where id="+id;
        //修改数据
        Object[] objects = new Object[2];
        objects[0]="XXXX";
        objects[1]="999999";
        jdbcTemplate.update(sql,objects);
        return "updateOk";
    }
}

测试

7.2 整合Druid

开源仓库:https://github.com/alibaba/druid

Druid 是阿里巴巴开源平台上一个数据库连接池实现,结合了 C3P0、DBCP 等 DB 池的优点,同时加入了日志监控。Druid能够提供强大的监控和扩展功能。

com.alibaba.druid.pool.DruidDataSource 基本配置参数:https://github.com/alibaba/druid/wiki/DruidDataSource%E9%85%8D%E7%BD%AE%E5%B1%9E%E6%80%A7%E5%88%97%E8%A1%A8

添加依赖



    com.alibaba
    druid
    1.2.8

在配置文件中修改数据源类型

spring:
  datasource:
    username: root
    password: 密码
    url: jdbc:mysql://localhost:3306/mybatis?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8
    driver-class-name: com.mysql.cj.jdbc.Driver
    type: com.alibaba.druid.pool.DruidDataSource # 自定义数据源

利用之前写好的SpringbootDataJdbcTest测试类打印查看当前的默认数据源

根据官方提供的参数,在配置文件中进行设置。

spring:
  datasource:
    username: root
    password: 密码
    url: jdbc:mysql://localhost:3306/mybatis?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8
    driver-class-name: com.mysql.cj.jdbc.Driver
    type: com.alibaba.druid.pool.DruidDataSource # 自定义数据源

    #以下属性Spring Boot 默认不注入,需要自己配置
    #druid 数据源专有配置
    initialSize: 5  #连接池初始化大小
    minIdle: 5    #最小连接池数量
    maxActive: 20   #最大连接数
    maxWait: 60000   #最大等待时间
    timeBetweenEvictionRunsMillis: 60000
    minEvictableIdleTimeMillis: 300000
    validationQuery: SELECT 1 FROM DUAL
    testWhileIdle: true
    testOnBorrow: false
    testOnReturn: false
    poolPreparedStatements: true

    #配置监控统计拦截的filters。stat:监控统计、log4j:日志记录、wall:防御sql注入
    #如果允许时报错  java.lang.ClassNotFoundException: org.apache.log4j.Priority
    #则导入 log4j 依赖即可
    filters: stat,wall,log4j
    maxPoolPreparedStatementPerConnectionSize: 20
    useGlobalDataSourceStat: true
    connectionProperties: druid.stat.mergeSql=true;druid.stat.slowSqlMillis=500

导入Log4j依赖



    log4j
    log4j
    1.2.17

配置文件中写好的Druid参数需要手动绑定属性,再添加到容器中。

创建一个config.DruidConfig类进行绑定

@Configuration
public class DruidConfig {
    
    @ConfigurationProperties(prefix="spring.datasource")
    @Bean
    public DataSource druidDataSource(){
        return (DataSource) new DruidDataSource();
    }
}

测试类

@SpringBootTest
public class SpringbootDataDruidTest {
    @Autowired
    DataSource dataSource;

    @Test
    public void contextLoads() throws SQLException{
        System.out.println(dataSource.getClass());
        Connection connection = dataSource.getConnection();
        System.out.println(connection);

        DruidDataSource druidDataSource=(DruidDataSource) dataSource;
        System.out.println("druidDateSource 数据源的最大连接数:"+druidDataSource.getMaxActive());
        System.out.println("druidDateSource 数据源的初始化连接数:"+druidDataSource.getInitialSize());
        connection.close();
    }
}

输出

配置Druid数据源监控

Druid 数据源具有监控的功能,并提供了一个 web 界面方便用户查看。

在DruidConfig类中添加以下方法来设置 Druid 的后台管理页面,如账号、密码。

@Bean
public ServletRegistrationBean statViewServlet() {
    ServletRegistrationBean bean = new ServletRegistrationBean(new StatViewServlet(), "/druid
        Map filterMap=new LinkedHashMap<>();

        filterMap.put("/user/add","authc");
        filterMap.put("/user/update","authc");

        bean.setFilterChainDefinitionMap(filterMap);

        return bean;
    }
	//......
}

编写一个登录页面templates/login.html

用户名:

密码:

在MyController中添加相关方法

@RequestMapping("/toLogin")
public String toLogin() {
    return "login";
}

在ShiroConfig的getShiroFilterFactoryBean()方法中设置登录的请求

@Bean(name="shiroFilterFactoryBean")
public ShiroFilterFactoryBean getShiroFilterFactoryBean(
    @Qualifier("defaultWebSecurityManager") DefaultWebSecurityManager securityManager){
    ShiroFilterFactoryBean bean = new ShiroFilterFactoryBean();
    bean.setSecurityManager(securityManager);
    
    Map filterMap=new LinkedHashMap<>();
    filterMap.put("/user/add","authc");
    filterMap.put("/user/update","authc");
    bean.setFilterChainDefinitionMap(filterMap);
    
    //设置登录请求
    bean.setLoginUrl("/toLogin");
    return bean;
}

实现用户认证

在MyController中添加登录请求相关方法

@RequestMapping("/login")
public String login(String username,String password,Model model){
    //获取当前的用户
    Subject subject = SecurityUtils.getSubject();
    //封装用户的登录数据
    UsernamePasswordToken token = new UsernamePasswordToken(username, password);
    try{
        subject.login(token); //登录
        return "index";
    }
    catch (UnknownAccountException e){
        model.addAttribute("msg","用户名错误");
        return "login";
    }
    catch (IncorrectCredentialsException e){
        model.addAttribute("msg","密码错误");
        return "login";
    }
}

修改login.html中的内容

用户名:

密码:

在UserRealm中修改认证方法

//认证
@Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
    System.out.println("执行了=>授权doGetAuthenticationInfo");
    //用户名,密码。这里先不从数据库中取
    String name="root";
    String password="123456";

    UsernamePasswordToken userToken = (UsernamePasswordToken) token;

    if(!userToken.getUsername().equals(name)){
        return null;  //用户名错误
    }

    //密码认证
    return new SimpleAuthenticationInfo("",password,"");
}

整合Mybatis

导入依赖


    org.projectlombok
    lombok


    mysql
    mysql-connector-java


    log4j
    log4j
    1.2.17


    com.alibaba
    druid
    1.1.12


    org.mybatis.spring.boot
    mybatis-spring-boot-starter
    2.1.3

编写application.yml,进行如下配置

spring:
  datasource:
    username: root
    password: 密码
    url: jdbc:mysql://localhost:3306/mybatis?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8
    driver-class-name: com.mysql.cj.jdbc.Driver
    type: com.alibaba.druid.pool.DruidDataSource # 自定义数据源

    #以下属性Spring Boot 默认不注入,需要自己配置
    #druid 数据源专有配置
    initialSize: 5  #连接池初始化大小
    minIdle: 5    #最小连接池数量
    maxActive: 20   #最大连接数
    maxWait: 60000   #最大等待时间
    timeBetweenEvictionRunsMillis: 60000
    minEvictableIdleTimeMillis: 300000
    validationQuery: SELECT 1 FROM DUAL
    testWhileIdle: true
    testOnBorrow: false
    testOnReturn: false
    poolPreparedStatements: true

    #配置监控统计拦截的filters。stat:监控统计、log4j:日志记录、wall:防御sql注入
    #如果允许时报错  java.lang.ClassNotFoundException: org.apache.log4j.Priority
    #则导入 log4j 依赖即可
    filters: stat,wall,log4j
    maxPoolPreparedStatementPerConnectionSize: 20
    useGlobalDataSourceStat: true
    connectionProperties: druid.stat.mergeSql=true;druid.stat.slowSqlMillis=500

在application.properties中配置mybatis相关选项

mybatis.type-aliases-package=com.infinite.shirosptingboot.pojo
mybatis.mapper-locations=classpath:mapper
    @Scheduled(cron="0/2 * * * * ?")   //每2秒执行一次
    public void hello(){
        System.out.println("hello ,schedule test");
    }
}

cron表达式

cron在线生成器

11、Redis

https://spring.io/projects/spring-data-redis

新建一个springboot项目,导入lombok、springbootdevtools、springConfigurationProcessor、springWeb这几个基础依赖,再导入一个SpringDataRedis(Access+Driver)依赖

注:springboot2.x后,原本使用的jedis被替换成了lettuce

jedis:采用直连方式,多线程操作的情况下不安全,若要避免,需要用到jedis pool连接池。更像BIO模式

lettuce:采用netty,实例可以在多个线程中进行共享,不存在线程不安全的情况,可以减少线程数据。更像NIO模式

源码

相关自动配置类RedisAutoConfiguration、配置类RedisProperties

@Configuration(
    proxyBeanMethods = false
)
@ConditionalOnClass({RedisOperations.class})
@EnableConfigurationProperties({RedisProperties.class})
@Import({LettuceConnectionConfiguration.class, JedisConnectionConfiguration.class})
public class RedisAutoConfiguration {
    public RedisAutoConfiguration() {
    }

    @Bean
    @ConditionalOnMissingBean(
        name = {"redisTemplate"}
    ) //若自己实现了一个redisTemplate,则可以替换掉这个默认的模板
    @ConditionalOnSingleCandidate(RedisConnectionFactory.class)
    public RedisTemplate redisTemplate(RedisConnectionFactory redisConnectionFactory) {
        //默认的RedisTemplate没有过多的设置,redis对象都需要序列化
        //两个类型都是object,后续使用时需要用到强制转换
        RedisTemplate template = new RedisTemplate();
        template.setConnectionFactory(redisConnectionFactory);
        return template;
    }

    @Bean
    @ConditionalOnMissingBean
    @ConditionalOnSingleCandidate(RedisConnectionFactory.class)
    public StringRedisTemplate stringRedisTemplate(RedisConnectionFactory redisConnectionFactory) {
        return new StringRedisTemplate(redisConnectionFactory);
    }
}
11.1 使用例

依赖


    org.springframework.boot
    spring-boot-starter-data-redis

完善配置文件内容

#配置redis
spring.redis.host=127.0.0.1
spring.redis.port=6379

编写一个测试类

@SpringBootTest
class Springboot08RedisApplicationTests {

    @Autowired
    private RedisTemplate redisTemplate;

    @Test
    void contextLoads() {
        //redisTemplate 可以操作不同的数据类型
        //opsForValue  操作字符串
        //opsForList 操作list
        //其他redis中的数据类型同理

        //除了基本操作,还可以执行事务和基本的CRUD

        // 获取redis的连接对象(不常用)
        //RedisConnection connection = redisTemplate.getConnectionFactory().getConnection();
        //connection.flushDb();
        //connection.flushAll();
        
        redisTemplate.opsForValue().set("myKey","infinite");
        System.out.println(redisTemplate.opsForValue().get("myKey"));
    }
}

注:本地要先开启redis服务

11.2 自定义RedisTemplate

进入RedisTemplate源码,会发现有几个RedisSerializer属性,这些属性是RedisTemplate的序列化配置

public void afterPropertiesSet() {
    super.afterPropertiesSet();
    boolean defaultUsed = false;
    if (this.defaultSerializer == null) {
        // JdkSerializationRedisSerializer 表示默认选择jdk序列化
        this.defaultSerializer = new JdkSerializationRedisSerializer(this.classLoader != null ? this.classLoader : this.getClass().getClassLoader());
    }
    //......
}

假如要实现用json序列化,可以自己实现一个RedisTemplate,内部具体实现可以参考RedisAutoConfiguration的源码

创建config.RedisConfig

@Configuration
public class RedisConfig {
    @Bean
    @ConditionalOnMissingBean(
            name = {"redisTemplate"}
    )
    @ConditionalOnSingleCandidate(RedisConnectionFactory.class)
    public RedisTemplate redisTemplate(RedisConnectionFactory redisConnectionFactory) {
        RedisTemplate template = new RedisTemplate();
        template.setConnectionFactory(redisConnectionFactory);
        return template;
    }
}

编写实体类pojo.User

@Data
@AllArgsConstructor
@NoArgsConstructor
@Component
public class User {
    private String name;
    private int age;
}

编写测试方法

@Test
public void test() throws JsonProcessingException {
    User user=new User("infinite",20);
    //进行json序列化,redis中存入json字符串。推荐使用json传输数据
    String jsonUser = new ObjectMapper().writeValueAsString(user);
    redisTemplate.opsForValue().set("user",jsonUser);
    System.out.println(redisTemplate.opsForValue().get("user"));
}

假如想要在redis中直接存入对象,则要将对象序列化,即User类要实现Serializable接口。

需求:自定义一个序列化方式

修改RedisConfig代码

//固定模板,完成后就不用再改动了
@Configuration
public class RedisConfig {
    @Bean
    @SuppressWarnings("all")
    public RedisTemplate redisTemplate(RedisConnectionFactory factory) {
        //为了开发使用方便,一般直接使用
        RedisTemplate template = new RedisTemplate();
        template.setConnectionFactory(factory);

        //Json序列化配置
        Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);
        ObjectMapper om = new ObjectMapper();
        om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
        om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
        jackson2JsonRedisSerializer.setObjectMapper(om);
        //String的序列化
        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();

        //key采用String的序列化方式
        template.setKeySerializer(stringRedisSerializer);
        //hash的key采用String的序列化方式
        template.setHashKeySerializer(stringRedisSerializer);
        //value采用jackson序列化方式
        template.setValueSerializer(jackson2JsonRedisSerializer);
        //hash的value采用jackson的序列化方式
        template.setHashValueSerializer(jackson2JsonRedisSerializer);
        return template;
    }
}

为了防止命名冲突,测试类中的redisTemplate需要通过@Qualifier()注解进行标识

@Autowired
@Qualifier("redisTemplate")
private RedisTemplate redisTemplate;

实际开发中,为了提高代码复用性,可以将项目中redis的常见操作进行抽象集成,整合到自定义的RedisUtil工具类中(和之前写jdbc、mybatis同理)。哪个类需要redis操作时,通过@Autowired装配这个工具类即可

可参考的自定义Redis工具类

12、分布式(待完善)

分布式系统的定义:分布式系统时若干独立计算机的集合,这些计算机对于用户来说就像单个系统。

分布式系统中的计算机之间通过网络进行通信,目的是利用更多的机器,处理更多的数据

著有当单个结点的处理能力无法满足日益增长的计算、存储任务,且硬件提升的成本高、应用程序难以进一步优化的时候,才需要考虑分布式系统。

12.1 分布式(待完善) 前置内容

背景

https://dubbo.apache.org/zh/index.html

背景相关的内容可以查看https://dubbo.apache.org/zh/docsv2.7/user/preface/background/

RPC

RPC(Remote Procedure Call):远程过程调用,是一种进程间的通信方式,本质是一种思想而非规范。RPC允许程序调用另一个地址空间(通常是共享网络的另一台机器上)的过程或函数,而不是程序员显式编码这个远程调用的细节,即调用本地和调用远程两种方式的代码基本是相同的。

例:现有两台服务器A、B,一个应用部署在A上,A现在想要调用B服务器上应用提供的函数/方法,由于不再一个内存空间中,A不能直接进行调用,需要通过网络来表达调用的予以和传输调用的数据。

为什么要用到RPC?假设有一个业务,它无法在一个进程内(或一台计算机内)通过本地调用的方式完成,比如不同系统(组织)之间的通讯。由于计算能力需要横向扩展,需要在多台机器组成的集群上部署应用,RPC实现的就是要项调用本地的函数一样去调用远程的函数。

https://www.jianshu.com/p/2accc2840a1b

RPC的两个核心模块:通讯、序列化(方便数据传输)

Dubbo概念

Dubbo是一款高性能、轻量级的开源java RPC框架。它提供了三大核心功能:面向接口的远程方法调用、只能容错和负载均衡、服务自动注册和实现

https://dubbo.apache.org/zh/docs/concepts/service-discovery/

  • Provider(服务提供者): 向服务提供方暴露服务,服务提供者在启动时,向注册中心注册自己提供的服务。
  • Consumer(服务消费者): 调用远程服务的服务消费方,服务消费者在启动时,向注册中心订阅自己所需的服务。消费者从提供者的地址列表中,基于软负载均衡算法,选择一台提供者进行调用,如果调用失败就换一台。
  • Registry(注册中心): 返回服务提供者的地址列表给消费者,如果有变更,注册中心将基于长连接推送变更数据给消费者。
  • Monitor(监控中心): 服务消费者和提供者,让内存中累计调用次数和调用时间,每分钟发送一次统计数据到监控中心
zookeeper

充当注册中心的一个开源项目

使用:

  1. 下载项目压缩包并解压

  2. 执行bin/zkServer.cmd,发现闪退。可以在zkServer.cmd添加pause以排错

  3. 修改conf/zoo.cfg配置文件(没有的话就复制同目录下的zoo_sample.cfg),重新以管理员模式运行bin/zkServer.cmd,以及bin.zkCli.cmd
    修改zoo.cfg中的dataDir、dataLogDir

    dataDir=C:TOOLSapache-zookeeper-3.8.0data
    dataLogDir=C:TOOLSapache-zookeeper-3.8.0log
    

可能出现的问题
1.ZooKeeper audit is disabled

​ 修改zkServer.cmd ,call %JAVA%中添加"-Dzookeeper.audit.enable=true"

客户端下测试

ls /:列出zookeeper根下保存的所有节点

create -e /indinite : 创建一个节点,后面如果跟一个值可以设置存放的内容

get /infinite: 获取/infinite节点的信息

安装dubbo-admin

这是一个springboot项目,作为监控管理后台,查看注册了哪些服务

去github上下载源码并解压

进入项目,解压lib中的jar包,修改dubbo-adminsrcmainresourcesapplication.properties文件中指定的zookeeper地址(默认为本地)

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

打包项目

C:TOOLSdubbo-admin-0.2.0>mvn clean package -D maven.test.skip=true

可能会打包失败,可以参考https://blog.csdn.net/qq_43612538/article/details/103548650

最终打包成dubbo-admin-0.0.1-SNAPSHOT.jar

先启动zookeeper的service端,再启动这个的jar包

12.2 分布式Dubbo+Zookeeper+SpringBoot

新建一个空项目

新建一个provider-server模块(spring),进入这个模块,端口配置为server.port=8001

新建接口service.TicketService

public interface TicketService {
    public String getTicket();
}

实现接口

public class TicketServiceImpl implements TicketService{
    @Override
    public String getTicket(){
        return "infinite";
    }
}

新建一个consumer-server模块(spring),进入这个模块,端口配置为server.port=8002

创建service.UserService类

 

导入依赖(两个模块分别导入)


    org.apache.dubbo
    dubbo-spring-boot-starter
    3.0.7


    com.github.sgroschupf
    zkclient
    0.1




    org.apache.curator
    curator-framework
    4.0.1


    org.apache.curator
    curator-recipes
    4.0.1


    org.apache.zookeeper
    zookeeper
    3.4.13
    
    
        
            org.slf4j
            slf4j-log4j12
        
    

完善provider-server的配置文件

server.port=8001

#服务应用名
dubbo.application.name=provider-server
#注册中心地址
dubbo.registry.address=zookeeper://127.0.0.1:2181
#哪些服务需要注册
dubbo.scan.base-packages=com.infinite.service

给TicketServiceImpl添加dubbo的@DubboService注解,启动时可以被扫描到并注册

@DubboService
public class TicketServiceImpl implements TicketService{
    @Override
    public String getTicket(){
        return "infinite";
    }
}

给主启动类添加@EnableDubbo注解

启动zookeeper的服务端,再启动provider-server,测试是否注册成功

完善consumer-server的配置

server.port=8002

# 消费者去哪里拿服务。需要暴露自己的名字
dubbo.application.name=consumer-server
# 注册中心的地址
dubbo.registry.address=zookeeper://127.0.0.1:2181

在service目录下复制一份provider-server的TicketService接口。

完善UserService

@DubboService
public class UserService {
    @DubboReference //引用,获取provider-server提供的类
    TicketService ticketService;  //同目录下复制了同一份接口,用于引用
    
    public void butTicket(){
        String ticket=ticketService.getTicket();
        System.out.println("在注册中心拿到==>"+ticket);
    }
}

编写测试

 
步骤 

前提:开启zookeeper服务

  1. 提供者提供服务
    1. 导入依赖
    2. 配置注册中心的地址,以及服务发现名、要扫描的包
    3. 在想要被注册的服务上,增加一个注解@DubboService
  2. 消费者如何消费
    1. 导入依赖
    2. 配置注册中心的地址,配置自己的服务名
    3. 从远程注入服务@DubboReference
      新建一个provider-server模块(spring),进入这个模块,端口配置为server.port=8001

新建接口service.TicketService

public interface TicketService {
    public String getTicket();
}

实现接口

public class TicketServiceImpl implements TicketService{
    @Override
    public String getTicket(){
        return "infinite";
    }
}

新建一个consumer-server模块(spring),进入这个模块,端口配置为server.port=8002

创建service.UserService类

 

导入依赖(两个模块分别导入)


    org.apache.dubbo
    dubbo-spring-boot-starter
    3.0.7


    com.github.sgroschupf
    zkclient
    0.1




    org.apache.curator
    curator-framework
    4.0.1


    org.apache.curator
    curator-recipes
    4.0.1


    org.apache.zookeeper
    zookeeper
    3.4.13
    
    
        
            org.slf4j
            slf4j-log4j12
        
    

完善provider-server的配置文件

server.port=8001

#服务应用名
dubbo.application.name=provider-server
#注册中心地址
dubbo.registry.address=zookeeper://127.0.0.1:2181
#哪些服务需要注册
dubbo.scan.base-packages=com.infinite.service

给TicketServiceImpl添加dubbo的@DubboService注解,启动时可以被扫描到并注册

@DubboService
public class TicketServiceImpl implements TicketService{
    @Override
    public String getTicket(){
        return "infinite";
    }
}

给主启动类添加@EnableDubbo注解

启动zookeeper的服务端,再启动provider-server,测试是否注册成功

完善consumer-server的配置

server.port=8002

# 消费者去哪里拿服务。需要暴露自己的名字
dubbo.application.name=consumer-server
# 注册中心的地址
dubbo.registry.address=zookeeper://127.0.0.1:2181

在service目录下复制一份provider-server的TicketService接口。

完善UserService

@DubboService
public class UserService {
    @DubboReference //引用,获取provider-server提供的类
    TicketService ticketService;  //同目录下复制了同一份接口,用于引用
    
    public void butTicket(){
        String ticket=ticketService.getTicket();
        System.out.println("在注册中心拿到==>"+ticket);
    }
}

编写测试

 
步骤 

前提:开启zookeeper服务

  1. 提供者提供服务
    1. 导入依赖
    2. 配置注册中心的地址,以及服务发现名、要扫描的包
    3. 在想要被注册的服务上,增加一个注解@DubboService
  2. 消费者如何消费
    1. 导入依赖
    2. 配置注册中心的地址,配置自己的服务名
    3. 从远程注入服务@DubboReference
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/919121.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号