🛒 Shop KDV Stratejisi v3 FINAL ✓

📅 2025-12-03 | ⚡ Runtime Hesaplama + Livewire Auto-Calculate + 2 Settings | 🏢 iXtif

🎯 v3 FINAL Strateji

✅ Database: Sadece Kaynak Veri (price_without_tax + tax_rate)

  • price_without_tax: 1.000 TL (KDV hariç - kaynak veri)
  • tax_rate: 20% (KDV oranı)
  • price_with_tax: ACCESSOR (runtime hesaplama)
// ShopProduct Model
public function getPriceWithTaxAttribute() {
return $this->price_without_tax * (1 + $this->tax_rate / 100);
}

// Kullanım:
$product->price_with_tax // 1200 TL (otomatik hesaplanır)

⚙️ 2 Settings (Settings Management)

  1. admin_price_input_mode: Admin varsayılan ne girsin? (with_tax / without_tax)
  2. product_price_display: Frontend nasıl göstersin? (with_tax / without_tax)

🔥 Admin Panel: Livewire ile Anlık Hesaplama!

Admin fiyat girerken, sistem otomatik diğer fiyatı hesaplar.

⚙️ Settings Management - 2 Ayar

Setting 1: admin_price_input_mode

Amaç: Admin panelde varsayılan olarak hangi fiyat girilsin?

Key: admin_price_input_mode
Type: select
Options:
- with_tax (KDV Dahil Girerim - B2C için)
- without_tax (KDV Hariç Girerim - B2B için)
Default: without_tax

Group: Product Management
Label: "Fiyat Girişi Varsayılan Modu"

Setting 2: product_price_display

Amaç: Frontend'de ürün kartlarında fiyat nasıl gösterilsin?

Key: product_price_display
Type: select
Options:
- with_tax (KDV Dahil Göster - B2C için)
- without_tax (KDV Hariç Göster - B2B için)
Default: with_tax

Group: Frontend Display
Label: "Ürün Kartlarında Fiyat Gösterimi"

👨‍💼 Admin Panel - Livewire Anlık Hesaplama

1. Setting Kontrol Et
admin_price_input_mode = "without_tax" (örnek)
2. Form Göster
Primary Input: "KDV Hariç Fiyat" (1000 TL)
Info Display: "KDV Dahil: 1200 TL" (disabled, info amaçlı)
3. Admin Değişiklik Yaptıkça Hesapla (Livewire)
wire:model.live="priceWithoutTax" → Değişince hesapla()
System: priceWithTax = priceWithoutTax * 1.20

Mod 1: without_tax (B2B)

<!-- Primary Input -->
<label>KDV Hariç Fiyat</label>
<input wire:model.live="priceWithoutTax">

<label>KDV Oranı</label>
<select wire:model.live="taxRate">
<option value="20">%20</option>
</select>

<!-- Info Display -->
<label>KDV Dahil (Hesaplanan)</label>
<input value="{{ $priceWithTax }}" disabled>

Mod 2: with_tax (B2C)

<!-- Primary Input -->
<label>KDV Dahil Fiyat</label>
<input wire:model.live="priceWithTax">

<label>KDV Oranı</label>
<select wire:model.live="taxRate">
<option value="20">%20</option>
</select>

<!-- Info Display -->
<label>KDV Hariç (Hesaplanan)</label>
<input value="{{ $priceWithoutTax }}" disabled>

Livewire Component

class ProductManageComponent extends Component
{
public $priceWithoutTax;
public $priceWithTax;
public $taxRate = 20;

public function mount() {
$this->inputMode = setting('admin_price_input_mode', 'without_tax');
}

public function updatedPriceWithoutTax() {
// KDV hariç değişince → KDV dahil hesapla
$this->priceWithTax = $this->priceWithoutTax * (1 + $this->taxRate / 100);
}

public function updatedPriceWithTax() {
// KDV dahil değişince → KDV hariç hesapla
$this->priceWithoutTax = $this->priceWithTax / (1 + $this->taxRate / 100);
}

public function updatedTaxRate() {
// KDV oranı değişince → Seçili moda göre yeniden hesapla
if ($this->inputMode === 'without_tax') {
$this->updatedPriceWithoutTax();
} else {
$this->updatedPriceWithTax();
}
}

public function save() {
// Database'e SADECE price_without_tax + tax_rate kaydet!
$this->product->update([
'price_without_tax' => $this->priceWithoutTax,
'tax_rate' => $this->taxRate,
]);
}
}

🗄️ Database Migration

Sadece 1 Alan Ekle!

// shop_products tablosuna:

