feat(resources): warn before switching a resource off, and pick dates in Jalali

The deactivation warning was blocked on task 07: there was no way to count "the
appointments on this resource" until occupancy rows linked the two. They do
now, so GET /resource/{uuid} returns upcoming_appointments. It stays off the
list endpoint, where it would be one count query per row.

It is a warning, not a block, and the wording says so: switching a resource off
does not cancel anything, it only removes the resource from future searches.
The panel shows it the moment the "active" box is unticked.

The calendar's exception range still used <input type="date">, which is
Gregorian. Operators say dates in Jalali, and the mental conversion is exactly
where an exception gets recorded a day off. PersianDateInput takes the same
YYYY-MM-DD string, so this is a drop-in swap.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
hamed
2026-08-01 13:45:25 +03:30
co-authored by Claude Opus 5
parent ba7cf7edc9
commit 000cf70761
9 changed files with 164 additions and 5 deletions
@@ -2,6 +2,7 @@
namespace App\Resource\Controller;
use App\Appointment\Availability\Repository\ResourceOccupancyRepository;
use App\Auth\Entity\User;
use App\Resource\Entity\ClinicResource;
use App\Resource\Repository\ClinicResourceRepository;
@@ -28,6 +29,7 @@ class ResourceController extends BaseController
private readonly ClinicResourceRepository $resources,
private readonly ResourceService $service,
private readonly SkillAssignmentService $skills,
private readonly ResourceOccupancyRepository $occupancy,
) {}
#[Route('/api/v1/resources', name: 'resource_list', methods: ['GET'])]
@@ -85,7 +87,13 @@ class ResourceController extends BaseController
{
$this->denyUnlessGranted($user, 'view');
return $this->success($this->context->resource($user, $uuid)->toArray());
$resource = $this->context->resource($user, $uuid);
// شمار نوبت‌های آینده کنار خودِ منبع می‌آید تا پنل بتواند پیش از خاموش‌کردنش
// هشدار بدهد. در فهرست نمی‌آید — آنجا یک کوئری per ردیف می‌شد.
return $this->success($resource->toArray() + [
'upcoming_appointments' => $this->occupancy->countUpcomingAppointments((int) $resource->getId()),
]);
}
#[Route('/api/v1/resource/{uuid}', name: 'resource_update', methods: ['PATCH'])]