DPI 1-4문항 레이어명 불일치시 "확인필요"로 처리

This commit is contained in:
2026-02-19 16:35:49 +09:00
parent a03dabcdf6
commit aadc68d2a7
32 changed files with 71 additions and 14 deletions

View File

@@ -14,20 +14,20 @@ const todayDate = getToday();
const examRound = '2622';
const codeTypes = [
'DIC',
// 'DIC',
'DPI',
];
const examTypes = [
'A',
'B',
'C',
// 'B',
// 'C',
// 'D'
];
// testMode가 true일 경우 TEST 폴더에 있는 답안 파일을 읽어옴
const testMode = false;
// const testMode = true;
// const testMode = false;
const testMode = true;
const outputExcelFiles = [];
codeTypes.forEach(codeType => {
@@ -36,9 +36,15 @@ codeTypes.forEach(codeType => {
if (!fs.existsSync(jsonPath)) return
const scoringJson = require(jsonPath);
const answerFilesDir = `./output/${examRound}/${type}/${testMode ? 'TEST' : codeType}`;
let outputExcelFile = `./score_result/${todayDate}_${codeType}_${examRound}${type}_채점결과.xlsx`;
let outputExcelFile =
`./score_result/${examRound}/${todayDate}_${codeType}_${examRound}${type}_채점결과.xlsx`;
// 폴더 경로 추출
const dirPath = path.dirname(outputExcelFile);
// 폴더가 없으면 생성
fs.mkdirSync(dirPath, { recursive: true });
if (testMode) {
outputExcelFile = `./00_${codeType}_${examRound}${type}_TEST.xlsx`;
outputExcelFile = `./score_result/test/00_${codeType}_${examRound}${type}_TEST.xlsx`;
}
// 답안 폴더 내부에 디렉토리가 아닌 일반 파일이 있을 경우 디렉토리만 필터링 해서 불러옴
@@ -91,17 +97,59 @@ codeTypes.forEach(codeType => {
console.error(`Error reading PSD file: ${psdPath}`, error);
}
});
// 기존 XML 파일 채점 방식 주석 처리 (20260213)
gpdpFiles.forEach((gpdpFile, index) => {
const gpdpPath = path.join('./', studentDir, gpdpFile);
console.log(`Reading ${gpdpPath}...`);
const xmlString = fs.readFileSync(gpdpPath, 'utf8');
// XML 문자열을 파싱하여 XML 문서 객체로 변환
const xmlDocument = new DOMParser().parseFromString(xmlString, 'application/xml');
// console.log('xmlDocument:', xmlDocument);
scoringResult[index + 1] = getGpdpScore(xmlDocument, scoringJson, index + 4);
if (!xmlString.trim().startsWith("<")) {
console.warn(`XML 형태 아님 → 스킵: ${gpdpFile}`);
return;
}
// 260219 - 파일명에서 번호 추출하여 점수 계산에 활용
// 파일명에서 번호 추출 (dpi_01_, dpi_02_ )
const fileNumberMatch = gpdpFile.match(/dpi_(\d+)_/);
const fileNumber = fileNumberMatch ? parseInt(fileNumberMatch[1], 10) : index + 1;
// 추출한 번호를 사용하여 scoringResult에 저장
scoringResult[fileNumber] = getGpdpScore(xmlDocument, scoringJson, fileNumber + 3);
});
// gpdpFiles.forEach((gpdpFile, index) => {
// const gpdpPath = path.join("./", studentDir, gpdpFile);
// console.log(`Reading ${gpdpPath}...`);
// let xmlString;
// try {
// xmlString = fs.readFileSync(gpdpPath, "utf8");
// } catch (err) {
// console.warn(`파일 읽기 실패, 스킵: ${gpdpPath}`);
// return;
// }
// const xmlDocument = new DOMParser().parseFromString(
// xmlString,
// "application/xml"
// );
// // ✅ XML 파싱 실패 여부 확인
// const parseError = xmlDocument.getElementsByTagName("parsererror");
// if (parseError.length > 0) {
// console.warn(`XML 아님 → 스킵: ${gpdpFile}`);
// return; // 그냥 패스
// }
// // 정상 XML만 점수 계산
// scoringResult[index + 1] = getGpdpScore(
// xmlDocument,
// scoringJson,
// index + 4
// );
// });
if (gmepFile.length === 0) {
// 곰믹스 채점 항목 갯수
const gmepItemCount = Object.keys(scoringJson[2]).length;
@@ -139,6 +187,10 @@ codeTypes.forEach(codeType => {
const workbook = XLSX.utils.book_new();
// 열 너비 계산
if (!Array.isArray(transposedData) || transposedData.length === 0) {
console.warn("transposedData 비어 있음 → 엑셀 컬럼 생성 스킵");
return; // 또는 continue / break (문맥에 따라)
}
const columnWidths = Object.keys(transposedData[0]).map(key => {
// 각 열의 최대 길이를 계산
const maxLength = Math.max(