在线学习平台-章模块

2023-12-13 11:03:37

在线学习平台------手把手教程👈

章与节是绑定在一起的,查询章的时候,对应的小节也要一起查询出来

sql1

sql语句这样写,会有问题。

如果有课程(课程下面无小节),这样的话关联出的内容都是空的

那么 在执行t2.del_flag = '2'时, 空值和2是比不出来的,所以这个章节会查不出来

在用最后一行 t1.course id = #{courseId}时,无论传入什么内容,课程下无小节的内容都查不出来

sql2

在排除假删的时候用的是t2.delflag != '2',要多或一个条件 t2.lessonId IS NULL

记得要设置好排序

?所需字段

前期准备:

? ? ? ? 同样先把在?com.mashang.elearing.domain下,用自定义生成实体类工具:

? ? ? ? 数据类型改成包装类,设置好主键是自动递增,章不需要设置自动填充之类的

package com.mashang.elearing.domain;

import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import lombok.Data;

import java.util.Date;

@Data
public class MsChapter {

  @TableId(type = IdType.AUTO)
  private Long chapterId;
  private Long courseId;
  private String chapterName;
  private Long chapterSort;
  private String delFlag;
  private String createBy;
  private Date createTime;
  private String updateBy;
  private Date updateTime;
  private String remark;

}

? ? ? ? 查询所有章节

? ? ? ? 创建返回实体类

? ? ? ? ?在domai下的Vo包创建MsChapterLessonVo

? ? ? ? ?章节是一对多的关系,在创建章之前,要先创建节的MsLessonVo

package com.mashang.elearing.domain.vo;

import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;


@ApiModel("节模块")
@Data
public class MsLessonsVo {

    @ApiModelProperty("节id")
    private Long lessonId;

    @ApiModelProperty("节名称")
    private String lessonName;

    @ApiModelProperty("节排序")
    private Long lessonSort;


}

??

package com.mashang.elearing.domain.vo;

import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;

import java.util.List;

@ApiModel("查询章节信息")
@Data
public class MsChapterLessonsVo {

    @ApiModelProperty("章id")
    private Long chapterId;

    @ApiModelProperty("课程id")
    private Long courseId;

    @ApiModelProperty("章名称")
    private String chapterName;

    @ApiModelProperty("章排序")
    private Long chapterSort;

    //一对多的查询,把小节作为章的一个信息
    @ApiModelProperty("节信息")
    private List<MsLessonsVo> lessons;
}

? ? ? ?mapper

????????在mapper层建一个接口MsChapterMapper继承BaseMapper<MsChapter>

? ? ? ? 写一个方法list(),返回的是节的集合,传入的是课程Id

package com.mashang.elearing.mapper;

import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.mashang.elearing.domain.MsChapter;
import com.mashang.elearing.domain.vo.MsChapterLessonsVo;

import java.util.List;

public interface MsChapterMapper extends BaseMapper<MsChapter> {

    List<MsChapterLessonsVo> list(Long courseId);

}

? ? ? ? xml

? ? ? ? 创建MsChapterMapper.xml

? ? ? ? 绑定com.mashang.elearing.mapper.MsChapterMapper

<?xml version="1.0" encoding="utf-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
<mapper namespace="com.mashang.elearing.mapper.MsChapterMapper">


    <resultMap id="listMap" type="msChapterLessonsVo">
<!--   主键     -->
        <id property="chapterId" column="chapter_id"></id>
        <result property="courseId" column="course_id"></result>
        <result property="chapterName" column="chapter_name"></result>
        <result property="chapterSort" column="chapter_sort"></result>
        <!-- 一对多用的是collection 和 ofType绑定   -->
        <!-- 多对多用的是association 和 javaType绑定   -->
        <collection property="lessons" ofType="msLessonsVo">
            <id property="lessonId" column="lesson_id"></id>
            <result property="lessonName" column="lesson_name"></result>
            <result property="lessonSort" column="lesson_sort"></result>
        </collection>
    </resultMap>
    <select id="list" resultMap="listMap">
        SELECT
            t1.chapter_id,
            t1.course_id,
            t1.chapter_name,
            t1.chapter_sort,
            t2.lesson_id,
            t2.lesson_name,
            t2.lesson_sort
            from ms_chapter t1
            LEFT JOIN ms_lesson t2
            on t1.chapter_id = t2.chapter_id
        where t1.del_flag != '2'
        AND (t2.del_flag != '2' OR t2.del_flag IS NULL)
        AND t1.course_id = #{courseId}
        ORDER BY t1.chapter_sort,t2.lesson_sort
    </select>



