라벨할당 임시 커밋

This commit is contained in:
2026-01-02 17:58:25 +09:00
parent 23494e13a3
commit d72e9de61e
7 changed files with 313 additions and 141 deletions

View File

@@ -1,12 +1,12 @@
package com.kamco.cd.kamcoback.label.service;
import com.kamco.cd.kamcoback.label.dto.LabelAllocateDto.Sheet;
import com.kamco.cd.kamcoback.label.dto.LabelAllocateDto;
import com.kamco.cd.kamcoback.label.dto.LabelAllocateDto.TargetInspector;
import com.kamco.cd.kamcoback.label.dto.LabelAllocateDto.TargetUser;
import com.kamco.cd.kamcoback.postgres.core.LabelAllocateCoreService;
import jakarta.transaction.Transactional;
import java.util.Comparator;
import java.util.Iterator;
import java.util.List;
import java.util.Objects;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
@@ -20,91 +20,30 @@ public class LabelAllocateService {
this.labelAllocateCoreService = labelAllocateCoreService;
}
/**
* 도엽 count 수와 할당된 count 수를 비교해서 많은 수부터 먼저 배정하고 나머지를 분배 배정하는 로직
*
* @param sheets
* @param targetUsers
*/
public static void allocateSheetCount(List<Sheet> sheets, List<TargetUser> targetUsers) {
// 1⃣ 실제 도엽 기준 할당
allocateSheets(sheets, targetUsers);
// 2⃣ 전체 부족분 비율 계산
distributeShortage(targetUsers); // 항상 마지막에 한 번만 호출해야함
}
public static void allocateSheets(List<Sheet> sheets, List<TargetUser> targets) {
// 도엽 큰 것부터 (선택 사항)
sheets.sort(Comparator.comparingInt(Sheet::getCount).reversed());
for (TargetUser target : targets) {
Iterator<Sheet> it = sheets.iterator();
while (it.hasNext() && target.getRemainDemand() > 0) {
Sheet sheet = it.next();
int assignable = Math.min(sheet.getCount(), target.getRemainDemand());
if (assignable > 0) {
target.assign(sheet.getSheetId(), assignable);
sheet.decrease(assignable);
}
if (sheet.getCount() == 0) {
it.remove();
}
}
}
}
public static void distributeShortage(List<TargetUser> targets) {
int totalDemand = targets.stream().mapToInt(TargetUser::getDemand).sum();
int totalAllocated = targets.stream().mapToInt(t -> t.getAllocated()).sum();
int shortage = totalDemand - totalAllocated;
if (shortage <= 0) {
return;
}
int distributed = 0;
for (int i = 0; i < targets.size(); i++) {
TargetUser t = targets.get(i);
// 마지막 타겟이 나머지 가져가게 (반올림 오차 방지)
int share;
if (i == targets.size() - 1) {
share = shortage - distributed;
} else {
double ratio = (double) t.getDemand() / totalDemand;
share = (int) Math.round(shortage * ratio);
distributed += share;
}
t.setShortage(share);
}
}
/**
* 도엽 기준 asc sorting 해서 할당 수만큼 배정하는 로직
*
* @param targetUsers
*/
@Transactional
public void allocateAsc(List<TargetUser> targetUsers) {
public void allocateAsc(List<TargetUser> targetUsers, List<TargetInspector> targetInspectors) {
Long lastId = null;
//geom 잔여건수 != 프론트에서 넘어 온 총 건수 -> return
Long chargeCnt = labelAllocateCoreService.findLabelUnAssignedCnt(3L); //TODO
Long totalDemand = targetUsers.stream().mapToLong(TargetUser::getDemand).sum();
if (!Objects.equals(chargeCnt, totalDemand)) {
log.info("chargeCnt != totalDemand");
return;
}
//라벨러에게 건수만큼 할당
for (TargetUser target : targetUsers) {
int remaining = target.getDemand();
while (remaining > 0) {
int batchSize = Math.min(remaining, 500);
int batchSize = Math.min(remaining, 100);
List<Long> ids = labelAllocateCoreService.fetchNextIds(lastId, batchSize);
if (ids.isEmpty()) {
@@ -112,11 +51,29 @@ public class LabelAllocateService {
}
labelAllocateCoreService.assignOwner(
ids, Long.valueOf(target.getUserId())); // TODO : userId를 숫자값을 가져올지 사번을 가져올지 고민
ids, target.getUserId());
remaining -= ids.size();
lastId = ids.get(ids.size() - 1);
}
}
//검수자에게 userCount명 만큼 할당
List<LabelAllocateDto.Basic> list = labelAllocateCoreService.findAssignedLabelerList(3L);
int reviewerIndex = 0;
int count = 0;
log.info("list : " + list.size());
for (LabelAllocateDto.Basic labeler : list) {
TargetInspector inspector = targetInspectors.get(reviewerIndex);
labelAllocateCoreService.assignInspector(labeler.getAssignmentUid(), inspector.getInspectorUid());
count++;
if (count == inspector.getUserCount()) {
reviewerIndex++;
count = 0;
}
}
}
}