CRM/backend/app/Http/Controllers/Api/NoteController.php

129 خطوط
4.9 KiB
PHP

<?php
namespace App\Http\Controllers\Api;
use App\Http\Controllers\Controller;
use App\Http\Requests\StoreCallNoteRequest;
use App\Http\Requests\UpdateNoteRequest;
use App\Http\Resources\NoteResource;
use App\Http\Responses\ApiResponse;
use App\Models\Call;
use App\Models\Note;
use App\Services\ActivityLogger;
use App\Support\EntityResolver;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Gate;
class NoteController extends Controller
{
public function callIndex(Call $call): JsonResponse
{
Gate::authorize('view', $call);
$query = $call->notesHistory()->with('user:id,name');
if (! auth()->user()->hasRole('admin')) {
$query->where(fn ($visibility) => $visibility
->where('visibility', '<>', 'private')
->orWhere('user_id', auth()->id()));
}
$notes = $query->orderByDesc('is_pinned')->latest()->get();
return ApiResponse::success($notes->map(fn (Note $note) => $this->resource($note))->all());
}
public function callStore(StoreCallNoteRequest $request, Call $call): JsonResponse
{
Gate::authorize('create', [Note::class, $call]);
$note = DB::transaction(function () use ($request, $call): Note {
$note = $call->notesHistory()->create([
'user_id' => $request->user()->id,
'content' => $request->validated('content'),
'type' => $request->validated('type', 'general'),
'visibility' => $request->validated('visibility', 'team'),
]);
ActivityLogger::log('call_note_created', "Call note {$note->id} created", $note, null, $note->only(['type', 'visibility', 'is_pinned']));
return $note;
});
return ApiResponse::success($this->resource($note->load('user:id,name')), 201, 'یادداشت تماس ثبت شد.');
}
public function store(Request $request): JsonResponse
{
$validated = $request->validate([
'entity_type' => 'required|in:lead,company,deal',
'entity_id' => 'required|integer',
'content' => 'required|string|max:5000',
]);
$model = EntityResolver::authorize($validated['entity_type'], $validated['entity_id'], 'update');
$note = DB::transaction(function () use ($model, $validated): Note {
$note = $model->notes()->create([
'user_id' => auth()->id(),
'content' => $validated['content'],
'type' => 'general',
'visibility' => 'team',
]);
ActivityLogger::log('note_created', 'یادداشت جدید ثبت شد', $note, null, $note->only(['type', 'visibility']));
return $note;
});
return ApiResponse::success($this->resource($note->load('user:id,name')), 201, 'یادداشت ثبت شد.');
}
public function update(UpdateNoteRequest $request, Note $note): JsonResponse
{
Gate::authorize('update', $note);
$updated = DB::transaction(function () use ($request, $note): Note {
$before = $note->only(['type', 'visibility', 'is_pinned']);
$note->fill($request->validated());
$note->edited_at = now();
$note->save();
ActivityLogger::log('call_note_edited', "Note {$note->id} edited", $note, $before, $note->only(['type', 'visibility', 'is_pinned']));
return $note;
});
return ApiResponse::success($this->resource($updated->load('user:id,name')), message: 'یادداشت ویرایش شد.');
}
public function destroy(Note $note): JsonResponse
{
Gate::authorize('delete', $note);
DB::transaction(function () use ($note): void {
$before = $note->only(['type', 'visibility', 'is_pinned']);
$note->delete();
ActivityLogger::log('call_note_deleted', "Note {$note->id} deleted", $note, $before, ['deleted' => true]);
});
return ApiResponse::success(null, message: 'یادداشت حذف شد.');
}
public function pin(Note $note): JsonResponse
{
return $this->setPinned($note, true);
}
public function unpin(Note $note): JsonResponse
{
return $this->setPinned($note, false);
}
private function setPinned(Note $note, bool $pinned): JsonResponse
{
Gate::authorize('pin', $note);
$note->update(['is_pinned' => $pinned]);
ActivityLogger::log($pinned ? 'call_note_pinned' : 'call_note_unpinned', "Note {$note->id} pin changed", $note, ['is_pinned' => ! $pinned], ['is_pinned' => $pinned]);
return ApiResponse::success($this->resource($note->load('user:id,name')), message: $pinned ? 'یادداشت سنجاق شد.' : 'سنجاق یادداشت برداشته شد.');
}
private function resource(Note $note): array
{
return (new NoteResource($note))->resolve(request());
}
}