</mapper>

? ? ? ? service

? ? ? ? 在service包下创建接口IMsChapterService,继承IService<MsChpaterService>,写上对应的方法

package com.mashang.elearing.service;

import com.baomidou.mybatisplus.extension.service.IService;
import com.mashang.elearing.domain.MsChapter;

import com.mashang.elearing.domain.vo.MsChapterLessonsVo;

import java.util.List;

public interface IMsChapterService extends IService<MsChapter> {

    List<MsChapterLessonsVo> list(Long courseId);

}

? ? ? ? ServiceImpl

? ? ? ? 在service/impl里创建MsChapterServiceImpl继承ServiceImpl<MsChapterMapper,MsChapter> 实现 IMsChapterService,并注入mapper层的对象

@Service
public class MsChapterServiceImpl extends ServiceImpl<MsChapterMapper, MsChapter> implements
        IMsChapterService {

    @Autowired
    private MsChapterMapper msChapterMapper;
   
    @Override
    public List<MsChapterLessonsVo> list(Long courseId) {
    return msChapterMapper.list(courseId);
    }
    
}

? ? ? ? Controller

@Api(tags = "章模块")
@RestController
@RequestMapping("/chapter")
public class MsChapterController extends BaseController {

    @Autowired
    private IMsChapterService msChapterService;


    @ApiOperation("章节信息查询")
    @GetMapping
    public Result<List<MsChapterLessonsVo>> list(Long courseId){

        List<MsChapterLessonsVo> list = msChapterService.list(courseId);

        return Result.success(list);
    }
}

删除章

? ? ? ? 按找之前的方法,在各个层建好小节的类,用mybatisPlus来查询小节信息。

? ? ? ? 在章得到控制层注入小节的信息

方法1:

? ? ? ? 先查询章下是否有小节,如果有小节的话,不让删,没有小节的话就直接删

注意:ById结尾的方法要在主键设置TableId,不然会识别不出来

    @ApiOperation("删除")
    @DeleteMapping("/{chapterId}")
    public Result delete(@PathVariable Long chapterId){
//        plus的查询方法需要传入条件构造器
        LambdaQueryWrapper<MsLesson> qw = new LambdaQueryWrapper<>();
        qw.ne(MsLesson::getDelFlag,"2");    //假删不能查出来
        qw.eq(MsLesson::getChapterId,chapterId);    //根据章id查询小节信息
        long count = msLessonService.count(qw); //查询章下面是否含有小节

        if(count > 0){
            return Result.error("删除失败,章下面仍含有节");
        }

        //count == 0

        MsChapter msChapter = new MsChapter();
        msChapter.setDelFlag("2");
        msChapter.setChapterId(chapterId);
        //updatebyid需要传入MsChapter实体类
        return Result.to(msChapterService.updateById(msChapter));
    }

方法2:

????????先删除章,再判断章下面有没有小节,如果有小节,就把该章对应的小节的del_flag都设置成2(假删)? ? ? ?--- 涉及到两张表的删除,最好加上事物的注解@Transactional

