본문으로 건너뛰기
주문 수명 주기환불

환불

Tokenz Refunds API로 완료된 결제를 환불하는 방법을 알아봅니다.

Refunds API로 완료된 주문의 금액을 고객에게 반환할 수 있습니다. 환불을 시작하고 상태를 추적하며 수명 주기를 관리할 수 있습니다.

금액 형식: 모든 금액 값(amount 필드 등)은 각 통화의 최소 단위로 표시합니다. 통화별 정확한 형식은 지원 통화를 참고하세요.

개요

환불 시스템은 다음 관리 기능을 제공합니다.

  • 환불 생성: 사유를 지정하여 완료된 주문의 환불을 시작합니다.
  • 상태 추적: 대기 또는 실패 상태를 통해 환불 진행 상황을 확인합니다.
  • 감사 추적: 누가 언제 환불을 시작했는지 추적합니다.
  • 테스트 모드: 개발과 테스트를 위한 테스트 환경을 지원합니다.

환불 수명 주기

환불은 다음 절차를 거칩니다.

  1. 환불 시작: 판매자 또는 API가 완료된 주문의 환불을 시작합니다.
  2. 처리: 비동기로 처리되며 상태는 pending으로 유지됩니다.
  3. 실패: 문제가 있으면 환불이 실패할 수 있으며 상태가 failed로 변경됩니다.

환불 상태 값

환불은 다음 상태를 가집니다.

  • pending: 환불이 시작되어 처리 중입니다.
  • failed: 환불 시도가 실패했습니다.
다이어그램
다이어그램
100%
스크롤하여 탐색 · 확대하여 자세히 보기

환불 생성

주문 ID와 환불 사유를 포함하여 환불 엔드포인트로 POST 요청을 전송하세요.

bash
curl --request POST \
  --url https://api.tokenz.one/v2/refunds \
  --header 'Content-Type: application/json' \
  --header 'Authorization: Bearer secret_test_YOUR_KEY_HERE' \
  --data '{
    "orderId": "order_1p4LPTRKB5Z",
    "reason": "customer_cancellation",
    "detail": "Customer requested cancellation"
  }'

필수 매개변수

  • orderId: 환불할 주문 ID(완료된 주문이어야 함)
  • reason: 환불 사유. 유효한 값:
    • customer_cancellation: 고객이 주문을 취소함
    • duplicate_payment: 중복 결제
    • other: 기타 사유(detail 필요)
  • detail: 상세 설명(선택 사항이지만 reason이 other이면 필수)

응답

환불 생성이 성공하면 환불 객체를 반환합니다.

json
{
  "refund": {
    "id": "refund_1p4LS47fB1h",
    "object": "refund",
    "orderId": "order_1p4LPTRKB5Z",
    "amount": {
      "amount": 10000,
      "currency": "JPY"
    },
    "consumerAmount": {
      "amount": 10000,
      "currency": "JPY"
    },
    "status": "pending",
    "reason": "customer_cancellation",
    "initiatedBy": "apikey",
    "test": false,
    "createdAt": "2024-10-07T10:30:00Z",
    "updatedAt": "2024-10-07T10:30:00Z"
  }
}

환불 조회

특정 환불의 현재 상태와 상세 정보를 조회합니다.

bash
curl --request GET \
  --url https://api.tokenz.one/v2/refunds/refund_1p4LS47fB1h \
  --header 'Authorization: Bearer secret_test_YOUR_KEY_HERE'

응답 필드

  • id: 환불의 고유 식별자
  • orderId: 환불된 주문의 ID
  • amount: 통화의 최소 단위로 표시한 환불 금액
  • consumerAmount: 소비자 통화 기준 환불 금액(선택)
  • status: 현재 환불 상태(pending, failed)
  • reason: 환불 요청 사유
  • initiatedBy: 환불 시작 주체(merchantUser, apikey, admin)
  • test: 테스트 환불인지 여부
  • createdAt: 환불 생성 시각
  • updatedAt: 마지막 상태 업데이트 시각

환불 목록 조회

필터를 선택하여 전체 환불을 조회합니다.

bash
curl --request GET \
  --url 'https://api.tokenz.one/v2/refunds?orderId=order_1p4LPTRKB5Z&limit=10' \
  --header 'Authorization: Bearer secret_test_YOUR_KEY_HERE'

