谷粒学院项目笔记10——SpringCloud

 尚硅谷谷粒学院项目第十天内容之SpringCloud

概念

 微服务:是一种架构风格,指将一个服务拆分成多个独立的服务模块,从而解耦合

SpringCloud不是一个技术,而是多种技术的总称,SpringCloud依赖SpringBoot

attention:SpringCloud和SpringBoot之间有版本对应关系

SpringCloud里的技术:

版本区别

SNAPSHOT:快照版本,随时可能修改

M:MileStone,里程碑版本

           SR:Service Release,正式版本

GA:Generally Avaliable,稳定版本

 Nacos

在微服务中,service-edu和service-vod是两个独立的模块,现在要在service-edu模块中去调用service-vod模块,一个方法是引入依赖,可是,引入了依赖后,他们就不是互相独立的两个模块了

此时,我们通过nacos(注册中心)实现

安装

安装包解压,双击bin/startup.cmd启动nacos

访问:http://localhost:8848/nacos/

登录时用户名密码都是nacos

服务注册

在service模块中引入依赖

        <!--服务注册-->
         <dependency>
             <groupId>org.springframework.cloud</groupId>
             <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
         </dependency>

在service-edu的application.properties中配置nacos地址

#nacos服务地址
spring.cloud.nacos.discovery.server-addr=127.0.0.1:8848

在service-edu的启动类上加上注解

@EnableDiscoveryClient //启用nacos

启动service-edu模块,在nacos的服务列表中可以

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

看到,service-edu注册到了nacos中

如果模块启动失败,可能是类路径下的配置文件没有被重新加载

在service-vod模块重复以上操作进行服务注册

Feign 

服务调用feign用来解决两个独立的模块之间的相互调用问题

这两个独立的模块需要在nacos中进行注册

在service模块中引入依赖

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

在调用端(service-edu)启动类上添加服务发现注解

@EnableFeignClients //启用feign

创建client/VodClient.java用来指明feign调用哪个服务

@FeignClient("service-vod") //调用service-vod
@Component
public interface VodClient {

    //定义要调用的方法
    //根据视频id删除视频
    @DeleteMapping("vodservice/deleteVideo/{id}")
    public R deleteVideo(@PathVariable("id") String id); //注意:@PathVariable要指明参数名称
}

完善删除小节功能

EduVideoController

    //删除小节,同时删除小节对应的视频
    @DeleteMapping("deleteVideo/{videoId}")
    public R deleteVideo(@PathVariable String videoId){
        videoService.deleteByVideoId(videoId);
        return R.ok();
    }

EduVideoServiceImpl.java

    @Autowired
    private VodClient vodClient; //先注入
    @Override
    public void deleteByVideoId(String videoId) {
        EduVideo eduVideo = baseMapper.selectById(videoId);
        String videoSourceId = eduVideo.getVideoSourceId();
        if (!StringUtils.isEmpty(videoId)){
            vodClient.deleteVideo(videoSourceId);//删除阿里云中的视频
        }
        baseMapper.deleteById(videoId); //删除小节
    }

测试

根据课程id删除阿里云中的视频

service_vod模块

VodController

    //根据多个视频id删除多个视频
    @DeleteMapping("batchDeleteVideos")
    public R batchDeleteVideos(@RequestParam("videoList") List<String> videoList){
        vodService.batchDeleteVideos(videoList);
        return R.ok();
    }

VodServiceImpl

    //删除多个视频
    @Override
    public void batchDeleteVideos(List<String> videoList) {
        try{
            DefaultAcsClient client = InitClient.initVodClient(ConstantUtils.ACCESS_KEY_ID, ConstantUtils.ACCESS_KEY_SECRET);
            DeleteVideoRequest request = new DeleteVideoRequest();
            String s = StringUtils.join(videoList, ",");
            request.setVideoIds(s);
            client.getAcsResponse(request);
        }catch (Exception e){
            throw new GuliException(20001,"删除视频失败");
        }
    }

service_edu模块中

VodClient

    //根据多个视频id删除多个视频
    @DeleteMapping("vodservice/batchDeleteVideos")
    public R batchDeleteVideos(@RequestParam("videoList") List<String> videoList);

EduCourseServiceImpl

    //删除课程
    @Override
    public void deleteCourse(String courseId) {
        QueryWrapper<EduVideo> queryWrapper = new QueryWrapper<>();
        queryWrapper.select("video_source_id");
        queryWrapper.eq("course_id",courseId);
        List<EduVideo> eduVideoList = videoService.list(queryWrapper);
        List<String> videoList = new ArrayList<>();
        if (!eduVideoList.isEmpty()){
            for (EduVideo eduVideo:eduVideoList){
                String videoSourceId = eduVideo.getVideoSourceId();
                videoList.add(videoSourceId);
            }
            vodClient.batchDeleteVideos(videoList);
            videoService.removeByCourseId(courseId);
        }
        baseMapper.deleteById(courseId); //删除edu_course
        courseDescriptionService.removeById(courseId);
        chapterService.removeByCourseId(courseId);
    }

 swagger测试

SpringCloud接口调用流程

1、接口化请求调用:定义调用谁

2、feign:根据映射路径发起Http请求

3、hystrix:被调用的模块宕机时,及时熔断两个模块之间的连接

4、ribbon:当被调用的模块是分布式部署时,将请求负载均衡到被调用的模块上

5、httpClient:执行http请求(调用生产者的接口)

熔断器Hystrix

管理生产者(被调用端)和消费者(调用端)之间的调用情况

当生产者宕机时,熔断消费者对生产者的调用

使用

添加熔断器依赖

        <!--消费者调用生产者时的负载均衡-->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
        </dependency>

        <!--hystrix依赖,主要是用  @HystrixCommand -->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
        </dependency>

在调用端的配置文件中开启熔断机制

#开启熔断机制
feign.hystrix.enabled=true

创建VodClient接口的实现类,用于熔断后的处理

@Component
public class VodClientImpl implements VodClient{

    //service-vod模块熔断后,此方法被调用
    @Override
    public R deleteVideo(String id) {
        return R.error().message("service-vod模块被熔断了,删除视频失败");
    }

    @Override
    public R batchDeleteVideos(List<String> videoList) {
        return R.error().message("service-vod模块被熔断了,删除多个视频失败");
    }
}

修改VodClient接口的注解,指明service-vod被熔断后执行的类

@FeignClient(value = "service-vod",fallback = VodClientImpl.class) //调用service-vod
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值