using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace Domain.Entities.Developers;
///
/// API 결제 취소 감사 기록. ApiPurchase 1:1 (PurchaseID UNIQUE — 중복 취소 방지).
/// WasConfirmed=false → 보류 중 취소 (지갑 무관, Recovered/Shortfall 0).
/// WasConfirmed=true → 확정 후 취소 (StoreRevenue 회수, 잔액 부족분은 ShortfallAmount 에 기록).
///
public class ApiPurchaseCancel
{
[ForeignKey(nameof(PurchaseID))]
public virtual ApiPurchase? Purchase { get; private set; }
[Key]
public int ID { get; private set; }
public int PurchaseID { get; private set; }
public int ApplicationID { get; private set; }
public int ChannelID { get; private set; }
public int CreditedMemberID { get; private set; }
/// 확정(지갑 적립) 후의 취소였는지
public bool WasConfirmed { get; private set; }
/// 실제 회수액 (KRW). 보류 중 취소면 0.
public int RecoveredAmount { get; private set; }
/// 잔액 부족으로 회수하지 못한 금액 (KRW). 0 이면 완전 회수.
public int ShortfallAmount { get; private set; }
public DateTime CreatedAt { get; private set; } = DateTime.UtcNow;
private ApiPurchaseCancel() { }
public static ApiPurchaseCancel Create(ApiPurchase purchase, bool wasConfirmed, int recoveredAmount, int shortfallAmount)
{
if (purchase.ID <= 0)
{
throw new ArgumentException("Purchase must be persisted.", nameof(purchase));
}
if (recoveredAmount < 0)
{
throw new ArgumentOutOfRangeException(nameof(recoveredAmount));
}
if (shortfallAmount < 0)
{
throw new ArgumentOutOfRangeException(nameof(shortfallAmount));
}
return new ApiPurchaseCancel
{
PurchaseID = purchase.ID,
ApplicationID = purchase.ApplicationID,
ChannelID = purchase.ChannelID,
CreditedMemberID = purchase.CreditedMemberID,
WasConfirmed = wasConfirmed,
RecoveredAmount = recoveredAmount,
ShortfallAmount = shortfallAmount
};
}
}