From 74c8a1383da055d1f60fefcd59a890643f24137f Mon Sep 17 00:00:00 2001 From: "liu.zixi" Date: Wed, 19 Nov 2025 21:54:30 +0800 Subject: [PATCH] =?UTF-8?q?=E8=AF=BE=E7=A8=8B=E5=88=97=E8=A1=A8=E7=AE=A1?= =?UTF-8?q?=E7=90=86=E7=AB=AF=E6=96=B0=E7=89=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../module/course/api/CourseManageApi.java | 21 ++ .../module/course/dto/CoursePageQueryDTO.java | 75 +++++ .../com/xboe/module/course/entity/Course.java | 20 ++ .../course/service/ICoursePageService.java | 17 ++ .../service/impl/CoursePageServiceImpl.java | 257 ++++++++++++++++++ .../xboe/module/course/vo/CoursePageVo.java | 131 +++++++++ 6 files changed, 521 insertions(+) create mode 100644 servers/boe-server-all/src/main/java/com/xboe/module/course/dto/CoursePageQueryDTO.java create mode 100644 servers/boe-server-all/src/main/java/com/xboe/module/course/service/ICoursePageService.java create mode 100644 servers/boe-server-all/src/main/java/com/xboe/module/course/service/impl/CoursePageServiceImpl.java create mode 100644 servers/boe-server-all/src/main/java/com/xboe/module/course/vo/CoursePageVo.java diff --git a/servers/boe-server-all/src/main/java/com/xboe/module/course/api/CourseManageApi.java b/servers/boe-server-all/src/main/java/com/xboe/module/course/api/CourseManageApi.java index 7f62af7d..62817fdc 100644 --- a/servers/boe-server-all/src/main/java/com/xboe/module/course/api/CourseManageApi.java +++ b/servers/boe-server-all/src/main/java/com/xboe/module/course/api/CourseManageApi.java @@ -14,6 +14,7 @@ import com.xboe.api.ThirdApi; import com.xboe.module.course.dto.*; import com.xboe.module.course.entity.*; import com.xboe.module.course.service.*; +import com.xboe.module.course.vo.CoursePageVo; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.GetMapping; @@ -55,6 +56,9 @@ public class CourseManageApi extends ApiBaseController{ @Resource private ICourseService courseService; + + @Autowired + private ICoursePageService coursePageService; @Autowired IOutSideDataService outsideService; @@ -99,6 +103,23 @@ public class CourseManageApi extends ApiBaseController{ // PageList coursePageList = courseService.findPage(pager.getPageIndex(), pager.getPageSize(),dto); // return success(coursePageList); // } + + /** + * 新-管理端 课程列表 + * @return + */ + @PostMapping("/page") + public JsonResponse> managePage(@RequestBody CoursePageQueryDTO coursePageQueryDTO) { + // 处理入参逻辑 + if (coursePageQueryDTO.getLearningTimeStart() == null || coursePageQueryDTO.getLearningTimeEnd() == null) { + return badRequest("请指定正确的培训时间选择范围"); + } + // 管理端查询时不需要传入当前用户信息 + return success(coursePageService.pageQuery(null, coursePageQueryDTO)); + } + + @GetMapping("/export") + public void manageExport() {} /** * 管理列表的查询 diff --git a/servers/boe-server-all/src/main/java/com/xboe/module/course/dto/CoursePageQueryDTO.java b/servers/boe-server-all/src/main/java/com/xboe/module/course/dto/CoursePageQueryDTO.java new file mode 100644 index 00000000..2b295ba7 --- /dev/null +++ b/servers/boe-server-all/src/main/java/com/xboe/module/course/dto/CoursePageQueryDTO.java @@ -0,0 +1,75 @@ +package com.xboe.module.course.dto; + +import lombok.Data; + +import java.time.LocalDateTime; +import com.fasterxml.jackson.annotation.JsonFormat; + +@Data +public class CoursePageQueryDTO { + + /**课程名称*/ + private String name; + + /**资源归属一级*/ + private String resOwner1; + + /**资源归属二级*/ + private String resOwner2; + + /**资源归属三级*/ + private String resOwner3; + + /**是否发布,无就是全部*/ + private Boolean publish; + + /**创建人*/ + private String createUser; + + /**课程分类的一级*/ + private String sysType1; + + /**课程分类的二级*/ + private String sysType2; + + /**课程分类的三级*/ + private String sysType3; + + /**授课教师*/ + private String teacherName; + + /**培训时间筛选类型*/ + private String learningTimeType; + + /**培训时间-左区间*/ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8") + private LocalDateTime learningTimeStart; + + /**培训时间-右区间*/ + @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8") + private LocalDateTime learningTimeEnd; + + /**审核状态*/ + private String status; + + /**启用状态*/ + private Boolean enabled; + + /**是否公开课*/ + private Integer openCourse; + + /**创建来源*/ + private String createFrom; + + /**页码*/ + private Integer pageIndex; + + /**每页数量*/ + private Integer pageSize; + + /**排序字段*/ + private String orderField; + + /**排序顺序*/ + private Boolean orderAsc; +} \ No newline at end of file diff --git a/servers/boe-server-all/src/main/java/com/xboe/module/course/entity/Course.java b/servers/boe-server-all/src/main/java/com/xboe/module/course/entity/Course.java index 83aa02b3..ba84981c 100644 --- a/servers/boe-server-all/src/main/java/com/xboe/module/course/entity/Course.java +++ b/servers/boe-server-all/src/main/java/com/xboe/module/course/entity/Course.java @@ -406,6 +406,26 @@ public class Course extends BaseEntity { @Transient private Boolean isTip; + /** + * 课程时长(秒) + */ + @Column(name = "course_duration") + private Long courseDuration; + + /** + * 排序权重 + */ + @Column(name = "sort_weight") + private Integer sortWeight; + + /** + * 创建来源 + * teacher-教师端 + * admin-管理员端 + */ + @Column(name = "create_from") + private String createFrom; + public Course(String id,String name,String summary,String coverImg,String sysCreateAid,String sysCreateBy,Integer type,LocalDateTime publishTime){ super.setId(id); this.name=name; diff --git a/servers/boe-server-all/src/main/java/com/xboe/module/course/service/ICoursePageService.java b/servers/boe-server-all/src/main/java/com/xboe/module/course/service/ICoursePageService.java new file mode 100644 index 00000000..e6719825 --- /dev/null +++ b/servers/boe-server-all/src/main/java/com/xboe/module/course/service/ICoursePageService.java @@ -0,0 +1,17 @@ +package com.xboe.module.course.service; + +import com.xboe.common.PageList; +import com.xboe.core.CurrentUser; +import com.xboe.module.course.dto.CoursePageQueryDTO; +import com.xboe.module.course.vo.CoursePageVo; + +public interface ICoursePageService { + + /** + * 分页查询 + * @param currentUser 教师端传入此选项 + * @param coursePageQueryDTO + * @return + */ + PageList pageQuery(CurrentUser currentUser, CoursePageQueryDTO coursePageQueryDTO); +} diff --git a/servers/boe-server-all/src/main/java/com/xboe/module/course/service/impl/CoursePageServiceImpl.java b/servers/boe-server-all/src/main/java/com/xboe/module/course/service/impl/CoursePageServiceImpl.java new file mode 100644 index 00000000..e5764c84 --- /dev/null +++ b/servers/boe-server-all/src/main/java/com/xboe/module/course/service/impl/CoursePageServiceImpl.java @@ -0,0 +1,257 @@ +package com.xboe.module.course.service.impl; + +import com.xboe.common.OrderCondition; +import com.xboe.common.PageList; +import com.xboe.core.CurrentUser; +import com.xboe.core.orm.FieldFilters; +import com.xboe.core.orm.IFieldFilter; +import com.xboe.core.orm.QueryBuilder; +import com.xboe.data.dto.UserOrgIds; +import com.xboe.data.outside.IOutSideDataService; +import com.xboe.module.course.dao.CourseDao; +import com.xboe.module.course.dao.CourseTeacherDao; +import com.xboe.module.course.dto.CoursePageQueryDTO; +import com.xboe.module.course.entity.Course; +import com.xboe.module.course.entity.CourseTeacher; +import com.xboe.module.course.service.ICoursePageService; +import com.xboe.module.course.vo.CoursePageVo; +import lombok.extern.slf4j.Slf4j; +import org.apache.commons.lang3.StringUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import javax.annotation.Resource; +import java.util.ArrayList; +import java.util.List; +import java.util.stream.Collectors; + +@Service +@Slf4j +public class CoursePageServiceImpl implements ICoursePageService { + + @Resource + private CourseDao courseDao; + + @Resource + private CourseTeacherDao courseTeacherDao; + + @Autowired + private IOutSideDataService outSideDataService; + + @Override + public PageList pageQuery(CurrentUser currentUser, CoursePageQueryDTO coursePageQueryDTO) { + /* + * 1. 前置权限过滤 + * 权限说明:管理员登录后当前页面只可查看本人创建的课程及被授权的课程,其他课程不可见,被赋予查看权的用户可直接引用可查看的课程 + */ + UserOrgIds userOrgIds = outSideDataService.getOrgIds(); + + List orgIds = userOrgIds.getIds(); + + boolean isSystemAdmin = userOrgIds.getPermissions().containsKey(UserOrgIds.IsSystemAdminKey) + && userOrgIds.getPermissions().get(UserOrgIds.IsSystemAdminKey); + + String currentAccountId = currentUser == null ? null : currentUser.getAccountId(); + + // 构建查询条件 + List filters = createFilters(coursePageQueryDTO); + + // 自动添加过滤已删除 + filters.add(FieldFilters.eq("c.deleted", false)); + + // 添加权限过滤条件 + if (!isSystemAdmin) { + // 非系统管理员需要进行权限过滤 + List permissionFilters = new ArrayList<>(); + + // 添加组织权限过滤 + if (orgIds != null && !orgIds.isEmpty()) { + permissionFilters.add(FieldFilters.in("c.orgId", orgIds)); + } + + // 添加创建人过滤(可以看到自己创建的课程) + if (StringUtils.isNotBlank(currentAccountId)) { + permissionFilters.add(FieldFilters.eq("c.sysCreateAid", currentAccountId)); + } + + // 如果有权限条件,则添加OR条件 + if (!permissionFilters.isEmpty()) { + filters.add(FieldFilters.or(permissionFilters)); + } + } + + QueryBuilder query = QueryBuilder.from(Course.class.getSimpleName() + " c").addFilters(filters); + // 处理排序 + handleOrder(query, coursePageQueryDTO.getOrderField(), coursePageQueryDTO.getOrderAsc()); + + // 设置分页参数 + int pageIndex = coursePageQueryDTO.getPageIndex() != null ? coursePageQueryDTO.getPageIndex() : 0; + int pageSize = coursePageQueryDTO.getPageSize() != null ? coursePageQueryDTO.getPageSize() : 10; + query.setPageIndex(pageIndex); + query.setPageSize(pageSize); + + // 执行查询 + PageList coursePageList = courseDao.findPage(query.builder()); + + // 转换为CoursePageVo + PageList result = new PageList<>(); + result.setCount(coursePageList.getCount()); + result.setPageSize(coursePageList.getPageSize()); + + // 子查询:根据课程id查询课程下的教师 + List courseIds = coursePageList.getList().stream() + .map(Course::getId) + .collect(Collectors.toList()); + List courseTeacherList = getCourseTeacherList(courseIds); + List voList = coursePageList.getList().stream() + .map(c -> convertToVo(c, courseTeacherList)) + .collect(Collectors.toList()); + result.setList(voList); + + return result; + } + + /** + * 生成过滤条件 + * + * @param dto + * @return + */ + private List createFilters(CoursePageQueryDTO dto) { + List filters = new ArrayList<>(); + + if (StringUtils.isNotBlank(dto.getName())) { + filters.add(FieldFilters.like("c.name", dto.getName())); + } + + if (StringUtils.isNotBlank(dto.getCreateUser())) { + filters.add(FieldFilters.like("c.sysCreateBy", dto.getCreateUser())); + } + + if (StringUtils.isNotBlank(dto.getResOwner3())) { + filters.add(FieldFilters.eq("c.resOwner3", dto.getResOwner3())); + } + if (StringUtils.isNotBlank(dto.getResOwner2())) { + filters.add(FieldFilters.eq("c.resOwner2", dto.getResOwner2())); + } + if (StringUtils.isNotBlank(dto.getResOwner1())) { + filters.add(FieldFilters.eq("c.resOwner1", dto.getResOwner1())); + } + + if (dto.getPublish() != null) { + filters.add(FieldFilters.eq("c.published", dto.getPublish())); + } + + // 状态查询 + if (StringUtils.isNotBlank(dto.getStatus())) { + filters.add(FieldFilters.eq("c.status", Integer.valueOf(dto.getStatus()))); + } + + // 系统分类查询 + if (StringUtils.isNotBlank(dto.getSysType3())) { + filters.add(FieldFilters.eq("c.sysType3", dto.getSysType3())); + } + if (StringUtils.isNotBlank(dto.getSysType2())) { + filters.add(FieldFilters.eq("c.sysType2", dto.getSysType2())); + } + if (StringUtils.isNotBlank(dto.getSysType1())) { + filters.add(FieldFilters.eq("c.sysType1", dto.getSysType1())); + } + + // 是否启用 + if (dto.getEnabled() != null) { + filters.add(FieldFilters.eq("c.enabled", dto.getEnabled())); + } + + // 时间范围查询(待定) + + return filters; + } + + private List getCourseTeacherList(List courseIds) { + return courseTeacherDao.findList(OrderCondition.desc("courseId"), FieldFilters.in("courseId", courseIds)); + } + + /** + * 将Course转换为CoursePageVo + * @param course + * @return + */ + private CoursePageVo convertToVo(Course course, List courseTeacherList) { + CoursePageVo vo = new CoursePageVo(); + vo.setId(course.getId()); + vo.setName(course.getName()); + vo.setCoverImg(course.getCoverImg()); + vo.setSysType1(course.getSysType1()); + vo.setSysType2(course.getSysType2()); + vo.setSysType3(course.getSysType3()); + vo.setResOwner1(course.getResOwner1()); + vo.setResOwner2(course.getResOwner2()); + vo.setResOwner3(course.getResOwner3()); + vo.setSysCreateBy(course.getSysCreateBy()); + vo.setCreateFrom(course.getCreateFrom()); + vo.setSysCreateTime(course.getSysCreateTime()); + vo.setForUsers(course.getForUsers()); + vo.setStatus(course.getStatus()); + // auditType 需要从其他地方获取,这里暂时设置为默认值 + vo.setAuditType(1); + vo.setPublished(course.getPublished()); + vo.setStudys(course.getStudys()); + vo.setScore(course.getScore()); + // courseDuration 需要计算,这里暂时设置为默认值 + vo.setCourseDuration(course.getCourseDuration()); + vo.setEnabled(course.getEnabled()); + + // 获取教师名称 + List teacherNames = courseTeacherList.stream() + .filter(ct -> StringUtils.equals(ct.getCourseId(), course.getId())) + .map(CourseTeacher::getTeacherName) + .collect(Collectors.toList()); + + if (!teacherNames.isEmpty()) { + vo.setTeacherName(String.join(",", teacherNames)); + } + + return vo; + } + + private void handleOrder(QueryBuilder query, String orderField, Boolean orderAsc) { + if (StringUtils.isNotBlank(orderField)) { + boolean isAsc = orderAsc == null || orderAsc; + // 1. 多字段排序 + if (StringUtils.equals(orderField, "sysType")) { + if (isAsc) { + query.addOrder(OrderCondition.asc("c.sysType1")); + query.addOrder(OrderCondition.asc("c.sysType2")); + query.addOrder(OrderCondition.asc("c.sysType3")); + } else { + query.addOrder(OrderCondition.desc("c.sysType1")); + query.addOrder(OrderCondition.desc("c.sysType2")); + query.addOrder(OrderCondition.desc("c.sysType3")); + } + } else if (StringUtils.equals(orderField, "resOwner")) { + if (isAsc) { + query.addOrder(OrderCondition.asc("c.resOwner1")); + query.addOrder(OrderCondition.asc("c.resOwner2")); + query.addOrder(OrderCondition.asc("c.resOwner3")); + } else { + query.addOrder(OrderCondition.desc("c.resOwner1")); + query.addOrder(OrderCondition.desc("c.resOwner2")); + query.addOrder(OrderCondition.desc("c.resOwner3")); + } + } else { + if (isAsc) { + query.addOrder(OrderCondition.asc("c." + orderField)); + } else { + query.addOrder(OrderCondition.desc("c." + orderField)); + } + } + } else { + OrderCondition isTop = OrderCondition.desc("c.isTop"); + query.addOrder(isTop); + + OrderCondition sortWeightOc = OrderCondition.asc("c.sortWeight"); + query.addOrder(sortWeightOc); + } + } +} \ No newline at end of file diff --git a/servers/boe-server-all/src/main/java/com/xboe/module/course/vo/CoursePageVo.java b/servers/boe-server-all/src/main/java/com/xboe/module/course/vo/CoursePageVo.java new file mode 100644 index 00000000..b2e60d06 --- /dev/null +++ b/servers/boe-server-all/src/main/java/com/xboe/module/course/vo/CoursePageVo.java @@ -0,0 +1,131 @@ +package com.xboe.module.course.vo; + +import lombok.Data; +import org.springframework.format.annotation.DateTimeFormat; + +import java.time.LocalDateTime; + +@Data +public class CoursePageVo { + + /** + * 课程ID + */ + private String id; + + /** + * 课程名称 + */ + private String name; + + /** + * 课程封面图片地址 + */ + private String coverImg; + + /** + * 课程分类一级 + */ + private String sysType1; + + /** + * 课程分类二级 + */ + private String sysType2; + + /** + * 课程分类三级 + */ + private String sysType3; + + /** + * 资源归属一级 + */ + private String resOwner1; + + /** + * 资源归属二级 + */ + private String resOwner2; + + /** + * 资源归属三级 + */ + private String resOwner3; + + /** + * 创建人 + */ + private String sysCreateBy; + + /** + * 创建来源 + * teacher-教师端 + * admin-管理员端 + */ + private String createFrom; + + /** + * 创建时间 + */ + @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss") + private LocalDateTime sysCreateTime; + + /** + * 目标人群 + */ + private String forUsers; + + /** + * 审核状态 + * 1-无审核状态 + * 2-审核中 + * 3-审核驳回 + * 5-审核通过 + */ + private Integer status; + + /** + * 课程审核类型 + * 1-课程创建 + * 2-课程编辑 + * 3-课程启用 + * 4-课程停用 + * 5-撤回申请 + */ + private Integer auditType; + + /** + * 发布状态 + * false-未发布 + * true-已发布 + */ + private Boolean published; + + /** + * 学习人数 + */ + private Integer studys; + + /** + * 课程评分 + */ + private Float score; + + /** + * 课程时长(秒) + */ + private Long courseDuration; + + /** + * 启用状态 + * false-停用 + * true-启用 + */ + private Boolean enabled; + + /** + * 授课教师 + */ + private String teacherName; +} \ No newline at end of file