매일 손으로 하던 정산 확인을 자동으로 만들기로 했다. 만들고 나서도 여전히 손으로 확인하고 있었다. 무엇이 남았는지 보려고 하던 일을 그대로 적어 봤다.
Table of contents
Open Table of contents
한 줄이던 일이 일곱 단계였다
적어 보니 이랬다.
1. 어제 주문 목록을 뽑는다
2. 결제 내역과 맞춰 본다
3. 안 맞는 것을 찾는다
4. 안 맞는 것의 원인을 본다
5. 고칠 수 있으면 고친다
6. 못 고치면 담당자에게 알린다
7. 결과를 엑셀로 정리해서 보낸다
일곱 단계였다. 처음에는 이것을 정산 확인 자동화라는 한 줄로 생각했다.
한 줄로 부르면 전부 자동이 되는 것처럼 들린다. 일곱 단계로 적으니 이야기가 달라졌다.
사람이 남는 단계를 갈랐다
각 단계가 자동으로 되는지 갈라 봤다.
1. 목록 뽑기 자동 가능
2. 맞춰 보기 자동 가능
3. 안 맞는 것 찾기 자동 가능
4. 원인 보기 사람의 판단이 들어간다
5. 고치기 원인에 따라 다르다
6. 알리기 자동 가능
7. 정리해서 보내기 자동 가능
앞의 셋은 MySQL 에서 목록을 뽑고 결제 내역과 JOIN 으로 맞추면 됐다. 4번이 사람의 일이었고 5번은 원인에 따라 갈렸다.
이것을 처음에 밝혀 두는 것과 만든 뒤에 알게 되는 것은 달랐다. 밝혀 두면 남는 일이 실패가 아니라 설계가 된다.
끝난 것의 기준을 정했다
cron 배치가 돌고 나면 무엇이 끝난 것인지를 정했다.
배치가 끝났다 = 어제 주문 전부에 대해 다음 중 하나가 정해졌다
- 맞음
- 안 맞음 (사유 코드가 붙음)
- 확인 불가 (사유 코드가 붙음)
settle_check 의 모든 행이 MATCH 와 MISMATCH 와 UNKNOWN 중 하나가 되면 배치는 끝난 것이고 사람이 볼 것은 뒤의 둘이다.
SELECT check_state, COUNT(*) FROM settle_check WHERE check_date = ? GROUP BY check_state;
MATCH 1,842
MISMATCH 12
UNKNOWN 3
이 기준이 없으면 배치가 도는 것 자체를 끝난 것으로 여기게 된다. GROUP BY 로 상태별 건수를 세는 것만으로 그날의 상황이 보였다.
결과 — 사람이 보는 몫
처음에는 MISMATCH 가 하루 80건이었다. 하나씩 원인을 봤다.
결제 취소 후 재결제 51건 → 자동 판정 가능
부분 취소 18건 → 자동 판정 가능
쿠폰 중복 적용 7건 → 실제 문제
원인 불명 4건
앞의 둘은 규칙을 알고 나니 자동으로 판정할 수 있었다. hasRecancel() 이 참이고 finalAmount 가 결제액과 같으면 MATCH 로 본다.
if ($order->hasRecancel() && $order->finalAmount === $payment->amount) {
return 'MATCH';
}
MISMATCH 80건이 12건이 됐고 남은 것이 실제로 봐야 할 것이었다. 자동화는 한 번에 끝나는 것이 아니라 사람이 보는 몫을 줄여 가는 일이었다. 사유 코드를 붙여 둔 것이 그 작업의 재료가 됐다.
12건을 어떻게 알릴지도 정했다. 매일 아침 9시에 메일로 보내되 건수만 보내지 않고 목록을 첨부하고 0건이어도 보낸다.
2014-02-24 정산 확인
전체 1,857건
안 맞음 12건 (첨부)
확인 불가 3건 (첨부)
0건이어도 보내기로 한 것은 안 오는 것과 0건인 것을 구분하기 위해서였다. 배치가 죽어 있으면 메일이 안 온다. 메일이 안 오는 것은 눈에 안 띄므로 다음 날 배치가 settle_check 에 어제 것이 있는지 보게 했다.
// 다음 날 배치가 시작할 때 어제 것이 있는지 본다
$yesterday = $db->count("SELECT COUNT(*) FROM settle_check WHERE check_date = ?", $y);
if ($yesterday === 0) {
error_log('어제 정산 확인 기록이 없다. 배치가 안 돌았을 수 있다.');
}
만들고도 손으로 계속 확인한 것은 믿을 수 있는지 몰라서였다. 2주 동안 손으로 한 결과와 배치 결과를 비교해 차이가 0이면 손을 떼기로 했다. 2주 동안 세 번 달랐고 세 번 다 배치가 맞고 손이 틀렸다. 기준을 정해 두지 않았으면 계속 둘 다 했을 것이다.
정리
- 한 줄로 부르면 전부 자동인 것처럼 들린다
- 하던 일을 단계로 적으면 어디까지 자동인지 갈린다
- 판단이 들어가는 단계는 자동이 되지 않는다
- 사람이 남는 것을 먼저 밝히면 설계가 된다
cron배치가 무엇을 하면 끝난 것인지 기준을 정한다- 기준이 없으면
cron이 도는 것을 끝난 것으로 여긴다 GROUP BY로 세어 사유 코드가 붙은 것만 사람이 본다- 반복되는 사유부터 자동 처리로 옮긴다. 80건이 12건이 됐다
- 0건이어도 알린다. 안 오는 것과 0건이 구분된다
- 배치가 안 돌았을 때 다음 날 걸리게 한다
- 손으로 하던 것을 언제 그만둘지 기준을 정한다