$table->decimal('price_without_tax', 12, 2)
->nullable()
->after('base_price')
->comment('KDV hariç fiyat (kaynak veri)');

// tax_rate zaten var (mevcut alan)
// price_with_tax ekleme! (accessor ile hesaplanır)

price_with_tax alanı database'e eklenmeyecek! Accessor ile runtime hesaplanır.

🎨 Frontend - Fiyat Gösterimi

// Ürün kartında (component, blade)
@php
$displayMode = setting('product_price_display', 'with_tax');
@endphp

@if($displayMode === 'with_tax')
<span class="price">{{ number_format($product->price_with_tax, 2) }} TL</span>
<span class="tax-info">(KDV Dahil)</span>
@else
<span class="price">{{ number_format($product->price_without_tax, 2) }} TL</span>
<span class="tax-info">+ KDV</span>
@endif

🛒 Cart + Checkout: HER ZAMAN KDV Dahil!

// Sepet ve Checkout sayfalarında Settings'e bakma!
// DAIMA price_with_tax kullan:

Ara Toplam (KDV Hariç): {{ $cart->subtotal }} TL
KDV ({{ $cart->taxRate }}%): {{ $cart->taxAmount }} TL
---------------------------------------------
Toplam (KDV Dahil): {{ $cart->total }} TL

🛍️ CartService - Güncelleme

protected function setPricing(CartItem $cartItem, $item, array $options = []): void
{
// Database'den direkt al (hesaplamaya gerek yok!)
$priceWithoutTax = $item->price_without_tax ?? 0;
$taxRate = $item->tax_rate ?? 20.0;

// price_with_tax accessor ile otomatik hesaplanır
$priceWithTax = $item->price_with_tax; // Accessor çağrısı
$taxAmount = $priceWithTax - $priceWithoutTax;

// CartItem'a kaydet
$cartItem->unit_price = $priceWithoutTax;
$cartItem->tax_rate = $taxRate;
$cartItem->tax_amount = $taxAmount;
$cartItem->final_price = $priceWithTax;
$cartItem->quantity = $quantity;

// Toplam
$cartItem->subtotal = $priceWithoutTax * $quantity;
$cartItem->total = $priceWithTax * $quantity;
}

🔄 KDV Oranı Değişirse Ne Olur?

Senaryo: KDV %20'den %25'e Çıktı
Devlet KDV oranını artırdı
Admin Panel: Toplu Güncelleme
Tüm ürünlerin tax_rate'ini %20 → %25 yap
Otomatik Yansır!
price_with_tax accessor'u yeni oranla hesaplar:
1000 * 1.25 = 1250 TL
Kullanıcı Yeni Fiyatı Görür
Hiçbir kod değişikliği gerekmez!

✅ Avantajlar

  • ✅ KDV oranı değişince otomatik güncellenir
  • ✅ Database'de sadece kaynak veri (price_without_tax + tax_rate)
  • ✅ Her zaman tutarlı fiyat
  • ✅ Manuel güncelleme gerekmez

💳 Subscription - Aynı Mantık

// billing_cycles yapısı:
"billing_cycles": {
"monthly": {
"name": {"tr": "1 Aylık"},
"duration_months": 1,
"price_without_tax": 166.58, // Kaynak veri
"tax_rate": 20.00 // KDV oranı
// price_with_tax YOK! Accessor ile hesaplanır
}
}

// SubscriptionPlan Model:
public function getCyclePriceWithTax(string $cycle): float {
$cycleData = $this->billing_cycles[$cycle] ?? [];
$priceWithoutTax = $cycleData['price_without_tax'] ?? 0;
$taxRate = $cycleData['tax_rate'] ?? 20;
return $priceWithoutTax * (1 + $taxRate / 100);
}

✅ Özet - Adım Adım

1. Migration: price_without_tax ekle
2. ShopProduct: getPriceWithTaxAttribute() accessor ekle
3. Settings: 2 ayar ekle (admin_price_input_mode + product_price_display)
4. Admin Panel: Livewire anlık hesaplama ekle
5. Frontend: Settings'e göre fiyat göster
6. Cart: HER ZAMAN price_with_tax
7. Subscription: Aynı mantığı uygula

🎯 Sonuç

v3 FINAL Avantajları

  • Runtime hesaplama: KDV oranı değişince otomatik güncellenir
  • Livewire auto-calculate: Admin anlık sonuç görür
  • 2 Settings: Esneklik (admin giriş + frontend gösterim)
  • Temiz database: Sadece kaynak veri (price_without_tax + tax_rate)
  • Universal: Shop + Subscription aynı mantık
  • Tutarlılık garantili: Her zaman doğru hesaplama