feat: Implement Magic Wallet functionality
Build and Deploy to Kubernetes / build-and-deploy (push) Successful in 8m36s

- Added ClubMembershipCycle entity and DbSet to IApplicationDbContext.
- Updated VAT rate from 9% to 10% in VatCalculator and related areas.
- Introduced Magic Wallet settings in SystemConstants.
- Enhanced UserWallet entity to support Magic Wallet features.
- Updated TransactionType enum to include Magic Wallet transactions.
- Configured UserWallet to handle Magic Wallet properties in ApplicationDbContext.
- Implemented OrmCommissionCalculationStrategy to exclude Magic Wallet users from commission calculations.
- Added Protobuf definitions for Magic Wallet methods and responses.
- Created PaymentCallbackController endpoint for handling Magic Wallet charge callbacks.
- Updated UserOrderService to manage Magic Wallet state transitions.
- Developed UserWalletService to support Magic Wallet operations.
- Created ChargeMagicWalletCommand and its handler for initiating Magic Wallet charges.
- Implemented VerifyMagicWalletChargeCommand and handler for payment verification.
- Added validation for ChargeMagicWalletCommand.
- Established ClubMembershipCycle configuration for EF Core.
- Introduced WalletMode enum to differentiate between Normal and Magic modes.
This commit is contained in:
masoodafar-web
2026-02-21 19:50:28 +03:30
parent 04e8c49fa7
commit 2a569a024f
23 changed files with 914 additions and 22 deletions
@@ -55,4 +55,9 @@ public class ClubMembership : BaseAuditableEntity
/// ClubMembershipHistory Collection Navigation Reference
/// </summary>
public virtual ICollection<ClubMembershipHistory>? ClubMembershipHistories { get; set; }
/// <summary>
/// دوره‌های خرید پکیج — هر خرید پکیج یک Cycle جدید
/// </summary>
public virtual ICollection<ClubMembershipCycle>? Cycles { get; set; }
}
@@ -0,0 +1,64 @@
namespace CMSMicroservice.Domain.Entities.Club;
/// <summary>
/// دوره خرید پکیج — هر بار خرید پکیج ۵۶M یک Cycle جدید ایجاد می‌شود.
/// برای حل مشکل overwrite شدن ClubMembership.ActivatedAt در محاسبه کمیسیون.
/// </summary>
public class ClubMembershipCycle : BaseAuditableEntity
{
/// <summary>
/// شناسه کاربر
/// </summary>
public long UserId { get; set; }
/// <summary>
/// User Navigation Property
/// </summary>
public virtual User User { get; set; }
/// <summary>
/// شناسه عضویت باشگاه
/// </summary>
public long ClubMembershipId { get; set; }
/// <summary>
/// ClubMembership Navigation Property
/// </summary>
public virtual ClubMembership ClubMembership { get; set; }
/// <summary>
/// شماره دور (1, 2, 3, ...)
/// </summary>
public int CycleNumber { get; set; }
/// <summary>
/// تاریخ خرید پکیج — این فیلد برای محاسبه کمیسیون هفتگی استفاده می‌شود
/// (به‌جای ClubMembership.ActivatedAt که overwrite می‌شد)
/// </summary>
public DateTime PackagePurchasedAt { get; set; }
/// <summary>
/// تاریخ شروع حالت جادویی (وقتی Balance=0 شد)
/// </summary>
public DateTime? MagicStartedAt { get; set; }
/// <summary>
/// تاریخ پایان حالت جادویی
/// </summary>
public DateTime? MagicCompletedAt { get; set; }
/// <summary>
/// نحوه خرید پکیج در این دور
/// </summary>
public PackagePurchaseMethod PurchaseMethod { get; set; }
/// <summary>
/// مبلغ پکیج (ریال)
/// </summary>
public long PackageAmount { get; set; }
/// <summary>
/// آیا این دور فعلی است؟ فقط یک رکورد true می‌باشد
/// </summary>
public bool IsCurrentCycle { get; set; }
}
@@ -18,7 +18,36 @@ public class UserWallet : BaseAuditableEntity
/// موجودی تخفیف - فقط برای خرید از فروشگاه باشگاه مشتریان
/// </summary>
public long DiscountBalance { get; set; }
#region Magic Wallet
/// <summary>
/// حالت کیف‌پول — Normal: کمیسیون فعال | Magic: شارژ ×2.5 بدون کمیسیون
/// </summary>
public WalletMode WalletMode { get; set; } = WalletMode.Normal;
/// <summary>
/// مجموع واریزی واقعی در دور جادویی فعلی (ریال) — سقف: MagicWalletMaxDeposit
/// </summary>
public long MagicTotalDeposited { get; set; }
/// <summary>
/// مجموع اعتبار داده‌شده در دور جادویی فعلی (ریال) — واریز × 2.5
/// </summary>
public long MagicTotalCredited { get; set; }
/// <summary>
/// زمان شروع دور جادویی فعلی
/// </summary>
public DateTime? MagicActivatedAt { get; set; }
/// <summary>
/// زمان پایان دور جادویی فعلی
/// </summary>
public DateTime? MagicCompletedAt { get; set; }
#endregion
//UserWalletChangeLog Collection Navigation Reference
public virtual ICollection<UserWalletChangeLog> UserWalletChangeLogs { get; set; }
}