ข้ามไปยังเนื้อหาหลัก

การสร้าง Refunds

Refunds ช่วยให้คุณคืนเงินให้กับลูกค้าสำหรับธุรกรรมที่ charge สำเร็จแล้ว คู่มือนี้ครอบคลุมวิธีการสร้าง refunds เต็มจำนวนผ่านทั้ง API และ Dashboard

ภาพรวม

Refunds เป็นสิ่งจำเป็นสำหรับการจัดการการคืนสินค้า การยกเลิก ข้อพิพาทของลูกค้า และสถานการณ์อื่นๆ ที่คุณต้องการกลับรายการการชำระเงิน เมื่อคุณสร้าง refund:

  • จำนวน charge เต็มจำนวนจะถูกคืนให้กับวิธีการชำระเงินของลูกค้า
  • เงินทุนมักจะถูกคืนภายใน 5-10 วันทำการ (แตกต่างกันตามผู้ออกบัตร)
  • สถานะ refund สามารถติดตามได้ตลอดกระบวนการ
  • ค่าธรรมเนียมธุรกรรมเดิมจะไม่ถูกคืนตามค่าเริ่มต้น
  • Charge จะยังคงอยู่ในประวัติธุรกรรมของคุณด้วยสถานะ refunded

คุณสมบัติหลัก

  • การประมวลผลทันที: Refunds ถูกประมวลผลทันทีผ่าน API
  • วิธีการชำระเงินหลายแบบ: รองรับ refunds บัตรและวิธีการชำระเงินทางเลือก
  • การติดตามสถานะ: การอัปเดตสถานะ refund แบบเรียลไทม์
  • การแจ้งเตือนอัตโนมัติ: การแจ้งเตือนลูกค้า (ถ้ามีการกำหนดค่า)
  • รองรับ Metadata: เพิ่ม metadata แบบกำหนดเองเพื่อติดตามเหตุผลของ refund
  • Webhook Events: รับการแจ้งเตือนเมื่อสถานะ refund เปลี่ยนแปลง

เมื่อใดควรใช้ Refunds

สถานการณ์ทั่วไปสำหรับการสร้าง refunds:

  • การคืนสินค้า: ลูกค้าคืนสินค้า
  • การยกเลิกบริการ: ลูกค้ายกเลิกบริการหรือการสมัครสมาชิก
  • Charges ซ้ำซ้อน: การ charge ซ้ำโดยไม่ตั้งใจ
  • ข้อพิพาทของลูกค้า: แก้ไขข้อร้องเรียนของลูกค้า
  • สินค้าที่มีข้อบกพร่อง: รายการที่ไม่ตรงตามมาตรฐานคุณภาพ
  • สินค้าหมด: ไม่สามารถดำเนินการตามคำสั่งซื้อได้
  • การปรับราคา: แก้ไขข้อผิดพลาดในการเรียกเก็บเงิน

การสร้าง Refunds ผ่าน API

Refund เต็มจำนวน

สร้าง refund เต็มจำนวนโดยไม่ระบุจำนวน:

const omise = require('omise')({
secretKey: 'skey_test_123456789',
});

// Create a full refund
async function createFullRefund() {
try {
const refund = await omise.charges.createRefund('chrg_test_123456789', {
metadata: {
reason: 'Customer requested refund',
order_id: 'ORD-12345',
refund_type: 'product_return'
}
});

console.log('Refund created:', refund.id);
console.log('Amount refunded:', refund.amount);
console.log('Status:', refund.status);
console.log('Created at:', new Date(refund.created * 1000));

return refund;
} catch (error) {
console.error('Refund failed:', error.message);
throw error;
}
}

createFullRefund();

API Response

การสร้าง refund ที่สำเร็จจะคืนค่า:

{
"object": "refund",
"id": "rfnd_test_5xyz789abc",
"location": "/charges/chrg_test_123456789/refunds/rfnd_test_5xyz789abc",
"amount": 100000,
"currency": "thb",
"charge": "chrg_test_123456789",
"transaction": "trxn_test_5xyz789abc",
"created": "2024-01-15T10:30:00Z",
"status": "pending",
"metadata": {
"reason": "Customer requested refund",
"order_id": "ORD-12345",
"refund_type": "product_return"
}
}

การสร้าง Refunds ผ่าน Dashboard

