mirror of
https://github.com/PlayEdu/PlayEdu
synced 2025-07-23 17:49:34 +08:00
课程与附件关联
This commit is contained in:
parent
cd475f080e
commit
b9623983c7
@ -0,0 +1,150 @@
|
||||
/*
|
||||
* Copyright (C) 2023 杭州白书科技有限公司
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package xyz.playedu.api.controller.backend;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
import org.springframework.validation.annotation.Validated;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
import xyz.playedu.api.constant.BPermissionConstant;
|
||||
import xyz.playedu.api.constant.BackendConstant;
|
||||
import xyz.playedu.api.domain.CourseAttachment;
|
||||
import xyz.playedu.api.exception.NotFoundException;
|
||||
import xyz.playedu.api.middleware.BackendPermissionMiddleware;
|
||||
import xyz.playedu.api.request.backend.CourseAttachmentMultiRequest;
|
||||
import xyz.playedu.api.request.backend.CourseAttachmentRequest;
|
||||
import xyz.playedu.api.request.backend.CourseAttachmentSortRequest;
|
||||
import xyz.playedu.api.service.CourseAttachmentService;
|
||||
import xyz.playedu.api.types.JsonResponse;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
@RestController
|
||||
@Slf4j
|
||||
@RequestMapping("/backend/v1/course/{courseId}/attachment")
|
||||
public class CourseAttachmentController {
|
||||
|
||||
@Autowired private CourseAttachmentService attachmentService;
|
||||
|
||||
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
|
||||
@PostMapping("/create")
|
||||
public JsonResponse store(
|
||||
@PathVariable(name = "courseId") Integer courseId,
|
||||
@RequestBody @Validated CourseAttachmentRequest req)
|
||||
throws NotFoundException {
|
||||
// 附件类型校验
|
||||
String type = req.getType();
|
||||
if (!BackendConstant.RESOURCE_TYPE_ATTACHMENT.contains(type)) {
|
||||
return JsonResponse.error("附件类型不支持");
|
||||
}
|
||||
|
||||
// 课时重复添加校验
|
||||
List<Integer> existsRids = attachmentService.getRidsByCourseId(courseId);
|
||||
if (existsRids != null) {
|
||||
if (existsRids.contains(req.getRid())) {
|
||||
return JsonResponse.error("附件已存在");
|
||||
}
|
||||
}
|
||||
|
||||
CourseAttachment courseAttachment =
|
||||
attachmentService.create(
|
||||
courseId,
|
||||
req.getSort(),
|
||||
req.getTitle(),
|
||||
type,
|
||||
req.getRid());
|
||||
return JsonResponse.success();
|
||||
}
|
||||
|
||||
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
|
||||
@PostMapping("/create-batch")
|
||||
@Transactional
|
||||
public JsonResponse storeMulti(
|
||||
@PathVariable(name = "courseId") Integer courseId,
|
||||
@RequestBody @Validated CourseAttachmentMultiRequest req) {
|
||||
if (req.getAttachments().size() == 0) {
|
||||
return JsonResponse.error("参数为空");
|
||||
}
|
||||
|
||||
List<Integer> existsRids = attachmentService.getRidsByCourseId(courseId);
|
||||
|
||||
List<CourseAttachment> attachments = new ArrayList<>();
|
||||
Date now = new Date();
|
||||
|
||||
for (CourseAttachmentMultiRequest.AttachmentItem item : req.getAttachments()) {
|
||||
if (existsRids.contains(item.getRid())) {
|
||||
return JsonResponse.error("附件《" + item.getTitle() + "》已存在");
|
||||
}
|
||||
|
||||
attachments.add(
|
||||
new CourseAttachment() {
|
||||
{
|
||||
setCourseId(courseId);
|
||||
setSort(item.getSort());
|
||||
setType(item.getType());
|
||||
setRid(item.getRid());
|
||||
setTitle(item.getTitle());
|
||||
setCreatedAt(now);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
attachmentService.saveBatch(attachments);
|
||||
return JsonResponse.success();
|
||||
}
|
||||
|
||||
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
|
||||
@GetMapping("/{id}")
|
||||
public JsonResponse edit(
|
||||
@PathVariable(name = "courseId") Integer courseId,
|
||||
@PathVariable(name = "id") Integer id)
|
||||
throws NotFoundException {
|
||||
CourseAttachment courseAttachment = attachmentService.findOrFail(id, courseId);
|
||||
return JsonResponse.data(courseAttachment);
|
||||
}
|
||||
|
||||
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
|
||||
@PutMapping("/{id}")
|
||||
public JsonResponse update(
|
||||
@PathVariable(name = "courseId") Integer courseId,
|
||||
@PathVariable(name = "id") Integer id,
|
||||
@RequestBody @Validated CourseAttachmentRequest req)
|
||||
throws NotFoundException {
|
||||
CourseAttachment courseAttachment = attachmentService.findOrFail(id, courseId);
|
||||
attachmentService.update(courseAttachment, req.getSort(), req.getTitle());
|
||||
return JsonResponse.success();
|
||||
}
|
||||
|
||||
@BackendPermissionMiddleware(slug = BPermissionConstant.COURSE)
|
||||
@DeleteMapping("/{id}")
|
||||
public JsonResponse destroy(
|
||||
@PathVariable(name = "courseId") Integer courseId,
|
||||
@PathVariable(name = "id") Integer id)
|
||||
throws NotFoundException {
|
||||
CourseAttachment courseAttachment = attachmentService.findOrFail(id, courseId);
|
||||
attachmentService.removeById(courseAttachment.getId());
|
||||
return JsonResponse.success();
|
||||
}
|
||||
|
||||
@PutMapping("/update/sort")
|
||||
public JsonResponse updateSort(
|
||||
@PathVariable(name = "courseId") Integer courseId,
|
||||
@RequestBody @Validated CourseAttachmentSortRequest req) {
|
||||
attachmentService.updateSort(req.getIds(), courseId);
|
||||
return JsonResponse.success();
|
||||
}
|
||||
}
|
@ -26,7 +26,6 @@ import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import xyz.playedu.api.BCtx;
|
||||
import xyz.playedu.api.constant.BPermissionConstant;
|
||||
import xyz.playedu.api.constant.BackendConstant;
|
||||
import xyz.playedu.api.domain.*;
|
||||
import xyz.playedu.api.event.CourseDestroyEvent;
|
||||
import xyz.playedu.api.exception.NotFoundException;
|
||||
@ -54,6 +53,10 @@ public class CourseController {
|
||||
|
||||
@Autowired private CourseHourService hourService;
|
||||
|
||||
@Autowired private CourseAttachmentService attachmentService;
|
||||
|
||||
@Autowired private ResourceService resourceService;
|
||||
|
||||
@Autowired private DepartmentService departmentService;
|
||||
|
||||
@Autowired private ApplicationContext ctx;
|
||||
@ -192,6 +195,28 @@ public class CourseController {
|
||||
courseService.updateClassHour(course.getId(), classHourCount);
|
||||
}
|
||||
|
||||
// 课程附件
|
||||
if (req.getAttachments().size() > 0) {
|
||||
List<CourseAttachment> insertAttachments = new ArrayList<>();
|
||||
final Integer[] sort = {0};
|
||||
for (CourseRequest.AttachmentItem attachmentItem : req.getAttachments()) {
|
||||
insertAttachments.add(
|
||||
new CourseAttachment() {
|
||||
{
|
||||
setCourseId(course.getId());
|
||||
setSort(sort[0]++);
|
||||
setTitle(attachmentItem.getName());
|
||||
setType(attachmentItem.getType());
|
||||
setRid(attachmentItem.getRid());
|
||||
setCreatedAt(now);
|
||||
}
|
||||
});
|
||||
}
|
||||
if (insertAttachments.size() > 0) {
|
||||
attachmentService.saveBatch(insertAttachments);
|
||||
}
|
||||
}
|
||||
|
||||
return JsonResponse.success();
|
||||
}
|
||||
|
||||
@ -203,28 +228,20 @@ public class CourseController {
|
||||
List<Integer> categoryIds = courseService.getCategoryIdsByCourseId(course.getId());
|
||||
List<CourseChapter> chapters = chapterService.getChaptersByCourseId(course.getId());
|
||||
List<CourseHour> hours = hourService.getHoursByCourseId(course.getId());
|
||||
List<CourseAttachment> attachments = attachmentService.getAttachmentsByCourseId(course.getId());
|
||||
Map<Integer,String> resourceMap = resourceService.chunks(attachments.stream().map(CourseAttachment::getRid).toList())
|
||||
.stream().collect(Collectors.toMap(Resource::getId, Resource::getUrl));
|
||||
attachments.forEach(courseAttachment -> {
|
||||
courseAttachment.setUrl(resourceMap.get(courseAttachment.getRid()));
|
||||
});
|
||||
|
||||
HashMap<String, Object> data = new HashMap<>();
|
||||
data.put("course", course);
|
||||
data.put("dep_ids", depIds); // 已关联的部门
|
||||
data.put("category_ids", categoryIds); // 已关联的分类
|
||||
data.put("chapters", chapters);
|
||||
data.put(
|
||||
"hours",
|
||||
hours.stream()
|
||||
.filter(
|
||||
courseHour ->
|
||||
BackendConstant.RESOURCE_TYPE_VIDEO.equals(
|
||||
courseHour.getType()))
|
||||
.collect(Collectors.groupingBy(CourseHour::getChapterId)));
|
||||
data.put(
|
||||
"attachments",
|
||||
hours.stream()
|
||||
.filter(
|
||||
courseHour ->
|
||||
BackendConstant.RESOURCE_TYPE_ATTACHMENT.contains(
|
||||
courseHour.getType()))
|
||||
.collect(Collectors.groupingBy(CourseHour::getChapterId)));
|
||||
data.put("hours", hours.stream().collect(Collectors.groupingBy(CourseHour::getChapterId)));
|
||||
data.put("attachments", attachments);
|
||||
return JsonResponse.data(data);
|
||||
}
|
||||
|
||||
|
@ -52,6 +52,9 @@ public class CourseAttachment implements Serializable {
|
||||
/** 资源id */
|
||||
private Integer rid;
|
||||
|
||||
/** 资源url */
|
||||
private String url;
|
||||
|
||||
/** */
|
||||
@JsonIgnore private Date createdAt;
|
||||
|
||||
@ -86,6 +89,9 @@ public class CourseAttachment implements Serializable {
|
||||
&& (this.getRid() == null
|
||||
? other.getRid() == null
|
||||
: this.getRid().equals(other.getRid()))
|
||||
&& (this.getUrl() == null
|
||||
? other.getUrl() == null
|
||||
: this.getUrl().equals(other.getUrl()))
|
||||
&& (this.getCreatedAt() == null
|
||||
? other.getCreatedAt() == null
|
||||
: this.getCreatedAt().equals(other.getCreatedAt()));
|
||||
@ -101,6 +107,7 @@ public class CourseAttachment implements Serializable {
|
||||
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 + ((getUrl() == null) ? 0 : getUrl().hashCode());
|
||||
result = prime * result + ((getCreatedAt() == null) ? 0 : getCreatedAt().hashCode());
|
||||
return result;
|
||||
}
|
||||
@ -117,6 +124,7 @@ public class CourseAttachment implements Serializable {
|
||||
sb.append(", title=").append(title);
|
||||
sb.append(", type=").append(type);
|
||||
sb.append(", rid=").append(rid);
|
||||
sb.append(", url=").append(url);
|
||||
sb.append(", createdAt=").append(createdAt);
|
||||
sb.append(", serialVersionUID=").append(serialVersionUID);
|
||||
sb.append("]");
|
||||
|
@ -20,6 +20,7 @@ import org.springframework.context.event.EventListener;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import xyz.playedu.api.event.CourseDestroyEvent;
|
||||
import xyz.playedu.api.service.CourseAttachmentService;
|
||||
import xyz.playedu.api.service.CourseDepartmentService;
|
||||
import xyz.playedu.api.service.UserCourseHourRecordService;
|
||||
import xyz.playedu.api.service.UserCourseRecordService;
|
||||
@ -41,6 +42,8 @@ public class CourseDestroyListener {
|
||||
|
||||
@Autowired private UserCourseHourRecordService userCourseHourRecordService;
|
||||
|
||||
@Autowired private CourseAttachmentService courseAttachmentService;
|
||||
|
||||
@EventListener
|
||||
public void departmentRelateRemove(CourseDestroyEvent event) {
|
||||
courseDepartmentService.removeByCourseId(event.getCourseId());
|
||||
@ -51,6 +54,11 @@ public class CourseDestroyListener {
|
||||
courseCategoryService.removeByCourseId(event.getCourseId());
|
||||
}
|
||||
|
||||
@EventListener
|
||||
public void attachmentRelateRemove(CourseDestroyEvent event) {
|
||||
courseAttachmentService.remove(event.getCourseId());
|
||||
}
|
||||
|
||||
@EventListener
|
||||
public void removeUserRecords(CourseDestroyEvent event) {
|
||||
userCourseRecordService.removeByCourseId(event.getCourseId());
|
||||
|
@ -0,0 +1,35 @@
|
||||
/*
|
||||
* Copyright (C) 2023 杭州白书科技有限公司
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package xyz.playedu.api.request.backend;
|
||||
|
||||
import jakarta.validation.constraints.NotNull;
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Data
|
||||
public class CourseAttachmentMultiRequest {
|
||||
@Data
|
||||
public static class AttachmentItem {
|
||||
private String title;
|
||||
private Integer sort;
|
||||
private String type;
|
||||
private Integer rid;
|
||||
}
|
||||
|
||||
@NotNull(message = "attachments参数不存在")
|
||||
private List<AttachmentItem> attachments;
|
||||
}
|
@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Copyright (C) 2023 杭州白书科技有限公司
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package xyz.playedu.api.request.backend;
|
||||
|
||||
import jakarta.validation.constraints.NotBlank;
|
||||
import jakarta.validation.constraints.NotNull;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class CourseAttachmentRequest {
|
||||
|
||||
@NotBlank(message = "请输入附件名称")
|
||||
private String title;
|
||||
|
||||
@NotNull(message = "sort参数不存在")
|
||||
private Integer sort;
|
||||
|
||||
@NotBlank(message = "请选择附件类型")
|
||||
private String type;
|
||||
|
||||
@NotNull(message = "rid参数不存在")
|
||||
private Integer rid;
|
||||
}
|
@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (C) 2023 杭州白书科技有限公司
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package xyz.playedu.api.request.backend;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Data
|
||||
public class CourseAttachmentSortRequest {
|
||||
private List<Integer> ids;
|
||||
}
|
@ -72,6 +72,13 @@ public class CourseRequest {
|
||||
private List<HourItem> hours;
|
||||
}
|
||||
|
||||
@Data
|
||||
public static class AttachmentItem {
|
||||
private String name;
|
||||
private String type;
|
||||
private Integer rid;
|
||||
}
|
||||
|
||||
// 格式
|
||||
// [
|
||||
// {
|
||||
@ -100,4 +107,14 @@ public class CourseRequest {
|
||||
// ]
|
||||
@NotNull(message = "hours参数不存在")
|
||||
private List<HourItem> hours;
|
||||
|
||||
// 格式
|
||||
// [
|
||||
// {
|
||||
// 'name' => '附件名',
|
||||
// 'type' => '附件类型',
|
||||
// 'rid' => '资源id',
|
||||
// }...
|
||||
// ]
|
||||
private List<AttachmentItem> attachments;
|
||||
}
|
||||
|
@ -27,7 +27,7 @@ public interface CourseAttachmentService extends IService<CourseAttachment> {
|
||||
|
||||
void update(CourseAttachment courseAttachment, Integer sort, String title);
|
||||
|
||||
List<CourseAttachment> getAttachmentByCourseId(Integer courseId);
|
||||
List<CourseAttachment> getAttachmentsByCourseId(Integer courseId);
|
||||
|
||||
CourseAttachment create(
|
||||
Integer courseId,
|
||||
@ -42,7 +42,7 @@ public interface CourseAttachmentService extends IService<CourseAttachment> {
|
||||
|
||||
void updateSort(List<Integer> ids, Integer cid);
|
||||
|
||||
List<Integer> getRidsByCourseId(Integer courseId, String type);
|
||||
List<Integer> getRidsByCourseId(Integer courseId);
|
||||
|
||||
List<CourseAttachment> chunk(List<Integer> attachmentIds);
|
||||
}
|
||||
|
@ -53,7 +53,7 @@ public class CourseAttachmentServiceImpl extends ServiceImpl<CourseAttachmentMap
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CourseAttachment> getAttachmentByCourseId(Integer courseId) {
|
||||
public List<CourseAttachment> getAttachmentsByCourseId(Integer courseId) {
|
||||
return list(query().getWrapper().eq("course_id", courseId).orderByAsc("sort"));
|
||||
}
|
||||
|
||||
@ -108,8 +108,8 @@ public class CourseAttachmentServiceImpl extends ServiceImpl<CourseAttachmentMap
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Integer> getRidsByCourseId(Integer courseId, String type) {
|
||||
return list(query().getWrapper().eq("course_id", courseId).eq("type", type)).stream()
|
||||
public List<Integer> getRidsByCourseId(Integer courseId) {
|
||||
return list(query().getWrapper().eq("course_id", courseId)).stream()
|
||||
.map(CourseAttachment::getRid)
|
||||
.toList();
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user