了解springcloud微服务基本组件等相关基础知识

基本组件

  • 服务发现——Eureka
  • 客服端负载均衡——Ribbon
  • 远程调用——Feign
  • 断路器——Hystrix
  • 服务网关——Zuul
  • 分布式配置——Spring Cloud Config

父工程环境搭建

pom依赖
子模块依赖管理

<dependencyManagement>
        <dependencies>
            <!-- 导入SpringCloud需要的依赖信息 -->
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>Hoxton.SR8</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
            <!-- SpringBoot依赖信息 -->
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-dependencies</artifactId>
                <version>2.3.3.RELEASE</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>

            <!--SpringBoot整合MyBatis的依赖-->
            <dependency>
                <groupId>org.mybatis.spring.boot</groupId>
                <artifactId>mybatis-spring-boot-starter</artifactId>
                <version>2.1.3</version>
            </dependency>

            <!--druid依赖信息-->
            <dependency>
                <groupId>com.alibaba</groupId>
                <artifactId>druid</artifactId>
                <version>1.1.17</version>
            </dependency>



        </dependencies>
    </dependencyManagement>

环境相关依赖

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

eureka环境搭建

pom环境

	 <dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>
  • 配置中心
server:
  port: 5000
eureka:
  instance:
    hostname: localhost
  client:
    register-with-eureka: false # 自己就是注册中心,所以自己不注册自己
    fetch-registry: false # 自己就是注册中心,所以不需要“从注册中心取回信息”
    service-url: # 客户端访问 Eureka 时使用的地址
      defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/

  • 主启动类
@EnableEurekaServer
@SpringBootApplication
public class eureka {
    public static void main(String[] args) {

        SpringApplication.run(eureka.class,args);
    }
}

  • 展示

基本服务提供

pom环境

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

        <dependency>
            <groupId>com.JW.springcloud</groupId>
            <artifactId>pro43-spring-cloud-common</artifactId>
            <version>0.0.1-SNAPSHOT</version>
        </dependency>


        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
<!--            <version>2.2.0.RELEASE</version>-->
        </dependency>


        <!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-netflix-hystrix -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
<!--            <version>2.2.4.RELEASE</version>-->
        </dependency>


        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-actuator</artifactId>
            <version>2.4.2</version>
        </dependency>



    </dependencies>

  • 配置文件
server:
  port: 1001

eureka:
  client:
    service-url:
      defaultZone: http://localhost:5000/eureka/
spring:
  application:
    name: springcloud-provider
  • controller方法
import com.JW.springcloud.Employee;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;

import org.springframework.http.HttpRequest;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import springcloud.JW.springcloud.Config.ResultEntity;

import javax.servlet.http.HttpServletRequest;

@RestController
public class EmployeeHandler {
    @RequestMapping("/provider/get/employee/remote")
    public Employee getEmployeeRemote(HttpServletRequest request) {
        int serverPort = request.getServerPort();
        return new Employee(555, "tom555-" + serverPort, 555.55);
    }

    @RequestMapping("/provider/get/employee/by/id")
    public Employee getEmployeeById(@RequestParam("empId") Integer empId) {
        return new Employee(empId, "tom999-", 999.99);
    }

    @RequestMapping("/provider/save/emp")
    public Employee saveEmp(@RequestBody Employee employee) {

        return employee;
    }

    //熔断方法
    @HystrixCommand(fallbackMethod = "getEmpBackup")
    @RequestMapping("/provider/circuit/breaker/get/emp")
    public ResultEntity<Employee> getEmp(@RequestParam("signal") String signal) {
        if ("bang".equals(signal)) {
            throw new RuntimeException();
        }
        return ResultEntity.successWithData(new Employee(666, "sam666", 666.66));
    }

    public ResultEntity<Employee> getEmpBackup(@RequestParam("signal") String signal) {
        return ResultEntity.failed("circuit break workded,with signal=" + signal);
    }
}
  • 自定义封装返回值类型
public class ResultEntity<T> {

    public static final String SUCCESS = "SUCCESS";
    public static final String FAILED = "FAILED";
    public static final String NO_MESSAGE = "NO_MESSAGE";
    public static final String NO_DATA = "NO_DATA";

    /*** 操作成功,不需要返回数据 * @return */
    public static ResultEntity<String> successWithoutData() {
        return new ResultEntity<String>(SUCCESS, NO_MESSAGE, NO_DATA);
    }

