优化课程创建

This commit is contained in:
none 2023-03-15 10:40:33 +08:00
parent fb94e93f80
commit cca6d050bc
13 changed files with 213 additions and 136 deletions

View File

@ -15,8 +15,6 @@ import xyz.playedu.api.service.CourseChapterService;
import xyz.playedu.api.types.JsonResponse;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
/**
* @Author 杭州白书科技有限公司
@ -32,21 +30,6 @@ public class CourseChapterController {
@Autowired
private ApplicationContext ctx;
@GetMapping("/index")
public JsonResponse index(@PathVariable(name = "courseId") Integer courseId) {
List<CourseChapter> chapters = chapterService.getChaptersByCourseId(courseId);
return JsonResponse.data(chapters);
}
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
@GetMapping("/create")
public JsonResponse create(@PathVariable(name = "courseId") Integer courseId) {
List<CourseChapter> chapters = chapterService.getChaptersByCourseId(courseId);
HashMap<String, Object> data = new HashMap<>();
data.put("chapters", chapters);
return JsonResponse.data(data);
}
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
@PostMapping("/create")
public JsonResponse store(@PathVariable(name = "courseId") Integer courseId, @RequestBody @Validated CourseChapterRequest req) {

View File

@ -14,12 +14,15 @@ import xyz.playedu.api.event.CourseDestroyEvent;
import xyz.playedu.api.exception.NotFoundException;
import xyz.playedu.api.middleware.BackendPermissionMiddleware;
import xyz.playedu.api.request.backend.CourseRequest;
import xyz.playedu.api.service.CourseChapterService;
import xyz.playedu.api.service.CourseHourService;
import xyz.playedu.api.service.CourseService;
import xyz.playedu.api.service.ResourceCategoryService;
import xyz.playedu.api.types.JsonResponse;
import xyz.playedu.api.types.paginate.CoursePaginateFiler;
import xyz.playedu.api.types.paginate.PaginationResult;
import java.text.ParseException;
import java.util.*;
import java.util.stream.Collectors;
@ -38,6 +41,12 @@ public class CourseController {
@Autowired
private ResourceCategoryService categoryService;
@Autowired
private CourseChapterService chapterService;
@Autowired
private CourseHourService hourService;
@Autowired
private ApplicationContext ctx;
@ -74,8 +83,79 @@ public class CourseController {
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
@PostMapping("/create")
@Transactional
public JsonResponse store(@RequestBody @Validated CourseRequest req) {
courseService.createWithCategoryIdsAndDepIds(req.getTitle(), req.getThumb(), req.getIsShow(), req.getCategoryIds(), req.getDepIds());
public JsonResponse store(@RequestBody @Validated CourseRequest req) throws ParseException {
Course course = courseService.createWithCategoryIdsAndDepIds(req.getTitle(), req.getThumb(), req.getIsShow(), req.getCategoryIds(), req.getDepIds());
Map<String, Map<String, Object>[]> chapters = req.getChapters();
Date now = new Date();
if (req.getHours() != null) {//无章节课时配置
List<CourseHour> insertHours = new ArrayList<>();
for (Map<String, Object> hourItem : req.getHours()) {
// 资源类型
String typeVal = MapUtils.getString(hourItem, "type");
// 时长
Integer durationVal = MapUtils.getInteger(hourItem, "duration");
// 资源ID
Integer ridVal = MapUtils.getInteger(hourItem, "rid");
insertHours.add(new CourseHour() {{
setChapterId(0);
setCourseId(course.getId());
setType(typeVal);
setDuration(durationVal);
setRid(ridVal);
setCreatedAt(now);
}});
}
if (insertHours.size() > 0) {
hourService.saveBatch(insertHours);
}
} else {
if (chapters == null) {
return JsonResponse.error("请配置课时");
}
List<CourseHour> insertHours = new ArrayList<>();
final Integer[] chapterSort = {0};
for (Map.Entry<String, Map<String, Object>[]> entry : chapters.entrySet()) {
String chapterName = entry.getKey();
Map<String, Object>[] hoursList = entry.getValue();
CourseChapter tmpChapter = new CourseChapter() {{
setCourseId(course.getId());
setSort(chapterSort[0]++);
setName(chapterName);
setCreatedAt(now);
setUpdatedAt(now);
}};
chapterService.save(tmpChapter);
final Integer[] hourSort = {0};
for (Map<String, Object> hourItem : hoursList) {
// 资源类型
String typeVal = MapUtils.getString(hourItem, "type");
// 时长
Integer durationVal = MapUtils.getInteger(hourItem, "duration");
// 资源ID
Integer ridVal = MapUtils.getInteger(hourItem, "rid");
insertHours.add(new CourseHour() {{
setChapterId(tmpChapter.getId());
setCourseId(course.getId());
setType(typeVal);
setDuration(durationVal);
setRid(ridVal);
setCreatedAt(now);
setSort(hourSort[0]++);
}});
}
}
if (insertHours.size() > 0) {
hourService.saveBatch(insertHours);
}
}
return JsonResponse.success();
}
@ -85,11 +165,15 @@ public class CourseController {
Course course = courseService.findOrFail(id);
List<Integer> depIds = courseService.getDepIdsByCourseId(course.getId());
List<Integer> categoryIds = courseService.getCategoryIdsByCourseId(course.getId());
List<CourseChapter> chapters = chapterService.getChaptersByCourseId(course.getId());
List<CourseHour> hours = hourService.getHoursByCourseId(course.getId());
HashMap<String, Object> data = new HashMap<>();
data.put("course", course);
data.put("dep_ids", depIds);
data.put("category_ids", categoryIds);
data.put("dep_ids", depIds);//已关联的部门
data.put("category_ids", categoryIds);//已关联的分类
data.put("chapters", chapters);
data.put("hours", hours.stream().collect(Collectors.toMap(CourseHour::getChapterId, e -> e)));
return JsonResponse.data(data);
}

View File

@ -38,12 +38,6 @@ public class CourseHourController {
@Autowired
private ApplicationContext ctx;
@GetMapping("/index")
public JsonResponse index(@PathVariable(name = "courseId") Integer courseId) {
List<CourseHour> hours = hourService.getHoursByCourseId(courseId);
return JsonResponse.data(hours);
}
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
@GetMapping("/create")
public JsonResponse create(@PathVariable(name = "courseId") Integer courseId) {
@ -79,7 +73,7 @@ public class CourseHourController {
Integer chapterId = req.getChapterId();
chapterService.findOrFail(chapterId, courseId);
CourseHour courseHour = hourService.create(courseId, chapterId, req.getTitle(), type, req.getDuration(), req.getPublishedAt());
CourseHour courseHour = hourService.create(courseId, chapterId, req.getSort(), req.getTitle(), type, req.getRid(), req.getDuration());
ctx.publishEvent(new CourseHourCreatedEvent(this, PlayEduBContext.getAdminUserID(), courseHour.getCourseId(), courseHour.getChapterId(), courseHour.getId(), new Date()));
return JsonResponse.success();
}
@ -99,7 +93,7 @@ public class CourseHourController {
Integer chapterId = req.getChapterId();
chapterService.findOrFail(chapterId, courseId);
hourService.update(courseHour, chapterId, req.getTitle(), req.getDuration(), req.getPublishedAt());
hourService.update(courseHour, chapterId, req.getSort(), req.getTitle(), req.getDuration());
return JsonResponse.success();
}

View File

@ -4,21 +4,19 @@ import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import java.io.Serializable;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;
/**
*
* @TableName course_hour
*/
@TableName(value = "course_hour")
@TableName(value ="course_hour")
@Data
public class CourseHour implements Serializable {
/**
*
*
*/
@TableId(type = IdType.AUTO)
private Integer id;
@ -26,15 +24,18 @@ public class CourseHour implements Serializable {
/**
* 课程ID
*/
@JsonProperty("course_id")
private Integer courseId;
/**
* 章节ID
*/
@JsonProperty("chapter_id")
private Integer chapterId;
/**
* 升序
*/
private Integer sort;
/**
* 课时名
*/
@ -45,23 +46,21 @@ public class CourseHour implements Serializable {
*/
private String type;
/**
* 资源id
*/
private Integer rid;
/**
* 时长[s]
*/
private Integer duration;
/**
* 发布时间
*
*/
@JsonProperty("published_at")
private Date publishedAt;
@JsonProperty("created_at")
private Date createdAt;
@JsonProperty("updated_at")
private Date updatedAt;
@TableField(exist = false)
private static final long serialVersionUID = 1L;
@ -78,14 +77,14 @@ public class CourseHour implements Serializable {
}
CourseHour other = (CourseHour) that;
return (this.getId() == null ? other.getId() == null : this.getId().equals(other.getId()))
&& (this.getCourseId() == null ? other.getCourseId() == null : this.getCourseId().equals(other.getCourseId()))
&& (this.getChapterId() == null ? other.getChapterId() == null : this.getChapterId().equals(other.getChapterId()))
&& (this.getTitle() == null ? other.getTitle() == null : this.getTitle().equals(other.getTitle()))
&& (this.getType() == null ? other.getType() == null : this.getType().equals(other.getType()))
&& (this.getDuration() == null ? other.getDuration() == null : this.getDuration().equals(other.getDuration()))
&& (this.getPublishedAt() == null ? other.getPublishedAt() == null : this.getPublishedAt().equals(other.getPublishedAt()))
&& (this.getCreatedAt() == null ? other.getCreatedAt() == null : this.getCreatedAt().equals(other.getCreatedAt()))
&& (this.getUpdatedAt() == null ? other.getUpdatedAt() == null : this.getUpdatedAt().equals(other.getUpdatedAt()));
&& (this.getCourseId() == null ? other.getCourseId() == null : this.getCourseId().equals(other.getCourseId()))
&& (this.getChapterId() == null ? other.getChapterId() == null : this.getChapterId().equals(other.getChapterId()))
&& (this.getSort() == null ? other.getSort() == null : this.getSort().equals(other.getSort()))
&& (this.getTitle() == null ? other.getTitle() == null : this.getTitle().equals(other.getTitle()))
&& (this.getType() == null ? other.getType() == null : this.getType().equals(other.getType()))
&& (this.getRid() == null ? other.getRid() == null : this.getRid().equals(other.getRid()))
&& (this.getDuration() == null ? other.getDuration() == null : this.getDuration().equals(other.getDuration()))
&& (this.getCreatedAt() == null ? other.getCreatedAt() == null : this.getCreatedAt().equals(other.getCreatedAt()));
}
@Override
@ -95,12 +94,12 @@ public class CourseHour implements Serializable {
result = prime * result + ((getId() == null) ? 0 : getId().hashCode());
result = prime * result + ((getCourseId() == null) ? 0 : getCourseId().hashCode());
result = prime * result + ((getChapterId() == null) ? 0 : getChapterId().hashCode());
result = prime * result + ((getSort() == null) ? 0 : getSort().hashCode());
result = prime * result + ((getTitle() == null) ? 0 : getTitle().hashCode());
result = prime * result + ((getType() == null) ? 0 : getType().hashCode());
result = prime * result + ((getRid() == null) ? 0 : getRid().hashCode());
result = prime * result + ((getDuration() == null) ? 0 : getDuration().hashCode());
result = prime * result + ((getPublishedAt() == null) ? 0 : getPublishedAt().hashCode());
result = prime * result + ((getCreatedAt() == null) ? 0 : getCreatedAt().hashCode());
result = prime * result + ((getUpdatedAt() == null) ? 0 : getUpdatedAt().hashCode());
return result;
}
@ -113,12 +112,12 @@ public class CourseHour implements Serializable {
sb.append(", id=").append(id);
sb.append(", courseId=").append(courseId);
sb.append(", chapterId=").append(chapterId);
sb.append(", sort=").append(sort);
sb.append(", title=").append(title);
sb.append(", type=").append(type);
sb.append(", rid=").append(rid);
sb.append(", duration=").append(duration);
sb.append(", publishedAt=").append(publishedAt);
sb.append(", createdAt=").append(createdAt);
sb.append(", updatedAt=").append(updatedAt);
sb.append(", serialVersionUID=").append(serialVersionUID);
sb.append("]");
return sb.toString();

View File

@ -18,7 +18,7 @@ public class CourseChapterDestroyListener {
@EventListener
public void resetCourseHourChapterId(CourseChapterDestroyEvent event) {
hourService.resetChapterIdByCourseIdAndChapterId(event.getCourseId(), event.getChapterId());
hourService.remove(event.getCourseId(), event.getChapterId());
}
}

View File

@ -7,7 +7,7 @@ import com.baomidou.mybatisplus.core.mapper.BaseMapper;
/**
* @author tengteng
* @description 针对表course_hour的数据库操作Mapper
* @createDate 2023-02-26 18:10:09
* @createDate 2023-03-15 10:16:45
* @Entity xyz.playedu.api.domain.CourseHour
*/
@Mapper

View File

@ -22,15 +22,17 @@ public class CourseHourRequest {
@NotBlank(message = "请输入课时标题")
private String title;
@NotNull(message = "duration参数不存在")
private Integer duration;
@NotNull(message = "sort参数不存在")
private Integer sort;
@NotNull(message = "type参数不存在")
@NotBlank(message = "请选择课时类型")
private String type;
@NotNull(message = "duration参数不存在")
private Integer duration;
@NotNull(message = "published_at参数不存在")
@JsonProperty("published_at")
private Date publishedAt;
@NotNull(message = "rid参数不存在")
private Integer rid;
}

View File

@ -5,6 +5,8 @@ import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.util.Map;
/**
* @Author 杭州白书科技有限公司
* @create 2023/2/24 14:38
@ -31,4 +33,30 @@ public class CourseRequest {
@NotNull(message = "category_ids参数不存在")
@JsonProperty("category_ids")
private Integer[] categoryIds;
// 格式
// [
// '章节名' => [
// [
// 'name' => '课时名',
// 'type' => '课时类型', // 可选值[VIDEO]
// 'duration' => 时长, // 单位[]
// 'rid' => 资源ID, // 如果是type=VIDEO的话则对应视频的id
// ]...
// ]...
// ]
@NotNull(message = "chapters参数不存在")
private Map<String, Map<String, Object>[]> chapters;
// 格式
// [
// [
// 'name' => '课时名',
// 'type' => '课时类型',
// 'duration' => '时长',
// 'rid' => '资源id',
// ]...
// ]
@NotNull(message = "hours参数不存在")
private Map<String, Object>[] hours;
}

View File

@ -4,28 +4,24 @@ import xyz.playedu.api.domain.CourseHour;
import com.baomidou.mybatisplus.extension.service.IService;
import xyz.playedu.api.exception.NotFoundException;
import java.util.Date;
import java.util.List;
/**
* @author tengteng
* @description 针对表course_hour的数据库操作Service
* @createDate 2023-02-26 17:48:12
*/
* @author tengteng
* @description 针对表course_hour的数据库操作Service
* @createDate 2023-03-15 10:16:45
*/
public interface CourseHourService extends IService<CourseHour> {
List<CourseHour> getHoursByCourseId(Integer courseId);
CourseHour create(Integer courseId, Integer chapterId, String title, String type, Integer duration, Date publishedAt);
void update(CourseHour courseHour, Integer chapterId, String title, Integer duration, Date publishedAt);
CourseHour findOrFail(Integer id) throws NotFoundException;
CourseHour findOrFail(Integer id, Integer courseId) throws NotFoundException;
void update(CourseHour courseHour, Integer chapterId, Integer sort, String title, Integer duration);
List<CourseHour> getHoursByCourseId(Integer courseId);
CourseHour create(Integer courseId, Integer chapterId, Integer sort, String title, String type, Integer rid, Integer duration);
Integer getCourseClassHourByCourseId(Integer courseId);
void resetChapterIdByCourseIdAndChapterId(Integer courseId,Integer chapterId);
void remove(Integer courseId, Integer chapterId);
}

View File

@ -17,7 +17,7 @@ public interface CourseService extends IService<Course> {
PaginationResult<Course> paginate(int page, int size, CoursePaginateFiler filter);
void createWithCategoryIdsAndDepIds(String title, String thumb, Integer isShow, Integer[] categoryIds, Integer[] depIds);
Course createWithCategoryIdsAndDepIds(String title, String thumb, Integer isShow, Integer[] categoryIds, Integer[] depIds);
void updateWithCategoryIdsAndDepIds(Course course, String title, String thumb, Integer isShow, Integer[] categoryIds, Integer[] depIds);

View File

@ -13,63 +13,52 @@ import java.util.List;
/**
* @author tengteng
* @description 针对表course_hour的数据库操作Service实现
* @createDate 2023-02-26 17:48:12
* @createDate 2023-03-15 10:16:45
*/
@Service
public class CourseHourServiceImpl extends ServiceImpl<CourseHourMapper, CourseHour> implements CourseHourService {
@Override
public List<CourseHour> getHoursByCourseId(Integer courseId) {
return list(query().getWrapper().eq("course_id", courseId).orderByAsc("published_at"));
}
@Override
public CourseHour create(Integer courseId, Integer chapterId, String title, String type, Integer duration, Date publishedAt) {
CourseHour courseHour = new CourseHour();
courseHour.setCourseId(courseId);
courseHour.setChapterId(chapterId);
courseHour.setTitle(title);
courseHour.setType(type);
courseHour.setDuration(duration);
courseHour.setPublishedAt(publishedAt);
courseHour.setCreatedAt(new Date());
courseHour.setUpdatedAt(new Date());
save(courseHour);
return courseHour;
}
@Override
public void update(CourseHour courseHour, Integer chapterId, String title, Integer duration, Date publishedAt) {
CourseHour newCourseHour = new CourseHour();
newCourseHour.setId(courseHour.getId());
newCourseHour.setChapterId(chapterId);
newCourseHour.setTitle(title);
newCourseHour.setDuration(duration);
newCourseHour.setPublishedAt(publishedAt);
newCourseHour.setCreatedAt(new Date());
newCourseHour.setUpdatedAt(new Date());
updateById(newCourseHour);
}
@Override
public CourseHour findOrFail(Integer id) throws NotFoundException {
CourseHour courseHour = getOne(query().getWrapper().eq("id", id));
if (courseHour == null) {
throw new NotFoundException("课时不存在");
}
return courseHour;
}
@Override
public CourseHour findOrFail(Integer id, Integer courseId) throws NotFoundException {
CourseHour courseHour = getOne(query().getWrapper().eq("id", id).eq("course_id", courseId));
if (courseHour == null) {
CourseHour hour = getOne(query().getWrapper().eq("id", id).eq("course_id", courseId));
if (hour == null) {
throw new NotFoundException("课时不存在");
}
return courseHour;
return hour;
}
@Override
public void update(CourseHour courseHour, Integer chapterId, Integer sort, String title, Integer duration) {
CourseHour hour = new CourseHour();
hour.setId(courseHour.getId());
hour.setChapterId(chapterId);
hour.setSort(sort);
hour.setTitle(title);
hour.setDuration(duration);
updateById(hour);
}
@Override
public List<CourseHour> getHoursByCourseId(Integer courseId) {
return list(query().getWrapper().eq("course_id", courseId).orderByAsc("sort"));
}
@Override
public CourseHour create(Integer courseId, Integer chapterId, Integer sort, String title, String type, Integer rid, Integer duration) {
CourseHour hour = new CourseHour();
hour.setCourseId(courseId);
hour.setChapterId(chapterId);
hour.setSort(sort);
hour.setTitle(title);
hour.setType(type);
hour.setRid(rid);
hour.setDuration(duration);
hour.setCreatedAt(new Date());
save(hour);
return hour;
}
@Override
@ -78,8 +67,8 @@ public class CourseHourServiceImpl extends ServiceImpl<CourseHourMapper, CourseH
}
@Override
public void resetChapterIdByCourseIdAndChapterId(Integer courseId, Integer chapterId) {
update(update().getWrapper().eq("course_id", courseId).eq("chapter_id", chapterId).set("chapter_id", 0));
public void remove(Integer courseId, Integer chapterId) {
remove(query().getWrapper().eq("course_id", courseId).eq("chapter_id", chapterId));
}
}

View File

@ -91,7 +91,7 @@ public class CourseServiceImpl extends ServiceImpl<CourseMapper, Course> impleme
@Override
@Transactional
public void createWithCategoryIdsAndDepIds(String title, String thumb, Integer isShow, Integer[] categoryIds, Integer[] depIds) {
public Course createWithCategoryIdsAndDepIds(String title, String thumb, Integer isShow, Integer[] categoryIds, Integer[] depIds) {
// 创建课程
Course course = new Course();
course.setTitle(title);
@ -104,6 +104,8 @@ public class CourseServiceImpl extends ServiceImpl<CourseMapper, Course> impleme
relateCategories(course, categoryIds);
// 关联部门
relateDepartments(course, depIds);
return course;
}
@Override

View File

@ -8,17 +8,17 @@
<id property="id" column="id" jdbcType="INTEGER"/>
<result property="courseId" column="course_id" jdbcType="INTEGER"/>
<result property="chapterId" column="chapter_id" jdbcType="INTEGER"/>
<result property="sort" column="sort" jdbcType="INTEGER"/>
<result property="title" column="title" jdbcType="VARCHAR"/>
<result property="type" column="type" jdbcType="VARCHAR"/>
<result property="rid" column="rid" jdbcType="INTEGER"/>
<result property="duration" column="duration" jdbcType="INTEGER"/>
<result property="publishedAt" column="published_at" jdbcType="TIMESTAMP"/>
<result property="createdAt" column="created_at" jdbcType="TIMESTAMP"/>
<result property="updatedAt" column="updated_at" jdbcType="TIMESTAMP"/>
</resultMap>
<sql id="Base_Column_List">
id,course_id,chapter_id,
title,type,duration,
published_at,created_at,updated_at
sort,title,type,
rid,duration,created_at
</sql>
</mapper>