diff --git a/app/Livewire/Forms/Studio/Master/Warehouse/AdjustmentStockForm.php b/app/Livewire/Forms/Studio/Master/Warehouse/AdjustmentStockForm.php index 24e346e..0b19193 100644 --- a/app/Livewire/Forms/Studio/Master/Warehouse/AdjustmentStockForm.php +++ b/app/Livewire/Forms/Studio/Master/Warehouse/AdjustmentStockForm.php @@ -82,7 +82,7 @@ public function save(Warehouse $warehouse): void StockActivityLogService::logWarehouse( logName: 'adjustment', event: 'update', - description: "Manual adjustment for {$this->name}: changed from {$oldStockValue} to {$newStockValue}. Note: ".($this->note ?? '-'), + description: "Penyesuaian manual untuk {$this->name}: berubah dari {$oldStockValue} menjadi {$newStockValue}. Catatan: ".($this->note ?? '-'), performedOn: $item, warehouse: $warehouse, quantityChange: $newStockValue - $oldStockValue, diff --git a/app/Livewire/Studio/Dashboard/Analysis.php b/app/Livewire/Studio/Dashboard/Analysis.php index 9a90015..00cbcfc 100644 --- a/app/Livewire/Studio/Dashboard/Analysis.php +++ b/app/Livewire/Studio/Dashboard/Analysis.php @@ -128,7 +128,7 @@ public function render(): View [ 'title' => 'Pegawai', 'value' => User::whereHas('employee') - ->when(! empty($outletIds), fn($q) => $q->whereHas('outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + ->when(! empty($outletIds), fn ($q) => $q->whereHas('outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->withoutDeveloper() ->count(), @@ -141,7 +141,7 @@ public function render(): View ], [ 'title' => 'Voucher Aktif', - 'value' => Voucher::when(! empty($outletIds), fn($q) => $q->whereHas('outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + 'value' => Voucher::when(! empty($outletIds), fn ($q) => $q->whereHas('outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->active() ->count(), @@ -150,7 +150,7 @@ public function render(): View [ 'title' => 'Member', 'value' => User::whereHas('customer') - ->when(! empty($outletIds), fn($q) => $q->whereHas('outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + ->when(! empty($outletIds), fn ($q) => $q->whereHas('outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->count(), 'description' => 'Total pelanggan yang sudah mendaftar sebagai member resmi.', @@ -174,39 +174,39 @@ public function render(): View ], [ 'title' => 'Parfum', - 'value' => Perfume::when(! empty($outletIds), fn($q) => $q->whereHas('outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + 'value' => Perfume::when(! empty($outletIds), fn ($q) => $q->whereHas('outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->count(), 'description' => 'Jumlah varian bibit parfum yang tersedia dalam katalog.', ], [ 'title' => 'Produk', - 'value' => Product::when(! empty($outletIds), fn($q) => $q->whereHas('outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + 'value' => Product::when(! empty($outletIds), fn ($q) => $q->whereHas('outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->count(), 'description' => 'Jumlah item produk jadi (seperti aksesoris) yang terdaftar.', ], [ 'title' => 'Botol', - 'value' => Bottle::when(! empty($outletIds), fn($q) => $q->whereHas('outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + 'value' => Bottle::when(! empty($outletIds), fn ($q) => $q->whereHas('outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->count(), 'description' => 'Jumlah jenis botol parfum yang tersedia.', ], ]; - $orderQuery = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $orderQuery = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); $totalIncome = (clone $orderQuery)->sum('total'); $totalCogs = (clone $orderQuery)->sum('cogs'); $totalDiscount = (clone $orderQuery)->sum(DB::raw('discount + COALESCE(voucher_discount, 0)')); - $expenseQuery = Expense::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $expenseQuery = Expense::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); $totalExpense = $expenseQuery->sum('amount'); - $payrollQuery = Payroll::when(! empty($outletIds), fn($q) => $q->whereHas('user.outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + $payrollQuery = Payroll::when(! empty($outletIds), fn ($q) => $q->whereHas('user.outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->paid(); $totalPayroll = $payrollQuery->sum('total_salary'); @@ -215,7 +215,7 @@ public function render(): View $netProfit = $grossProfit - $totalExpense - $totalPayroll; $totalOrdersCount = (clone $orderQuery)->count(); - $totalItemsCount = OrderItem::whereHas('order', fn($q) => $q->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate))->sum('quantity'); + $totalItemsCount = OrderItem::whereHas('order', fn ($q) => $q->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate))->sum('quantity'); $aov = $totalOrdersCount > 0 ? $totalIncome / $totalOrdersCount : 0; $profitMargin = $totalIncome > 0 ? ($netProfit / $totalIncome) * 100 : 0; @@ -225,7 +225,7 @@ public function render(): View ->whereNotNull('customer_id') ->groupBy('customer_id') ->get(); - $repeatCustomers = $customerOrders->filter(fn($c) => $c->count > 1)->count(); + $repeatCustomers = $customerOrders->filter(fn ($c) => $c->count > 1)->count(); $totalCustomers = $customerOrders->count(); $loyaltyRate = $totalCustomers > 0 ? ($repeatCustomers / $totalCustomers) * 100 : 0; @@ -237,12 +237,12 @@ public function render(): View ], $user->hasRole(['Developer', 'Owner']) ? [ 'title' => 'Profit Margin', - 'value' => round($profitMargin, 1) . '%', + 'value' => round($profitMargin, 1).'%', 'description' => 'Persentase keuntungan bersih dibandingkan dengan total pendapatan.', ] : null, [ 'title' => 'Loyalty Rate', - 'value' => round($loyaltyRate, 1) . '%', + 'value' => round($loyaltyRate, 1).'%', 'description' => 'Persentase pelanggan yang melakukan pembelian lebih dari satu kali.', ], [ @@ -295,27 +295,27 @@ public function render(): View 'title' => 'Parfum Terjual', 'value' => formatCurrencyNumber( OrderItem::where('orderable_type', Perfume::class) - ->whereHas('order', fn($q) => $q->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate)) + ->whereHas('order', fn ($q) => $q->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate)) ->sum('quantity') - ) . ' ml', + ).' ml', 'description' => 'Total volume cairan parfum yang terjual dalam satuan mililiter (ml).', ], [ 'title' => 'Produk Terjual', 'value' => formatCurrencyNumber( OrderItem::where('orderable_type', Product::class) - ->whereHas('order', fn($q) => $q->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate)) + ->whereHas('order', fn ($q) => $q->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate)) ->sum('quantity') - ) . ' pcs', + ).' pcs', 'description' => 'Total jumlah unit produk yang terjual dalam satuan pcs.', ], [ 'title' => 'Botol Terjual', 'value' => formatCurrencyNumber( OrderItem::where('orderable_type', Bottle::class) - ->whereHas('order', fn($q) => $q->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate)) + ->whereHas('order', fn ($q) => $q->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds))->when($dateQuery || ($startDate && $endDate), $filterDate)) ->sum('quantity') - ) . ' pcs', + ).' pcs', 'description' => 'Total jumlah unit botol yang terjual dalam satuan pcs.', ], ]); @@ -324,7 +324,7 @@ public function render(): View [ 'title' => 'Beban Toko', 'value' => formatCurrencyNumber( - Expense::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + Expense::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->sum('amount'), 'Rp' @@ -345,7 +345,7 @@ public function render(): View [ 'title' => 'Penggajian', 'value' => formatCurrencyNumber( - Payroll::when(! empty($outletIds), fn($q) => $q->whereHas('user.outlets', fn($q2) => $q2->whereIn('outlets.id', $outletIds))) + Payroll::when(! empty($outletIds), fn ($q) => $q->whereHas('user.outlets', fn ($q2) => $q2->whereIn('outlets.id', $outletIds))) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->paid() ->sum('total_salary'), @@ -357,7 +357,7 @@ public function render(): View $topPerfumes = OrderItem::where('orderable_type', Perfume::class) ->whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); }) ->with('orderable') @@ -366,7 +366,7 @@ public function render(): View ->orderByDesc('total_sales_value') ->take(5) ->get() - ->map(fn($item) => [ + ->map(fn ($item) => [ 'name' => $item->orderable?->name ?? 'Unknown', 'sale_price' => formatCurrencyNumber($item->orderable?->sale_price ?? 0, 'Rp'), 'total_sold' => formatCurrencyNumber($item->total_sold), @@ -376,7 +376,7 @@ public function render(): View $topProducts = OrderItem::where('orderable_type', Product::class) ->whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); }) ->with('orderable') @@ -385,7 +385,7 @@ public function render(): View ->orderByDesc('total_sales_value') ->take(5) ->get() - ->map(fn($item) => [ + ->map(fn ($item) => [ 'name' => $item->orderable?->name ?? 'Unknown', 'sale_price' => formatCurrencyNumber($item->orderable?->sale_price ?? 0, 'Rp'), 'total_sold' => formatCurrencyNumber($item->total_sold), @@ -395,7 +395,7 @@ public function render(): View $topBottles = OrderItem::where('orderable_type', Bottle::class) ->whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); }) ->with('orderable') @@ -404,7 +404,7 @@ public function render(): View ->orderByDesc('total_sales_value') ->take(5) ->get() - ->map(fn($item) => [ + ->map(fn ($item) => [ 'name' => $item->orderable?->name ?? 'Unknown', 'sale_price' => formatCurrencyNumber($item->orderable?->sale_price ?? 0, 'Rp'), 'total_sold' => formatCurrencyNumber($item->total_sold), @@ -415,9 +415,9 @@ public function render(): View // --- Chart Data Logic --- // 1. Revenue & Profit Trend - $trendDates = collect(range(29, 0))->map(fn($i) => now()->subDays($i)->format('Y-m-d')); + $trendDates = collect(range(29, 0))->map(fn ($i) => now()->subDays($i)->format('Y-m-d')); $ordersTrend = Order::query() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->where('created_at', '>=', now()->subDays(30)->startOfDay()) ->select(DB::raw('DATE(created_at) as date'), DB::raw('SUM(total) as revenue'), DB::raw('SUM(total) - SUM(cogs) - SUM(discount) - SUM(COALESCE(voucher_discount,0)) as gross_profit'), DB::raw('count(*) as count')) ->groupBy('date') @@ -425,7 +425,7 @@ public function render(): View ->keyBy('date'); $expensesTrend = Expense::query() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->where('created_at', '>=', now()->subDays(30)->startOfDay()) ->select(DB::raw('DATE(created_at) as date'), DB::raw('SUM(amount) as total_expense')) ->groupBy('date') @@ -433,9 +433,9 @@ public function render(): View ->keyBy('date'); $this->revenueTrendChart = [ - 'labels' => $trendDates->map(fn($d) => Carbon::parse($d)->format('d M'))->toArray(), - 'revenue' => $trendDates->map(fn($d) => (int) ($ordersTrend->get($d)?->revenue ?? 0))->toArray(), - 'profit' => $trendDates->map(fn($d) => (int) (($ordersTrend->get($d)?->gross_profit ?? 0) - ($expensesTrend->get($d)?->total_expense ?? 0)))->toArray(), + 'labels' => $trendDates->map(fn ($d) => Carbon::parse($d)->format('d M'))->toArray(), + 'revenue' => $trendDates->map(fn ($d) => (int) ($ordersTrend->get($d)?->revenue ?? 0))->toArray(), + 'profit' => $trendDates->map(fn ($d) => (int) (($ordersTrend->get($d)?->gross_profit ?? 0) - ($expensesTrend->get($d)?->total_expense ?? 0)))->toArray(), ]; // 2. busiest hour @@ -448,26 +448,26 @@ public function render(): View ->keyBy('hour'); $this->hourlySalesChart = [ - 'labels' => collect(range(0, 23))->map(fn($h) => str_pad($h, 2, '0', STR_PAD_LEFT) . ':00')->toArray(), - 'data' => collect(range(0, 23))->map(fn($h) => $hourlySales->get($h)?->count ?? 0)->toArray(), + 'labels' => collect(range(0, 23))->map(fn ($h) => str_pad($h, 2, '0', STR_PAD_LEFT).':00')->toArray(), + 'data' => collect(range(0, 23))->map(fn ($h) => $hourlySales->get($h)?->count ?? 0)->toArray(), ]; // 3. Product Category Distribution $perfumeSales = OrderItem::where('orderable_type', Perfume::class) ->whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); })->sum(DB::raw('unit_price * quantity')); $productSales = OrderItem::where('orderable_type', Product::class) ->whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); })->sum(DB::raw('unit_price * quantity')); $bottleSales = OrderItem::where('orderable_type', Bottle::class) ->whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); })->sum(DB::raw('unit_price * quantity')); @@ -478,7 +478,7 @@ public function render(): View // 4. Payment Method $paymentMethods = Payment::whereHas('order', function ($q) use ($outletIds, $dateQuery, $startDate, $endDate, $filterDate) { - $q->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $q->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate); }) ->select('method', DB::raw('SUM(amount) as total')) @@ -486,13 +486,13 @@ public function render(): View ->get(); $this->paymentMethodChart = [ - 'labels' => $paymentMethods->map(fn($pm) => $pm->method?->label() ?? 'Unknown')->toArray(), + 'labels' => $paymentMethods->map(fn ($pm) => $pm->method?->label() ?? 'Unknown')->toArray(), 'data' => $paymentMethods->pluck('total')->toArray(), ]; // 5. Outlet Performance $outletPerformance = Order::query() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->when($dateQuery || ($startDate && $endDate), $filterDate) ->select('outlet_id', DB::raw('SUM(total) as revenue')) ->groupBy('outlet_id') @@ -500,7 +500,7 @@ public function render(): View ->get(); $this->outletPerformanceChart = [ - 'labels' => $outletPerformance->map(fn($op) => $op->outlet?->name ?? 'Outlet #' . $op->outlet_id)->toArray(), + 'labels' => $outletPerformance->map(fn ($op) => $op->outlet?->name ?? 'Outlet #'.$op->outlet_id)->toArray(), 'data' => $outletPerformance->pluck('revenue')->toArray(), ]; @@ -546,7 +546,7 @@ public function render(): View $this->dayOfWeekSalesChart = [ 'labels' => array_values($days), - 'data' => collect(range(1, 7))->map(fn($d) => (int) ($dayOfWeekSales->get($d)?->revenue ?? 0))->toArray(), + 'data' => collect(range(1, 7))->map(fn ($d) => (int) ($dayOfWeekSales->get($d)?->revenue ?? 0))->toArray(), ]; // 8. Customer Type (Member vs Guest) @@ -560,13 +560,13 @@ public function render(): View // 9. Transaction Trend (Daily Count) $this->transactionTrendChart = [ - 'labels' => $trendDates->map(fn($d) => Carbon::parse($d)->format('d M'))->toArray(), - 'data' => $trendDates->map(fn($d) => (int) ($ordersTrend->get($d)?->count ?? 0))->toArray(), + 'labels' => $trendDates->map(fn ($d) => Carbon::parse($d)->format('d M'))->toArray(), + 'data' => $trendDates->map(fn ($d) => (int) ($ordersTrend->get($d)?->count ?? 0))->toArray(), ]; // 10. AOV Trend (Daily Revenue / Daily Count) $this->aovTrendChart = [ - 'labels' => $trendDates->map(fn($d) => Carbon::parse($d)->format('d M'))->toArray(), + 'labels' => $trendDates->map(fn ($d) => Carbon::parse($d)->format('d M'))->toArray(), 'data' => $trendDates->map(function ($d) use ($ordersTrend) { $rev = $ordersTrend->get($d)?->revenue ?? 0; $count = $ordersTrend->get($d)?->count ?? 0; @@ -595,7 +595,7 @@ public function render(): View // 14. Voucher Usage Trend $vouchersTrend = Order::query() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->where('created_at', '>=', now()->subDays(30)->startOfDay()) ->whereNotNull('voucher_id') ->select(DB::raw('DATE(created_at) as date'), DB::raw('count(*) as count')) @@ -604,8 +604,8 @@ public function render(): View ->keyBy('date'); $this->voucherUsageTrendChart = [ - 'labels' => $trendDates->map(fn($d) => Carbon::parse($d)->format('d M'))->toArray(), - 'data' => $trendDates->map(fn($d) => (int) ($vouchersTrend->get($d)?->count ?? 0))->toArray(), + 'labels' => $trendDates->map(fn ($d) => Carbon::parse($d)->format('d M'))->toArray(), + 'data' => $trendDates->map(fn ($d) => (int) ($vouchersTrend->get($d)?->count ?? 0))->toArray(), ]; $this->countingData = $countingData; diff --git a/app/Livewire/Studio/Dashboard/Overview.php b/app/Livewire/Studio/Dashboard/Overview.php index 0db838e..c95f0b1 100644 --- a/app/Livewire/Studio/Dashboard/Overview.php +++ b/app/Livewire/Studio/Dashboard/Overview.php @@ -59,53 +59,53 @@ public function render(): View $outletIds = $user->outlets()->pluck('outlets.id')->toArray(); } - $todayOrder = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $todayOrder = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->today() ->count(); - $yesterdayOrder = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $yesterdayOrder = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->yesterday() ->count(); - $todayIncome = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $todayIncome = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->today() ->sum('total'); - $yesterdayIncome = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $yesterdayIncome = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->yesterday() ->sum('total'); - $todayCogs = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $todayCogs = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->today() ->sum('cogs'); - $yesterdayCogs = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $yesterdayCogs = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->yesterday() ->sum('cogs'); - $todayDiscount = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $todayDiscount = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->today() ->sum(DB::raw('discount + COALESCE(voucher_discount, 0)')); - $yesterdayDiscount = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $yesterdayDiscount = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->yesterday() ->sum(DB::raw('discount + COALESCE(voucher_discount, 0)')); - $todayVoucher = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $todayVoucher = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->today() ->whereNotNull('voucher_id') ->count(); - $yesterdayVoucher = Order::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $yesterdayVoucher = Order::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->yesterday() ->whereNotNull('voucher_id') ->count(); - $todayExpense = Expense::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $todayExpense = Expense::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->today() ->sum('amount'); - $yesterdayExpense = Expense::when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + $yesterdayExpense = Expense::when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->yesterday() ->sum('amount'); @@ -122,21 +122,21 @@ public function render(): View $todaySoldPerfume = OrderItem::where('orderable_type', Perfume::class) ->whereHas( 'order', - fn($q) => $q->today()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)) + fn ($q) => $q->today()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)) ) ->sum('quantity'); $yesterdaySoldPerfume = OrderItem::where('orderable_type', Perfume::class) ->whereHas( 'order', - fn($q) => $q->yesterday()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)) + fn ($q) => $q->yesterday()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)) ) ->sum('quantity'); $todayTopPerfume = OrderItem::where('orderable_type', Perfume::class) ->whereHas( 'order', - fn($q) => $q->today()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)) + fn ($q) => $q->today()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)) ) ->select('orderable_id', 'orderable_type', DB::raw('SUM(quantity) as total_sold')) ->groupBy('orderable_id', 'orderable_type') @@ -147,7 +147,7 @@ public function render(): View $yesterdayTopPerfume = OrderItem::where('orderable_type', Perfume::class) ->whereHas( 'order', - fn($q) => $q->yesterday()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)) + fn ($q) => $q->yesterday()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)) ) ->select('orderable_id', 'orderable_type', DB::raw('SUM(quantity) as total_sold')) ->groupBy('orderable_id', 'orderable_type') @@ -172,26 +172,26 @@ public function render(): View $hourFunc = DB::getDriverName() === 'sqlite' ? "CAST(strftime('%H', created_at) AS INTEGER)" : 'HOUR(created_at)'; $todayHourly = Order::whereDate('created_at', now()) - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->select(DB::raw("$hourFunc as hour"), DB::raw('count(*) as count')) ->groupBy('hour') ->get()->keyBy('hour'); $yesterdayHourly = Order::whereDate('created_at', now()->yesterday()) - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->select(DB::raw("$hourFunc as hour"), DB::raw('count(*) as count')) ->groupBy('hour') ->get()->keyBy('hour'); $this->hourlyComparisonChart = [ - 'labels' => collect(range(0, 23))->map(fn($h) => str_pad($h, 2, '0', STR_PAD_LEFT) . ':00')->toArray(), - 'today' => collect(range(0, 23))->map(fn($h) => $todayHourly->get($h)?->count ?? 0)->toArray(), - 'yesterday' => collect(range(0, 23))->map(fn($h) => $yesterdayHourly->get($h)?->count ?? 0)->toArray(), + 'labels' => collect(range(0, 23))->map(fn ($h) => str_pad($h, 2, '0', STR_PAD_LEFT).':00')->toArray(), + 'today' => collect(range(0, 23))->map(fn ($h) => $todayHourly->get($h)?->count ?? 0)->toArray(), + 'yesterday' => collect(range(0, 23))->map(fn ($h) => $yesterdayHourly->get($h)?->count ?? 0)->toArray(), ]; // 2. Today's Distribution (Category) $categorySales = OrderItem::whereHas('order', function ($q) use ($outletIds) { - $q->today()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)); + $q->today()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)); }) ->select('orderable_type', DB::raw('SUM(unit_price * quantity) as total')) ->groupBy('orderable_type') @@ -208,25 +208,25 @@ public function render(): View // 3. Today's Payment Methods $paymentMethods = Payment::whereHas('order', function ($q) use ($outletIds) { - $q->today()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)); + $q->today()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)); }) ->select('method', DB::raw('SUM(amount) as total')) ->groupBy('method') ->get(); $this->todayPaymentChart = [ - 'labels' => $paymentMethods->map(fn($pm) => $pm->method?->label() ?? 'Unknown')->toArray(), + 'labels' => $paymentMethods->map(fn ($pm) => $pm->method?->label() ?? 'Unknown')->toArray(), 'data' => $paymentMethods->pluck('total')->toArray(), ]; // 4. Today's Customer Type $todayMemberOrders = Order::query() ->today() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->whereNotNull('customer_id')->count(); $todayGuestOrders = Order::query() ->today() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->whereNull('customer_id')->count(); $this->todayCustomerTypeChart = [ @@ -236,7 +236,7 @@ public function render(): View // 5. Today's Top 5 Selling Items $todayTopItems = OrderItem::whereHas('order', function ($q) use ($outletIds) { - $q->today()->when(! empty($outletIds), fn($q2) => $q2->whereIn('outlet_id', $outletIds)); + $q->today()->when(! empty($outletIds), fn ($q2) => $q2->whereIn('outlet_id', $outletIds)); }) ->with('orderable') ->select('orderable_id', 'orderable_type', DB::raw('SUM(quantity) as total_sold')) @@ -246,14 +246,14 @@ public function render(): View ->get(); $this->todayTopSellingChart = [ - 'labels' => $todayTopItems->map(fn($item) => $item->orderable?->name ?? 'Unknown')->toArray(), - 'data' => $todayTopItems->pluck('total_sold')->map(fn($val) => (int) $val)->toArray(), + 'labels' => $todayTopItems->map(fn ($item) => $item->orderable?->name ?? 'Unknown')->toArray(), + 'data' => $todayTopItems->pluck('total_sold')->map(fn ($val) => (int) $val)->toArray(), ]; // 6. Today's Top 5 Customers $todayTopCustomers = Order::query() ->today() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->whereNotNull('customer_id') ->select('customer_id', DB::raw('SUM(total) as total_spent')) ->groupBy('customer_id') @@ -263,18 +263,18 @@ public function render(): View ->get(); $this->todayTopCustomersChart = [ - 'labels' => $todayTopCustomers->map(fn($o) => $o->customer?->user?->employee?->full_name ?? $o->customer?->user?->name ?? 'Customer #' . $o->customer_id)->toArray(), - 'data' => $todayTopCustomers->pluck('total_spent')->map(fn($val) => (int) $val)->toArray(), + 'labels' => $todayTopCustomers->map(fn ($o) => $o->customer?->user?->employee?->full_name ?? $o->customer?->user?->name ?? 'Customer #'.$o->customer_id)->toArray(), + 'data' => $todayTopCustomers->pluck('total_spent')->map(fn ($val) => (int) $val)->toArray(), ]; // 7. Today's Discount Distribution (With Discount vs Regular) $withDiscount = Order::query() ->today() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->where('discount', '>', 0)->count(); $noDiscount = Order::query() ->today() - ->when(! empty($outletIds), fn($q) => $q->whereIn('outlet_id', $outletIds)) + ->when(! empty($outletIds), fn ($q) => $q->whereIn('outlet_id', $outletIds)) ->where('discount', '<=', 0)->count(); $this->todayDiscountChart = [ @@ -288,7 +288,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayAov, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayAov, 'Rp'), 'trend' => $yesterdayAov > 0 - ? round((($todayAov - $yesterdayAov) / $yesterdayAov) * 100, 1) . '%' + ? round((($todayAov - $yesterdayAov) / $yesterdayAov) * 100, 1).'%' : '∞%', 'trendUp' => $todayAov > $yesterdayAov, 'description' => 'Rata-rata nilai belanja pelanggan dalam satu kali checkout.', @@ -296,10 +296,10 @@ public function render(): View $user->hasRole(['Developer', 'Owner']) ? [ 'title' => 'Profit Margin', - 'value' => round($todayProfitMargin, 1) . '%', - 'previous' => round($yesterdayProfitMargin, 1) . '%', + 'value' => round($todayProfitMargin, 1).'%', + 'previous' => round($yesterdayProfitMargin, 1).'%', 'trend' => $yesterdayProfitMargin > 0 - ? round($todayProfitMargin - $yesterdayProfitMargin, 1) . '%' + ? round($todayProfitMargin - $yesterdayProfitMargin, 1).'%' : '∞%', 'trendUp' => $todayProfitMargin > $yesterdayProfitMargin, 'description' => 'Persentase keuntungan bersih dibandingkan dengan total pendapatan.', @@ -310,7 +310,7 @@ public function render(): View 'value' => $todayOrder, 'previous' => $yesterdayOrder, 'trend' => $yesterdayOrder > 0 - ? round((($todayOrder - $yesterdayOrder) / $yesterdayOrder) * 100, 1) . '%' + ? round((($todayOrder - $yesterdayOrder) / $yesterdayOrder) * 100, 1).'%' : '∞%', 'trendUp' => $todayOrder > $yesterdayOrder, 'description' => 'Total frekuensi transaksi atau pesanan yang masuk selama periode ini.', @@ -321,7 +321,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayIncome, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayIncome, 'Rp'), 'trend' => $yesterdayIncome > 0 - ? round((($todayIncome - $yesterdayIncome) / $yesterdayIncome) * 100, 1) . '%' + ? round((($todayIncome - $yesterdayIncome) / $yesterdayIncome) * 100, 1).'%' : '∞%', 'trendUp' => $todayIncome > $yesterdayIncome, 'formatted' => formatCurrencyNumber($todayIncome, 'Rp'), @@ -333,7 +333,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayCogs, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayCogs, 'Rp'), 'trend' => $yesterdayCogs > 0 - ? round((($todayCogs - $yesterdayCogs) / $yesterdayCogs) * 100, 1) . '%' + ? round((($todayCogs - $yesterdayCogs) / $yesterdayCogs) * 100, 1).'%' : '∞%', 'trendUp' => $todayCogs > $yesterdayCogs, 'formatted' => formatCurrencyNumber($todayCogs, 'Rp'), @@ -342,10 +342,10 @@ public function render(): View [ 'title' => 'Member Baru', - 'value' => $todayNewMembers . ' Orang', - 'previous' => $yesterdayNewMembers . ' Orang', + 'value' => $todayNewMembers.' Orang', + 'previous' => $yesterdayNewMembers.' Orang', 'trend' => $yesterdayNewMembers > 0 - ? round((($todayNewMembers - $yesterdayNewMembers) / $yesterdayNewMembers) * 100, 1) . '%' + ? round((($todayNewMembers - $yesterdayNewMembers) / $yesterdayNewMembers) * 100, 1).'%' : '∞%', 'trendUp' => $todayNewMembers > $yesterdayNewMembers, 'description' => 'Jumlah pelanggan baru yang mendaftar menjadi member selama periode ini.', @@ -356,7 +356,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayDiscount, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayDiscount, 'Rp'), 'trend' => $yesterdayDiscount > 0 - ? round((($todayDiscount - $yesterdayDiscount) / $yesterdayDiscount) * 100, 1) . '%' + ? round((($todayDiscount - $yesterdayDiscount) / $yesterdayDiscount) * 100, 1).'%' : '∞%', 'trendUp' => $todayDiscount > $yesterdayDiscount, 'formatted' => formatCurrencyNumber($todayDiscount, 'Rp'), @@ -368,7 +368,7 @@ public function render(): View 'value' => $todayVoucher, 'previous' => $yesterdayVoucher, 'trend' => $yesterdayVoucher > 0 - ? round((($todayVoucher - $yesterdayVoucher) / $yesterdayVoucher) * 100, 1) . '%' + ? round((($todayVoucher - $yesterdayVoucher) / $yesterdayVoucher) * 100, 1).'%' : '∞%', 'trendUp' => $todayVoucher > $yesterdayVoucher, 'description' => 'Jumlah transaksi yang menggunakan voucher diskon selama periode ini.', @@ -379,7 +379,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayExpense, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayExpense, 'Rp'), 'trend' => $yesterdayExpense > 0 - ? round((($todayExpense - $yesterdayExpense) / $yesterdayExpense) * 100, 1) . '%' + ? round((($todayExpense - $yesterdayExpense) / $yesterdayExpense) * 100, 1).'%' : '∞%', 'trendUp' => $todayExpense > $yesterdayExpense, 'description' => 'Total biaya operasional atau pengeluaran toko yang tercatat selama periode ini.', @@ -390,7 +390,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayPurchase, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayPurchase, 'Rp'), 'trend' => $yesterdayPurchase > 0 - ? round((($todayPurchase - $yesterdayPurchase) / $yesterdayPurchase) * 100, 1) . '%' + ? round((($todayPurchase - $yesterdayPurchase) / $yesterdayPurchase) * 100, 1).'%' : '∞%', 'trendUp' => $todayPurchase > $yesterdayPurchase, 'description' => 'Total pengeluaran untuk pembelian stok barang atau inventaris selama periode ini.', @@ -401,7 +401,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayGrossProfit, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayGrossProfit, 'Rp'), 'trend' => $yesterdayGrossProfit > 0 - ? round((($todayGrossProfit - $yesterdayGrossProfit) / $yesterdayGrossProfit) * 100, 1) . '%' + ? round((($todayGrossProfit - $yesterdayGrossProfit) / $yesterdayGrossProfit) * 100, 1).'%' : '∞%', 'trendUp' => $todayGrossProfit > $yesterdayGrossProfit, 'description' => 'Pendapatan dikurangi dengan HPP dan Diskon.', @@ -412,7 +412,7 @@ public function render(): View 'value' => formatCurrencyNumber($todayNetProfit, 'Rp'), 'previous' => formatCurrencyNumber($yesterdayNetProfit, 'Rp'), 'trend' => $yesterdayNetProfit > 0 - ? round((($todayNetProfit - $yesterdayNetProfit) / $yesterdayNetProfit) * 100, 1) . '%' + ? round((($todayNetProfit - $yesterdayNetProfit) / $yesterdayNetProfit) * 100, 1).'%' : '∞%', 'trendUp' => $todayNetProfit > $yesterdayNetProfit, 'description' => 'Laba kotor dikurangi dengan beban operasional dan gaji.', @@ -420,10 +420,10 @@ public function render(): View [ 'title' => 'Parfum Terjual', - 'value' => $todaySoldPerfume . ' ml', - 'previous' => $yesterdaySoldPerfume . ' ml', + 'value' => $todaySoldPerfume.' ml', + 'previous' => $yesterdaySoldPerfume.' ml', 'trend' => $yesterdaySoldPerfume > 0 - ? round((($todaySoldPerfume - $yesterdaySoldPerfume) / $yesterdaySoldPerfume) * 100, 1) . '%' + ? round((($todaySoldPerfume - $yesterdaySoldPerfume) / $yesterdaySoldPerfume) * 100, 1).'%' : '∞%', 'trendUp' => $todaySoldPerfume > $yesterdaySoldPerfume, 'description' => 'Total volume cairan parfum yang terjual dalam satuan mililiter (ml).', @@ -431,10 +431,10 @@ public function render(): View [ 'title' => 'Top Parfum', - 'value' => optional($todayTopPerfume?->orderable)->name . ' (' . $todayTopPerfume?->total_sold . 'ml)' ?? '-', - 'previous' => optional($yesterdayTopPerfume?->orderable)->name . '(' . $yesterdayTopPerfume?->total_sold . 'ml)' ?? '-', + 'value' => optional($todayTopPerfume?->orderable)->name.' ('.$todayTopPerfume?->total_sold.'ml)' ?? '-', + 'previous' => optional($yesterdayTopPerfume?->orderable)->name.'('.$yesterdayTopPerfume?->total_sold.'ml)' ?? '-', 'trend' => ($yesterdayTopPerfume && $yesterdayTopPerfume->total_sold > 0) - ? round((($todayTopPerfume?->total_sold - $yesterdayTopPerfume?->total_sold) / $yesterdayTopPerfume?->total_sold) * 100, 1) . '%' + ? round((($todayTopPerfume?->total_sold - $yesterdayTopPerfume?->total_sold) / $yesterdayTopPerfume?->total_sold) * 100, 1).'%' : '∞%', 'trendUp' => ($todayTopPerfume?->total_sold ?? 0) > ($yesterdayTopPerfume?->total_sold ?? 0), 'description' => 'Nama varian parfum yang paling banyak terjual hari ini.', diff --git a/app/Services/StockActivityLogService.php b/app/Services/StockActivityLogService.php index f086519..91306c8 100644 --- a/app/Services/StockActivityLogService.php +++ b/app/Services/StockActivityLogService.php @@ -37,7 +37,7 @@ public static function purchase( self::logWarehouse( logName: self::LOG_PURCHASE, event: 'increase', - description: "Purchase #{$purchase->hash_id}: Added {$quantity} stock to Warehouse.", + description: "Pembelian #{$purchase->hash_id}: Menambah {$quantity} stok ke Gudang.", performedOn: $product, warehouse: $purchase->warehouse, quantityChange: $quantity, @@ -69,7 +69,7 @@ public static function distribution( self::logWarehouse( logName: self::LOG_DISTRIBUTION, event: 'decrease', - description: "Restock #{$restock->hash_id}: Moved {$quantity} stock from Warehouse to Outlet.", + description: "Restock #{$restock->hash_id}: Memindahkan {$quantity} stok dari Gudang ke Outlet.", performedOn: $product, warehouse: $restock->warehouse, quantityChange: -1 * abs($quantity), @@ -87,7 +87,7 @@ public static function distribution( self::logOutlet( logName: self::LOG_DISTRIBUTION, event: 'increase', - description: "Restock #{$restock->hash_id}: Received {$quantity} stock from Warehouse.", + description: "Restock #{$restock->hash_id}: Menerima {$quantity} stok dari Gudang.", performedOn: $product, outlet: $restock->outlet, quantityChange: abs($quantity), @@ -116,7 +116,7 @@ public static function sale( self::logOutlet( logName: self::LOG_SALE, event: 'decrease', - description: "Order #{$order->hash_id}: Sold {$quantity} items.", + description: "Pesanan #{$order->hash_id}: Menjual {$quantity} item.", performedOn: $product, outlet: $order->outlet, quantityChange: -1 * abs($quantity), @@ -147,7 +147,7 @@ public static function stockOpname( self::logOutlet( logName: self::LOG_STOCK_OPNAME, event: $event, - description: "Stock Opname #{$stockOpname->hash_id}: Adjusted stock by {$quantityChange}.", + description: "Stock Opname #{$stockOpname->hash_id}: Penyesuaian stok sebesar {$quantityChange}.", performedOn: $product, outlet: $stockOpname->outlet, quantityChange: $quantityChange, @@ -180,7 +180,7 @@ public static function transfer( self::logOutlet( logName: self::LOG_TRANSFER, event: 'decrease', - description: "Stock Transfer #{$stockTransfer->hash_id}: Moved {$quantity} stock from Source to Destination Outlet.", + description: "Transfer Stok #{$stockTransfer->hash_id}: Memindahkan {$quantity} stok dari Outlet Asal ke Outlet Tujuan.", performedOn: $product, outlet: $stockTransfer->sourceOutlet, quantityChange: -1 * abs($quantity), @@ -198,7 +198,7 @@ public static function transfer( self::logOutlet( logName: self::LOG_TRANSFER, event: 'increase', - description: "Stock Transfer #{$stockTransfer->hash_id}: Received {$quantity} stock from Source Outlet.", + description: "Transfer Stok #{$stockTransfer->hash_id}: Menerima {$quantity} stok dari Outlet Asal.", performedOn: $product, outlet: $stockTransfer->destinationOutlet, quantityChange: abs($quantity), @@ -213,6 +213,55 @@ public static function transfer( ); } + /** + * Generic log method that delegates to logOutlet or logWarehouse. + */ + public static function log( + string $logName, + string $event, + string $description, + Model $performedOn, + ?Model $outlet = null, + ?Warehouse $warehouse = null, + int $quantityChange = 0, + int $previousStock = 0, + int $newStock = 0, + array $extraProperties = [], + ?Model $causedBy = null + ): void { + if ($warehouse) { + self::logWarehouse( + logName: $logName, + event: $event, + description: $description, + performedOn: $performedOn, + warehouse: $warehouse, + quantityChange: $quantityChange, + previousStock: $previousStock, + newStock: $newStock, + extraProperties: $extraProperties, + causedBy: $causedBy + ); + + return; + } + + if ($outlet) { + self::logOutlet( + logName: $logName, + event: $event, + description: $description, + performedOn: $performedOn, + outlet: $outlet, + quantityChange: $quantityChange, + previousStock: $previousStock, + newStock: $newStock, + extraProperties: $extraProperties, + causedBy: $causedBy + ); + } + } + /** * Log stock related activity for Outlet. */ @@ -236,7 +285,7 @@ public static function logOutlet( 'previous_stock' => $previousStock, 'new_stock' => $newStock, 'location_type' => 'outlet', - 'location_name' => $outlet->name ?? 'Unknown Outlet', + 'location_name' => $outlet->name ?? 'Outlet Tidak Diketahui', ], $extraProperties); activity($logName) @@ -270,7 +319,7 @@ public static function logWarehouse( 'previous_stock' => $previousStock, 'new_stock' => $newStock, 'location_type' => 'warehouse', - 'location_name' => $warehouse->name ?? 'Unknown Warehouse', + 'location_name' => $warehouse->name ?? 'Gudang Tidak Diketahui', ], $extraProperties); activity($logName) diff --git a/app/Traits/Restock/WithRestockStock.php b/app/Traits/Restock/WithRestockStock.php index 115cee3..193e154 100644 --- a/app/Traits/Restock/WithRestockStock.php +++ b/app/Traits/Restock/WithRestockStock.php @@ -128,7 +128,7 @@ public function reverseStockTransfer($warehouse, $outlet, $item): void StockActivityLogService::logWarehouse( logName: StockActivityLogService::LOG_DISTRIBUTION, event: 'increase', - description: "Restock #{$restock->hash_id} Deleted: Returned {$quantity} stock to Warehouse.", + description: "Restock #{$restock->hash_id} Dihapus: Mengembalikan {$quantity} stok ke Gudang.", performedOn: $item->restockable, warehouse: $warehouse, quantityChange: $quantity, @@ -156,7 +156,7 @@ public function reverseStockTransfer($warehouse, $outlet, $item): void StockActivityLogService::logOutlet( logName: StockActivityLogService::LOG_DISTRIBUTION, event: 'decrease', - description: "Restock #{$restock->hash_id} Deleted: Removed {$quantity} stock from Outlet.", + description: "Restock #{$restock->hash_id} Dihapus: Menghapus {$quantity} stok dari Outlet.", performedOn: $item->restockable, outlet: $outlet, quantityChange: -1 * abs($quantity), diff --git a/app/Traits/StockTransfer/WithStockTransferStock.php b/app/Traits/StockTransfer/WithStockTransferStock.php index 7867f23..7537e2e 100644 --- a/app/Traits/StockTransfer/WithStockTransferStock.php +++ b/app/Traits/StockTransfer/WithStockTransferStock.php @@ -128,7 +128,7 @@ public function reverseStockTransferBetweenOutlets($sourceOutlet, $destinationOu StockActivityLogService::logOutlet( logName: StockActivityLogService::LOG_TRANSFER, event: 'increase', - description: "Stock Transfer #{$stockTransfer->hash_id} Deleted: Returned {$quantity} stock to source outlet.", + description: "Transfer Stok #{$stockTransfer->hash_id} Dihapus: Mengembalikan {$quantity} stok ke outlet asal.", performedOn: $item->transferable, outlet: $sourceOutlet, quantityChange: $quantity, @@ -156,7 +156,7 @@ public function reverseStockTransferBetweenOutlets($sourceOutlet, $destinationOu StockActivityLogService::logOutlet( logName: StockActivityLogService::LOG_TRANSFER, event: 'decrease', - description: "Stock Transfer #{$stockTransfer->hash_id} Deleted: Removed {$quantity} stock from destination outlet.", + description: "Transfer Stok #{$stockTransfer->hash_id} Dihapus: Menghapus {$quantity} stok dari outlet tujuan.", performedOn: $item->transferable, outlet: $destinationOutlet, quantityChange: -1 * abs($quantity),