quantity; switch ($item->restockable_type) { case Perfume::class: $relation = 'perfumes'; break; case Product::class: $relation = 'products'; break; case Bottle::class: $relation = 'bottles'; break; default: return; } // Decrease warehouse stock $warehouseItem = $warehouse->{$relation}() ->where("{$relation}.id", $item->restockable_id) ->lockForUpdate() ->withPivot('stock') ->first(); $warehousePreviousStock = 0; if ($warehouseItem) { $warehousePreviousStock = $warehouseItem->pivot->stock ?? 0; } if ($warehousePreviousStock < $quantity) { throw new \Exception("Stok {$item->restockable->name} di gudang tidak mencukupi. Tersisa {$warehousePreviousStock}, diminta {$quantity}."); } $warehouseNewStock = $warehousePreviousStock - $quantity; $warehouse->{$relation}()->updateExistingPivot($item->restockable_id, [ 'stock' => $warehouseNewStock, ]); // Increase outlet stock $outletItem = $outlet->{$relation}() ->where("{$relation}.id", $item->restockable_id) ->lockForUpdate() ->withPivot('stock') ->first(); if ($outletItem) { $outletPreviousStock = $outletItem->pivot->stock ?? 0; $outlet->{$relation}()->updateExistingPivot($item->restockable_id, [ 'stock' => $outletPreviousStock + $quantity, ]); } else { $outletPreviousStock = 0; $outlet->{$relation}()->attach($item->restockable_id, [ 'stock' => $quantity, ]); } $outletNewStock = $outletPreviousStock + $quantity; $restock = $item->restock ?? Restock::find($item->restock_id); if ($restock) { StockActivityLogService::distribution( restock: $restock, product: $item->restockable, quantity: $quantity, warehousePreviousStock: $warehousePreviousStock, warehouseNewStock: $warehouseNewStock, outletPreviousStock: $outletPreviousStock, outletNewStock: $outletNewStock ); } } public function reverseStockTransfer($warehouse, $outlet, $item): void { $quantity = $item->quantity; switch ($item->restockable_type) { case Perfume::class: $relation = 'perfumes'; break; case Product::class: $relation = 'products'; break; case Bottle::class: $relation = 'bottles'; break; default: return; } // Return items to Warehouse $warehousePivot = $warehouse->{$relation}() ->where("{$relation}.id", $item->restockable_id) ->first(); $currentWarehouseStock = $warehousePivot?->pivot?->stock ?? 0; $newWarehouseStock = $currentWarehouseStock + $quantity; if ($warehousePivot) { $warehouse->{$relation}()->updateExistingPivot($item->restockable_id, [ 'stock' => $newWarehouseStock, ]); } else { $warehouse->{$relation}()->attach($item->restockable_id, [ 'stock' => $quantity, ]); } $restock = $item->restock ?? Restock::find($item->restock_id); if ($restock) { StockActivityLogService::logWarehouse( logName: StockActivityLogService::LOG_DISTRIBUTION, event: 'increase', description: "Restock #{$restock->hash_id} Dihapus: Mengembalikan {$quantity} stok ke Gudang.", performedOn: $item->restockable, warehouse: $warehouse, quantityChange: $quantity, previousStock: $currentWarehouseStock, newStock: $newWarehouseStock, extraProperties: ['restock_id' => $restock->id] ); } // Remove items from Outlet $outletPivot = $outlet->{$relation}() ->where("{$relation}.id", $item->restockable_id) ->first(); $currentOutletStock = $outletPivot?->pivot?->stock ?? 0; $newOutletStock = max(0, $currentOutletStock - $quantity); if ($outletPivot) { $outlet->{$relation}()->updateExistingPivot($item->restockable_id, [ 'stock' => $newOutletStock, ]); } if ($restock) { StockActivityLogService::logOutlet( logName: StockActivityLogService::LOG_DISTRIBUTION, event: 'decrease', description: "Restock #{$restock->hash_id} Dihapus: Menghapus {$quantity} stok dari Outlet.", performedOn: $item->restockable, outlet: $outlet, quantityChange: -1 * abs($quantity), previousStock: $currentOutletStock, newStock: $newOutletStock, extraProperties: ['restock_id' => $restock->id] ); } } }