같은 기간인데 손잡이 세 개로 매출이 에서 까지 움직입니다 (). 그래서 숫자를 주고받을 때는 정의를 같이 주고받아야 합니다. 회사의 기본은 환불 뺀 · 테스트 뺀 · 부가세 별도 입니다.
같은 기간, 어디서 얼마나 팔렸나
| 채널 | 매출 | 주문 | 객단가 | 비중 |
|---|---|---|---|---|
| 손입력 | ||||
| 합계 | 100.0% |
오프라인 팝업만 담당자가 매주 월요일에 스프레드시트로 넣습니다. 손으로 넣는 칸은 손으로 넣는다고 화면에 적어 둡니다. 안 그러면 월요일 오전마다 "매출이 왜 떨어졌냐" 는 질문을 받습니다.
쓴 돈과 남은 사람
광고비 로 를 벌었습니다. 이 숫자는 플랫폼이 알려 준 값이라 서로 겹칩니다 — 메타와 구글이 같은 주문을 각자 자기 성과로 셉니다. 합이 실제 매출을 넘는 날도 있습니다.
이탈률은 해지 버튼을 누른 사람만 셉니다. 결제 실패로 조용히 빠진 사람은 따로 셉니다 — 둘을 합치면 무엇을 고쳐야 할지 알 수 없습니다.
숫자가 저절로 최신이 되게 만드는 쪽 — 이 일의 대부분입니다
원천 · 6
적재 · 변환
지표 · 화면
실패는 지우지 않고 남깁니다
새벽에 깨지 않으려고
이 숫자가 무엇을 세는지 한 문장으로 적어 둡니다
결제가 확정된 주문의 상품 금액 합계. 환불·취소를 뺀 뒤, 부가세는 빼고 셉니다.
세는 것
안 세는 것
실제로 도는 쿼리
-- mart_daily.revenue · 매일 05:30 + 10분마다 증분SELECT o.ordered_on AS d, o.channel, SUM(i.paid_amount - i.refunded_amount) AS revenue FROM stg_order_items i JOIN stg_orders o ON o.order_id = i.order_id WHERE o.status IN ('PAID','PREP','SHIPPING','DONE') AND o.is_test = false -- 테스트 계정 12개 AND o.customer_id NOT IN (SELECT id FROM internal_accounts) AND i.kind = 'GOODS' -- 배송비 · 부가세 제외 GROUP BY 1, 2;
같은 기간에 결제가 확정된 주문서의 개수. 한 주문서에 상품이 몇 개든 1건입니다.
세는 것
안 세는 것
실제로 도는 쿼리
SELECT o.ordered_on AS d, o.channel, COUNT(DISTINCT o.order_id) AS orders FROM stg_orders o WHERE o.status IN ('PAID','PREP','SHIPPING','DONE') AND o.is_test = false GROUP BY 1, 2;
매출 ÷ 주문 수. 두 숫자를 각각 정의한 다음, 나눈 것뿐입니다.
세는 것
안 세는 것
실제로 도는 쿼리
-- 저장하지 않고 화면에서 나눕니다. 저장하면 반올림이 쌓입니다.SELECT d, channel, revenue, orders, CASE WHEN orders = 0 THEN NULL ELSE ROUND(revenue::numeric / orders) END AS aov FROM mart_daily;
오늘 기준으로 다음 배송 예정일이 잡혀 있는 사람. 결제 성공 여부와 무관하게, 구독을 유지하고 있는 상태입니다.
세는 것
안 세는 것
실제로 도는 쿼리
-- 매일 06:00 스냅숏. 과거를 다시 계산하지 않고 그날 값을 그대로 남깁니다.SELECT CURRENT_DATE AS d, COUNT(*) FILTER (WHERE s.state = 'ACTIVE') AS active, COUNT(*) FILTER (WHERE s.state = 'PAUSED') AS paused, COUNT(*) FILTER (WHERE s.state = 'DUNNING') AS dunning FROM subscriptions s WHERE s.state IN ('ACTIVE','PAUSED','DUNNING') AND (s.paused_at IS NULL OR s.paused_at > CURRENT_DATE - INTERVAL '8 weeks');
이번 달에 스스로 해지 버튼을 누른 사람 ÷ 달 시작 시점의 활성 구독자.
세는 것
안 세는 것
실제로 도는 쿼리
WITH base AS ( SELECT active FROM mart_subs_daily WHERE d = DATE_TRUNC('month', CURRENT_DATE)), quit AS ( SELECT COUNT(*) AS n FROM subscription_events WHERE kind = 'CANCEL_BY_USER' -- 결제 실패는 여기 안 들어옵니다 AND at BETWEEN DATE_TRUNC('month', CURRENT_DATE) AND CURRENT_DATE)SELECT ROUND(quit.n::numeric / NULLIF(base.active, 0) * 100, 2) AS churn_pct FROM base, quit;
2026년 8월 마감 · 대시보드와 밖의 숫자를 한 줄씩 맞춰 봅니다
남는 차이 0원순서를 정해 두면 누가 해도 같은 결과가 나옵니다
| # | 무엇을 | 어디서 | 확인하는 것 |
|---|---|---|---|
| 1 | 기간을 못박는다 | 대시보드 | 결제일 기준 8/1 00:00 ~ 8/31 23:59. 배송일이 아니라 결제일입니다. |
| 2 | 정의를 못박는다 | 지표 정의 | 손잡이 세 개를 기본값으로 되돌립니다. 남이 켜 둔 채로 비교하면 그날 하루를 날립니다. |
| 3 | 부가세·배송비를 더한다 | 대시보드 | PG 는 실제로 긁힌 총액을 봅니다. 우리는 상품 금액만 봅니다. |
| 4 | 정산 주기를 옮긴다 | 정산서 | 말일 이틀치는 다음 달 입금입니다. 전월 말일치가 이번 달에 들어옵니다. |
| 5 | 수수료를 뺀다 | 정산서 | 카드사·간편결제마다 요율이 다릅니다. 평균이 아니라 정산서의 실제 합계를 씁니다. |
| 6 | 남는 차이를 적는다 | 문서 | 0원이 아니면 원인을 찾을 때까지 마감하지 않습니다. 원인은 다음 달 목록에 넣습니다. |
울려야 할 때만 울리게 만드는 일
→
90일간
울리고 나서 무엇을 했는지까지 남깁니다
세 가지에 답이 없으면 만들지 않습니다
화면보다 먼저 정한 것들
보기 좋은 화면은 하루면 만듭니다. 어려운 쪽은 그 화면이 내일 아침에도 맞는 숫자를 들고 있게 만드는 것입니다. 원천이 여섯이고 그중 하나는 사람입니다. 그래서 수집·정제·집계·캐시를 먼저 세우고 화면은 마지막에 붙였습니다.
회의에서 숫자가 안 맞는 이유는 대개 계산이 틀려서가 아니라 서로 다른 것을 세고 있어서입니다.
지표마다 한 문장 정의와 세는 것 / 안 세는 것 목록, 실제 쿼리, 주인을 붙여 두었습니다.
화면의 숫자를 누르면 바로 그 정의로 갑니다.
수집이 실패한 날을 0으로 채우면 그래프가 떨어집니다. 그러면 사람들은 없는 원인을 찾기 시작하고, 그날 오전이 통째로 날아갑니다. 그래서 그날은 막대를 그리지 않고 빗금으로 비워 두고, 위에 왜 비었는지와 다시 받는 단추를 답니다.
오프라인 팝업 매출만 담당자가 월요일에 시트로 넣습니다. 자동으로 들어오는 숫자와 나란히 두면 똑같아 보이지만 성격이 다릅니다. 사람도 파이프라인의 한 단계로 취급하고, 늦으면 담당자에게 먼저 알립니다.
대시보드 매출과 통장 입금액은 달라야 정상입니다. 부가세·배송비·수수료·정산 주기 때문입니다. 중요한 건 왜 다른지 한 줄씩 댈 수 있느냐입니다. 한 번 표로 만들어 두면 그다음부터 30분이면 끝납니다.
화면을 열 때마다 412만 행을 세지 않습니다. 5분마다 미리 세어 둡니다. 대신 모든 숫자 옆에 언제 센 값인지를 붙입니다 — "지금 이 숫자는 3분 전 값입니다" 를 알면 사람들은 기다릴 줄 압니다. 모르면 새로고침을 스무 번 누릅니다.
PG 정산은 D+2 에 확정됩니다. 최근 이틀 숫자는 나중에 바뀝니다.
이걸 안 적어 두면 "어제 봤을 때랑 다른데요" 가 매주 나옵니다.
많이 우는 경보는 사람을 지치게 하고, 지친 사람은 알림을 끄는 게 아니라 읽지 않게 됩니다. 경보를 만들기 전에 세 가지를 묻습니다 — 울리면 누가 무엇을 하는가, 새벽에 깨워도 되는가, 지난 90일에 몇 번 울렸을 규칙인가.
엑셀로 내보낸 파일은 반년 뒤에도 메일함을 돌아다닙니다. 그래서 내보낸 파일의 첫 줄에 기간 · 정의 · 채널 · 집계 시각을 같이 적습니다. 숫자만 있는 파일은 반드시 오해를 만듭니다.
서버도 데이터베이스도 없습니다. 숫자는 날짜로 만든 값이고, 새로고침하면 처음으로 돌아갑니다. 실제 프로젝트에서는 이 자리에 수집 작업 스케줄러, 창고, 집계 배치, 캐시, 그리고 매달 마감 다음 날 이 화면을 열어 보는 사람이 있습니다.