ultimatepos/Modules/Maintenance/Http/Controllers/Api/V1/AssetDocumentController.php

128 lines
4.5 KiB
PHP

<?php
namespace Modules\Maintenance\Http\Controllers\Api\V1;
use App\Http\Controllers\Controller;
use Modules\Maintenance\Models\AssetDocument;
use Modules\Maintenance\Models\Equipment;
use Modules\Maintenance\Models\EquipmentPart;
use Modules\Maintenance\Models\PartCatalog;
use Modules\Maintenance\Traits\ResolvesBusiness;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Storage;
class AssetDocumentController extends Controller
{
use ResolvesBusiness;
private const TYPE_MAP = [
'equipment' => Equipment::class,
'equipment_part' => EquipmentPart::class,
'part_catalog' => PartCatalog::class,
];
public function index(Request $request)
{
$business = $this->resolveBusiness($request);
if (! $business) {
return $this->jsonError('کسب‌وکار یافت نشد.', 404);
}
$request->validate([
'documentable_type' => ['required', 'string', 'in:equipment,equipment_part,part_catalog'],
'documentable_id' => ['required', 'integer'],
]);
$model = $this->resolveDocumentable($request->get('documentable_type'), (int) $request->get('documentable_id'));
if (! $model || $model->business_id !== $business->id) {
return $this->jsonError('مورد یافت نشد.', 404);
}
$docs = AssetDocument::where('business_id', $business->id)
->where('documentable_type', $model->getMorphClass())
->where('documentable_id', $model->id)
->orderBy('sort_order')
->get();
return $this->jsonSuccess(['items' => $docs]);
}
public function store(Request $request)
{
$business = $this->resolveBusiness($request);
if (! $business) {
return $this->jsonError('کسب‌وکار یافت نشد.', 404);
}
$data = $request->validate([
'documentable_type' => ['required', 'string', 'in:equipment,equipment_part,part_catalog'],
'documentable_id' => ['required', 'integer'],
'doc_type' => ['required', 'string', 'max:50'],
'title' => ['required', 'string', 'max:255'],
'file' => ['nullable', 'file', 'max:51200'],
'file_url' => ['nullable', 'url', 'max:500'],
'language' => ['nullable', 'string', 'max:10'],
'version' => ['nullable', 'string', 'max:50'],
'effective_date' => ['nullable', 'date'],
'notes' => ['nullable', 'string'],
'sort_order' => ['nullable', 'integer', 'min:0'],
]);
$model = $this->resolveDocumentable($data['documentable_type'], (int) $data['documentable_id']);
if (! $model || $model->business_id !== $business->id) {
return $this->jsonError('مورد یافت نشد.', 404);
}
$filePath = null;
$mimeType = null;
if ($request->hasFile('file')) {
$file = $request->file('file');
$filePath = $file->store("maintenance/docs/{$business->id}", 'public');
$mimeType = $file->getMimeType();
}
$doc = AssetDocument::create([
'business_id' => $business->id,
'documentable_type' => $model->getMorphClass(),
'documentable_id' => $model->id,
'doc_type' => $data['doc_type'],
'title' => $data['title'],
'file_path' => $filePath,
'file_url' => $data['file_url'] ?? null,
'mime_type' => $mimeType,
'language' => $data['language'] ?? 'fa',
'version' => $data['version'] ?? null,
'effective_date' => $data['effective_date'] ?? null,
'uploaded_by' => $request->user()?->id,
'notes' => $data['notes'] ?? null,
'sort_order' => $data['sort_order'] ?? 0,
]);
return $this->jsonSuccess($doc, 'سند ثبت شد.', 201);
}
public function destroy(Request $request, AssetDocument $assetDocument)
{
if (! $this->ensureBusinessOwnership($request, $assetDocument->business_id)) {
return $this->jsonError('دسترسی ندارید.', 403);
}
if ($assetDocument->file_path) {
Storage::disk('public')->delete($assetDocument->file_path);
}
$assetDocument->delete();
return $this->jsonSuccess(null, 'سند حذف شد.');
}
private function resolveDocumentable(string $type, int $id): ?object
{
$class = self::TYPE_MAP[$type] ?? null;
if (! $class) {
return null;
}
return $class::find($id);
}
}