ultimatepos/Modules/Maintenance/Http/Controllers/RepairDispatchController.php

179 lines
7.4 KiB
PHP

<?php
namespace Modules\Maintenance\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Routing\Controller;
use Modules\Maintenance\Http\Controllers\Concerns\AuthorizesMaintenance;
use Modules\Maintenance\Models\MaterialLine;
use Modules\Maintenance\Models\RepairDispatch;
use Modules\Maintenance\Services\MaterialListService;
use Modules\Maintenance\Services\RepairDispatchService;
use Modules\Maintenance\Utils\MaintenanceUtil;
use Yajra\DataTables\Facades\DataTables;
class RepairDispatchController extends Controller
{
use AuthorizesMaintenance;
public function __construct(
protected MaintenanceUtil $maintenanceUtil,
protected RepairDispatchService $dispatchService,
protected MaterialListService $materialService
) {}
public function index(Request $request)
{
$this->authorizeMaintenanceAccess('maintenance.repair_dispatch.view');
$business_id = $this->maintenanceUtil->getBusinessId();
if ($request->ajax()) {
$query = RepairDispatch::where('business_id', $business_id)
->with(['materialLine.sparePart', 'holdingEntity', 'orgUnit', 'serviceProvider'])
->orderByDesc('id');
if ($status = $request->get('status')) {
$query->where('status', $status);
}
if ($route = $request->get('route_type')) {
$query->where('route_type', $route);
}
$statusLabels = $this->dispatchService->statusLabels();
$routeLabels = $this->dispatchService->routeTypeLabels();
return DataTables::of($query)
->addColumn('part_name', fn ($row) => $row->materialLine?->displayName() ?? '—')
->addColumn('destination', fn ($row) => $row->destinationLabel())
->addColumn('route_label', fn ($row) => $routeLabels[$row->route_type] ?? $row->route_type)
->addColumn('status_label', fn ($row) => $statusLabels[$row->status] ?? $row->status)
->addColumn('action', function ($row) {
return '<a href="'.action([self::class, 'show'], [$row->id]).'" class="btn btn-xs btn-info"><i class="fa fa-eye"></i></a>';
})
->editColumn('sent_at', fn ($row) => $this->maintenanceUtil->formatDateTime($row->sent_at))
->editColumn('expected_return_at', fn ($row) => $this->maintenanceUtil->formatDate($row->expected_return_at))
->rawColumns(['action'])
->make(true);
}
return view('maintenance::repair_dispatches.index', [
'statuses' => $this->dispatchService->statusLabels(),
'route_types' => $this->dispatchService->routeTypeLabels(),
]);
}
public function show($id)
{
$this->authorizeMaintenanceAccess('maintenance.repair_dispatch.view');
$business_id = $this->maintenanceUtil->getBusinessId();
$dispatch = RepairDispatch::where('business_id', $business_id)
->with(['materialLine.sparePart', 'materialList', 'holdingEntity', 'orgUnit', 'serviceProvider', 'originLocation', 'events.user'])
->findOrFail($id);
return view('maintenance::repair_dispatches.show', [
'dispatch' => $dispatch,
'statuses' => $this->dispatchService->statusLabels(),
'route_types' => $this->dispatchService->routeTypeLabels(),
'next_action' => $this->dispatchService->nextActionLabel($dispatch),
'can_manage' => auth()->user()->can('maintenance.repair_dispatch.manage'),
]);
}
public function store(Request $request, int $lineId)
{
$this->authorizeMaintenanceAccess('maintenance.repair_dispatch.manage');
$business = $this->maintenanceUtil->getBusiness();
$line = MaterialLine::where('business_id', $business->id)
->with('materialList')
->findOrFail($lineId);
$data = $request->validate([
'route_type' => 'required|in:internal,external',
'holding_entity_id' => 'nullable|integer|exists:holding_entities,id',
'org_unit_id' => 'nullable|integer|exists:org_units,id',
'service_provider_id' => 'nullable|integer|exists:maintenance_service_providers,id',
'external_party_name' => 'nullable|string|max:255',
'external_address' => 'nullable|string',
'origin_location_id' => 'nullable|integer|exists:business_locations,id',
'quantity' => 'nullable|numeric|min:0.001',
'expected_return_at' => 'nullable|string',
'send_notes' => 'nullable|string',
'tracking_number_out' => 'nullable|string|max:100',
'carrier' => 'nullable|string|max:100',
]);
if (! empty($data['expected_return_at'])) {
$data['expected_return_at'] = $this->maintenanceUtil->parseInputDate($data['expected_return_at']);
}
try {
$dispatch = $this->dispatchService->createDispatch($line->materialList, $line, $data, auth()->user());
} catch (\InvalidArgumentException $e) {
return $this->maintenanceUtil->jsonOrRedirect($request, false, $e->getMessage());
}
return $this->maintenanceUtil->jsonOrRedirect(
$request,
true,
__('maintenance::lang.rd_created', ['ref' => $dispatch->dispatch_number]),
action([self::class, 'show'], [$dispatch->id])
);
}
public function advance(Request $request, $id)
{
$this->authorizeMaintenanceAccess('maintenance.repair_dispatch.manage');
$business_id = $this->maintenanceUtil->getBusinessId();
$dispatch = RepairDispatch::where('business_id', $business_id)->findOrFail($id);
$data = $request->validate([
'notes' => 'nullable|string',
'repair_report' => 'nullable|string',
'repair_cost' => 'nullable|integer|min:0',
'tracking_number_return' => 'nullable|string|max:100',
'receive_notes' => 'nullable|string',
]);
try {
$this->dispatchService->advanceStatus($dispatch, $data['notes'] ?? null, $data, auth()->user());
} catch (\InvalidArgumentException $e) {
return $this->maintenanceUtil->jsonOrRedirect($request, false, $e->getMessage());
}
return $this->maintenanceUtil->jsonOrRedirect($request, true, __('maintenance::lang.rd_status_updated'));
}
public function cancel(Request $request, $id)
{
$this->authorizeMaintenanceAccess('maintenance.repair_dispatch.manage');
$business_id = $this->maintenanceUtil->getBusinessId();
$dispatch = RepairDispatch::where('business_id', $business_id)->findOrFail($id);
$data = $request->validate(['notes' => 'nullable|string']);
try {
$this->dispatchService->cancel($dispatch, $data['notes'] ?? null, auth()->user());
} catch (\InvalidArgumentException $e) {
return $this->maintenanceUtil->jsonOrRedirect($request, false, $e->getMessage());
}
return $this->maintenanceUtil->jsonOrRedirect($request, true, __('maintenance::lang.rd_cancelled'));
}
public function orgUnits(Request $request)
{
$business_id = $this->maintenanceUtil->getBusinessId();
$entityId = $request->get('entity_id');
return response()->json([
'success' => true,
'data' => $this->maintenanceUtil->getOrgUnitsDropdown($business_id, $entityId),
]);
}
}