@burdenoff/microfe-proserviceworld 2026.706.3 → 2026.709.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (119) hide show
  1. package/dist/dev/main.d.ts +2 -0
  2. package/dist/dev/main.d.ts.map +1 -0
  3. package/dist/generated/global-operations.d.ts +2 -0
  4. package/dist/generated/global-operations.d.ts.map +1 -0
  5. package/dist/generated/global-types.d.ts +18199 -0
  6. package/dist/generated/global-types.d.ts.map +1 -0
  7. package/dist/generated/wspace-operations.d.ts +2 -0
  8. package/dist/generated/wspace-operations.d.ts.map +1 -0
  9. package/dist/generated/wspace-types.d.ts +43046 -0
  10. package/dist/generated/wspace-types.d.ts.map +1 -0
  11. package/dist/index.d.ts +2 -0
  12. package/dist/index.d.ts.map +1 -0
  13. package/dist/index.js +3 -1
  14. package/dist/proserviceworld/ProServiceWorldRoot.d.ts +5 -0
  15. package/dist/proserviceworld/ProServiceWorldRoot.d.ts.map +1 -0
  16. package/dist/proserviceworld/ProServiceWorldRoutes.d.ts +2 -0
  17. package/dist/proserviceworld/ProServiceWorldRoutes.d.ts.map +1 -0
  18. package/dist/proserviceworld/ProServiceWorldRoutes.js +95 -42
  19. package/dist/proserviceworld/ProServiceWorldRoutes.js.map +1 -1
  20. package/dist/proserviceworld/components/DiscussionThread.d.ts +12 -0
  21. package/dist/proserviceworld/components/DiscussionThread.d.ts.map +1 -0
  22. package/dist/proserviceworld/components/FeatureFlaggedPage.d.ts +8 -0
  23. package/dist/proserviceworld/components/FeatureFlaggedPage.d.ts.map +1 -0
  24. package/dist/proserviceworld/components/FeatureFlaggedPage.js +17 -0
  25. package/dist/proserviceworld/components/FeatureFlaggedPage.js.map +1 -0
  26. package/dist/proserviceworld/components/LoadMore.d.ts +12 -0
  27. package/dist/proserviceworld/components/LoadMore.d.ts.map +1 -0
  28. package/dist/proserviceworld/components/LoadMore.js +30 -0
  29. package/dist/proserviceworld/components/LoadMore.js.map +1 -0
  30. package/dist/proserviceworld/components/TagPicker.d.ts +11 -0
  31. package/dist/proserviceworld/components/TagPicker.d.ts.map +1 -0
  32. package/dist/proserviceworld/components/TagPicker.js +31 -0
  33. package/dist/proserviceworld/components/TagPicker.js.map +1 -0
  34. package/dist/proserviceworld/components/ui.d.ts +82 -0
  35. package/dist/proserviceworld/components/ui.d.ts.map +1 -0
  36. package/dist/proserviceworld/hooks/useAnalytics.d.ts +18 -0
  37. package/dist/proserviceworld/hooks/useAnalytics.d.ts.map +1 -0
  38. package/dist/proserviceworld/hooks/useAnalytics.js +21 -0
  39. package/dist/proserviceworld/hooks/useAnalytics.js.map +1 -0
  40. package/dist/proserviceworld/hooks/useEntityComments.d.ts +27 -0
  41. package/dist/proserviceworld/hooks/useEntityComments.d.ts.map +1 -0
  42. package/dist/proserviceworld/hooks/useFiles.d.ts +23 -0
  43. package/dist/proserviceworld/hooks/useFiles.d.ts.map +1 -0
  44. package/dist/proserviceworld/hooks/usePageViewAnalytics.d.ts +10 -0
  45. package/dist/proserviceworld/hooks/usePageViewAnalytics.d.ts.map +1 -0
  46. package/dist/proserviceworld/hooks/usePageViewAnalytics.js +24 -0
  47. package/dist/proserviceworld/hooks/usePageViewAnalytics.js.map +1 -0
  48. package/dist/proserviceworld/hooks/useProServiceWorldApi.d.ts +351 -0
  49. package/dist/proserviceworld/hooks/useProServiceWorldApi.d.ts.map +1 -0
  50. package/dist/proserviceworld/hooks/useProServiceWorldApi.js +47 -27
  51. package/dist/proserviceworld/hooks/useProServiceWorldApi.js.map +1 -1
  52. package/dist/proserviceworld/i18n/index.d.ts +13 -0
  53. package/dist/proserviceworld/i18n/index.d.ts.map +1 -0
  54. package/dist/proserviceworld/i18n/index.js +171 -0
  55. package/dist/proserviceworld/i18n/index.js.map +1 -0
  56. package/dist/proserviceworld/index.d.ts +6 -0
  57. package/dist/proserviceworld/index.d.ts.map +1 -0
  58. package/dist/proserviceworld/index.js +2 -0
  59. package/dist/proserviceworld/pages/AnalyticsPage.d.ts +4 -0
  60. package/dist/proserviceworld/pages/AnalyticsPage.d.ts.map +1 -0
  61. package/dist/proserviceworld/pages/ClientDetailPage.d.ts +4 -0
  62. package/dist/proserviceworld/pages/ClientDetailPage.d.ts.map +1 -0
  63. package/dist/proserviceworld/pages/ClientsPage.d.ts +9 -0
  64. package/dist/proserviceworld/pages/ClientsPage.d.ts.map +1 -0
  65. package/dist/proserviceworld/pages/ClientsPage.js +218 -155
  66. package/dist/proserviceworld/pages/ClientsPage.js.map +1 -1
  67. package/dist/proserviceworld/pages/CompliancePage.d.ts +4 -0
  68. package/dist/proserviceworld/pages/CompliancePage.d.ts.map +1 -0
  69. package/dist/proserviceworld/pages/ConflictsPage.d.ts +4 -0
  70. package/dist/proserviceworld/pages/ConflictsPage.d.ts.map +1 -0
  71. package/dist/proserviceworld/pages/DashboardPage.d.ts +4 -0
  72. package/dist/proserviceworld/pages/DashboardPage.d.ts.map +1 -0
  73. package/dist/proserviceworld/pages/DocumentsPage.d.ts +4 -0
  74. package/dist/proserviceworld/pages/DocumentsPage.d.ts.map +1 -0
  75. package/dist/proserviceworld/pages/EngagementDetailPage.d.ts +4 -0
  76. package/dist/proserviceworld/pages/EngagementDetailPage.d.ts.map +1 -0
  77. package/dist/proserviceworld/pages/EngagementDetailPage.js +162 -156
  78. package/dist/proserviceworld/pages/EngagementDetailPage.js.map +1 -1
  79. package/dist/proserviceworld/pages/EngagementsPage.d.ts +4 -0
  80. package/dist/proserviceworld/pages/EngagementsPage.d.ts.map +1 -0
  81. package/dist/proserviceworld/pages/EngagementsPage.js +201 -140
  82. package/dist/proserviceworld/pages/EngagementsPage.js.map +1 -1
  83. package/dist/proserviceworld/pages/InvoicesPage.d.ts +4 -0
  84. package/dist/proserviceworld/pages/InvoicesPage.d.ts.map +1 -0
  85. package/dist/proserviceworld/pages/MattersPage.d.ts +4 -0
  86. package/dist/proserviceworld/pages/MattersPage.d.ts.map +1 -0
  87. package/dist/proserviceworld/pages/MattersPage.js +212 -158
  88. package/dist/proserviceworld/pages/MattersPage.js.map +1 -1
  89. package/dist/proserviceworld/pages/PracticeAreasPage.d.ts +4 -0
  90. package/dist/proserviceworld/pages/PracticeAreasPage.d.ts.map +1 -0
  91. package/dist/proserviceworld/pages/TimePage.d.ts +4 -0
  92. package/dist/proserviceworld/pages/TimePage.d.ts.map +1 -0
  93. package/dist/proserviceworld/providers/ProServiceWorldProvider.d.ts +6 -0
  94. package/dist/proserviceworld/providers/ProServiceWorldProvider.d.ts.map +1 -0
  95. package/dist/proserviceworld/services/assistantApi.d.ts +74 -0
  96. package/dist/proserviceworld/services/assistantApi.d.ts.map +1 -0
  97. package/dist/proserviceworld/services/assistantApi.js +203 -0
  98. package/dist/proserviceworld/services/assistantApi.js.map +1 -0
  99. package/dist/proserviceworld/services/createSandboxAssistantTransport.d.ts +28 -0
  100. package/dist/proserviceworld/services/createSandboxAssistantTransport.d.ts.map +1 -0
  101. package/dist/proserviceworld/services/createSandboxAssistantTransport.js +120 -0
  102. package/dist/proserviceworld/services/createSandboxAssistantTransport.js.map +1 -0
  103. package/dist/proserviceworld/types/index.d.ts +57 -0
  104. package/dist/proserviceworld/types/index.d.ts.map +1 -0
  105. package/dist/proserviceworld/utils/cn.d.ts +4 -0
  106. package/dist/proserviceworld/utils/cn.d.ts.map +1 -0
  107. package/dist/proserviceworld/utils/native.d.ts +23 -0
  108. package/dist/proserviceworld/utils/native.d.ts.map +1 -0
  109. package/dist/proserviceworld/utils/native.js +14 -0
  110. package/dist/proserviceworld/utils/native.js.map +1 -0
  111. package/dist/proserviceworld/utils/nav.d.ts +6 -0
  112. package/dist/proserviceworld/utils/nav.d.ts.map +1 -0
  113. package/dist/proserviceworld/utils/navigation.d.ts +2 -0
  114. package/dist/proserviceworld/utils/navigation.d.ts.map +1 -0
  115. package/dist/proserviceworld/utils/pageContext.d.ts +12 -0
  116. package/dist/proserviceworld/utils/pageContext.d.ts.map +1 -0
  117. package/dist/proserviceworld/utils/pageContext.js +74 -0
  118. package/dist/proserviceworld/utils/pageContext.js.map +1 -0
  119. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"file":"EngagementDetailPage.js","names":[],"sources":["../../../src/proserviceworld/pages/EngagementDetailPage.tsx"],"sourcesContent":["import type { FC } from 'react';\nimport { useState } from 'react';\nimport { useParams } from 'react-router-dom';\nimport { Button } from '@burdenoff/fe-libs/ui';\nimport {\n ArrowLeft,\n ArrowRight,\n Plus,\n CheckCircle2,\n FileText,\n Flag,\n Clock,\n DollarSign,\n} from 'lucide-react';\nimport {\n useEngagement,\n useTransitionEngagement,\n useCreateDeliverable,\n useTransitionDeliverable,\n useCreateMilestone,\n useCompleteMilestone,\n useTimeEntries,\n type PswEngagementStatus,\n type PswDeliverableStatus,\n} from '../hooks/useProServiceWorldApi';\nimport { useNav } from '../utils/nav';\nimport { DiscussionThread } from '../components/DiscussionThread';\nimport {\n PageHeader,\n SectionCard,\n LoadingBlock,\n ErrorState,\n Empty,\n StatusPill,\n Modal,\n Field,\n TextInput,\n TextArea,\n NativeSelect,\n Banner,\n MetricCard,\n fmtDate,\n fmtMoney,\n fmtMinutesAsHours,\n humanize,\n} from '../components/ui';\n\n// Mirrors the svc ENGAGEMENT_TRANSITIONS state machine so we only offer valid moves.\nconst NEXT: Record<PswEngagementStatus, PswEngagementStatus[]> = {\n PROPOSAL: ['ACCEPTED', 'CANCELLED'],\n ACCEPTED: ['IN_PROGRESS', 'CANCELLED'],\n IN_PROGRESS: ['REVIEW', 'CANCELLED'],\n REVIEW: ['DELIVERED', 'IN_PROGRESS', 'CANCELLED'],\n DELIVERED: ['INVOICED', 'CANCELLED'],\n INVOICED: ['CLOSED'],\n CLOSED: [],\n CANCELLED: [],\n};\nconst DELIVERABLE_STATUSES: PswDeliverableStatus[] = [\n 'DRAFT',\n 'INTERNAL_REVIEW',\n 'CLIENT_REVIEW',\n 'ACCEPTED',\n 'REJECTED',\n];\n\nexport const EngagementDetailPage: FC = () => {\n const { id = '' } = useParams();\n const nav = useNav();\n const { data: e, isLoading, error, refetch } = useEngagement(id);\n const time = useTimeEntries({ engagementId: id });\n const transition = useTransitionEngagement();\n const [addDeliverable, setAddDeliverable] = useState(false);\n const [addMilestone, setAddMilestone] = useState(false);\n const [banner, setBanner] = useState<{ tone: 'success' | 'danger'; text: string } | null>(null);\n\n if (isLoading) return <LoadingBlock />;\n if (error) return <ErrorState error={error} onRetry={() => void refetch()} />;\n if (!e) return <Empty title=\"Engagement not found\" />;\n\n const nextStates = NEXT[e.status] ?? [];\n const loggedMinutes = (time.data?.items ?? []).reduce((sum, t) => sum + t.minutes, 0);\n\n return (\n <div className=\"space-y-6\">\n <button\n type=\"button\"\n onClick={() => nav('engagements')}\n className=\"flex items-center gap-1.5 text-sm text-text-secondary transition-colors hover:text-accent\"\n >\n <ArrowLeft className=\"h-4 w-4\" /> Back to engagements\n </button>\n\n <PageHeader\n title={e.name}\n subtitle={\n e.client ? `${e.client.name} · ${humanize(e.feeArrangement)}` : humanize(e.feeArrangement)\n }\n actions={<StatusPill status={e.status} />}\n />\n\n {banner && (\n <Banner tone={banner.tone} onClose={() => setBanner(null)}>\n {banner.text}\n </Banner>\n )}\n\n <div className=\"grid grid-cols-2 gap-3 lg:grid-cols-4\">\n <MetricCard\n label=\"Fee\"\n value={fmtMoney(e.feeAmount, e.currency)}\n hint={humanize(e.feeArrangement)}\n icon={<DollarSign className=\"h-4 w-4\" />}\n tone=\"success\"\n />\n <MetricCard\n label=\"Deliverables\"\n value={e.deliverables.length}\n icon={<FileText className=\"h-4 w-4\" />}\n tone=\"info\"\n />\n <MetricCard\n label=\"Milestones\"\n value={e.milestones.length}\n icon={<Flag className=\"h-4 w-4\" />}\n tone=\"accent\"\n />\n <MetricCard\n label=\"Time logged\"\n value={fmtMinutesAsHours(loggedMinutes)}\n hint={`${time.data?.totalCount ?? 0} entries`}\n icon={<Clock className=\"h-4 w-4\" />}\n tone=\"warning\"\n />\n </div>\n\n {nextStates.length > 0 && (\n <SectionCard title=\"Advance lifecycle\">\n <div className=\"flex flex-col gap-4 sm:flex-row sm:items-center sm:justify-between\">\n <div className=\"flex items-center gap-2 text-sm text-text-secondary\">\n <span>Currently</span>\n <StatusPill status={e.status} />\n </div>\n <div className=\"flex flex-wrap gap-2\">\n {nextStates.map((s) => {\n const isCancel = s === 'CANCELLED';\n return (\n <Button\n key={s}\n size=\"sm\"\n variant={isCancel ? 'outline' : 'default'}\n disabled={transition.isPending}\n onClick={() =>\n transition.mutate(\n { id: e.id, status: s },\n {\n onSuccess: () =>\n setBanner({ tone: 'success', text: `Moved to ${humanize(s)}.` }),\n onError: (err) =>\n setBanner({\n tone: 'danger',\n text: err instanceof Error ? err.message : 'Transition failed.',\n }),\n }\n )\n }\n >\n {humanize(s)}\n {!isCancel && <ArrowRight className=\"ml-1.5 h-4 w-4\" />}\n </Button>\n );\n })}\n </div>\n </div>\n </SectionCard>\n )}\n\n <div className=\"grid grid-cols-1 gap-4 lg:grid-cols-2\">\n <SectionCard\n title=\"Deliverables\"\n action={\n <Button size=\"sm\" variant=\"outline\" onClick={() => setAddDeliverable(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n Add\n </Button>\n }\n >\n {e.deliverables.length === 0 ? (\n <Empty\n title=\"No deliverables\"\n description=\"Track the tangible outputs of this engagement.\"\n icon={<FileText className=\"h-7 w-7\" />}\n />\n ) : (\n <ul className=\"space-y-2.5\">\n {e.deliverables.map((d) => (\n <li\n key={d.id}\n className=\"rounded-xl border border-border-seam bg-bg-canvas p-3.5 transition-colors hover:border-accent/40\"\n >\n <div className=\"flex items-start justify-between gap-3\">\n <div className=\"min-w-0\">\n <div className=\"flex items-center gap-2 text-sm font-medium text-text-primary\">\n <span className=\"truncate\">{d.name}</span>\n <span className=\"shrink-0 rounded-md bg-bg-sunken px-1.5 py-0.5 text-[10px] font-semibold text-text-tertiary\">\n v{d.version}\n </span>\n </div>\n {d.dueDate && (\n <div className=\"mt-0.5 text-xs text-text-tertiary\">\n Due {fmtDate(d.dueDate)}\n </div>\n )}\n </div>\n <DeliverableStatusSelect\n id={d.id}\n engagementId={e.id}\n status={d.status}\n onDone={() => void refetch()}\n />\n </div>\n </li>\n ))}\n </ul>\n )}\n </SectionCard>\n\n <SectionCard\n title=\"Milestones\"\n action={\n <Button size=\"sm\" variant=\"outline\" onClick={() => setAddMilestone(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n Add\n </Button>\n }\n >\n {e.milestones.length === 0 ? (\n <Empty\n title=\"No milestones\"\n description=\"Add checkpoints — some can trigger billing.\"\n icon={<Flag className=\"h-7 w-7\" />}\n />\n ) : (\n <ul className=\"space-y-2.5\">\n {e.milestones.map((m) => (\n <li\n key={m.id}\n className=\"flex items-center justify-between gap-3 rounded-xl border border-border-seam bg-bg-canvas p-3.5 transition-colors hover:border-accent/40\"\n >\n <div className=\"min-w-0\">\n <div className=\"truncate text-sm font-medium text-text-primary\">{m.name}</div>\n <div className=\"mt-0.5 text-xs text-text-tertiary\">\n {m.triggersInvoice ? `Bills ${fmtMoney(m.triggerAmount, e.currency)} · ` : ''}\n Due {fmtDate(m.dueDate)}\n </div>\n </div>\n <div className=\"flex shrink-0 items-center gap-2\">\n <StatusPill status={m.status} />\n {m.status !== 'COMPLETED' && m.status !== 'CANCELLED' && (\n <CompleteMilestoneButton\n id={m.id}\n engagementId={e.id}\n onDone={() => void refetch()}\n />\n )}\n </div>\n </li>\n ))}\n </ul>\n )}\n </SectionCard>\n </div>\n\n <div className=\"grid grid-cols-1 gap-4 lg:grid-cols-3\">\n <div className=\"lg:col-span-2\">\n <DiscussionThread entityType=\"proserviceworld-engagement\" entityId={e.id} />\n </div>\n\n <SectionCard\n title=\"Time logged\"\n description={fmtMinutesAsHours(loggedMinutes)}\n action={\n <Button size=\"sm\" variant=\"outline\" onClick={() => nav('time')}>\n <Clock className=\"mr-1.5 h-4 w-4\" />\n Log time\n </Button>\n }\n >\n {time.isLoading ? (\n <LoadingBlock label=\"Loading…\" />\n ) : !time.data || time.data.items.length === 0 ? (\n <Empty\n title=\"No time logged\"\n description=\"Time logged against this engagement will appear here.\"\n icon={<Clock className=\"h-7 w-7\" />}\n />\n ) : (\n <ul className=\"space-y-2\">\n {time.data.items.slice(0, 8).map((t) => (\n <li\n key={t.id}\n className=\"rounded-lg border border-border-seam bg-bg-canvas p-3 text-sm\"\n >\n <div className=\"flex items-center justify-between gap-2\">\n <span className=\"whitespace-nowrap text-xs text-text-tertiary\">\n {fmtDate(t.date)}\n </span>\n <span className=\"flex items-center gap-2\">\n <span className=\"font-medium text-text-primary\">\n {fmtMinutesAsHours(t.minutes)}\n </span>\n <StatusPill status={t.status} />\n </span>\n </div>\n <div className=\"mt-1 truncate text-text-secondary\">\n {t.narrative || 'Time entry'}\n </div>\n </li>\n ))}\n </ul>\n )}\n </SectionCard>\n </div>\n\n {addDeliverable && (\n <DeliverableModal\n engagementId={e.id}\n onClose={() => setAddDeliverable(false)}\n onDone={() => {\n void refetch();\n setBanner({ tone: 'success', text: 'Deliverable added.' });\n }}\n />\n )}\n {addMilestone && (\n <MilestoneModal\n engagementId={e.id}\n onClose={() => setAddMilestone(false)}\n onDone={() => {\n void refetch();\n setBanner({ tone: 'success', text: 'Milestone added.' });\n }}\n />\n )}\n </div>\n );\n};\n\nconst DeliverableStatusSelect: FC<{\n id: string;\n engagementId: string;\n status: PswDeliverableStatus;\n onDone: () => void;\n}> = ({ id, engagementId, status, onDone }) => {\n const transition = useTransitionDeliverable();\n return (\n <NativeSelect\n value={status}\n disabled={transition.isPending}\n onChange={(ev) =>\n transition.mutate(\n { id, status: ev.target.value as PswDeliverableStatus, engagementId },\n { onSuccess: onDone }\n )\n }\n className=\"w-40 shrink-0\"\n >\n {DELIVERABLE_STATUSES.map((s) => (\n <option key={s} value={s}>\n {humanize(s)}\n </option>\n ))}\n </NativeSelect>\n );\n};\n\nconst CompleteMilestoneButton: FC<{ id: string; engagementId: string; onDone: () => void }> = ({\n id,\n engagementId,\n onDone,\n}) => {\n const complete = useCompleteMilestone();\n return (\n <Button\n variant=\"ghost\"\n size=\"sm\"\n aria-label=\"Complete milestone\"\n disabled={complete.isPending}\n onClick={() => complete.mutate({ id, engagementId }, { onSuccess: onDone })}\n >\n <CheckCircle2 className=\"h-4 w-4\" />\n </Button>\n );\n};\n\nconst DeliverableModal: FC<{ engagementId: string; onClose: () => void; onDone: () => void }> = ({\n engagementId,\n onClose,\n onDone,\n}) => {\n const create = useCreateDeliverable();\n const [form, setForm] = useState({\n name: '',\n description: '',\n dueDate: '',\n acceptanceCriteria: '',\n });\n const [err, setErr] = useState<string | null>(null);\n const set = (k: keyof typeof form) => (e: { target: { value: string } }) =>\n setForm((f) => ({ ...f, [k]: e.target.value }));\n const submit = () => {\n setErr(null);\n if (!form.name.trim()) return setErr('Name is required.');\n create.mutate(\n {\n engagementId,\n name: form.name.trim(),\n description: form.description.trim() || null,\n acceptanceCriteria: form.acceptanceCriteria.trim() || null,\n dueDate: form.dueDate ? new Date(form.dueDate).toISOString() : null,\n },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n };\n return (\n <Modal\n open\n onClose={onClose}\n title=\"Add deliverable\"\n footer={\n <>\n <Button variant=\"outline\" onClick={onClose} disabled={create.isPending}>\n Cancel\n </Button>\n <Button onClick={submit} disabled={create.isPending}>\n {create.isPending ? 'Adding…' : 'Add'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Name\" required>\n <TextInput value={form.name} onChange={set('name')} placeholder=\"Draft audit report\" />\n </Field>\n <Field label=\"Due date\">\n <TextInput type=\"date\" value={form.dueDate} onChange={set('dueDate')} />\n </Field>\n <Field label=\"Acceptance criteria\">\n <TextArea value={form.acceptanceCriteria} onChange={set('acceptanceCriteria')} />\n </Field>\n <Field label=\"Description\">\n <TextArea value={form.description} onChange={set('description')} />\n </Field>\n </div>\n </Modal>\n );\n};\n\nconst MilestoneModal: FC<{ engagementId: string; onClose: () => void; onDone: () => void }> = ({\n engagementId,\n onClose,\n onDone,\n}) => {\n const create = useCreateMilestone();\n const [form, setForm] = useState({\n name: '',\n dueDate: '',\n triggerAmount: '',\n triggersInvoice: false,\n });\n const [err, setErr] = useState<string | null>(null);\n const submit = () => {\n setErr(null);\n if (!form.name.trim()) return setErr('Name is required.');\n create.mutate(\n {\n engagementId,\n name: form.name.trim(),\n dueDate: form.dueDate ? new Date(form.dueDate).toISOString() : null,\n triggerAmount: form.triggerAmount ? Number(form.triggerAmount) : 0,\n triggersInvoice: form.triggersInvoice,\n },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n };\n return (\n <Modal\n open\n onClose={onClose}\n title=\"Add milestone\"\n footer={\n <>\n <Button variant=\"outline\" onClick={onClose} disabled={create.isPending}>\n Cancel\n </Button>\n <Button onClick={submit} disabled={create.isPending}>\n {create.isPending ? 'Adding…' : 'Add'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Name\" required>\n <TextInput\n value={form.name}\n onChange={(e) => setForm((f) => ({ ...f, name: e.target.value }))}\n placeholder=\"Phase 1 sign-off\"\n />\n </Field>\n <Field label=\"Due date\">\n <TextInput\n type=\"date\"\n value={form.dueDate}\n onChange={(e) => setForm((f) => ({ ...f, dueDate: e.target.value }))}\n />\n </Field>\n <Field\n label=\"Trigger amount\"\n hint=\"Amount billed when this milestone completes (if it triggers an invoice).\"\n >\n <TextInput\n type=\"number\"\n min=\"0\"\n value={form.triggerAmount}\n onChange={(e) => setForm((f) => ({ ...f, triggerAmount: e.target.value }))}\n />\n </Field>\n <label className=\"flex items-center gap-2 text-sm text-text-secondary\">\n <input\n type=\"checkbox\"\n checked={form.triggersInvoice}\n onChange={(e) => setForm((f) => ({ ...f, triggersInvoice: e.target.checked }))}\n />\n Completing this milestone triggers an invoice\n </label>\n </div>\n </Modal>\n );\n};\n"],"mappings":"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"}