? ? ? ? 在mapper,和serice写上对应方法,去ServiceImpl实现,记得要在ServiceImpl注入节的对象

 @Transactional
    @Override
    public int delete(Long chapterId) {

        int rs = 0;
        //先删除章信息
        MsChapter msChapter = new MsChapter();
        msChapter.setChapterId(chapterId);
        msChapter.setDelFlag("2");
        rs = msChapterMapper.updateById(msChapter);

        //先查一下是否含有小节信息
        LambdaQueryWrapper<MsLesson> qw = new  LambdaQueryWrapper<>();
        qw.ne(MsLesson::getDelFlag,"2");
        qw.eq(MsLesson::getChapterId,chapterId);
//        qw.eq(MsLesson::getChapterSort,msChapter.getChapterSort());
        //查询出没被假删且对应章下面的课程
        Long count = msLessonMapper.selectCount(qw);

        //含有小节信息
        //如果有节,就根据章id将节的del_flag设置成2
        if (count > 0){
            MsLesson msLesson = new MsLesson();
            msLesson.setDelFlag("2");

            LambdaUpdateWrapper<MsLesson> uw = new LambdaUpdateWrapper<>();
            //更新当前传进来的章id的小节的del_flag = '2'
            uw.eq(MsLesson::getChapterId,chapterId);
                    //需要传入一个实体类和条件构造器
            //把满足条件的uw都设置成MsLesson
            msLessonMapper.update(msLesson,uw);
        }
        return rs;
    }

添加章

? ? ? ? 在com.mashan.elearning.domain.params.chapter下创建添加的参数实体类

添加不需要courseId,章Id可以自动递增

必要要串课程Id

package com.mashang.elearing.domain.params.chapter;


import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;

import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;

@ApiModel("章添加")
@Data
public class MsChapterCreate {

//  @ApiModelProperty("章id")
//  private Long chapterId;

  @ApiModelProperty(value = "课程id",required = true)
  @NotNull(message = "课程id不为空")
  private Long courseId;

  @ApiModelProperty(value = "章名称",required = true)
  @NotBlank(message = "章名称不为空")
  private String chapterName;

  @ApiModelProperty(value = "序号")
  private Long chapterSort;


}

先判断章是否存在,存在的话序号要批量递增,不存在可以直接插入,涉及到了事务的操作

? ? ? ? 在IMsChapterService接口下创建添加方法去impl去实现,实现时要加上事物的注解

int create(MsChapterCreate create);

? ? ? ? 实现添加方法

? ? ? ? 传入的参数和最后create方法所需参数不同,依然需要转

package com.mashang.elearing.mapping;

import com.mashang.elearing.domain.MsChapter;

import com.mashang.elearing.domain.params.chapter.MsChapterCreate;

import org.mapstruct.Mapper;
import org.mapstruct.factory.Mappers;

import java.util.List;

@Mapper
public interface MsChapterMapping {
    MsChapterMapping INSTANCE = Mappers.getMapper(MsChapterMapping.class);
    
    MsChapter to(MsChapterCreate create);

}
? ? ? ??Impl实现
//添加章
    @Transactional
    @Override
    public int create(MsChapterCreate create) {

        MsChapter msChapter = MsChapterMapping.INSTANCE.to(create);

        //先判断当前课程是否有该章,有的话把chapterId > 传入章id 的所有chapterId + 1
        updateSort(msChapter);

        int rs = msChapterMapper.insert(msChapter);
        return rs;
    }


    public void updateSort(MsChapter msChapter){
        //查询当前课程存不存在该序号
        LambdaQueryWrapper<MsChapter> qw = new LambdaQueryWrapper<>();
        qw.ne(MsChapter::getDelFlag,"2");   //固定排除假删除
        qw.eq(MsChapter::getCourseId,msChapter.getCourseId());  //查询当前课程
        qw.eq(MsChapter::getChapterSort,msChapter.getChapterSort());    //如果有相同序号的就代表重复了
        Long count = msChapterMapper.selectCount(qw);

        //如果有该章,需要将该章后面的sort+1
        if (count > 0){
            //将该章后面的sort+1
            LambdaUpdateWrapper<MsChapter> uw = new LambdaUpdateWrapper<>();

            uw.ge(MsChapter::getChapterSort, msChapter.getChapterSort());
            uw.setSql("chapter_sort = chapter_sort + 1");
            msChapterMapper.update(null,uw);
        }
    }