กระบวนการทีละขั้นตอน

  1. ไปที่ธุรกรรม

    • ล็อกอินเข้า Omise Dashboard
    • ไปที่ "Transactions" > "Charges"
  2. ค้นหา Charge

    • ใช้แถบค้นหาเพื่อค้นหา charge ID
    • หรือกรองตามวันที่ จำนวน หรือสถานะ
    • คลิกที่ charge เพื่อดูรายละเอียด
  3. เริ่ม Refund

    • คลิกปุ่ม "Refund"
    • จำนวน charge เต็มจำนวนจะถูกกรอกล่วงหน้า
    • คุณสามารถแก้ไขจำนวนสำหรับ refunds บางส่วน
  4. เพิ่มรายละเอียด Refund (ไม่บังคับ)

    • ป้อนเหตุผลสำหรับ refund
    • เพิ่มบันทึกภายใน
    • เลือกหมวดหมู่ refund (การคืนสินค้า การยกเลิก ฯลฯ)
  5. ยืนยัน Refund

    • ตรวจสอบรายละเอียด refund
    • คลิก "Confirm Refund"
    • Refund จะถูกประมวลผลทันที
  6. ติดตามสถานะ

    • ดูสถานะ refund บนหน้ารายละเอียด charge
    • ตรวจสอบส่วน "Refunds" สำหรับความพยายาม refund ทั้งหมด
    • ติดตาม webhook events สำหรับการอัปเดตสถานะ

วงจรชีวิตสถานะ Refund

เข้าใจสถานะ refund:

Pending

  • Refund ถูกสร้างและกำลังถูกประมวลผล
  • โดยทั่วไปใช้เวลาสองสามนาที
  • ลูกค้ายังไม่ได้รับเงิน

Successful

  • Refund เสร็จสมบูรณ์
  • เงินทุนถูกส่งไปยังผู้ให้บริการการชำระเงิน
  • ลูกค้าควรได้รับเงินภายใน 5-10 วันทำการ

Failed

  • Refund ไม่สามารถประมวลผลได้
  • เหตุผลทั่วไป: ยอดเงินไม่เพียงพอ บัตรไม่ถูกต้อง บัตรหมดอายุ
  • ติดต่อฝ่ายสนับสนุนหากปัญหายังคงอยู่

กรณีการใช้งานทั่วไป

1. ขั้นตอนการคืนสินค้า

async function handleProductReturn(orderId, chargeId) {
// อัปเดตสถานะคำสั่งซื้อ
await updateOrderStatus(orderId, 'return_requested');

// สร้าง refund
const refund = await omise.charges.createRefund(chargeId, {
metadata: {
reason: 'product_return',
order_id: orderId,
return_tracking: 'TRACK123456',
warehouse_received: 'pending'
}
});

// ส่งการแจ้งเตือนลูกค้า
await sendCustomerEmail({
template: 'refund_initiated',
orderId: orderId,
refundId: refund.id,
estimatedDays: '5-10 business days'
});

return refund;
}

2. การยกเลิกบริการ

def handle_subscription_cancellation(subscription_id, charge_id, prorate=True):
"""Handle subscription cancellation with optional proration"""

# คำนวณจำนวน refund ถ้ามีการคำนวณตามสัดส่วน
if prorate:
charge = omise.Charge.retrieve(charge_id)
days_used = calculate_days_used(subscription_id)
days_in_period = 30
refund_amount = int(charge.amount * (days_in_period - days_used) / days_in_period)
else:
refund_amount = None # Full refund

# สร้าง refund
refund = omise.Charge.retrieve(charge_id).refund(
amount=refund_amount,
metadata={
'reason': 'subscription_cancellation',
'subscription_id': subscription_id,
'prorated': prorate
}
)

# ยกเลิกการสมัครสมาชิก
cancel_subscription(subscription_id)

return refund

แนวปฏิบัติที่ดีที่สุด

1. เพิ่ม Metadata เสมอ

รวมบริบทสำหรับทุก refund:

const refund = await omise.charges.createRefund(chargeId, {
metadata: {
reason: 'customer_request',
category: 'product_return',
requested_by: 'customer_service_rep_42',
ticket_id: 'SUPPORT-12345',
timestamp: new Date().toISOString()
}
});

2. ใช้การจัดการข้อผิดพลาดที่เหมาะสม

def safe_refund(charge_id, reason):
"""สร้าง refund ด้วยการจัดการข้อผิดพลาดที่ครอบคลุม"""
try:
refund = omise.Charge.retrieve(charge_id).refund(
metadata={'reason': reason}
)
return {'success': True, 'refund_id': refund.id}

except omise.errors.InvalidRequestError as e:
return {'success': False, 'error': 'invalid_request', 'message': str(e)}

except omise.errors.AuthenticationError as e:
return {'success': False, 'error': 'authentication', 'message': str(e)}

except omise.errors.BaseError as e:
return {'success': False, 'error': 'api_error', 'message': str(e)}

except Exception as e:
return {'success': False, 'error': 'unknown', 'message': str(e)}

