Accept Merge Request #140: (hyc -> master)

Merge Request: 【修改】ps考点出题完善

Created By: @华允传
Accepted By: @华允传
URL: https://g-iswv8783.coding.net/p/education/d/pengchen-exam-java/git/merge/140?initial=true
This commit is contained in:
华允传
2025-07-04 18:50:15 +08:00
committed by Coding
10 changed files with 225 additions and 31 deletions

View File

@@ -1,11 +1,14 @@
package pc.exam.pp.module.exam.dal.dataobject;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.Accessors;
import java.util.List;
@TableName(value = "exam_ps_keyword", autoResultMap = true)
@Data
@Accessors(chain = true)
@@ -27,11 +30,11 @@ public class ExamPsKeyword {
/**
* 键
*/
private String keyName;
private String key;
/**
* 值
*/
private String keyValue;
private String value;
/**
* 权值
*/
@@ -40,4 +43,9 @@ public class ExamPsKeyword {
* 类型(学生考点1结果考点2)
*/
private String type;
private Integer sort;
@TableField(exist = false)
private List<ExamPsKeyword> children;
}

View File

@@ -0,0 +1,19 @@
package pc.exam.pp.module.judgement.controller.admin.getpoints.dto;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import pc.exam.pp.module.exam.dal.dataobject.ExamPsKeyword;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsReturnVo;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsVo;
import java.util.List;
@Data
@NoArgsConstructor
@AllArgsConstructor
public class PsViewReturnDto {
private List<ExamPsKeyword> pointList;
private List<ExamPsKeyword> answerList;
}

View File

@@ -0,0 +1,36 @@
package pc.exam.pp.module.judgement.controller.admin.getpoints.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class PsReturnVo {
/**
* 主键id
*/
private String id;
/**
* 试题id
*/
private String quId;
/**
* 父id
*/
private String parentId;
private String key;
private String rate;
private String value;
private List<PsReturnVo> children;
}

View File

@@ -4,6 +4,7 @@ import pc.exam.pp.module.exam.dal.dataobject.ExamPsKeyword;
import pc.exam.pp.module.exam.dal.dataobject.ExamQuestionAnswer;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsAnswerSubmitDTO;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsViewDto;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsViewReturnDto;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.FilePointsVo;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.Points;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PointsVo;
@@ -31,5 +32,5 @@ public interface ExamGetPointsService {
void set_ps_point(PsAnswerSubmitDTO psAnswerSubmitDTO);
PsViewDto getPsPointById(String quId);
PsViewReturnDto getPsPointById(String quId);
}

View File

@@ -23,6 +23,7 @@ import pc.exam.pp.module.infra.service.config.ConfigService;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsAnswerNode;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsAnswerSubmitDTO;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsViewDto;
import pc.exam.pp.module.judgement.controller.admin.getpoints.dto.PsViewReturnDto;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.*;
import pc.exam.pp.module.judgement.controller.service.ps.IPsService;
import pc.exam.pp.module.judgement.controller.utils.ps.PsUtil;
@@ -464,8 +465,12 @@ public class ExamGetPointsServiceImpl implements ExamGetPointsService{
}
//给List统一设置type
String type = psAnswerSubmitDTO.getType();
for (ExamPsKeyword keyword : stuList) {
for (int i = 0; i < stuList.size(); i++) {
ExamPsKeyword keyword = stuList.get(i);
keyword.setType(type);
// 设置排序值
keyword.setSort(i + 1);
}
stuList.forEach(System.out::println);
//先根据删除试题id删除
@@ -475,16 +480,67 @@ public class ExamGetPointsServiceImpl implements ExamGetPointsService{
}
@Override
public PsViewDto getPsPointById(String quId) {
PsViewDto psViewDto=new PsViewDto();
List<PsVo> pointList=psService.selectPsPointByType(quId,"1");
List<PsVo> answerList=psService.selectPsPointByType(quId,"2");
psViewDto.setAnswerList(answerList);
psViewDto.setPointList(pointList);
public PsViewReturnDto getPsPointById(String quId) {
PsViewReturnDto psViewDto=new PsViewReturnDto();
List<ExamPsKeyword> pointList=psService.selectPsPointByType(quId,"1");
List<ExamPsKeyword> answerList=psService.selectPsPointByType(quId,"2");
// 构建树形结构
List<ExamPsKeyword> treeAnswerList = buildTree(answerList);
psViewDto.setAnswerList(treeAnswerList);
List<ExamPsKeyword> treePointList = buildTree(pointList);
psViewDto.setPointList(treePointList);
return psViewDto;
}
/**
* 构建答案树形结构
*/
private List<ExamPsKeyword> buildTree(List<ExamPsKeyword> flatList) {
if (CollectionUtils.isEmpty(flatList)) {
return Collections.emptyList();
}
// 第一步:构建所有节点
Map<String, ExamPsKeyword> nodeMap = new LinkedHashMap<>();
Map<String, List<ExamPsKeyword>> parentChildMap = new HashMap<>();
flatList.forEach(item -> {
ExamPsKeyword node = new ExamPsKeyword();
node.setId(item.getId());
node.setKey(item.getKey());
node.setValue(item.getValue()); // 先保留原始值
node.setRate(item.getRate());
node.setType(item.getType());
node.setSort(item.getSort());
nodeMap.put(item.getId(), node);
String parentId = item.getParentId() != null ? item.getParentId() : "0";
parentChildMap.computeIfAbsent(parentId, k -> new ArrayList<>()).add(node);
});
// 第二步:建立父子关系并识别真正父节点
Set<ExamPsKeyword> realParents = new HashSet<>();
parentChildMap.forEach((parentId, children) -> {
if ("0".equals(parentId)) {
children.forEach(node -> {
// 标记没有子节点的独立节点
if (!parentChildMap.containsKey(node.getId())) {
node.setChildren(null);
}
});
} else {
ExamPsKeyword parent = nodeMap.get(parentId);
if (parent != null) {
parent.setChildren(children);
realParents.add(parent); // 记录真正有子节点的父节点
}
}
});
// 第三步对有子节点的父节点设置value=null
realParents.forEach(parent -> parent.setValue(null));
return parentChildMap.getOrDefault("0", Collections.emptyList());
}
// 递归转换方法
@@ -496,8 +552,8 @@ public class ExamGetPointsServiceImpl implements ExamGetPointsService{
keyword.setId(id);
keyword.setQuId(quId);
keyword.setParentId(parentId);
keyword.setKeyName(node.getKey());
keyword.setKeyValue(node.getValue());
keyword.setKey(node.getKey());
keyword.setValue(node.getValue());
keyword.setRate(node.getRate() == null ? null : node.getRate().toString());
resultList.add(keyword);

View File

@@ -3,6 +3,7 @@ package pc.exam.pp.module.judgement.controller.service.ps;
import org.apache.ibatis.annotations.Param;
import org.springframework.stereotype.Service;
import pc.exam.pp.module.exam.dal.dataobject.ExamPsKeyword;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsReturnVo;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsVo;
import java.util.List;
@@ -13,6 +14,6 @@ public interface IPsService {
void insertPsKeywordList(List<ExamPsKeyword> resultList);
List<PsVo> selectPsPointByType(String quId, String type);
List<ExamPsKeyword> selectPsPointByType(String quId, String type);
}

View File

@@ -3,6 +3,7 @@ package pc.exam.pp.module.judgement.controller.service.ps;
import jakarta.annotation.Resource;
import org.springframework.stereotype.Service;
import pc.exam.pp.module.exam.dal.dataobject.ExamPsKeyword;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsReturnVo;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsVo;
import pc.exam.pp.module.judgement.dal.mysql.ps.PsMapper;
@@ -19,11 +20,11 @@ public class PsServiceImpl implements IPsService {
@Override
public void insertPsKeywordList(List<ExamPsKeyword> resultList) {
psMapper.insertBatch(resultList);
psMapper.insertPsKeywordList(resultList);
}
@Override
public List<PsVo> selectPsPointByType(String quId, String type) {
public List<ExamPsKeyword> selectPsPointByType(String quId, String type) {
return psMapper.selectPsPointByType(quId,type);
}
}

View File

@@ -4,6 +4,8 @@ import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.sql.*;
import java.util.ArrayList;
import java.util.List;
public class MySQLExporterUtil {
@@ -36,7 +38,9 @@ public class MySQLExporterUtil {
// 导出视图结构
exportViews(conn, writer);
// 导出存储过程
exportProcedures(conn, writer);
// exportProcedures(conn, writer);
// 4. 导出所有触发器
// exportTriggers(conn,writer);
System.out.println("导出成功!文件路径: " + outputFile);
} catch (Exception e) {
e.printStackTrace();
@@ -68,20 +72,33 @@ public class MySQLExporterUtil {
// 获取 CREATE TABLE 语句
String createTableSQL = rs.next() ? rs.getString("Create Table") : "";
// 移除 AUTO_INCREMENT 部分
createTableSQL = createTableSQL.replaceAll("AUTO_INCREMENT=\\d+", "");
// 移除 ENGINE, CHARSET 和 ROW_FORMAT 部分
createTableSQL = createTableSQL.replaceAll("ENGINE=[^ ]+|DEFAULT CHARSET=[^ ]+|ROW_FORMAT=[^ ]+", "");
// 清理多余的空格
createTableSQL = createTableSQL.trim();
// // 移除 AUTO_INCREMENT 部分
// createTableSQL = createTableSQL.replaceAll("AUTO_INCREMENT=\\d+", "");
//
// // 移除 ENGINE, CHARSET 和 ROW_FORMAT 部分
// createTableSQL = createTableSQL.replaceAll("ENGINE=[^ ]+|DEFAULT CHARSET=[^ ]+|ROW_FORMAT=[^ ]+", "");
//
// // 清理多余的空格
// createTableSQL = createTableSQL.trim();
return createTableSQL;
}
}
/**
* 导出所有触发器
*/
private void exportTriggers(Connection conn, FileWriter writer) throws SQLException, IOException {
writer.write("\n-- ----------------------------\n");
writer.write("-- 触发器\n");
writer.write("-- ----------------------------\n\n");
List<String> triggers = getAllTriggers(conn);
for (String trigger : triggers) {
String ddl = getTriggerDDL(conn,trigger);
writer.write(ddl + ";\n\n");
}
}
private void exportTableData(Connection conn, String tableName, FileWriter writer) throws SQLException, IOException {
String query = "SELECT * FROM " + tableName;
@@ -141,4 +158,29 @@ public class MySQLExporterUtil {
return "";
}
}
/**
* 获取触发器的DDL语句
*/
private String getTriggerDDL(Connection conn,String triggerName) throws SQLException {
try (Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SHOW CREATE TRIGGER `" + triggerName + "`")) {
if (rs.next()) {
return rs.getString(3); // 创建语句在第3列
}
}
return "";
}
/**
* 获取所有触发器
*/
private List<String> getAllTriggers(Connection conn) throws SQLException {
List<String> triggers = new ArrayList<>();
try (Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SHOW TRIGGERS FROM " + databaseName)) {
while (rs.next()) {
triggers.add(rs.getString("Trigger"));
}
}
return triggers;
}
}

View File

@@ -4,6 +4,7 @@ import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import pc.exam.pp.framework.mybatis.core.mapper.BaseMapperX;
import pc.exam.pp.module.exam.dal.dataobject.ExamPsKeyword;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsReturnVo;
import pc.exam.pp.module.judgement.controller.admin.getpoints.vo.PsVo;
import java.util.List;
@@ -15,6 +16,10 @@ public interface PsMapper extends BaseMapperX<ExamPsKeyword> {
void deleteByQuId(String quId);
List<PsVo> selectPsPointByType(@Param("quId") String quId
,@Param("type") String type);
List<ExamPsKeyword> selectPsPointByType(@Param("quId") String quId
, @Param("type") String type);
void insertPsKeywordList(List<ExamPsKeyword> resultList);
}

View File

@@ -7,21 +7,46 @@
<id property="id" column="id" jdbcType="VARCHAR"/>
<result property="quId" column="qu_id" jdbcType="VARCHAR"/>
<result property="parentId" column="parent_id" jdbcType="VARCHAR"/>
<result property="keyName" column="key_name" jdbcType="VARCHAR"/>
<result property="keyValue" column="key_value" jdbcType="VARCHAR"/>
<result property="key" column="key_name" jdbcType="VARCHAR"/>
<result property="value" column="key_value" jdbcType="VARCHAR"/>
<result property="rate" column="rate" jdbcType="VARCHAR"/>
<result property="type" column="type" jdbcType="VARCHAR"/>
<result property="sort" column="sort" jdbcType="VARCHAR"/>
</resultMap>
<insert id="insertPsKeywordList" parameterType="java.util.List">
INSERT INTO exam_ps_keyword (
id,
qu_id,
parent_id,
key_name,
key_value,
rate,
type,
sort
) VALUES
<foreach collection="list" item="item" separator=",">
(
#{item.id},
#{item.quId},
#{item.parentId},
#{item.key},
#{item.value},
#{item.rate},
#{item.type},
#{item.sort}
)
</foreach>
</insert>
<delete id="deleteByQuId">
delete from exam_ps_keyword where qu_id =#{quId}
</delete>
<select id="selectPsPointByType" resultMap="ExamPsKeywordResult">
select id,qu_id,parent_id,key_name,key_value,rate,type from exam_ps_keyword where qu_id=#{quId}
select id,qu_id,parent_id,key_name,key_value,rate,type,sort from exam_ps_keyword where qu_id=#{quId}
and type=#{type}
order by sort asc
</select>