128 lines
4.7 KiB
PHP
128 lines
4.7 KiB
PHP
<?php
|
|
|
|
namespace App\Modules\Maintenance\Services;
|
|
|
|
use App\Business;
|
|
use App\Modules\Maintenance\Models\Equipment;
|
|
use App\Modules\Maintenance\Models\FailureReport;
|
|
use App\Modules\Maintenance\Models\Overhaul;
|
|
use App\Modules\Maintenance\Models\SparePartConsumption;
|
|
use App\Modules\Maintenance\Models\WorkOrder;
|
|
use Carbon\Carbon;
|
|
use Illuminate\Support\Collection;
|
|
|
|
class MaintenanceReportService
|
|
{
|
|
public function equipmentCostReport(Business $business, ?int $equipmentId = null): Collection
|
|
{
|
|
$query = WorkOrder::where('business_id', $business->id)
|
|
->where('status', 'completed')
|
|
->with('equipment:id,name,code');
|
|
|
|
if ($equipmentId) {
|
|
$query->where('equipment_id', $equipmentId);
|
|
}
|
|
|
|
return $query->get()
|
|
->groupBy('equipment_id')
|
|
->map(fn ($orders, $eqId) => [
|
|
'equipment_id' => (int) $eqId,
|
|
'equipment' => $orders->first()->equipment,
|
|
'total_cost' => (int) $orders->sum('cost'),
|
|
'work_order_count' => $orders->count(),
|
|
])
|
|
->values();
|
|
}
|
|
|
|
public function downtimeReport(Business $business, ?string $from = null, ?string $to = null): Collection
|
|
{
|
|
$query = FailureReport::where('business_id', $business->id)->with('equipment:id,name,code');
|
|
|
|
if ($from) {
|
|
$query->where('reported_at', '>=', $from);
|
|
}
|
|
if ($to) {
|
|
$query->where('reported_at', '<=', $to);
|
|
}
|
|
|
|
return $query->get()->map(fn ($r) => [
|
|
'equipment' => $r->equipment,
|
|
'failure_type' => $r->failure_type,
|
|
'downtime_hours' => (float) $r->downtime_hours,
|
|
'repair_hours' => (float) $r->repair_hours,
|
|
'cost' => (int) $r->cost,
|
|
'reported_at' => $r->reported_at?->toDateTimeString(),
|
|
]);
|
|
}
|
|
|
|
public function technicianPerformance(Business $business): Collection
|
|
{
|
|
return WorkOrder::where('business_id', $business->id)
|
|
->where('status', 'completed')
|
|
->whereNotNull('assigned_technician_id')
|
|
->with('assignedTechnician:id,name')
|
|
->get()
|
|
->groupBy('assigned_technician_id')
|
|
->map(fn ($orders, $techId) => [
|
|
'technician_id' => (int) $techId,
|
|
'technician' => $orders->first()->assignedTechnician,
|
|
'completed_count' => $orders->count(),
|
|
'total_labor_hours' => (float) $orders->sum('labor_hours'),
|
|
'total_cost' => (int) $orders->sum('cost'),
|
|
])
|
|
->values();
|
|
}
|
|
|
|
public function sparePartsConsumption(Business $business, ?string $from = null, ?string $to = null): Collection
|
|
{
|
|
$query = SparePartConsumption::where('business_id', $business->id)
|
|
->with(['sparePart:id,part_number,name', 'equipment:id,name']);
|
|
|
|
if ($from) {
|
|
$query->where('created_at', '>=', $from);
|
|
}
|
|
if ($to) {
|
|
$query->where('created_at', '<=', $to);
|
|
}
|
|
|
|
return $query->orderByDesc('created_at')->get();
|
|
}
|
|
|
|
public function monthlyStatistics(Business $business, int $year, int $month): array
|
|
{
|
|
$start = Carbon::create($year, $month, 1)->startOfMonth();
|
|
$end = $start->copy()->endOfMonth();
|
|
$bid = $business->id;
|
|
|
|
return [
|
|
'period' => $start->format('Y-m'),
|
|
'work_orders_completed' => WorkOrder::where('business_id', $bid)
|
|
->where('status', 'completed')
|
|
->whereBetween('completed_at', [$start, $end])
|
|
->count(),
|
|
'overhauls_completed' => Overhaul::where('business_id', $bid)
|
|
->where('status', 'completed')
|
|
->whereBetween('updated_at', [$start, $end])
|
|
->count(),
|
|
'failures' => FailureReport::where('business_id', $bid)
|
|
->whereBetween('reported_at', [$start, $end])
|
|
->count(),
|
|
'total_cost' => (int) WorkOrder::where('business_id', $bid)
|
|
->where('status', 'completed')
|
|
->whereBetween('completed_at', [$start, $end])
|
|
->sum('cost'),
|
|
'total_downtime_hours' => (float) FailureReport::where('business_id', $bid)
|
|
->whereBetween('reported_at', [$start, $end])
|
|
->sum('downtime_hours'),
|
|
];
|
|
}
|
|
|
|
public function failureAnalysis(Business $business): Collection
|
|
{
|
|
return FailureReport::where('business_id', $business->id)
|
|
->selectRaw('failure_type, count(*) as count, sum(downtime_hours) as total_downtime, sum(cost) as total_cost')
|
|
->groupBy('failure_type')
|
|
->get();
|
|
}
|
|
}
|