refactor: worker_id → user_id 전체 마이그레이션 (Phase 1-4)
sso_users.user_id를 단일 식별자로 통합. JWT에서 worker_id 제거, department_id/is_production 추가. 백엔드 15개 모델, 11개 컨트롤러, 4개 서비스, 7개 라우트, 프론트엔드 32+ JS/11+ HTML 변환. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -246,7 +246,7 @@ async function loadWorkData(date) {
|
||||
// ========== 요약 카드 업데이트 ========== //
|
||||
function updateSummaryCards() {
|
||||
// 오늘 작업자 수
|
||||
const todayWorkersCount = new Set(workData.map(w => w.worker_id)).size;
|
||||
const todayWorkersCount = new Set(workData.map(w => w.user_id)).size;
|
||||
updateSummaryCard(elements.todayWorkers, todayWorkersCount, '명');
|
||||
|
||||
// 총 작업 시간
|
||||
@@ -326,7 +326,7 @@ function displayWorkStatus() {
|
||||
|
||||
// 작업자별 상황 분석
|
||||
const workerStatusList = allWorkers.map(worker => {
|
||||
const todayWork = workData.filter(w => w.worker_id === worker.worker_id);
|
||||
const todayWork = workData.filter(w => w.user_id === worker.user_id);
|
||||
const totalHours = todayWork.reduce((sum, w) => sum + parseFloat(w.work_hours || 0), 0);
|
||||
|
||||
// 휴가/연차 제외한 실제 작업시간 계산
|
||||
@@ -453,7 +453,7 @@ function displayWorkStatus() {
|
||||
else if (worker.status === 'partial') iconKey = 'partial';
|
||||
|
||||
return `
|
||||
<tr data-worker-id="${worker.worker_id}">
|
||||
<tr data-user-id="${worker.user_id}">
|
||||
<td data-label="작업자" class="worker-info">
|
||||
<div class="worker-avatar">
|
||||
<span>${worker.worker_name.charAt(0)}</span>
|
||||
@@ -492,7 +492,7 @@ function displayWorkStatus() {
|
||||
|
||||
<td data-label="액션" class="worker-actions">
|
||||
<div class="action-buttons">
|
||||
<button class="action-btn btn-edit" onclick="openWorkerModal(${worker.worker_id}, '${worker.worker_name}')" title="작업입력">
|
||||
<button class="action-btn btn-edit" onclick="openWorkerModal(${worker.user_id}, '${worker.worker_name}')" title="작업입력">
|
||||
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||||
<path d="M11 4H4a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-7"></path>
|
||||
<path d="M18.5 2.5a2.121 2.121 0 0 1 3 3L12 15l-4 1 1-4 9.5-9.5z"></path>
|
||||
@@ -500,7 +500,7 @@ function displayWorkStatus() {
|
||||
<span class="action-text">작업입력</span>
|
||||
</button>
|
||||
${worker.vacationType ? `
|
||||
<button class="action-btn btn-vacation" onclick="handleVacation(${worker.worker_id}, '${worker.vacationType}')" title="${worker.vacationType === 'full' ? '연차처리' : worker.vacationType === 'half' ? '반차처리' : '반반차처리'}">
|
||||
<button class="action-btn btn-vacation" onclick="handleVacation(${worker.user_id}, '${worker.vacationType}')" title="${worker.vacationType === 'full' ? '연차처리' : worker.vacationType === 'half' ? '반차처리' : '반반차처리'}">
|
||||
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||||
<rect x="3" y="4" width="18" height="18" rx="2" ry="2"></rect>
|
||||
<line x1="16" y1="2" x2="16" y2="6"></line>
|
||||
@@ -511,7 +511,7 @@ function displayWorkStatus() {
|
||||
</button>
|
||||
` : ''}
|
||||
${worker.status === 'overtime-warning' ? `
|
||||
<button class="action-btn btn-confirm" onclick="confirmOvertime(${worker.worker_id})" title="정상확인">
|
||||
<button class="action-btn btn-confirm" onclick="confirmOvertime(${worker.user_id})" title="정상확인">
|
||||
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round">
|
||||
<polyline points="20 6 9 17 4 12"></polyline>
|
||||
</svg>
|
||||
@@ -563,16 +563,16 @@ function displayWorkersAsCards(workers) {
|
||||
elements.workersContainer.innerHTML = `
|
||||
<div class="workers-grid grid grid-cols-4">
|
||||
${workers.map(worker => {
|
||||
const todayWork = workData.filter(w => w.worker_id === worker.worker_id);
|
||||
const todayWork = workData.filter(w => w.user_id === worker.user_id);
|
||||
const totalHours = todayWork.reduce((sum, w) => sum + parseFloat(w.work_hours || 0), 0);
|
||||
|
||||
|
||||
// 휴가/연차 제외한 실제 작업시간 계산
|
||||
const actualWorkHours = todayWork
|
||||
.filter(w => w.project_id !== 13) // 연차/휴무 프로젝트 제외
|
||||
.reduce((sum, w) => sum + parseFloat(w.work_hours || 0), 0);
|
||||
|
||||
|
||||
const hasError = todayWork.some(w => w.work_status_id === 2);
|
||||
|
||||
|
||||
// 정규 작업과 에러 작업 건수 분리
|
||||
const regularWorkCount = todayWork.filter(w => w.project_id !== 13 && w.work_status_id !== 2).length;
|
||||
const errorWorkCount = todayWork.filter(w => w.project_id !== 13 && w.work_status_id === 2).length;
|
||||
@@ -631,7 +631,7 @@ function displayWorkersAsList(workers) {
|
||||
</thead>
|
||||
<tbody>
|
||||
${workers.map(worker => {
|
||||
const todayWork = workData.filter(w => w.worker_id === worker.worker_id);
|
||||
const todayWork = workData.filter(w => w.user_id === worker.user_id);
|
||||
const totalHours = todayWork.reduce((sum, w) => sum + parseFloat(w.work_hours || 0), 0);
|
||||
const hasError = todayWork.some(w => w.work_status_id === 2);
|
||||
|
||||
@@ -852,7 +852,7 @@ async function processVacation(workerId, vacationType, hours) {
|
||||
// 휴가용 작업 보고서 생성 (특별한 작업 유형으로)
|
||||
const vacationReport = {
|
||||
report_date: selectedDate,
|
||||
worker_id: workerId,
|
||||
user_id: workerId,
|
||||
project_id: 1, // 기본 프로젝트 (휴가용)
|
||||
work_type_id: 999, // 휴가 전용 작업 유형 (DB에 추가 필요)
|
||||
work_status_id: 1, // 정상 상태
|
||||
@@ -887,10 +887,10 @@ async function processOvertimeConfirmation(workerId) {
|
||||
|
||||
// 새로운 근태 관리 API 사용
|
||||
const overtimeData = {
|
||||
worker_id: workerId,
|
||||
user_id: workerId,
|
||||
date: selectedDate
|
||||
};
|
||||
|
||||
|
||||
const response = await window.apiCall('/attendance/overtime/approve', 'POST', overtimeData);
|
||||
|
||||
if (response.success) {
|
||||
@@ -1104,7 +1104,7 @@ async function loadModalData() {
|
||||
|
||||
async function loadModalExistingWork() {
|
||||
try {
|
||||
const response = await window.apiCall(`/daily-work-reports?date=${currentModalWorker.date}&worker_id=${currentModalWorker.id}`);
|
||||
const response = await window.apiCall(`/daily-work-reports?date=${currentModalWorker.date}&user_id=${currentModalWorker.id}`);
|
||||
modalExistingWork = Array.isArray(response) ? response : (response.data || []);
|
||||
} catch (error) {
|
||||
console.error('기존 작업 로드 오류:', error);
|
||||
@@ -1258,7 +1258,7 @@ async function saveModalNewWork() {
|
||||
|
||||
const workData = {
|
||||
report_date: currentModalWorker.date,
|
||||
worker_id: currentModalWorker.id,
|
||||
user_id: currentModalWorker.id,
|
||||
work_entries: [{
|
||||
project_id: parseInt(projectId),
|
||||
task_id: parseInt(workTypeId), // work_type_id를 task_id로 매핑
|
||||
@@ -1332,7 +1332,7 @@ async function handleModalVacation(vacationType) {
|
||||
try {
|
||||
// 새로운 근태 관리 API 사용
|
||||
const vacationData = {
|
||||
worker_id: currentModalWorker.id,
|
||||
user_id: currentModalWorker.id,
|
||||
date: currentModalWorker.date,
|
||||
vacation_type: vacation.code
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user