쿼리 매개변수

  • orderId: 주문 ID로 필터
  • status: 환불 상태로 필터(pending, failed)
  • limit: 최대 반환 수(1~100, 기본: 10)
  • createdAfter: 지정 시각 이후 생성된 환불(ISO 8601)
  • createdBefore: 지정 시각 이전 생성된 환불(ISO 8601)

응답

json
{
  "refunds": {
    "items": [
      {
        "id": "refund_1p4LS47fB1h",
        "object": "refund",
        "orderId": "order_1p4LPTRKB5Z",
        "amount": {
          "amount": 10000,
          "currency": "JPY"
        },
        "consumerAmount": {
          "amount": 10000,
          "currency": "JPY"
        },
        "status": "pending",
        "reason": "customer_cancellation",
        "initiatedBy": "apikey",
        "test": false,
        "createdAt": "2024-10-07T10:30:00Z",
        "updatedAt": "2024-10-07T10:30:00Z"
      }
    ],
    "hasMore": false
  }
}

환불 웹훅

환불 이벤트 알림을 받도록 웹훅을 설정하세요.

refund.created

환불이 생성되면 발생합니다.

json
{
  "id": "d4e5f6a7-b8c9-0123-defa-234567890123",
  "object": "refund.created",
  "createdAt": "2024-10-07T10:30:00Z",
  "test": false,
  "eventData": {
    "type": "refund",
    "version": "v2",
    "data": {
      "refund": {
        "id": "refund_1p4LS47fB1h",
        "object": "refund",
        "orderId": "order_1p4LPTRKB5Z",
        "amount": {
          "amount": 10000,
          "currency": "JPY"
        },
        "consumerAmount": {
          "amount": 10000,
          "currency": "JPY"
        },
        "status": "pending",
        "reason": "customer_cancellation",
        "initiatedBy": "apikey",
        "test": false,
        "createdAt": "2024-10-07T10:30:00Z",
        "updatedAt": "2024-10-07T10:30:00Z"
      }
    }
  }
}

refund.failed

환불이 실패하면 발생합니다.

json
{
  "id": "e5f6a7b8-c9d0-1234-efab-345678901234",
  "object": "refund.failed",
  "createdAt": "2024-10-07T10:40:00Z",
  "test": false,
  "eventData": {
    "type": "refund",
    "version": "v2",
    "data": {
      "refund": {
        "id": "refund_1p4LS47fB1h",
        "object": "refund",
        "orderId": "order_1p4LPTRKB5Z",
        "amount": {
          "amount": 10000,
          "currency": "JPY"
        },
        "consumerAmount": {
          "amount": 10000,
          "currency": "JPY"
        },
        "status": "failed",
        "reason": "customer_cancellation",
        "initiatedBy": "apikey",
        "test": false,
        "createdAt": "2024-10-07T10:30:00Z",
        "updatedAt": "2024-10-07T10:40:00Z"
      }
    }
  }
}

오류 처리

Refunds API는 표준 HTTP 상태 코드와 상세 오류 메시지를 반환합니다.

일반적인 오류

  • 400 Bad Request: 요청 매개변수 또는 형식이 잘못되었습니다.
  • 401 Unauthorized: API 키가 없거나 유효하지 않습니다.
  • 403 Forbidden: 환불에 필요한 권한이 없습니다.
  • 404 Not Found: 주문 또는 환불을 찾을 수 없습니다.
  • 422 Unprocessable Entity: 비즈니스 로직 오류가 발생했습니다.

오류 응답 형식

json
{
  "status": 422,
  "code": "refund.amount-exceeds-available",
  "message": "Refund amount exceeds available refund amount for this order"
}

환불 테스트

테스트 모드로 환불 연동을 개발하고 테스트하세요.

  1. 테스트 API 키(secret_test_ 접두사)를 사용하세요.
  2. 테스트 Checkout Session으로 테스트 주문을 생성하세요.
  3. 테스트 환불 ID에는 _t 접미사가 있습니다(예: refund_1p4LS47fB1h_t).
  4. 테스트 웹훅은 설정된 테스트 엔드포인트로 전송됩니다.

API 레퍼런스

엔드포인트

  • POST /v2/refunds - 새 환불 생성
  • GET /v2/refunds/{refundId} - 특정 환불 조회
  • GET /v2/refunds - 선택적 필터로 환불 목록 조회

인증

모든 엔드포인트는 Bearer 토큰 인증이 필요합니다.

코드
Authorization: Bearer secret_test_YOUR_KEY_HERE