zoukankan      html  css  js  c++  java
  • 手摸手学会Spring Cloud Alibaba微服务构建示例,从0到1

    前言

    PS:一切脱离业务的架构,都是耍流氓~

    为何需要微服务

    当传统的单体应用无法满足日益见长的业务需求时(例如:并发,性能,可用性),就需要开始考虑微服务的架构。

    总的来说,现有的微服务体系,包含有许多的模块,这些模块需要互相搭配着使用,才能展现出微服务架构的魅力于优势。

    Spring Cloud Alibaba这一套,官方文档:https://github.com/alibaba/spring-cloud-alibaba/blob/master/README-zh.md

    一些准备

    nacos启动

    在微服务架构中,nacos为我们提供了服务发现与注册,统一配置的管理等一些功能。

    nacos下载地址:https://nacos.io/zh-cn/docs/quick-start.html,为了友好体验本实例,避免各组件间因版本不一致,导致冲突,我们下载2.0.3版本。

    默认配置情况下,nacos服务端口是8848,地址与端口后面的微服务里边会用到。

    sentinel启动

    在微服务架构中,sentinel为我们提供了服务的降级、熔断、限流等功能,可以很好的保证微服务系统中,核心接口的高可用性。

    下载地址:https://github.com/alibaba/Sentinel/releases/tag/1.8.2

    启动命令:nohup java -Dserver.port=9090  -Dcsp.sentinel.dashboard.server=localhost:9090 -Dproject.name=sentinel-dashboard -jar sentinel-dashboard-1.8.2.jar >> sentinel.log 2>&1 &

    PS:我们修改了sentinel服务的端口为9090

    工程结构

    工程pom.xml配置

    ParentPro父级工程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 http://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.3.2.RELEASE</version>
      </parent>
    
      <groupId>com.wslio</groupId>
      <artifactId>ParentPro</artifactId>
      <version>1.0</version>
    
      <!-- 父级项目中,此处配置为pom -->
      <packaging>pom</packaging>
    
      <properties>
        <java.version>1.8</java.version>
        <spring-boot-version>2.3.2.RELEASE</spring-boot-version>
        <spring-cloud-version>2.2.6.RELEASE</spring-cloud-version>
        <spring-cloud-dependencies>2.2.6.RELEASE</spring-cloud-dependencies>
        <spring-cloud-nacos-version>2.2.6.RELEASE</spring-cloud-nacos-version>
        <spring-cloud-openfeign-version>2.2.6.RELEASE</spring-cloud-openfeign-version>
        <spring-cloud-gateway-version>2.2.6.RELEASE</spring-cloud-gateway-version>
        <ali-csp-version>1.8.1</ali-csp-version>
      </properties>
    
      <!-- 这里放子模块 -->
      <modules>
        <module>Child-Common</module>
        <module>Child-Provider</module>
        <module>Child-Consumer</module>
        <module>Child-Gateway</module>
      </modules>
    
      <!-- 放共有的依赖 -->
      <dependencies>
        <!-- 所有的子工程都会用nacos来注册服务 -->
        <dependency>
          <groupId>com.alibaba.cloud</groupId>
          <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
        </dependency>
    
        <dependency>
          <groupId>org.projectlombok</groupId>
          <artifactId>lombok</artifactId>
          <version>1.18.20</version>
          <scope>provided</scope>
        </dependency>
    
      </dependencies>
    
      <!-- 统一依赖版本管理 -->
      <dependencyManagement>
        <dependencies>
          <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-alibaba-dependencies</artifactId>
            <version>${spring-cloud-dependencies}</version>
            <type>pom</type>
            <scope>import</scope>
          </dependency>
    
          <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
            <version>${spring-cloud-nacos-version}</version>
          </dependency>
    
          <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
            <version>${spring-cloud-openfeign-version}</version>
          </dependency>
    
          <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-gateway</artifactId>
            <version>${spring-cloud-gateway-version}</version>
          </dependency>
    
          <dependency>
            <groupId>com.alibaba.csp</groupId>
            <artifactId>sentinel-core</artifactId>
            <version>${ali-csp-version}</version>
          </dependency>
          <dependency>
            <groupId>com.alibaba.csp</groupId>
            <artifactId>sentinel-transport-simple-http</artifactId>
            <version>${ali-csp-version}</version>
          </dependency>
        </dependencies>
      </dependencyManagement>
    
      <build>
        <plugins>
          <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
            <configuration>
              <skip>true</skip>
            </configuration>
            <executions>
              <execution>
                <goals>
                  <goal>repackage</goal>
                </goals>
              </execution>
            </executions>
          </plugin>
        </plugins>
      </build>
    </project>
    View Code

     

    Child-Common子工程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.wslio</groupId>
            <artifactId>ParentPro</artifactId>
            <version>1.0</version>
            <relativePath>../pom.xml</relativePath>
        </parent>
        <groupId>com.wslio</groupId>
        <artifactId>Child-Common</artifactId>
        <version>1.0</version>
    
        <dependencies>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
        </dependencies>
    
        <build>
            <plugins>
                <plugin>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-maven-plugin</artifactId>
                    <configuration>
                        <!--被依赖的公共模块必须加上这个,打包之后启动,选择后面带EXE的启动,依赖该模块的其他模块就不会因为找不到依赖而打包出错-->
                        <classifier>exe</classifier>
                    </configuration>
                </plugin>
            </plugins>
        </build>
    </project>
    View Code

    Child-Consumer子工程pom.xml文件配置

    服务消费者,消费Provider工程的一些api接口。

    <?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.wslio</groupId>
            <artifactId>ParentPro</artifactId>
            <version>1.0</version>
            <relativePath>../pom.xml</relativePath>
        </parent>
        <groupId>com.wslio</groupId>
        <artifactId>Child-Consumer</artifactId>
        <version>1.0</version>
    
        <dependencies>
            <dependency>
                <groupId>com.wslio</groupId>
                <artifactId>Child-Common</artifactId>
                <version>1.0</version>
            </dependency>
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
            <dependency>
                <groupId>com.alibaba.cloud</groupId>
                <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
            </dependency>
            <dependency>
                <groupId>com.alibaba.csp</groupId>
                <artifactId>sentinel-core</artifactId>
            </dependency>
            <dependency>
                <groupId>com.alibaba.csp</groupId>
                <artifactId>sentinel-transport-simple-http</artifactId>
            </dependency>
            <dependency>
                <groupId>com.alibaba.csp</groupId>
                <artifactId>sentinel-web-servlet</artifactId>
            </dependency>
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-starter-openfeign</artifactId>
            </dependency>
        </dependencies>
    </project>
    View Code

    Child-Gateway子工程pom.xml文件配置

    在微服务架构中,gateway为我们的微服务提供了统一的入口,避免了微服务的调用难题,在gateway这层,还适合做一些通用的功能,比如微服务鉴权,操作日志等。

    <?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.wslio</groupId>
            <artifactId>ParentPro</artifactId>
            <version>1.0</version>
            <relativePath>../pom.xml</relativePath>
        </parent>
        <groupId>com.wslio</groupId>
        <artifactId>Child-Gateway</artifactId>
        <version>1.0</version>
    
        <dependencies>
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-starter-gateway</artifactId>
            </dependency>
        </dependencies>
    </project>
    View Code

    Child-Provider子工程pom.xml文件配置

    服务提供方,提供一些api接口服务,给其他工程调用的。

    <?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.wslio</groupId>
            <artifactId>ParentPro</artifactId>
            <version>1.0</version>
            <relativePath>../pom.xml</relativePath>
        </parent>
        <groupId>com.wslio</groupId>
        <artifactId>Child-Provider</artifactId>
        <version>1.0</version>
    
        <dependencies>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
        </dependencies>
    </project>
    View Code

     工程application.yml配置

    ParentPro工程

    不用配置application.yml

    Child-Common子工程

    server:
      port: 9003
    spring:
      application:
        name: child-common
      cloud:
        nacos:
          discovery:
            server-addr: 192.168.50.16:8848
    View Code

    Child-Consumer子工程

    server:
      port: 9012
    spring:
      application:
        name: child-consumer
      cloud:
        nacos:
          discovery:
            server-addr: 192.168.50.16:8848
        sentinel:
          transport:
            port: 8719
            dashboard: 192.168.50.16:9090
      main:
        allow-bean-definition-overriding: true
    feign:
      sentinel:
        enabled: true
    View Code

    Child-Gateway子工程

    server:
      port: 9004
    spring:
      application:
        name: child-gateway
      cloud:
        nacos:
          discovery:
            server-addr: 192.168.50.16:8848
        gateway:
          routes:
            - id: child-consumer
              uri: lb://child-consumer
              predicates:
                - Path=/consumer/*
    View Code

    Child-Provider子工程

    server:
      port: 9006
    spring:
      application:
        name: child-provider
      cloud:
        nacos:
          discovery:
            server-addr: 192.168.50.16:8848
    View Code

    工程java源代码

    ParentPro工程

    该工程没有源代码

    Child-Common子工程

    目录结构

    Child-Consumer子工程

    目录结构

    源代码:

    package com.wslio.childconsumer.controller;
    
    import com.wslio.childconsumer.service.ProviderService;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestParam;
    import org.springframework.web.bind.annotation.RestController;
    import javax.annotation.Resource;
    
    @RestController
    @Slf4j
    public class PlayerController {
        @Resource
        private ProviderService providerService;
    
        @RequestMapping("/consumer/musicplay")
        public String musicplay(@RequestParam String musicPath){
            log.info("musicplay 调用!");
            return providerService.musicPlay(musicPath);
        }
    
        @RequestMapping("/consumer/videoplay")
        public String videoplay(@RequestParam String videoPath){
            return providerService.videoPlay(videoPath);
        }
    }
    PlayerController.java
    package com.wslio.childconsumer.service;
    
    import com.wslio.childconsumer.service.impl.MusicServiceFallBack;
    import org.springframework.cloud.openfeign.FeignClient;
    import org.springframework.stereotype.Component;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestParam;
    
    @Component
    @FeignClient(value = "child-provider", fallback = MusicServiceFallBack.class)
    public interface ProviderService {
    
        @RequestMapping("/provider/musicplay")
        String musicPlay(@RequestParam String musicPath);
    
        @RequestMapping("/provider/videoplay")
        String videoPlay(@RequestParam String videoPath);
    }
    ProviderService.java
    package com.wslio.childconsumer.service.impl;
    
    import com.wslio.childconsumer.service.ProviderService;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.stereotype.Component;
    
    @Component
    @Slf4j
    public class MusicServiceFallBack implements ProviderService {
        @Override
        public String musicPlay(String musicPath) {
            log.error("musicPlay 调用失败! 服务降级!");
            return "musicPlay error!";
        }
    
        @Override
        public String videoPlay(String videoPath) {
            log.error("videoPlay 调用失败! 服务降级!");
            return "videoPlay error!";
        }
    }
    MusicServiceFallBack.java

    config目录下的文件没用到。

    Child-Gateway子工程

    目录结构

    Child-Provider子工程

    目录结构

     源代码:

    package com.wslio.childprovider.controller;
    
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestParam;
    import org.springframework.web.bind.annotation.RestController;
    
    @RestController
    @Slf4j
    public class MusicController {
    
        @RequestMapping("/provider/musicplay")
        public String musicPlay(@RequestParam String musicPath){
            log.info("播放音乐文件[{}]", musicPath);
            return musicPath;
        }
    }
    MusicController.java
    package com.wslio.childprovider.controller;
    
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestParam;
    import org.springframework.web.bind.annotation.RestController;
    
    @RestController
    @Slf4j
    public class VideoController {
    
        @RequestMapping("/provider/videoplay")
        public String videoPlay(@RequestParam String videoPath){
            log.info("播放视频文件[{}]", videoPath);
            return videoPath;
        }
    }
    VideoController.java

    PS:以上源码,里边没有涉及到分布式事务,没时间搞了。。。,但大致的架子已经搭起来,通过consumer可以顺利调取provider的服务,亦能通过gateway服务调用微服务!

    不想手动搞的,这里有git直通车分享,https://github.com/wslio/ParentPro.git

  • 相关阅读:
    7月24日学习
    7月23日学习
    7月22日学习
    7月21日学习
    【编程技巧】applicationContext.xml 里面可配置bean和数据库地址
    【编程技巧】 输入框只能输入中文
    【开发技术】Beyond Compare
    【编程技巧】Ext.QuickTips.init();
    【开发技术】常用正则表达式大全!(例如:匹配中文、匹配html)
    【编程技巧】addSubview和insertSubview的区别
  • 原文地址:https://www.cnblogs.com/wslio/p/15286614.html
Copyright © 2011-2022 走看看