3. ติดตามสถานะ Refund

async function trackRefundStatus(chargeId, refundId) {
const charge = await omise.charges.retrieve(chargeId);
const refund = charge.refunds.data.find(r => r.id === refundId);

switch (refund.status) {
case 'pending':
console.log('Refund กำลังถูกประมวลผล');
break;
case 'successful':
console.log('Refund เสร็จสมบูรณ์เรียบร้อย');
await notifyCustomerRefundComplete(charge.customer);
break;
case 'failed':
console.log(`Refund ล้มเหลว: ${refund.failure_message}`);
await escalateToSupport(refundId);
break;
}

return refund;
}

การจัดการข้อผิดพลาด

ข้อผิดพลาดทั่วไป

Refund แล้ว

// Error: charge_already_refunded
try {
const refund = await omise.charges.createRefund(chargeId);
} catch (error) {
if (error.code === 'charge_already_refunded') {
console.log('Charge นี้ถูก refund แล้ว');
// ตรวจสอบ refunds ที่มีอยู่
const charge = await omise.charges.retrieve(chargeId);
console.log('Existing refunds:', charge.refunds.data);
}
}

ยอดเงินไม่เพียงพอ

try:
refund = omise.Charge.retrieve(charge_id).refund()
except omise.errors.InvalidRequestError as e:
if 'insufficient' in str(e).lower():
print("ยอดเงินไม่เพียงพอในการประมวลผล refund")
notify_finance_team(charge_id)

Webhook Integration

จัดการ refund webhook events:

app.post('/webhooks/omise', async (req, res) => {
const event = req.body;

if (event.key === 'refund.create') {
const refund = event.data;
console.log(`Refund created: ${refund.id}`);

await updateRefundStatus(refund.charge, refund.id, 'pending');

} else if (event.key === 'refund.success') {
const refund = event.data;
console.log(`Refund successful: ${refund.id}`);

await updateOrderStatus(refund.metadata.order_id, 'refunded');
await notifyCustomer(refund.charge, 'refund_complete');

} else if (event.key === 'refund.fail') {
const refund = event.data;
console.log(`Refund failed: ${refund.id}`);

await createSupportTicket({
type: 'refund_failed',
refundId: refund.id,
chargeId: refund.charge
});
}

res.sendStatus(200);
});

การทดสอบ Refunds

Test Mode

ใช้ test API keys เพื่อทดสอบ refund flows:

// ทดสอบการสร้าง refund
const testRefund = await omise.charges.createRefund('chrg_test_123', {
metadata: { test: true }
});

// ตรวจสอบรายละเอียด refund
console.assert(testRefund.status === 'pending');
console.assert(testRefund.amount === testCharge.amount);

FAQ

ฉันสามารถ refund charge ได้ทันทีหลังจากสร้างหรือไม่?

ได้ คุณสามารถ refund charge ได้ทันทีที่มีสถานะ successful อย่างไรก็ตาม ถ้า charge ยังอยู่ในสถานะ pending คุณควรรอให้เสร็จสมบูรณ์ก่อนที่จะเริ่ม refund

ใช้เวลานานแค่ไหนที่ลูกค้าจะได้รับ refunds?

เวลา refund ขึ้นอยู่กับวิธีการชำระเงินและผู้ออกบัตร:

  • บัตรเครดิต: โดยทั่วไป 5-10 วันทำการ
  • บัตรเดบิต: โดยทั่วไป 5-10 วันทำการ
  • วิธีการชำระเงินทางเลือก: แตกต่างกันตามวิธี

Refund ถูกประมวลผลทันทีในฝั่ง Omise แต่เครดิตจริงในบัญชีลูกค้าขึ้นอยู่กับธนาคารหรือผู้ออกบัตร

ค่าธรรมเนียม refund ถูกคืนหรือไม่?

ไม่ ค่าธรรมเนียมธุรกรรมเดิมที่ Omise เรียกเก็บจะไม่ถูก refund คุณจะยังคงถูกเรียกเก็บค่าธรรมเนียมธุรกรรมสำหรับ charge เดิม แม้ว่าคุณจะ refund นี่เป็นแนวปฏิบัติมาตรฐานในผู้ประมวลผลการชำระเงินทั้งหมด

ฉันสามารถ refund ไปยังบัตรอื่นได้หรือไม่?

ไม่ได้ refunds ต้องถูกคืนไปยังวิธีการชำระเงินเดิมที่ใช้สำหรับ charge นี่เป็นข้อกำหนดด้านความปลอดภัยและไม่สามารถหลีกเลี่ยงได้

แหล่งข้อมูลที่เกี่ยวข้อง

ขั้นตอนถัดไป