From e43e8ec93e6b56257e180b76ae52f349548e39e6 Mon Sep 17 00:00:00 2001 From: hamed <15238-genius.ha@users.noreply.drupalcode.org> Date: Fri, 7 Aug 2026 14:38:21 +0330 Subject: [PATCH] refactor(dashboard): drop the services list from the staff dashboard MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The assigned-services card and its stat card are gone. The staff role has one job — today's sessions — and with /admin/my-services already removed, a list of services the operator cannot act on was the last thing on the page competing with the work itself. The remaining stat card no longer stretches the page: `.stat-grid` is built for four cards and collapses to one full-width column with a single child, so the staff grid is capped. The endpoint still returns `services` and `stats.services`; the field is documented and cheap, and nothing else needed to change to stop rendering it. Co-Authored-By: Claude Opus 5 --- assets/admin/pages/DashboardPage.test.tsx | 12 +++-- assets/admin/pages/DashboardPage.tsx | 61 +++++------------------ 2 files changed, 22 insertions(+), 51 deletions(-) diff --git a/assets/admin/pages/DashboardPage.test.tsx b/assets/admin/pages/DashboardPage.test.tsx index 866fce7b..2622bb93 100644 --- a/assets/admin/pages/DashboardPage.test.tsx +++ b/assets/admin/pages/DashboardPage.test.tsx @@ -220,14 +220,20 @@ describe('داشبورد پرسنل', () => { expect(screen.getByText('محمد رستمی')).toBeInTheDocument(); }); - it('کارت جلسات لینک است و کارت سرویس‌ها نیست', async () => { + it('کارت جلسات لینک است', async () => { renderWithProviders(); const sessions = (await screen.findByText('جلسات امروز من')).closest('a'); expect(sessions).toHaveAttribute('href', '/admin/my-sessions'); + }); - // صفحهٔ «سرویس‌های من» حذف شد؛ کارتِ بدون مقصد نباید لینک باشد. - expect(screen.getByText('سرویس‌های من').closest('a')).toBeNull(); + /** سرویس‌ها کارِ اپراتور نیستند؛ داشبورد فقط کارِ امروز را نشان می‌دهد. */ + it('هیچ‌جای داشبورد سرویس‌ها را نشان نمی‌دهد', async () => { + renderWithProviders(); + await screen.findByText('محمد رسولی'); + + expect(screen.queryByText('سرویس‌های من')).not.toBeInTheDocument(); + expect(screen.queryByText('سرویس‌های تخصیص‌یافته')).not.toBeInTheDocument(); }); it('هر ردیف کار به همان جلسه می‌رود', async () => { diff --git a/assets/admin/pages/DashboardPage.tsx b/assets/admin/pages/DashboardPage.tsx index c25454e5..a76d7d38 100644 --- a/assets/admin/pages/DashboardPage.tsx +++ b/assets/admin/pages/DashboardPage.tsx @@ -1015,13 +1015,6 @@ function StaffDashboard() { hint: sessions.length > 0 ? `${formatNumber(settled)} انجام شده` : 'کاری برای امروز نیست', icon: CalendarDaysIcon, color: 'var(--warning)', bg: 'var(--warning-bg)', }, - { - to: null, - label: 'سرویس‌های من', - value: formatNumber(d.stats?.services ?? 0), - hint: 'سرویس‌هایی که مجاز به انجامشان هستید', - icon: ClockIcon, color: 'var(--info)', bg: 'var(--info-bg)', - }, ]; return ( @@ -1044,25 +1037,19 @@ function StaffDashboard() { -
- {kpiCards.map(c => { - const body = ( - <> -
- -
-
{c.label}
-
{c.value}
-
{c.hint}
- - ); - - // فقط کارتی لینک می‌شود که صفحه‌ای پشتش باشد؛ سرویس‌ها صفحهٔ جدا ندارند و - // همین‌جا پایین‌تر فهرست می‌شوند. - return c.to === null - ?
{body}
- : {body}; - })} + {/* یک کارت تنها نباید تمام عرض صفحه را بگیرد؛ `.stat-grid` برای چهار کارت + طراحی شده و با یک فرزند به یک ستونِ تمام‌عرض تبدیل می‌شود. */} +
+ {kpiCards.map(c => ( + +
+ +
+
{c.label}
+
{c.value}
+
{c.hint}
+ + ))}
@@ -1107,28 +1094,6 @@ function StaffDashboard() { )}
-
-
-

سرویس‌های تخصیص‌یافته

-
- {d.services.length === 0 ? ( -

- هنوز سرویسی به شما تخصیص نیافته است. -

- ) : ( -
- {d.services.slice(0, 5).map(s => ( -
-
-
{s.name}
-
{s.section_name}
-
-
{formatRial(s.price_rials)}
-
- ))} -
- )} -
{/* نوبتِ مستقیمِ اختصاص‌یافته فقط وقتی نشان داده می‌شود که وجود داشته باشد؛ یک جدول همیشه-خالی زیر کارِ واقعی، فقط صفحه را بلند می‌کرد. */}