    /*** 操作成功,需要返回数据 * @param data * @return */
    public static <E> ResultEntity<E> successWithData(E data) {
        return new ResultEntity<E>(SUCCESS, NO_MESSAGE, data);
    }

    /*** 操作失败,返回错误消息 * @param message * @return */
    public static <E> ResultEntity<E> failed(String message) {
        return new ResultEntity<E>(FAILED, message, null);
    }

    private String result;
    private String message;
    private T data;

    public ResultEntity() {
    }

    public ResultEntity(String result, String message, T data) {
        super();
        this.result = result;
        this.message = message;
        this.data = data;

    }

    @Override
    public String toString() {
        return "ResultEntity{" +
                "result='" + result + '\'' +
                ", message='" + message + '\'' +
                ", data=" + data +
                '}';
    }

    public static String getSUCCESS() {
        return SUCCESS;
    }

    public static String getFAILED() {
        return FAILED;
    }

    public static String getNoMessage() {
        return NO_MESSAGE;
    }

    public static String getNoData() {
        return NO_DATA;
    }

    public String getResult() {
        return result;
    }

    public void setResult(String result) {
        this.result = result;
    }

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }
}

  • 主启动类配置
@EnableHystrix
@EnableCircuitBreaker
@EnableEurekaClient
@SpringBootApplication
public class CrowdMain {
    public static void main(String[] args) {
        SpringApplication.run(CrowdMain.class, args);
    }
}

在这里插入图片描述

Ribbon(远程调用)

pom环境

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

        <dependency>
            <groupId>com.JW.springcloud</groupId>
            <artifactId>pro43-spring-cloud-common</artifactId>
            <version>0.0.1-SNAPSHOT</version>
        </dependency>


        <!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-netflix-ribbon -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
            <version>2.2.3.RELEASE</version>
        </dependency>


        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>


    </dependencies>
  • 配置类
@Configuration
public class CloudConfig {
    @Bean
    @LoadBalanced //负载均衡器
    public RestTemplate getRestTemplate() {
        return new RestTemplate();
    }
}
server:
  port: 4000
spring:
  application:
    name: springcloud-consumer
eureka:
  client:
    service-url:
      defaultZone: http://localhost:5000/eureka/


  • 方法类
@RestController
public class HumanResourceHandler {
    @Autowired
    private RestTemplate restTemplate;

    @RequestMapping("/consumer/get/employee")
    public Employee getEmployeeRemote() {

        // 远程调用方法的主机地址
		//String host = "http://localhost:1000";


        String host = "http://springcloud-provider:1000";
        // 远程调用方法的具体 URL 地址
        String url = "/provider/get/employee/remote";


       
        // 远程调用方法的具体 URL 地址
        String url = "/provider/get/employee/remote";

        return restTemplate.getForObject(host + url, Employee.class);
    }
}

在这里插入图片描述
基于 @LoadBalanced环境测试

  • 同时开启provider服务1000,1001,1002端口
    在这里插入图片描述
  • 测试
    在这里插入图片描述

远程调用——Feign

创建实体common工程(远程调用开放接口工程)
pom环境

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

        <!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-netflix-hystrix -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
        </dependency>

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

Employee

 private Integer empId;
    private String empName;
    private Double empSalary;

远程调用接口

@Component
@FeignClient(value = "springcloud-provider")
public interface EmployeeRemoteService {



    @RequestMapping("/provider/get/employee/remote")
    public Employee getEmployeeRemote();



    @RequestMapping("/provider/get/employee/by/id")
    public Employee getEmployeeById(@RequestParam("empId") Integer empId);

    @RequestMapping("/provider/save/emp")
    public Employee saveEmp(@RequestBody Employee employee);

}


测试远程调用接口,创建消费者工程
pom环境

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

        <dependency>
            <groupId>com.JW.springcloud</groupId>
            <artifactId>pro43-spring-cloud-common</artifactId>
            <version>0.0.1-SNAPSHOT</version>
        </dependency>

        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
<!--            <version>2.1.2.RELEASE</version>-->
        </dependency>




<!--        <dependency>-->
<!--            <groupId>org.springframework.cloud</groupId>-->
<!--            <artifactId>spring-cloud-starter-openfeign</artifactId>-->
<!--            <version>2.1.2.RELEASE</version>-->
<!--        </dependency>-->

        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
<!--            <version>2.1.2.RELEASE</version>-->
        </dependency>


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




    </dependencies>