1
+ {"version":3,"file":"EngagementDetailPage.js","names":[],"sources":["../../../src/proserviceworld/pages/EngagementDetailPage.tsx"],"sourcesContent":["import type { FC } from 'react';\nimport { useState } from 'react';\nimport { useParams } from 'react-router-dom';\nimport { Button } from '@burdenoff/fe-libs/ui';\nimport {\n ArrowLeft,\n ArrowRight,\n Plus,\n CheckCircle2,\n FileText,\n Flag,\n Clock,\n DollarSign,\n} from 'lucide-react';\nimport {\n useEngagement,\n useTransitionEngagement,\n useCreateDeliverable,\n useTransitionDeliverable,\n useCreateMilestone,\n useCompleteMilestone,\n useTimeEntries,\n type PswEngagementStatus,\n type PswDeliverableStatus,\n} from '../hooks/useProServiceWorldApi';\nimport { useNav } from '../utils/nav';\nimport { useAnalytics } from '../hooks/useAnalytics';\nimport { DiscussionThread } from '../components/DiscussionThread';\nimport {\n PageHeader,\n SectionCard,\n LoadingBlock,\n ErrorState,\n Empty,\n StatusPill,\n Modal,\n Field,\n TextInput,\n TextArea,\n NativeSelect,\n Banner,\n MetricCard,\n fmtDate,\n fmtMoney,\n fmtMinutesAsHours,\n humanize,\n} from '../components/ui';\n\n// Mirrors the svc ENGAGEMENT_TRANSITIONS state machine so we only offer valid moves.\nconst NEXT: Record<PswEngagementStatus, PswEngagementStatus[]> = {\n PROPOSAL: ['ACCEPTED', 'CANCELLED'],\n ACCEPTED: ['IN_PROGRESS', 'CANCELLED'],\n IN_PROGRESS: ['REVIEW', 'CANCELLED'],\n REVIEW: ['DELIVERED', 'IN_PROGRESS', 'CANCELLED'],\n DELIVERED: ['INVOICED', 'CANCELLED'],\n INVOICED: ['CLOSED'],\n CLOSED: [],\n CANCELLED: [],\n};\nconst DELIVERABLE_STATUSES: PswDeliverableStatus[] = [\n 'DRAFT',\n 'INTERNAL_REVIEW',\n 'CLIENT_REVIEW',\n 'ACCEPTED',\n 'REJECTED',\n];\n\nexport const EngagementDetailPage: FC = () => {\n const { id = '' } = useParams();\n const nav = useNav();\n const { emitFact } = useAnalytics();\n const { data: e, isLoading, error, refetch } = useEngagement(id);\n const time = useTimeEntries({ engagementId: id });\n const transition = useTransitionEngagement();\n const [addDeliverable, setAddDeliverable] = useState(false);\n const [addMilestone, setAddMilestone] = useState(false);\n const [banner, setBanner] = useState<{ tone: 'success' | 'danger'; text: string } | null>(null);\n\n if (isLoading) return <LoadingBlock />;\n if (error) return <ErrorState error={error} onRetry={() => void refetch()} />;\n if (!e) return <Empty title=\"Engagement not found\" />;\n\n const nextStates = NEXT[e.status] ?? [];\n const loggedMinutes = (time.data?.items ?? []).reduce((sum, t) => sum + t.minutes, 0);\n\n return (\n <div className=\"space-y-6\">\n <button\n type=\"button\"\n onClick={() => nav('engagements')}\n className=\"flex items-center gap-1.5 text-sm text-text-secondary transition-colors hover:text-accent\"\n >\n <ArrowLeft className=\"h-4 w-4\" /> Back to engagements\n </button>\n\n <PageHeader\n title={e.name}\n subtitle={\n e.client ? `${e.client.name} · ${humanize(e.feeArrangement)}` : humanize(e.feeArrangement)\n }\n actions={<StatusPill status={e.status} />}\n />\n\n {banner && (\n <Banner tone={banner.tone} onClose={() => setBanner(null)}>\n {banner.text}\n </Banner>\n )}\n\n <div className=\"grid grid-cols-2 gap-3 lg:grid-cols-4\">\n <MetricCard\n label=\"Fee\"\n value={fmtMoney(e.feeAmount, e.currency)}\n hint={humanize(e.feeArrangement)}\n icon={<DollarSign className=\"h-4 w-4\" />}\n tone=\"success\"\n />\n <MetricCard\n label=\"Deliverables\"\n value={e.deliverables.length}\n icon={<FileText className=\"h-4 w-4\" />}\n tone=\"info\"\n />\n <MetricCard\n label=\"Milestones\"\n value={e.milestones.length}\n icon={<Flag className=\"h-4 w-4\" />}\n tone=\"accent\"\n />\n <MetricCard\n label=\"Time logged\"\n value={fmtMinutesAsHours(loggedMinutes)}\n hint={`${time.data?.totalCount ?? 0} entries`}\n icon={<Clock className=\"h-4 w-4\" />}\n tone=\"warning\"\n />\n </div>\n\n {nextStates.length > 0 && (\n <SectionCard title=\"Advance lifecycle\">\n <div className=\"flex flex-col gap-4 sm:flex-row sm:items-center sm:justify-between\">\n <div className=\"flex items-center gap-2 text-sm text-text-secondary\">\n <span>Currently</span>\n <StatusPill status={e.status} />\n </div>\n <div className=\"flex flex-wrap gap-2\">\n {nextStates.map((s) => {\n const isCancel = s === 'CANCELLED';\n return (\n <Button\n key={s}\n size=\"sm\"\n variant={isCancel ? 'outline' : 'default'}\n disabled={transition.isPending}\n onClick={() =>\n transition.mutate(\n { id: e.id, status: s },\n {\n onSuccess: () => {\n emitFact('psw.engagement.transitioned', {\n engagementId: e.id,\n status: s,\n });\n setBanner({ tone: 'success', text: `Moved to ${humanize(s)}.` });\n },\n onError: (err) =>\n setBanner({\n tone: 'danger',\n text: err instanceof Error ? err.message : 'Transition failed.',\n }),\n }\n )\n }\n >\n {humanize(s)}\n {!isCancel && <ArrowRight className=\"ml-1.5 h-4 w-4\" />}\n </Button>\n );\n })}\n </div>\n </div>\n </SectionCard>\n )}\n\n <div className=\"grid grid-cols-1 gap-4 lg:grid-cols-2\">\n <SectionCard\n title=\"Deliverables\"\n action={\n <Button size=\"sm\" variant=\"outline\" onClick={() => setAddDeliverable(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n Add\n </Button>\n }\n >\n {e.deliverables.length === 0 ? (\n <Empty\n title=\"No deliverables\"\n description=\"Track the tangible outputs of this engagement.\"\n icon={<FileText className=\"h-7 w-7\" />}\n />\n ) : (\n <ul className=\"space-y-2.5\">\n {e.deliverables.map((d) => (\n <li\n key={d.id}\n className=\"rounded-xl border border-border-seam bg-bg-canvas p-3.5 transition-colors hover:border-accent/40\"\n >\n <div className=\"flex items-start justify-between gap-3\">\n <div className=\"min-w-0\">\n <div className=\"flex items-center gap-2 text-sm font-medium text-text-primary\">\n <span className=\"truncate\">{d.name}</span>\n <span className=\"shrink-0 rounded-md bg-bg-sunken px-1.5 py-0.5 text-[10px] font-semibold text-text-tertiary\">\n v{d.version}\n </span>\n </div>\n {d.dueDate && (\n <div className=\"mt-0.5 text-xs text-text-tertiary\">\n Due {fmtDate(d.dueDate)}\n </div>\n )}\n </div>\n <DeliverableStatusSelect\n id={d.id}\n engagementId={e.id}\n status={d.status}\n onDone={() => void refetch()}\n />\n </div>\n </li>\n ))}\n </ul>\n )}\n </SectionCard>\n\n <SectionCard\n title=\"Milestones\"\n action={\n <Button size=\"sm\" variant=\"outline\" onClick={() => setAddMilestone(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n Add\n </Button>\n }\n >\n {e.milestones.length === 0 ? (\n <Empty\n title=\"No milestones\"\n description=\"Add checkpoints — some can trigger billing.\"\n icon={<Flag className=\"h-7 w-7\" />}\n />\n ) : (\n <ul className=\"space-y-2.5\">\n {e.milestones.map((m) => (\n <li\n key={m.id}\n className=\"flex items-center justify-between gap-3 rounded-xl border border-border-seam bg-bg-canvas p-3.5 transition-colors hover:border-accent/40\"\n >\n <div className=\"min-w-0\">\n <div className=\"truncate text-sm font-medium text-text-primary\">{m.name}</div>\n <div className=\"mt-0.5 text-xs text-text-tertiary\">\n {m.triggersInvoice ? `Bills ${fmtMoney(m.triggerAmount, e.currency)} · ` : ''}\n Due {fmtDate(m.dueDate)}\n </div>\n </div>\n <div className=\"flex shrink-0 items-center gap-2\">\n <StatusPill status={m.status} />\n {m.status !== 'COMPLETED' && m.status !== 'CANCELLED' && (\n <CompleteMilestoneButton\n id={m.id}\n engagementId={e.id}\n onDone={() => void refetch()}\n />\n )}\n </div>\n </li>\n ))}\n </ul>\n )}\n </SectionCard>\n </div>\n\n <div className=\"grid grid-cols-1 gap-4 lg:grid-cols-3\">\n <div className=\"lg:col-span-2\">\n <DiscussionThread entityType=\"proserviceworld-engagement\" entityId={e.id} />\n </div>\n\n <SectionCard\n title=\"Time logged\"\n description={fmtMinutesAsHours(loggedMinutes)}\n action={\n <Button size=\"sm\" variant=\"outline\" onClick={() => nav('time')}>\n <Clock className=\"mr-1.5 h-4 w-4\" />\n Log time\n </Button>\n }\n >\n {time.isLoading ? (\n <LoadingBlock label=\"Loading…\" />\n ) : !time.data || time.data.items.length === 0 ? (\n <Empty\n title=\"No time logged\"\n description=\"Time logged against this engagement will appear here.\"\n icon={<Clock className=\"h-7 w-7\" />}\n />\n ) : (\n <ul className=\"space-y-2\">\n {time.data.items.slice(0, 8).map((t) => (\n <li\n key={t.id}\n className=\"rounded-lg border border-border-seam bg-bg-canvas p-3 text-sm\"\n >\n <div className=\"flex items-center justify-between gap-2\">\n <span className=\"whitespace-nowrap text-xs text-text-tertiary\">\n {fmtDate(t.date)}\n </span>\n <span className=\"flex items-center gap-2\">\n <span className=\"font-medium text-text-primary\">\n {fmtMinutesAsHours(t.minutes)}\n </span>\n <StatusPill status={t.status} />\n </span>\n </div>\n <div className=\"mt-1 truncate text-text-secondary\">\n {t.narrative || 'Time entry'}\n </div>\n </li>\n ))}\n </ul>\n )}\n </SectionCard>\n </div>\n\n {addDeliverable && (\n <DeliverableModal\n engagementId={e.id}\n onClose={() => setAddDeliverable(false)}\n onDone={() => {\n void refetch();\n setBanner({ tone: 'success', text: 'Deliverable added.' });\n }}\n />\n )}\n {addMilestone && (\n <MilestoneModal\n engagementId={e.id}\n onClose={() => setAddMilestone(false)}\n onDone={() => {\n void refetch();\n setBanner({ tone: 'success', text: 'Milestone added.' });\n }}\n />\n )}\n </div>\n );\n};\n\nconst DeliverableStatusSelect: FC<{\n id: string;\n engagementId: string;\n status: PswDeliverableStatus;\n onDone: () => void;\n}> = ({ id, engagementId, status, onDone }) => {\n const transition = useTransitionDeliverable();\n return (\n <NativeSelect\n value={status}\n disabled={transition.isPending}\n onChange={(ev) =>\n transition.mutate(\n { id, status: ev.target.value as PswDeliverableStatus, engagementId },\n { onSuccess: onDone }\n )\n }\n className=\"w-40 shrink-0\"\n >\n {DELIVERABLE_STATUSES.map((s) => (\n <option key={s} value={s}>\n {humanize(s)}\n </option>\n ))}\n </NativeSelect>\n );\n};\n\nconst CompleteMilestoneButton: FC<{ id: string; engagementId: string; onDone: () => void }> = ({\n id,\n engagementId,\n onDone,\n}) => {\n const complete = useCompleteMilestone();\n return (\n <Button\n variant=\"ghost\"\n size=\"sm\"\n aria-label=\"Complete milestone\"\n disabled={complete.isPending}\n onClick={() => complete.mutate({ id, engagementId }, { onSuccess: onDone })}\n >\n <CheckCircle2 className=\"h-4 w-4\" />\n </Button>\n );\n};\n\nconst DeliverableModal: FC<{ engagementId: string; onClose: () => void; onDone: () => void }> = ({\n engagementId,\n onClose,\n onDone,\n}) => {\n const create = useCreateDeliverable();\n const [form, setForm] = useState({\n name: '',\n description: '',\n dueDate: '',\n acceptanceCriteria: '',\n });\n const [err, setErr] = useState<string | null>(null);\n const set = (k: keyof typeof form) => (e: { target: { value: string } }) =>\n setForm((f) => ({ ...f, [k]: e.target.value }));\n const submit = () => {\n setErr(null);\n if (!form.name.trim()) return setErr('Name is required.');\n create.mutate(\n {\n engagementId,\n name: form.name.trim(),\n description: form.description.trim() || null,\n acceptanceCriteria: form.acceptanceCriteria.trim() || null,\n dueDate: form.dueDate ? new Date(form.dueDate).toISOString() : null,\n },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n };\n return (\n <Modal\n open\n onClose={onClose}\n title=\"Add deliverable\"\n footer={\n <>\n <Button variant=\"outline\" onClick={onClose} disabled={create.isPending}>\n Cancel\n </Button>\n <Button onClick={submit} disabled={create.isPending}>\n {create.isPending ? 'Adding…' : 'Add'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Name\" required>\n <TextInput value={form.name} onChange={set('name')} placeholder=\"Draft audit report\" />\n </Field>\n <Field label=\"Due date\">\n <TextInput type=\"date\" value={form.dueDate} onChange={set('dueDate')} />\n </Field>\n <Field label=\"Acceptance criteria\">\n <TextArea value={form.acceptanceCriteria} onChange={set('acceptanceCriteria')} />\n </Field>\n <Field label=\"Description\">\n <TextArea value={form.description} onChange={set('description')} />\n </Field>\n </div>\n </Modal>\n );\n};\n\nconst MilestoneModal: FC<{ engagementId: string; onClose: () => void; onDone: () => void }> = ({\n engagementId,\n onClose,\n onDone,\n}) => {\n const create = useCreateMilestone();\n const [form, setForm] = useState({\n name: '',\n dueDate: '',\n triggerAmount: '',\n triggersInvoice: false,\n });\n const [err, setErr] = useState<string | null>(null);\n const submit = () => {\n setErr(null);\n if (!form.name.trim()) return setErr('Name is required.');\n create.mutate(\n {\n engagementId,\n name: form.name.trim(),\n dueDate: form.dueDate ? new Date(form.dueDate).toISOString() : null,\n triggerAmount: form.triggerAmount ? Number(form.triggerAmount) : 0,\n triggersInvoice: form.triggersInvoice,\n },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n };\n return (\n <Modal\n open\n onClose={onClose}\n title=\"Add milestone\"\n footer={\n <>\n <Button variant=\"outline\" onClick={onClose} disabled={create.isPending}>\n Cancel\n </Button>\n <Button onClick={submit} disabled={create.isPending}>\n {create.isPending ? 'Adding…' : 'Add'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Name\" required>\n <TextInput\n value={form.name}\n onChange={(e) => setForm((f) => ({ ...f, name: e.target.value }))}\n placeholder=\"Phase 1 sign-off\"\n />\n </Field>\n <Field label=\"Due date\">\n <TextInput\n type=\"date\"\n value={form.dueDate}\n onChange={(e) => setForm((f) => ({ ...f, dueDate: e.target.value }))}\n />\n </Field>\n <Field\n label=\"Trigger amount\"\n hint=\"Amount billed when this milestone completes (if it triggers an invoice).\"\n >\n <TextInput\n type=\"number\"\n min=\"0\"\n value={form.triggerAmount}\n onChange={(e) => setForm((f) => ({ ...f, triggerAmount: e.target.value }))}\n />\n </Field>\n <label className=\"flex items-center gap-2 text-sm text-text-secondary\">\n <input\n type=\"checkbox\"\n checked={form.triggersInvoice}\n onChange={(e) => setForm((f) => ({ ...f, triggersInvoice: e.target.checked }))}\n />\n Completing this milestone triggers an invoice\n </label>\n </div>\n </Modal>\n );\n};\n"],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ import { FC } from 'react';
2
+
3
+ export declare const EngagementsPage: FC;
4
+ //# sourceMappingURL=EngagementsPage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"EngagementsPage.d.ts","sourceRoot":"","sources":["../../../src/proserviceworld/pages/EngagementsPage.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAC;AAuEhC,eAAO,MAAM,eAAe,EAAE,EAsM7B,CAAC"}