결제 연동에서 사고가 나는 방식은 대부분 하나입니다. 브라우저가 보낸 금액을 서버가 그대로 믿는 것. 브라우저에서 오는 값은 사용자가 얼마든지 바꿀 수 있기 때문에, 10만 원짜리 상품을 100원에 결제하는 일이 실제로 가능합니다.

서버에서 다시 확인한다는 게 무슨 뜻인가요?

사용자가 "이 상품을 사겠다"고 보내면, 서버가 그 상품의 가격을 데이터베이스에서 직접 꺼내 결제 금액으로 쓴다는 뜻입니다. 브라우저가 보낸 금액은 화면 표시용으로만 쓰고, 실제 청구 금액은 절대 브라우저에서 받지 않습니다. 결제가 끝난 뒤에도 결제사에 다시 물어서 실제로 얼마가 결제됐는지 확인해야 합니다.

그 외에 반드시 확인할 것들

  • 검증된 결제 대행사를 쓰고 있는가 — 카드 번호를 직접 저장하지 마세요.
  • 테스트 모드로 결제부터 환불까지 전체 흐름을 통과해 봤는가.
  • 결제사가 보내는 자동 알림(웹훅)이 진짜 결제사에서 온 것인지 검증하는가.
  • 같은 알림이 두 번 와도 상품이 두 번 나가지 않는가.
  • 환불 정책과 처리 절차가 문서로 준비되어 있는가.
  • 사업자 등록과 통신판매업 신고를 마쳤는가.

왜 결제만큼은 직접 만들지 말라고 하나요?

다른 기능은 잘못돼도 고치면 되지만 결제는 잘못되면 그 순간 돈이 나가거나 들어오지 않기 때문입니다. 그리고 사고가 났을 때 피해자가 고객이라 신뢰까지 함께 잃습니다. 사고 한 번의 비용이 개발비보다 큰 유일한 영역입니다.

브라우저에서 오는 값은 전부 의심하세요. 금액, 수량, 할인율, 사용자 등급 어느 것도 그대로 믿으면 안 됩니다.