@RestController
public class EmployeeFeignHandler {
    @Autowired
    private EmployeeRemoteService employeeRemoteService;


    @RequestMapping("/feign/consumer/get/emp")
    public Employee getEmployeeRemote() {
        return employeeRemoteService.getEmployeeRemote();
    }}
server:
  port: 7000
spring:
  application:
    name: springcloud-consumer
eureka:
  client:
    service-url:
      defaultZone: http://localhost:5000/eureka/
feign:
  hystrix:
    enabled: true  //开启熔断功能

主启动类

@SpringBootApplication
@EnableFeignClients
@EnableHystrix
@EnableCircuitBreaker
public class app {
    public static void main(String[] args) {
        SpringApplication.run(app.class,args);
    }

}

在这里插入图片描述

Hystrix降级和熔断功能

以provider为例,加上如下配置

feign:
  hystrix:
    enabled: true

@HystrixCommand(fallbackMethod = "getEmpBackup")
    @RequestMapping("/provider/circuit/breaker/get/emp")
    public ResultEntity<Employee> getEmp(@RequestParam("signal") String signal) {
        if ("bang".equals(signal)) {
            throw new RuntimeException();
        }
        return ResultEntity.successWithData(new Employee(666, "sam666", 666.66));
    }

    public ResultEntity<Employee> getEmpBackup(@RequestParam("signal") String signal) {
        return ResultEntity.failed("circuit break workded,with signal=" + signal);
    }

测试,bang,生效
在这里插入图片描述
测试123
在这里插入图片描述
降级功能

  • 改变common工程,加入fallbackFactory 属性
@Component
@FeignClient(value = "springcloud-provider",fallbackFactory = MyFallBackFactory.class)
public interface EmployeeRemoteService {}
  • 同时加入MyFallBackFactory
@Component
public class MyFallBackFactory implements FallbackFactory<EmployeeRemoteService> {
    // cause 对象是失败原因对应的异常对象
    @Override
    public EmployeeRemoteService create(final Throwable cause) {
        return new EmployeeRemoteService() {
            @RequestMapping("/provider/save/emp")
            public Employee saveEmp(@RequestBody Employee employee) {
                return null;
            }

            @RequestMapping("/provider/get/employee/by/id")
            public Employee getEmployeeById(@RequestParam("empId") Integer empId) {
                return null;
            }

            @RequestMapping("/provider/get/employee/remote")
            public Employee getEmployeeRemote() {
                return new Employee(444, "call provider failed,fall back here, reason is " + cause.getClass().getName() + " " + cause.getMessage(), 444.444);
            }


        };
    }
}

测试正常访问http://localhost:4000/consumer/get/employee
在这里插入图片描述

  • 关闭provider服务
    在这里插入图片描述
  • 成功开启降级措施
    在这里插入图片描述

Zuu网关

pom环境

<dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-zuul</artifactId>
        </dependency>



    </dependencies>
server:
  port: 80
spring:
  application:
    name: springcloud-zuul
  main:
    allow-bean-definition-overriding: true
eureka:
  client:
    service-url:
      defaultZone: http://localhost:5000/eureka/


zuul:
  host:
    connect-timeout-millis: 3000
    socket-timeout-millis: 3000


  ignored-services: "*"       # 表示忽视直接通过application-name访问微服务,必须通过route
  sensitive-headers: "*"      # 在Zuul向其他微服务重定向时,保持原本的头信息(请求头、响应头)
  routes:                     # 指定网关路由
    crowd-protal:
      service-id: springcloud-auth  # 对应application-name
      path: /**               # 表示直接通过根路径访问,必须加上**,否则多层路径无法访问
    crowd-project:
      service-id: springcloud-provider
      path: /provider/**
    crowd-order:
      service-id: springcloud-consumer
      path: /consumer/**

主启动类

@SpringBootApplication
@EnableZuulProxy
public class zull {
    public static void main(String[] args) {
        SpringApplication.run(zull.class,args);
    }
}

样例:创建springcloud-auth实例
controller

@Controller
public class PortalHandler {

    @RequestMapping("/")
    public String showPortalPage() {
        // 这里实际开发中需要加载数据……
        return "index";
    }

}

配置

server:
  port: 2000
spring:
  application:
    name: springcloud-con
eureka:
  client:
    service-url:
      defaultZone: http://localhost:5000/eureka

以网关的形式去访问http://localhost/
在这里插入图片描述

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

唐 昊

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值