From 195af1db3dbbf4a45e682539244811ea26d6f237 Mon Sep 17 00:00:00 2001 From: Helena <37183360+helenarebane@users.noreply.github.com> Date: Mon, 25 Aug 2025 11:12:57 +0300 Subject: [PATCH] MED-137: add doctor other jobs view (#55) * add doctor jobs view * change translation * another translation change * clean up * add analaysis detail view to paths config * translation * merge fix * fix path * move components to shared * refactor * imports * clean up --- .../(legal)/privacy-policy/page.tsx | 1 + .../(legal)/terms-of-service/page.tsx | 1 + app/(marketing)/_components/site-footer.tsx | 4 +- .../site-header-account-section.tsx | 8 +- app/(marketing)/_components/site-header.tsx | 2 +- app/(marketing)/blog/[slug]/page.tsx | 1 + app/(marketing)/contact/page.tsx | 1 + app/(marketing)/faq/page.tsx | 1 + app/(marketing)/layout.tsx | 2 +- app/(marketing)/page.tsx | 2 +- .../_components/company-offer-form.tsx | 2 +- app/(public)/company-offer/page.tsx | 5 +- app/(public)/layout.tsx | 1 + app/admin/_components/admin-sidebar.tsx | 4 +- app/api/billing/webhook/route.ts | 2 +- app/auth/callback/error/page.tsx | 4 +- app/auth/callback/layout.tsx | 2 +- app/auth/callback/route.ts | 3 +- app/auth/confirm/layout.tsx | 2 +- app/auth/confirm/route.ts | 3 +- .../membership-confirmation-notification.tsx | 2 +- app/auth/membership-confirmation/layout.tsx | 1 + app/auth/membership-confirmation/page.tsx | 3 +- app/auth/password-reset/layout.tsx | 2 +- app/auth/password-reset/page.tsx | 4 +- app/auth/sign-in/layout.tsx | 2 +- app/auth/sign-in/page.tsx | 4 +- app/auth/sign-up/layout.tsx | 2 +- app/auth/sign-up/page.tsx | 4 +- .../_lib/server/update-account.ts | 3 +- app/auth/update-account/layout.tsx | 1 + app/auth/update-account/page.tsx | 6 +- app/auth/verify/layout.tsx | 2 +- app/auth/verify/page.tsx | 3 +- app/doctor/_components/analysis-view.tsx | 242 ++++++++ app/doctor/_components/doctor-dashboard.tsx | 36 ++ .../doctor/_components}/doctor-guard.tsx | 2 +- app/doctor/_components/doctor-sidebar.tsx | 57 +- app/doctor/_components/mobile-navigation.tsx | 28 +- .../_components/results-table-wrapper.tsx | 120 ++++ app/doctor/_components/results-table.tsx | 322 ++++++++++ app/doctor/analysis/[id]/page.tsx | 38 ++ app/doctor/completed-jobs/page.tsx | 22 + app/doctor/my-jobs/page.tsx | 21 + app/doctor/open-jobs/page.tsx | 22 + app/doctor/page.tsx | 11 +- app/global-error.tsx | 2 +- .../_components/analysis-level-bar.tsx | 6 +- .../analysis-results/_components/analysis.tsx | 16 +- .../(dashboard)/analysis-results/page.tsx | 7 +- app/home/(user)/(dashboard)/booking/page.tsx | 1 + app/home/(user)/(dashboard)/layout.tsx | 8 +- .../order-analysis-package/page.tsx | 3 +- .../(dashboard)/order-analysis/page.tsx | 1 + .../order-health-analysis/page.tsx | 1 + .../order/[orderId]/confirmed/page.tsx | 4 +- .../(dashboard)/order/[orderId]/page.tsx | 4 +- app/home/(user)/(dashboard)/order/page.tsx | 5 +- .../_components/compare-packages-modal.tsx | 6 +- app/home/(user)/_components/dashboard.tsx | 17 +- .../_components/home-account-selector.tsx | 4 +- .../_components/home-menu-navigation.tsx | 6 +- .../_components/home-mobile-navigation.tsx | 23 +- app/home/(user)/_components/home-sidebar.tsx | 3 +- .../_components/order-analyses-cards.tsx | 2 +- .../(user)/_components/user-notifications.tsx | 7 +- .../(user)/_lib/server/load-user-analysis.ts | 6 +- .../(user)/_lib/server/load-user-workspace.ts | 2 +- .../personal-account-checkout-form.tsx | 2 +- .../billing/_lib/server/server-actions.ts | 3 +- .../_lib/server/user-billing.service.ts | 6 +- app/home/(user)/billing/layout.tsx | 2 +- app/home/(user)/billing/page.tsx | 4 +- app/home/(user)/settings/layout.tsx | 1 + app/home/(user)/settings/page.tsx | 10 +- .../team-account-accounts-selector.tsx | 4 +- .../team-account-benefit-statistics.tsx | 5 +- .../team-account-layout-mobile-navigation.tsx | 9 +- .../team-account-layout-sidebar.tsx | 4 +- .../team-account-navigation-menu.tsx | 6 +- .../team-account-notifications.tsx | 7 +- .../_components/team-account-statistics.tsx | 5 +- .../server/team-account-workspace.loader.ts | 3 +- .../team-account-checkout-form.tsx | 2 +- .../billing/_lib/server/server-actions.ts | 3 +- .../_lib/server/team-billing.service.ts | 7 +- app/home/[account]/billing/layout.tsx | 2 +- app/home/[account]/billing/page.tsx | 1 + app/home/[account]/billing/return/page.tsx | 4 +- app/home/[account]/layout.tsx | 8 +- app/home/[account]/members/page.tsx | 1 + app/home/[account]/page.tsx | 2 +- app/home/[account]/settings/page.tsx | 5 +- app/join/page.tsx | 6 +- app/layout.tsx | 4 +- app/not-found.tsx | 2 +- app/robots.ts | 2 +- app/select-package/page.tsx | 3 +- app/sitemap.xml/route.ts | 2 +- app/update-password/page.tsx | 6 +- components/med-report-logo.tsx | 11 - lib/i18n/i18n.server.ts | 4 +- lib/i18n/i18n.settings.ts | 1 + lib/root-metdata.ts | 2 +- lib/utils.ts | 8 + middleware.ts | 38 +- .../montonio-order-handler.service.ts | 2 +- packages/features/doctor/package.json | 7 +- packages/features/doctor/src/lib/helpers.ts | 21 + .../server/actions/doctor-server-actions.ts | 110 ++++ .../actions/table-data-fetching-actions.ts | 69 +++ .../doctor-analysis-detail-view.schema.ts | 78 +++ .../server/schema/doctor-analysis.schema.ts | 135 ++++ .../services/doctor-analysis.service.ts | 583 ++++++++++++++++++ .../src/lib/server/utils/doctor-action.ts | 24 + packages/features/doctor/tsconfig.json | 21 +- .../src/components/success-notification.tsx | 2 +- packages/shared/package.json | 6 +- .../src/components}/analytics-provider.tsx | 0 .../shared/src/components}/app-logo.tsx | 2 +- .../shared/src/components}/auth-provider.tsx | 3 +- .../shared/src/components}/back-button.tsx | 0 .../src/components/confirmation-modal.tsx | 52 ++ .../shared/src/components}/header-auth.tsx | 0 .../shared/src/components/med-report-logo.tsx | 20 + .../shared/src/components}/package-header.tsx | 0 .../personal-account-dropdown-container.tsx | 6 +- .../src/components}/react-query-provider.tsx | 0 .../shared/src/components}/root-providers.tsx | 14 +- .../components}/select-analysis-package.tsx | 49 +- .../components}/select-analysis-packages.tsx | 0 .../shared/src/components/table-skeleton.tsx | 41 ++ .../src/components}/ui/button-tooltip.tsx | 0 .../src/components}/ui/info-tooltip.tsx | 0 .../shared/src/components}/ui/search.tsx | 0 .../src/components}/ui/submit-button.tsx | 0 .../shared/src/config}/app.config.ts | 0 .../shared/src/config}/auth.config.ts | 0 .../shared/src/config}/billing.config.ts | 0 .../src/config}/billing.sample.config.ts | 0 .../src/config}/feature-flags.config.ts | 4 +- packages/shared/src/config/index.ts | 21 + .../shared/src/config}/paths.config.ts | 10 +- .../personal-account-navigation.config.tsx | 3 +- .../team-account-navigation.config.tsx | 4 +- packages/shared/src/utils.ts | 36 ++ packages/supabase/src/database.types.ts | 65 +- pnpm-lock.yaml | 153 ++--- public/locales/en/common.json | 7 +- public/locales/en/doctor.json | 43 ++ public/locales/et/common.json | 13 +- public/locales/et/doctor.json | 43 ++ public/locales/ru/common.json | 7 +- public/locales/ru/doctor.json | 43 ++ ...4_doctor_analysis_permission_and_table.sql | 95 +++ tsconfig.json | 55 +- 156 files changed, 2823 insertions(+), 364 deletions(-) create mode 100644 app/doctor/_components/analysis-view.tsx create mode 100644 app/doctor/_components/doctor-dashboard.tsx rename {packages/features/doctor/src/components => app/doctor/_components}/doctor-guard.tsx (92%) create mode 100644 app/doctor/_components/results-table-wrapper.tsx create mode 100644 app/doctor/_components/results-table.tsx create mode 100644 app/doctor/analysis/[id]/page.tsx create mode 100644 app/doctor/completed-jobs/page.tsx create mode 100644 app/doctor/my-jobs/page.tsx create mode 100644 app/doctor/open-jobs/page.tsx delete mode 100644 components/med-report-logo.tsx create mode 100644 packages/features/doctor/src/lib/helpers.ts create mode 100644 packages/features/doctor/src/lib/server/actions/doctor-server-actions.ts create mode 100644 packages/features/doctor/src/lib/server/actions/table-data-fetching-actions.ts create mode 100644 packages/features/doctor/src/lib/server/schema/doctor-analysis-detail-view.schema.ts create mode 100644 packages/features/doctor/src/lib/server/schema/doctor-analysis.schema.ts create mode 100644 packages/features/doctor/src/lib/server/services/doctor-analysis.service.ts create mode 100644 packages/features/doctor/src/lib/server/utils/doctor-action.ts rename {components => packages/shared/src/components}/analytics-provider.tsx (100%) rename {components => packages/shared/src/components}/app-logo.tsx (90%) rename {components => packages/shared/src/components}/auth-provider.tsx (97%) rename {components => packages/shared/src/components}/back-button.tsx (100%) create mode 100644 packages/shared/src/components/confirmation-modal.tsx rename {components => packages/shared/src/components}/header-auth.tsx (100%) create mode 100644 packages/shared/src/components/med-report-logo.tsx rename {components => packages/shared/src/components}/package-header.tsx (100%) rename {components => packages/shared/src/components}/personal-account-dropdown-container.tsx (88%) rename {components => packages/shared/src/components}/react-query-provider.tsx (100%) rename {components => packages/shared/src/components}/root-providers.tsx (82%) rename {components => packages/shared/src/components}/select-analysis-package.tsx (75%) rename {components => packages/shared/src/components}/select-analysis-packages.tsx (100%) create mode 100644 packages/shared/src/components/table-skeleton.tsx rename {components => packages/shared/src/components}/ui/button-tooltip.tsx (100%) rename {components => packages/shared/src/components}/ui/info-tooltip.tsx (100%) rename {components => packages/shared/src/components}/ui/search.tsx (100%) rename {components => packages/shared/src/components}/ui/submit-button.tsx (100%) rename {config => packages/shared/src/config}/app.config.ts (100%) rename {config => packages/shared/src/config}/auth.config.ts (100%) rename {config => packages/shared/src/config}/billing.config.ts (100%) rename {config => packages/shared/src/config}/billing.sample.config.ts (100%) rename {config => packages/shared/src/config}/feature-flags.config.ts (97%) create mode 100644 packages/shared/src/config/index.ts rename {config => packages/shared/src/config}/paths.config.ts (89%) rename {config => packages/shared/src/config}/personal-account-navigation.config.tsx (97%) rename {config => packages/shared/src/config}/team-account-navigation.config.tsx (93%) create mode 100644 public/locales/en/doctor.json create mode 100644 public/locales/et/doctor.json create mode 100644 public/locales/ru/doctor.json create mode 100644 supabase/migrations/20250814110834_doctor_analysis_permission_and_table.sql diff --git a/app/(marketing)/(legal)/privacy-policy/page.tsx b/app/(marketing)/(legal)/privacy-policy/page.tsx index b8ff856..995210d 100644 --- a/app/(marketing)/(legal)/privacy-policy/page.tsx +++ b/app/(marketing)/(legal)/privacy-policy/page.tsx @@ -2,6 +2,7 @@ import { SitePageHeader } from '~/(marketing)/_components/site-page-header'; import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; + export async function generateMetadata() { const { t } = await createI18nServerInstance(); diff --git a/app/(marketing)/(legal)/terms-of-service/page.tsx b/app/(marketing)/(legal)/terms-of-service/page.tsx index ee7d0cb..6de2269 100644 --- a/app/(marketing)/(legal)/terms-of-service/page.tsx +++ b/app/(marketing)/(legal)/terms-of-service/page.tsx @@ -2,6 +2,7 @@ import { SitePageHeader } from '~/(marketing)/_components/site-page-header'; import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; + export async function generateMetadata() { const { t } = await createI18nServerInstance(); diff --git a/app/(marketing)/_components/site-footer.tsx b/app/(marketing)/_components/site-footer.tsx index ecbba27..88ad9d8 100644 --- a/app/(marketing)/_components/site-footer.tsx +++ b/app/(marketing)/_components/site-footer.tsx @@ -1,8 +1,8 @@ import { Footer } from '@kit/ui/marketing'; import { Trans } from '@kit/ui/trans'; -import { AppLogo } from '~/components/app-logo'; -import appConfig from '~/config/app.config'; +import { AppLogo } from '@kit/shared/components/app-logo'; +import appConfig from '@kit/shared/config/app.config'; export function SiteFooter() { return ( diff --git a/app/(marketing)/_components/site-header-account-section.tsx b/app/(marketing)/_components/site-header-account-section.tsx index bc28a47..b442ab8 100644 --- a/app/(marketing)/_components/site-header-account-section.tsx +++ b/app/(marketing)/_components/site-header-account-section.tsx @@ -13,8 +13,10 @@ import { Button } from '@kit/ui/button'; import { If } from '@kit/ui/if'; import { Trans } from '@kit/ui/trans'; -import featuresFlagConfig from '~/config/feature-flags.config'; -import pathsConfig from '~/config/paths.config'; +import { featureFlagsConfig } from '@kit/shared/config'; + +import { pathsConfig } from '@kit/shared/config'; + const ModeToggle = dynamic(() => import('@kit/ui/mode-toggle').then((mod) => ({ @@ -30,7 +32,7 @@ const paths = { }; const features = { - enableThemeToggle: featuresFlagConfig.enableThemeToggle, + enableThemeToggle: featureFlagsConfig.enableThemeToggle, }; export function SiteHeaderAccountSection({ diff --git a/app/(marketing)/_components/site-header.tsx b/app/(marketing)/_components/site-header.tsx index b18a9cd..57d5192 100644 --- a/app/(marketing)/_components/site-header.tsx +++ b/app/(marketing)/_components/site-header.tsx @@ -2,7 +2,7 @@ import { UserWorkspace } from '@/app/home/(user)/_lib/server/load-user-workspace import { Header } from '@kit/ui/marketing'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; import { SiteHeaderAccountSection } from './site-header-account-section'; diff --git a/app/(marketing)/blog/[slug]/page.tsx b/app/(marketing)/blog/[slug]/page.tsx index 8c4ce1c..76d48cb 100644 --- a/app/(marketing)/blog/[slug]/page.tsx +++ b/app/(marketing)/blog/[slug]/page.tsx @@ -8,6 +8,7 @@ import { createCmsClient } from '@kit/cms'; import { withI18n } from '~/lib/i18n/with-i18n'; + import { Post } from '../../blog/_components/post'; interface BlogPageProps { diff --git a/app/(marketing)/contact/page.tsx b/app/(marketing)/contact/page.tsx index 8597d77..6a6f516 100644 --- a/app/(marketing)/contact/page.tsx +++ b/app/(marketing)/contact/page.tsx @@ -6,6 +6,7 @@ import { ContactForm } from '~/(marketing)/contact/_components/contact-form'; import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; + export async function generateMetadata() { const { t } = await createI18nServerInstance(); diff --git a/app/(marketing)/faq/page.tsx b/app/(marketing)/faq/page.tsx index 5c8beee..3fcc944 100644 --- a/app/(marketing)/faq/page.tsx +++ b/app/(marketing)/faq/page.tsx @@ -9,6 +9,7 @@ import { SitePageHeader } from '~/(marketing)/_components/site-page-header'; import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; + export const generateMetadata = async () => { const { t } = await createI18nServerInstance(); diff --git a/app/(marketing)/layout.tsx b/app/(marketing)/layout.tsx index d285e1c..5b308e2 100644 --- a/app/(marketing)/layout.tsx +++ b/app/(marketing)/layout.tsx @@ -4,7 +4,7 @@ import { SiteFooter } from '~/(marketing)/_components/site-footer'; import { SiteHeader } from '~/(marketing)/_components/site-header'; import { withI18n } from '~/lib/i18n/with-i18n'; -import { loadCurrentUserAccounts } from '../home/(user)/_lib/server/load-accounts'; +import { loadCurrentUserAccounts } from '~/home/(user)/_lib/server/load-accounts'; function SiteLayout(props: React.PropsWithChildren) { const accounts = use(loadCurrentUserAccounts()); diff --git a/app/(marketing)/page.tsx b/app/(marketing)/page.tsx index 47d1c5b..4f39285 100644 --- a/app/(marketing)/page.tsx +++ b/app/(marketing)/page.tsx @@ -1,6 +1,6 @@ import Link from 'next/link'; -import { MedReportLogo } from '@/components/med-report-logo'; +import { MedReportLogo } from '@kit/shared/components/med-report-logo'; import { ArrowRightIcon } from 'lucide-react'; import { CtaButton, Hero } from '@kit/ui/marketing'; diff --git a/app/(public)/company-offer/_components/company-offer-form.tsx b/app/(public)/company-offer/_components/company-offer-form.tsx index c8c0b6e..080b0dc 100644 --- a/app/(public)/company-offer/_components/company-offer-form.tsx +++ b/app/(public)/company-offer/_components/company-offer-form.tsx @@ -4,7 +4,7 @@ import { useState } from 'react'; import { useRouter } from 'next/navigation'; -import { SubmitButton } from '@/components/ui/submit-button'; +import { SubmitButton } from '@kit/shared/components/ui/submit-button'; import { sendCompanyOfferEmail } from '@/lib/services/mailer.service'; import { CompanySubmitData } from '@/lib/types/company'; import { companyOfferSchema } from '@/lib/validations/company-offer.schema'; diff --git a/app/(public)/company-offer/page.tsx b/app/(public)/company-offer/page.tsx index 62070b7..01cb9b7 100644 --- a/app/(public)/company-offer/page.tsx +++ b/app/(public)/company-offer/page.tsx @@ -1,8 +1,7 @@ import React from 'react'; -import { MedReportLogo } from '@/components/med-report-logo'; -import { withI18n } from '@/lib/i18n/with-i18n'; - +import { MedReportLogo } from '@kit/shared/components/med-report-logo'; +import { withI18n } from '~/lib/i18n/with-i18n'; import { Trans } from '@kit/ui/trans'; import CompanyOfferForm from './_components/company-offer-form'; diff --git a/app/(public)/layout.tsx b/app/(public)/layout.tsx index b6f3825..b897a04 100644 --- a/app/(public)/layout.tsx +++ b/app/(public)/layout.tsx @@ -1,5 +1,6 @@ import { withI18n } from '~/lib/i18n/with-i18n'; + function SiteLayout(props: React.PropsWithChildren) { return (
diff --git a/app/admin/_components/admin-sidebar.tsx b/app/admin/_components/admin-sidebar.tsx index e66c622..0492b98 100644 --- a/app/admin/_components/admin-sidebar.tsx +++ b/app/admin/_components/admin-sidebar.tsx @@ -19,8 +19,8 @@ import { useSidebar, } from '@kit/ui/shadcn-sidebar'; -import { AppLogo } from '~/components/app-logo'; -import { ProfileAccountDropdownContainer } from '~/components/personal-account-dropdown-container'; +import { AppLogo } from '@kit/shared/components/app-logo'; +import { ProfileAccountDropdownContainer } from '@kit/shared/components/personal-account-dropdown-container'; export function AdminSidebar({ accounts, diff --git a/app/api/billing/webhook/route.ts b/app/api/billing/webhook/route.ts index a38754a..d641654 100644 --- a/app/api/billing/webhook/route.ts +++ b/app/api/billing/webhook/route.ts @@ -4,7 +4,7 @@ import { enhanceRouteHandler } from '@kit/next/routes'; import { getLogger } from '@kit/shared/logger'; import { getSupabaseServerAdminClient } from '@kit/supabase/server-admin-client'; -import billingConfig from '~/config/billing.config'; +import { billingConfig } from '@kit/shared/config'; /** * @description Handle the webhooks from Stripe related to checkouts diff --git a/app/auth/callback/error/page.tsx b/app/auth/callback/error/page.tsx index ef70846..1d10580 100644 --- a/app/auth/callback/error/page.tsx +++ b/app/auth/callback/error/page.tsx @@ -7,9 +7,11 @@ import { Alert, AlertDescription, AlertTitle } from '@kit/ui/alert'; import { Button } from '@kit/ui/button'; import { Trans } from '@kit/ui/trans'; -import pathsConfig from '~/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; + import { withI18n } from '~/lib/i18n/with-i18n'; + interface AuthCallbackErrorPageProps { searchParams: Promise<{ error: string; diff --git a/app/auth/callback/layout.tsx b/app/auth/callback/layout.tsx index ff7b33b..1efc0a4 100644 --- a/app/auth/callback/layout.tsx +++ b/app/auth/callback/layout.tsx @@ -1,6 +1,6 @@ import { AuthLayoutShell } from '@kit/auth/shared'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; function AuthLayout({ children }: React.PropsWithChildren) { return {children}; diff --git a/app/auth/callback/route.ts b/app/auth/callback/route.ts index e8aa56a..0786a08 100644 --- a/app/auth/callback/route.ts +++ b/app/auth/callback/route.ts @@ -4,7 +4,8 @@ import type { NextRequest } from 'next/server'; import { createAuthCallbackService } from '@kit/supabase/auth'; import { getSupabaseServerClient } from '@kit/supabase/server-client'; -import pathsConfig from '~/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; + export async function GET(request: NextRequest) { const service = createAuthCallbackService(getSupabaseServerClient()); diff --git a/app/auth/confirm/layout.tsx b/app/auth/confirm/layout.tsx index ff7b33b..1efc0a4 100644 --- a/app/auth/confirm/layout.tsx +++ b/app/auth/confirm/layout.tsx @@ -1,6 +1,6 @@ import { AuthLayoutShell } from '@kit/auth/shared'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; function AuthLayout({ children }: React.PropsWithChildren) { return {children}; diff --git a/app/auth/confirm/route.ts b/app/auth/confirm/route.ts index ac5cc8b..db0ef3f 100644 --- a/app/auth/confirm/route.ts +++ b/app/auth/confirm/route.ts @@ -3,7 +3,8 @@ import { NextRequest, NextResponse } from 'next/server'; import { createAuthCallbackService } from '@kit/supabase/auth'; import { getSupabaseServerClient } from '@kit/supabase/server-client'; -import pathsConfig from '~/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; + export async function GET(request: NextRequest) { const service = createAuthCallbackService(getSupabaseServerClient()); diff --git a/app/auth/membership-confirmation/_components/membership-confirmation-notification.tsx b/app/auth/membership-confirmation/_components/membership-confirmation-notification.tsx index bd681a5..4229e32 100644 --- a/app/auth/membership-confirmation/_components/membership-confirmation-notification.tsx +++ b/app/auth/membership-confirmation/_components/membership-confirmation-notification.tsx @@ -2,7 +2,7 @@ import React from 'react'; -import pathsConfig from '@/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; import { useTranslation } from 'react-i18next'; import { usePersonalAccountData } from '@kit/accounts/hooks/use-personal-account-data'; diff --git a/app/auth/membership-confirmation/layout.tsx b/app/auth/membership-confirmation/layout.tsx index e3d32c7..c024555 100644 --- a/app/auth/membership-confirmation/layout.tsx +++ b/app/auth/membership-confirmation/layout.tsx @@ -1,5 +1,6 @@ import { withI18n } from '~/lib/i18n/with-i18n'; + async function SiteLayout(props: React.PropsWithChildren) { return (
diff --git a/app/auth/membership-confirmation/page.tsx b/app/auth/membership-confirmation/page.tsx index c6aef9b..f4ae5fe 100644 --- a/app/auth/membership-confirmation/page.tsx +++ b/app/auth/membership-confirmation/page.tsx @@ -1,7 +1,6 @@ import { redirect } from 'next/navigation'; -import pathsConfig from '@/config/paths.config'; - +import { pathsConfig } from '@kit/shared/config'; import { getSupabaseServerClient } from '@kit/supabase/server-client'; import { withI18n } from '~/lib/i18n/with-i18n'; diff --git a/app/auth/password-reset/layout.tsx b/app/auth/password-reset/layout.tsx index ff7b33b..1efc0a4 100644 --- a/app/auth/password-reset/layout.tsx +++ b/app/auth/password-reset/layout.tsx @@ -1,6 +1,6 @@ import { AuthLayoutShell } from '@kit/auth/shared'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; function AuthLayout({ children }: React.PropsWithChildren) { return {children}; diff --git a/app/auth/password-reset/page.tsx b/app/auth/password-reset/page.tsx index 1447373..aaa1a5f 100644 --- a/app/auth/password-reset/page.tsx +++ b/app/auth/password-reset/page.tsx @@ -5,10 +5,12 @@ import { Button } from '@kit/ui/button'; import { Heading } from '@kit/ui/heading'; import { Trans } from '@kit/ui/trans'; -import pathsConfig from '~/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; + import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; + export const generateMetadata = async () => { const { t } = await createI18nServerInstance(); diff --git a/app/auth/sign-in/layout.tsx b/app/auth/sign-in/layout.tsx index ff7b33b..1efc0a4 100644 --- a/app/auth/sign-in/layout.tsx +++ b/app/auth/sign-in/layout.tsx @@ -1,6 +1,6 @@ import { AuthLayoutShell } from '@kit/auth/shared'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; function AuthLayout({ children }: React.PropsWithChildren) { return {children}; diff --git a/app/auth/sign-in/page.tsx b/app/auth/sign-in/page.tsx index 4fc9223..3728b38 100644 --- a/app/auth/sign-in/page.tsx +++ b/app/auth/sign-in/page.tsx @@ -1,14 +1,12 @@ import Link from 'next/link'; -import { register } from 'module'; import { SignInMethodsContainer } from '@kit/auth/sign-in'; +import { authConfig, pathsConfig } from '@kit/shared/config'; import { Button } from '@kit/ui/button'; import { Heading } from '@kit/ui/heading'; import { Trans } from '@kit/ui/trans'; -import authConfig from '~/config/auth.config'; -import pathsConfig from '~/config/paths.config'; import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; diff --git a/app/auth/sign-up/layout.tsx b/app/auth/sign-up/layout.tsx index ff7b33b..1efc0a4 100644 --- a/app/auth/sign-up/layout.tsx +++ b/app/auth/sign-up/layout.tsx @@ -1,6 +1,6 @@ import { AuthLayoutShell } from '@kit/auth/shared'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; function AuthLayout({ children }: React.PropsWithChildren) { return {children}; diff --git a/app/auth/sign-up/page.tsx b/app/auth/sign-up/page.tsx index 61acc81..5c0a4e2 100644 --- a/app/auth/sign-up/page.tsx +++ b/app/auth/sign-up/page.tsx @@ -1,13 +1,13 @@ import Link from 'next/link'; import { SignUpMethodsContainer } from '@kit/auth/sign-up'; +import { authConfig, pathsConfig } from '@kit/shared/config'; import { Button } from '@kit/ui/button'; import { Heading } from '@kit/ui/heading'; import { Trans } from '@kit/ui/trans'; -import authConfig from '~/config/auth.config'; -import pathsConfig from '~/config/paths.config'; import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; + import { withI18n } from '~/lib/i18n/with-i18n'; export const generateMetadata = async () => { diff --git a/app/auth/update-account/_lib/server/update-account.ts b/app/auth/update-account/_lib/server/update-account.ts index a7a424a..e2fcd0f 100644 --- a/app/auth/update-account/_lib/server/update-account.ts +++ b/app/auth/update-account/_lib/server/update-account.ts @@ -8,7 +8,8 @@ import { AccountSubmitData, createAuthApi } from '@kit/auth/api'; import { enhanceAction } from '@kit/next/actions'; import { getSupabaseServerClient } from '@kit/supabase/server-client'; -import pathsConfig from '~/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; + import { UpdateAccountSchema } from '../schemas/update-account.schema'; diff --git a/app/auth/update-account/layout.tsx b/app/auth/update-account/layout.tsx index 8212f3c..d9687a8 100644 --- a/app/auth/update-account/layout.tsx +++ b/app/auth/update-account/layout.tsx @@ -1,5 +1,6 @@ import { withI18n } from '~/lib/i18n/with-i18n'; + async function SiteLayout(props: React.PropsWithChildren) { return (
diff --git a/app/auth/update-account/page.tsx b/app/auth/update-account/page.tsx index c594570..28a6395 100644 --- a/app/auth/update-account/page.tsx +++ b/app/auth/update-account/page.tsx @@ -1,11 +1,11 @@ import { redirect } from 'next/navigation'; -import { BackButton } from '@/components/back-button'; -import { MedReportLogo } from '@/components/med-report-logo'; -import pathsConfig from '@/config/paths.config'; import { signOutAction } from '@/lib/actions/sign-out'; import { getSupabaseServerClient } from '@/packages/supabase/src/clients/server-client'; +import { BackButton } from '@kit/shared/components/back-button'; +import { MedReportLogo } from '@kit/shared/components/med-report-logo'; +import { pathsConfig } from '@kit/shared/config'; import { Trans } from '@kit/ui/trans'; import { withI18n } from '~/lib/i18n/with-i18n'; diff --git a/app/auth/verify/layout.tsx b/app/auth/verify/layout.tsx index ff7b33b..1efc0a4 100644 --- a/app/auth/verify/layout.tsx +++ b/app/auth/verify/layout.tsx @@ -1,6 +1,6 @@ import { AuthLayoutShell } from '@kit/auth/shared'; -import { AppLogo } from '~/components/app-logo'; +import { AppLogo } from '@kit/shared/components/app-logo'; function AuthLayout({ children }: React.PropsWithChildren) { return {children}; diff --git a/app/auth/verify/page.tsx b/app/auth/verify/page.tsx index 2bddfa4..abc9203 100644 --- a/app/auth/verify/page.tsx +++ b/app/auth/verify/page.tsx @@ -4,7 +4,8 @@ import { MultiFactorChallengeContainer } from '@kit/auth/mfa'; import { checkRequiresMultiFactorAuthentication } from '@kit/supabase/check-requires-mfa'; import { getSupabaseServerClient } from '@kit/supabase/server-client'; -import pathsConfig from '~/config/paths.config'; +import { pathsConfig } from '@kit/shared/config'; + import { createI18nServerInstance } from '~/lib/i18n/i18n.server'; import { withI18n } from '~/lib/i18n/with-i18n'; diff --git a/app/doctor/_components/analysis-view.tsx b/app/doctor/_components/analysis-view.tsx new file mode 100644 index 0000000..2d43d7f --- /dev/null +++ b/app/doctor/_components/analysis-view.tsx @@ -0,0 +1,242 @@ +'use client'; + +import { useState } from 'react'; + +import { zodResolver } from '@hookform/resolvers/zod'; +import { useQueryClient } from '@tanstack/react-query'; +import { useForm } from 'react-hook-form'; + +import { giveFeedbackAction } from '@kit/doctor/actions/doctor-server-actions'; +import { + getDOBWithAgeStringFromPersonalCode, + getResultSetName, +} from '@kit/doctor/lib/helpers'; +import { + AnalysisResponse, + DoctorFeedback, + Order, + Patient, +} from '@kit/doctor/schema/doctor-analysis-detail-view.schema'; +import { + DoctorAnalysisFeedbackForm, + doctorAnalysisFeedbackSchema, +} from '@kit/doctor/schema/doctor-analysis.schema'; +import ConfirmationModal from '@kit/shared/components/confirmation-modal'; +import { getFullName } from '@kit/shared/utils'; +import { useUser } from '@kit/supabase/hooks/use-user'; +import { Button } from '@kit/ui/button'; +import { + Form, + FormControl, + FormField, + FormItem, + FormMessage, +} from '@kit/ui/form'; +import { toast } from '@kit/ui/sonner'; +import { Textarea } from '@kit/ui/textarea'; +import { Trans } from '@kit/ui/trans'; + +import Analysis from '~/home/(user)/(dashboard)/analysis-results/_components/analysis'; +import { bmiFromMetric } from '~/lib/utils'; + +export default function AnalysisView({ + patient, + order, + analyses, + feedback, +}: { + patient: Patient; + order: Order; + analyses: AnalysisResponse[]; + feedback?: DoctorFeedback; +}) { + const [isConfirmOpen, setIsConfirmOpen] = useState(false); + + const { data: user } = useUser(); + + const isInProgress = + !!feedback?.status && + feedback?.doctor_user_id && + feedback?.status !== 'COMPLETED'; + const isReadOnly = + !isInProgress || + (!!feedback?.doctor_user_id && feedback?.doctor_user_id !== user?.id); + + const form = useForm({ + resolver: zodResolver(doctorAnalysisFeedbackSchema), + defaultValues: { + feedbackValue: feedback?.value ?? '', + userId: patient.userId, + }, + }); + + const queryClient = useQueryClient(); + + if (!patient || !order || !analyses) { + return null; + } + + const onSubmit = async ( + data: DoctorAnalysisFeedbackForm, + status: 'DRAFT' | 'COMPLETED', + ) => { + try { + const feedbackPromise = giveFeedbackAction({ + ...data, + analysisOrderId: order.analysisOrderId, + status, + }); + + toast.promise(() => feedbackPromise, { + success: , + error: , + loading: , + }); + + queryClient.invalidateQueries({ + predicate: (query) => query.queryKey.includes('doctor-jobs'), + }); + + return setIsConfirmOpen(false); + } catch (error) { + toast.error(); + } + }; + + const handleDraftSubmit = () => { + const formData = form.getValues(); + onSubmit(formData, 'DRAFT'); + }; + + const handleCompleteSubmit = () => { + setIsConfirmOpen(true); + }; + + const confirmComplete = () => { + const formData = form.getValues(); + onSubmit(formData, 'COMPLETED'); + }; + + return ( + <> +

+ +

+
+
+ +
+
{getFullName(patient.firstName, patient.lastName)}
+
+ +
+
{patient.personalCode ?? ''}
+
+ +
+
{getDOBWithAgeStringFromPersonalCode(patient.personalCode)}
+
+ +
+
{patient.height}
+
+ +
+
{patient.weight}
+
+ +
+
{bmiFromMetric(patient?.height ?? 0, patient?.weight ?? 0)}
+
+ +
+
+
+ +
+
{patient.phone}
+
+ +
+
{patient.email}
+
+ +

+ +

+
+ {analyses.map((analysisData) => { + return ( + + ); + })} +
+ +

+ +

+ +

{feedback?.value ?? '-'}

+ + {!isReadOnly && ( +
+ + ( + + +