? ? ? ? controller层调用
@ApiOperation("添加")
    @PostMapping
    public Result create(@RequestBody @Validated MsChapterCreate create){

        int rs = msChapterService.create(create);

        return Result.to(rs);
    }

? ? ? ? 修改接口

? ? ? ? 修改和添加类型,都是需要先判断该序号是否存在,如何存在,把该序号以后的序号做统一递增,然后再执行添加或者修改操作

? ? ? ? 实体类

? ? ? ? 在domain下的params包下创建关于章的实体类

????????修改需要传courseId,要查询当前课程下是否有该章节

package com.mashang.elearing.domain.params.chapter;


import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;

import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;

@ApiModel("章修改")
@Data
public class MsChapterUpdate {


  @ApiModelProperty("章id")
  @NotNull(message = "章id不为空")
  private Long chapterId;

  @ApiModelProperty(value = "课程id",required = true)
  @NotNull(message = "课程id不为空")
  private Long courseId;

  @ApiModelProperty(value = "章名称",required = true)
  @NotBlank(message = "章名称不为空")
  private String chapterName;

  @ApiModelProperty(value = "序号")
  private Long chapterSort;


}

? ? ? ? 实体类转化

MsChapter to(MsChapterUpdate update);

????????Service

? ? ? ? IMsChapterService下定义一个方法

int create(MsChapterCreate create);

? ? ? ? 去Impl实现

@Transactional
    @Override
    public int update(MsChapterUpdate update) {
        //修改接口,先修改,修改完如果有冲突的序号,该序号后面需要再递增
        //这样的话,自己也会被修改掉 比如 4 改成  2
        //原本就有2的话,调用updateSort方法,会把两个2都+1,这样就冲突了

        //所以应该是先判断是否存在修改后的序号,有的话先统一递增。再修改

        //先进行实体类转化
        MsChapter msChapter = MsChapterMapping.INSTANCE.to(update);

        //先判断当前课程是否有该章,有的话把chapterId >= 传入章id 的所有chapterId + 1
        updateSort(msChapter);

        //然后再执行操作
        int rs = msChapterMapper.updateById(msChapter);
        return rs;
    }

    public void updateSort(MsChapter msChapter){
        //查询当前课程存不存在该序号
        LambdaQueryWrapper<MsChapter> qw = new LambdaQueryWrapper<>();
        qw.ne(MsChapter::getDelFlag,"2");   //固定排除假删除
        qw.eq(MsChapter::getCourseId,msChapter.getCourseId());  //查询当前课程
        qw.eq(MsChapter::getChapterSort,msChapter.getChapterSort());    //如果有相同序号的就代表重复了
        Long count = msChapterMapper.selectCount(qw);

        //如果有该章,需要将该章后面的sort+1
        if (count > 0){
            //将该章后面的sort+1
            LambdaUpdateWrapper<MsChapter> uw = new LambdaUpdateWrapper<>();

            uw.ge(MsChapter::getChapterSort, msChapter.getChapterSort());
            uw.setSql("chapter_sort = chapter_sort + 1");
            msChapterMapper.update(null,uw);
        }
    }

? ? ? ? ????????controlloer

? ? ? ? 记得再控制层加上参数验证@Validated,和用Json的形式传参@RequestBody

@ApiOperation("修改")
    @PutMapping
    public Result update(@RequestBody @Validated MsChapterUpdate update){
        int rs = msChapterService.update(update);
        return Result.to(rs);
    }

查询章节详情接口

????????

 //修改的时候要先把章节信息查出来
    //查询详情直接用plus构造就行
    @ApiOperation("详情")
    @GetMapping("/{chapterId}")
    public Result<MsChapterDtlVo> getById(@PathVariable Long chapterId){
        MsChapter msChapter = msChapterService.getById(chapterId);
        return Result.success(MsChapterMapping.INSTANCE.to(msChapter));
    }

文章来源:https://blog.csdn.net/2302_76649176/article/details/134951480
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。