diff --git a/app/api/playedu-api/src/main/java/xyz/playedu/api/controller/backend/jc/TextbookController.java b/app/api/playedu-api/src/main/java/xyz/playedu/api/controller/backend/jc/TextbookController.java index 8024395..9ced289 100644 --- a/app/api/playedu-api/src/main/java/xyz/playedu/api/controller/backend/jc/TextbookController.java +++ b/app/api/playedu-api/src/main/java/xyz/playedu/api/controller/backend/jc/TextbookController.java @@ -9,21 +9,33 @@ import org.springframework.validation.annotation.Validated; import org.springframework.web.bind.annotation.*; import xyz.playedu.common.annotation.Log; import xyz.playedu.common.constant.BusinessTypeConstant; +import xyz.playedu.common.constant.CommonConstant; +import xyz.playedu.common.domain.Department; +import xyz.playedu.common.domain.Group; +import xyz.playedu.common.domain.User; +import xyz.playedu.common.domain.UserGroup; +import xyz.playedu.common.exception.NotFoundException; +import xyz.playedu.common.service.*; import xyz.playedu.common.types.JsonResponse; import xyz.playedu.common.types.paginate.PaginationResult; import xyz.playedu.common.util.StringUtil; import xyz.playedu.course.constants.CourseConstant; +import xyz.playedu.course.domain.Course; import xyz.playedu.course.domain.CourseDepartmentUser; import xyz.playedu.jc.domain.BookDepartmentUser; +import xyz.playedu.jc.domain.JCResource; import xyz.playedu.jc.domain.Textbook; import xyz.playedu.jc.domain.dto.TextbookRequestDTO; import xyz.playedu.jc.service.IBookDepartmentUserService; import xyz.playedu.jc.service.ITextbookService; +import xyz.playedu.jc.service.JCIResourceService; import xyz.playedu.knowledge.domain.KnowledgeMessages; import java.util.ArrayList; import java.util.HashMap; import java.util.List; +import java.util.Map; +import java.util.stream.Collectors; /** * 教材管理 后台接口 @@ -38,17 +50,222 @@ public class TextbookController { @Autowired private IBookDepartmentUserService bookDepartmentUserService; + @Autowired + private JCIResourceService jciResourceService; + @Autowired private DepartmentService departmentService; + @Autowired private UserGroupService userGroupService; + @Autowired private UserDepartmentService userDepartmentService; + @Autowired private UserService userService; + @Autowired private GroupService groupService; + @GetMapping("/index") public JsonResponse index(@RequestParam HashMap params) { /** 调用服务层分页查询方法,Service 层已包含完整的分页信息 */ PaginationResult result = textbookService.paginate(params); + HashMap data = new HashMap<>(); + data.put("data", result.getData()); + data.put("total", result.getTotal()); + // 课程封面资源ID + List rids = new ArrayList<>(); + rids.addAll(result.getData().stream().map(Textbook::getThumb).toList()); + + List bookIds = result.getData().stream().map(Textbook::getId).toList(); +// data.put("course_category_ids", courseService.getCategoryIdsGroup(courseIds)); +// data.put("categories", categoryService.id2name()); +// data.put("departments", departmentService.id2name()); + +// Map courseIdRecordCountMap = new HashMap<>(); +// doGetRecords(courseIds) +// .forEach( +// (key, value) -> { +// courseIdRecordCountMap.put(key, value.size()); +// }); +// data.put("records", courseIdRecordCountMap); + // 获取签名url + data.put("resource_url", jciResourceService.chunksPreSignUrlByIds(rids)); + + // 指派范围 + Map book_user_count = new HashMap<>(); + List courseDepartmentUserList = + bookDepartmentUserService.chunksByBookIds(bookIds); + if (StringUtil.isNotEmpty(courseDepartmentUserList)) { + List depIds = + courseDepartmentUserList.stream() + .filter( + courseDepartmentUser -> + CourseConstant.COURSE_TYPE_DEP + == courseDepartmentUser.getType()) + .map(BookDepartmentUser::getRangeId) + .distinct() + .toList(); + Map depMap = new HashMap<>(); + if (StringUtil.isNotEmpty(depIds)) { + depMap = + departmentService.chunk(depIds).stream() + .collect(Collectors.toMap(Department::getId, e -> e)); + } + Map finalDepMap = depMap; + courseDepartmentUserList.stream() + .collect(Collectors.groupingBy(BookDepartmentUser::getBookId)) + .forEach( + (key, value) -> { + if (StringUtil.isNotEmpty(value)) { + List courseDepIds = new ArrayList<>(); + List courseUserIds = new ArrayList<>(); + value.forEach( + courseDepartmentUser -> { + if (CourseConstant.COURSE_TYPE_DEP + == courseDepartmentUser.getType()) { + Department dep = + finalDepMap.get( + courseDepartmentUser + .getRangeId()); + if (StringUtil.isNotNull(dep)) { + courseDepIds.add(dep.getId()); + String parentChain = ""; + if (StringUtil.isEmpty( + dep.getParentChain())) { + parentChain = dep.getId() + ""; + } else { + parentChain = + dep.getParentChain() + + "," + + dep.getId(); + } + List childDepartmentList = + departmentService + .getChildDepartmentsByParentChain( + dep.getId(), + parentChain); + if (StringUtil.isNotEmpty( + childDepartmentList)) { + courseDepIds.addAll( + childDepartmentList.stream() + .map(Department::getId) + .toList()); + } + } + } else if (CourseConstant.COURSE_TYPE_GROUP + == courseDepartmentUser.getType()) { + List userGroupList = + userGroupService.chunksByGroupIds( + new ArrayList<>() { + { + add( + courseDepartmentUser + .getRangeId()); + } + }); + if (StringUtil.isNotEmpty(userGroupList)) { + courseUserIds.addAll( + userGroupList.stream() + .map(UserGroup::getUserId) + .toList()); + } + } else { + courseUserIds.add( + courseDepartmentUser.getRangeId()); + } + }); + if (StringUtil.isNotEmpty(courseDepIds)) { + List departmentUserIds = + userDepartmentService.getUserIdsByDepIds( + courseDepIds); + if (StringUtil.isNotEmpty(departmentUserIds)) { + courseUserIds.addAll(departmentUserIds); + } + } + // 过滤本地逻辑删除的学员 + List userIds = + userService.chunks(courseUserIds).stream() + .filter( + user -> + user.getDeleted().intValue() + == CommonConstant.ZERO + .intValue()) + .map(User::getId) + .toList(); + book_user_count.put( + key, userIds.stream().distinct().toList().size()); + } + }); + } + data.put("course_user_count", book_user_count); /** 直接返回 Service 层的结果 */ - return JsonResponse.data(result); + return JsonResponse.data(data); } + @GetMapping("/{id}") + @Log(title = "线上课-编辑", businessType = BusinessTypeConstant.GET) + public JsonResponse edit(@PathVariable(name = "id") Integer id) throws NotFoundException { + Textbook textbook = textbookService.findOrFail(id); + + HashMap data = new HashMap<>(); + data.put("textbook", textbook); + + List rids = new ArrayList<>(); + rids.add(textbook.getThumb()); + // 获取签名url + data.put("resource_url", jciResourceService.chunksPreSignUrlByIds(rids)); + + // 指派范围 + List courseDepartmentUserList = + bookDepartmentUserService.chunksByCourseId(id); + if (StringUtil.isNotEmpty(courseDepartmentUserList)) { + Map deps = + departmentService + .chunk( + courseDepartmentUserList.stream() + .filter( + dto -> + CourseConstant.COURSE_TYPE_DEP + == dto.getType()) + .map(BookDepartmentUser::getRangeId) + .toList()) + .stream() + .collect(Collectors.toMap(Department::getId, Department::getName)); + data.put("deps", deps); + Map users = + userService + .chunks( + courseDepartmentUserList.stream() + .filter( + dto -> + CourseConstant.COURSE_TYPE_USER + == dto.getType()) + .map(BookDepartmentUser::getRangeId) + .toList()) + .stream() + .filter( + user -> + user.getDeleted().intValue() + == CommonConstant.ZERO.intValue()) + .collect(Collectors.toMap(User::getId, User::getName)); + data.put("users", users); + Map groups = + groupService + .chunkByIds( + courseDepartmentUserList.stream() + .filter( + dto -> + CourseConstant.COURSE_TYPE_GROUP + == dto.getType()) + .map(BookDepartmentUser::getRangeId) + .toList()) + .stream() + .collect(Collectors.toMap(Group::getId, Group::getName)); + data.put("groups", groups); + } else { + data.put("deps", new HashMap<>()); + data.put("users", new HashMap<>()); + data.put("groups", new HashMap<>()); + } + return JsonResponse.data(data); + + } @GetMapping("/list") public JsonResponse list() { @@ -56,11 +273,11 @@ public class TextbookController { return JsonResponse.data(list); } - @GetMapping("/{id}") - public JsonResponse detail(@PathVariable("id") Integer id) { - Textbook one = textbookService.getById(id); - return JsonResponse.data(one); - } +// @GetMapping("/{id}") +// public JsonResponse detail(@PathVariable("id") Integer id) { +// Textbook one = textbookService.getById(id); +// return JsonResponse.data(one); +// } // @Transactional @PostMapping diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/JCResource.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/JCResource.java index 938c58b..8fac273 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/JCResource.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/JCResource.java @@ -31,8 +31,8 @@ public class JCResource { @TableField("name") private String name; - @TableField("konwledge_code") - private String konwledgeCode; + @TableField("knowledge_code") + private String knowledgeCode; /** 文本描述 AI分析或自动填入 */ diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/Textbook.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/Textbook.java index d4ce03b..ccc2380 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/Textbook.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/Textbook.java @@ -25,7 +25,7 @@ public class Textbook { /** 封面地址 */ @TableField("thumb") - private String thumb; + private Integer thumb; /** 简介 */ @TableField("short_desc") diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/dto/TextbookRequestDTO.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/dto/TextbookRequestDTO.java index 8b9f1b9..567fa73 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/dto/TextbookRequestDTO.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/domain/dto/TextbookRequestDTO.java @@ -26,7 +26,7 @@ public class TextbookRequestDTO { /** 封面地址 */ @TableField("thumb") - private String thumb; + private Integer thumb; /** 简介 */ @TableField("short_desc") diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/IBookDepartmentUserService.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/IBookDepartmentUserService.java index 991b070..9ca0091 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/IBookDepartmentUserService.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/IBookDepartmentUserService.java @@ -1,8 +1,15 @@ package xyz.playedu.jc.service; import com.baomidou.mybatisplus.extension.service.IService; +import xyz.playedu.course.domain.CourseDepartmentUser; import xyz.playedu.jc.domain.BookDepartmentUser; +import java.util.List; + public interface IBookDepartmentUserService extends IService { void removeByBookId(Integer bookId); + + List chunksByBookIds(List bookIds); + + List chunksByCourseId(Integer courseId); } \ No newline at end of file diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/ITextbookService.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/ITextbookService.java index c989c7e..54f337e 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/ITextbookService.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/ITextbookService.java @@ -1,7 +1,9 @@ package xyz.playedu.jc.service; import com.baomidou.mybatisplus.extension.service.IService; +import xyz.playedu.common.exception.NotFoundException; import xyz.playedu.common.types.paginate.PaginationResult; +import xyz.playedu.jc.domain.JCResource; import xyz.playedu.jc.domain.Textbook; import java.util.HashMap; @@ -12,4 +14,7 @@ import java.util.HashMap; public interface ITextbookService extends IService { PaginationResult paginate(HashMap params); + + Textbook findOrFail(Integer id) throws NotFoundException; + } \ No newline at end of file diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/JCIResourceService.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/JCIResourceService.java index 94398ab..ff83fb5 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/JCIResourceService.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/JCIResourceService.java @@ -1,7 +1,14 @@ package xyz.playedu.jc.service; import com.baomidou.mybatisplus.extension.service.IService; +import xyz.playedu.common.exception.NotFoundException; +import xyz.playedu.course.domain.Course; import xyz.playedu.jc.domain.JCResource; +import java.util.List; +import java.util.Map; + public interface JCIResourceService extends IService { + Map chunksPreSignUrlByIds(List ids); + } diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/BookDepartmentUserServiceImpl.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/BookDepartmentUserServiceImpl.java index 59da17f..ff7f235 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/BookDepartmentUserServiceImpl.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/BookDepartmentUserServiceImpl.java @@ -2,10 +2,13 @@ package xyz.playedu.jc.service.impl; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import org.springframework.stereotype.Service; +import xyz.playedu.course.domain.CourseDepartmentUser; import xyz.playedu.jc.domain.BookDepartmentUser; import xyz.playedu.jc.mapper.BookDepartmentUserMapper; import xyz.playedu.jc.service.IBookDepartmentUserService; +import java.util.List; + @Service public class BookDepartmentUserServiceImpl extends ServiceImpl @@ -15,4 +18,15 @@ public class BookDepartmentUserServiceImpl public void removeByBookId(Integer bookId) { remove(query().getWrapper().eq("book_id", bookId)); } + + @Override + public List chunksByBookIds(List bookIds) { + return List.of(); + } + + @Override + public List chunksByCourseId(Integer bookId) { + return list(query().getWrapper().eq("book_id", bookId)); + } + } \ No newline at end of file diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/JCResourceServiceImpl.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/JCResourceServiceImpl.java index 54e450a..7f1f4f2 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/JCResourceServiceImpl.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/JCResourceServiceImpl.java @@ -1,13 +1,50 @@ package xyz.playedu.jc.service.impl; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; +import xyz.playedu.common.exception.NotFoundException; +import xyz.playedu.common.service.AppConfigService; +import xyz.playedu.common.util.S3Util; +import xyz.playedu.common.util.StringUtil; +import xyz.playedu.course.domain.Course; import xyz.playedu.jc.domain.JCResource; import xyz.playedu.jc.mapper.JCResourceMapper; import xyz.playedu.jc.service.JCIResourceService; +import xyz.playedu.resource.domain.Resource; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; @Service public class JCResourceServiceImpl extends ServiceImpl implements JCIResourceService { + + @Autowired + private AppConfigService appConfigService; + + @Override + public Map chunksPreSignUrlByIds(List ids) { + S3Util s3Util = new S3Util(appConfigService.getS3Config()); + + Map preSignUrlMap = new HashMap<>(); + if (StringUtil.isNotEmpty(ids)) { + List resourceList = list(query().getWrapper().in("id", ids)); + if (StringUtil.isNotEmpty(resourceList)) { + resourceList.forEach( + resource -> { + String name = resource.getName() + "." + resource.getExtension(); + String url = s3Util.generateDownloadUrl(resource.getPath(), name); + if (StringUtil.isNotEmpty(url)) { + preSignUrlMap.put(resource.getId(), url); + } + }); + } + } + return preSignUrlMap; + } + + } \ No newline at end of file diff --git a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/TextbookServiceImpl.java b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/TextbookServiceImpl.java index 91e90d6..2315fa3 100644 --- a/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/TextbookServiceImpl.java +++ b/app/api/playedu-course/src/main/java/xyz/playedu/jc/service/impl/TextbookServiceImpl.java @@ -7,7 +7,9 @@ import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import lombok.extern.slf4j.Slf4j; import org.apache.commons.collections4.MapUtils; import org.springframework.stereotype.Service; +import xyz.playedu.common.exception.NotFoundException; import xyz.playedu.common.types.paginate.PaginationResult; +import xyz.playedu.jc.domain.JCResource; import xyz.playedu.jc.domain.Textbook; import xyz.playedu.jc.mapper.TextbookMapper; import xyz.playedu.jc.service.ITextbookService; @@ -85,4 +87,13 @@ public class TextbookServiceImpl return emptyResult; } } + + @Override + public Textbook findOrFail(Integer id) throws NotFoundException { + Textbook textbook = getOne(query().getWrapper().eq("id", id)); + if (textbook == null) { + throw new NotFoundException("课程不存在"); + } + return textbook; + } } \ No newline at end of file