@burdenoff/microfe-proserviceworld 2026.706.2 → 2026.706.3

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 (26) hide show
  1. package/dist/proserviceworld/components/DiscussionThread.js +1 -1
  2. package/dist/proserviceworld/components/DiscussionThread.js.map +1 -1
  3. package/dist/proserviceworld/components/ui.js +18 -18
  4. package/dist/proserviceworld/components/ui.js.map +1 -1
  5. package/dist/proserviceworld/hooks/useEntityComments.js.map +1 -1
  6. package/dist/proserviceworld/pages/AnalyticsPage.js +277 -111
  7. package/dist/proserviceworld/pages/AnalyticsPage.js.map +1 -1
  8. package/dist/proserviceworld/pages/ClientDetailPage.js +219 -151
  9. package/dist/proserviceworld/pages/ClientDetailPage.js.map +1 -1
  10. package/dist/proserviceworld/pages/ClientsPage.js +148 -127
  11. package/dist/proserviceworld/pages/ClientsPage.js.map +1 -1
  12. package/dist/proserviceworld/pages/CompliancePage.js +140 -96
  13. package/dist/proserviceworld/pages/CompliancePage.js.map +1 -1
  14. package/dist/proserviceworld/pages/DashboardPage.js +221 -104
  15. package/dist/proserviceworld/pages/DashboardPage.js.map +1 -1
  16. package/dist/proserviceworld/pages/EngagementDetailPage.js +211 -181
  17. package/dist/proserviceworld/pages/EngagementDetailPage.js.map +1 -1
  18. package/dist/proserviceworld/pages/EngagementsPage.js +144 -106
  19. package/dist/proserviceworld/pages/EngagementsPage.js.map +1 -1
  20. package/dist/proserviceworld/pages/InvoicesPage.js +144 -129
  21. package/dist/proserviceworld/pages/InvoicesPage.js.map +1 -1
  22. package/dist/proserviceworld/pages/MattersPage.js +163 -122
  23. package/dist/proserviceworld/pages/MattersPage.js.map +1 -1
  24. package/dist/proserviceworld/pages/TimePage.js +112 -92
  25. package/dist/proserviceworld/pages/TimePage.js.map +1 -1
  26. package/package.json +1 -1
@@ -1,55 +1,90 @@
1
1
  import { useClients as e, useComplianceChecks as t, useCreateComplianceCheck as n, useEngagements as r, useMatters as i, useResolveComplianceCheck as a } from "../hooks/useProServiceWorldApi.js";
2
- import { Banner as o, Empty as s, ErrorState as c, Field as l, LoadingBlock as u, Modal as d, NativeSelect as f, PageHeader as p, SectionCard as m, StatusPill as h, TableWrap as g, Td as _, TextArea as v, TextInput as y, Th as b, enumOptions as x, fmtDate as S, humanize as C } from "../components/ui.js";
3
- import { useState as w } from "react";
4
- import { Plus as T, ShieldCheck as E } from "lucide-react";
5
- import { Fragment as D, jsx as O, jsxs as k } from "react/jsx-runtime";
6
- import { Button as A } from "@burdenoff/fe-libs/ui";
2
+ import { Banner as o, Empty as s, ErrorState as c, Field as l, LoadingBlock as u, MetricCard as d, Modal as f, NativeSelect as p, PageHeader as m, SectionCard as h, StatusPill as g, TableWrap as _, Td as v, TextArea as y, TextInput as b, Th as x, enumOptions as S, fmtDate as C, humanize as w } from "../components/ui.js";
3
+ import { useState as T } from "react";
4
+ import { BadgeCheck as E, CheckCircle2 as D, Clock as O, Database as k, FileCheck as A, GraduationCap as j, ListChecks as M, Lock as N, Plus as P, Scale as F, ShieldCheck as I } from "lucide-react";
5
+ import { Fragment as L, jsx as R, jsxs as z } from "react/jsx-runtime";
6
+ import { Button as B } from "@burdenoff/fe-libs/ui";
7
7
  //#region src/proserviceworld/pages/CompliancePage.tsx
8
- var j = [
8
+ var V = [
9
9
  "ENGAGEMENT_ACCEPTANCE",
10
10
  "INDEPENDENCE",
11
11
  "LICENSING",
12
12
  "CONTINUING_EDUCATION",
13
13
  "DATA_RETENTION",
14
14
  "LEGAL_HOLD"
15
- ], M = [
15
+ ], H = [
16
16
  "IN_REVIEW",
17
17
  "PASSED",
18
18
  "FAILED",
19
19
  "WAIVED"
20
- ], N = [
20
+ ], U = [
21
21
  "CLIENT",
22
22
  "ENGAGEMENT",
23
23
  "MATTER"
24
- ], P = () => {
25
- let [e, n] = w(""), [r, i] = w(!1), [a, l] = w(null), [d, v] = w(null), { data: y, isLoading: D, error: j, refetch: M } = t({ status: e || void 0 });
26
- return /* @__PURE__ */ k("div", {
24
+ ], W = {
25
+ ENGAGEMENT_ACCEPTANCE: /* @__PURE__ */ R(A, { className: "h-3.5 w-3.5" }),
26
+ INDEPENDENCE: /* @__PURE__ */ R(F, { className: "h-3.5 w-3.5" }),
27
+ LICENSING: /* @__PURE__ */ R(E, { className: "h-3.5 w-3.5" }),
28
+ CONTINUING_EDUCATION: /* @__PURE__ */ R(j, { className: "h-3.5 w-3.5" }),
29
+ DATA_RETENTION: /* @__PURE__ */ R(k, { className: "h-3.5 w-3.5" }),
30
+ LEGAL_HOLD: /* @__PURE__ */ R(N, { className: "h-3.5 w-3.5" })
31
+ }, G = () => {
32
+ let [e, n] = T(""), [r, i] = T(!1), [a, l] = T(null), [f, y] = T(null), { data: b, isLoading: E, error: k, refetch: A } = t({ status: e || void 0 }), j = b ?? [], N = j.filter((e) => e.status === "PENDING").length, F = j.filter((e) => e.status === "IN_REVIEW").length, L = j.filter((e) => e.status === "PASSED" || e.status === "FAILED" || e.status === "WAIVED").length;
33
+ return /* @__PURE__ */ z("div", {
27
34
  className: "space-y-6",
28
35
  children: [
29
- /* @__PURE__ */ O(p, {
36
+ /* @__PURE__ */ R(m, {
30
37
  title: "Compliance",
31
38
  subtitle: "The duties that travel with the work — acceptance, independence, licensing, CE, retention and legal hold — as gates, not afterthoughts.",
32
- icon: /* @__PURE__ */ O(E, { className: "h-6 w-6" }),
33
- actions: /* @__PURE__ */ k(A, {
39
+ icon: /* @__PURE__ */ R(I, { className: "h-6 w-6" }),
40
+ actions: /* @__PURE__ */ z(B, {
34
41
  onClick: () => i(!0),
35
- children: [/* @__PURE__ */ O(T, { className: "mr-1.5 h-4 w-4" }), "New check"]
42
+ children: [/* @__PURE__ */ R(P, { className: "mr-1.5 h-4 w-4" }), "New check"]
36
43
  })
37
44
  }),
38
- d && /* @__PURE__ */ O(o, {
45
+ f && /* @__PURE__ */ R(o, {
39
46
  tone: "success",
40
- onClose: () => v(null),
41
- children: d
47
+ onClose: () => y(null),
48
+ children: f
42
49
  }),
43
- /* @__PURE__ */ O("div", {
50
+ b && b.length > 0 && /* @__PURE__ */ z("div", {
51
+ className: "grid grid-cols-2 gap-3 lg:grid-cols-4",
52
+ children: [
53
+ /* @__PURE__ */ R(d, {
54
+ label: "Checks",
55
+ value: j.length,
56
+ icon: /* @__PURE__ */ R(M, { className: "h-4 w-4" })
57
+ }),
58
+ /* @__PURE__ */ R(d, {
59
+ label: "Pending",
60
+ value: N,
61
+ icon: /* @__PURE__ */ R(O, { className: "h-4 w-4" }),
62
+ tone: N ? "warning" : "neutral"
63
+ }),
64
+ /* @__PURE__ */ R(d, {
65
+ label: "In review",
66
+ value: F,
67
+ icon: /* @__PURE__ */ R(I, { className: "h-4 w-4" }),
68
+ tone: "info"
69
+ }),
70
+ /* @__PURE__ */ R(d, {
71
+ label: "Resolved",
72
+ value: L,
73
+ icon: /* @__PURE__ */ R(D, { className: "h-4 w-4" }),
74
+ tone: "success"
75
+ })
76
+ ]
77
+ }),
78
+ /* @__PURE__ */ R("div", {
44
79
  className: "flex justify-end",
45
- children: /* @__PURE__ */ k(f, {
80
+ children: /* @__PURE__ */ z(p, {
46
81
  value: e,
47
82
  onChange: (e) => n(e.target.value),
48
83
  className: "sm:w-52",
49
- children: [/* @__PURE__ */ O("option", {
84
+ children: [/* @__PURE__ */ R("option", {
50
85
  value: "",
51
86
  children: "All statuses"
52
- }), x([
87
+ }), S([
53
88
  "PENDING",
54
89
  "IN_REVIEW",
55
90
  "PASSED",
@@ -58,43 +93,52 @@ var j = [
58
93
  ])]
59
94
  })
60
95
  }),
61
- D ? /* @__PURE__ */ O(u, {}) : j ? /* @__PURE__ */ O(c, {
62
- error: j,
63
- onRetry: () => void M()
64
- }) : !y || y.length === 0 ? /* @__PURE__ */ O(s, {
96
+ E ? /* @__PURE__ */ R(u, {}) : k ? /* @__PURE__ */ R(c, {
97
+ error: k,
98
+ onRetry: () => void A()
99
+ }) : !b || b.length === 0 ? /* @__PURE__ */ R(s, {
65
100
  title: "No compliance checks",
66
101
  description: "Raise a check to gate acceptance or track a professional obligation.",
67
- icon: /* @__PURE__ */ O(E, { className: "h-8 w-8" }),
68
- action: /* @__PURE__ */ k(A, {
102
+ icon: /* @__PURE__ */ R(I, { className: "h-8 w-8" }),
103
+ action: /* @__PURE__ */ z(B, {
69
104
  onClick: () => i(!0),
70
- children: [/* @__PURE__ */ O(T, { className: "mr-1.5 h-4 w-4" }), "New check"]
105
+ children: [/* @__PURE__ */ R(P, { className: "mr-1.5 h-4 w-4" }), "New check"]
71
106
  })
72
- }) : /* @__PURE__ */ O(m, {
73
- title: `${y.length} check${y.length === 1 ? "" : "s"}`,
74
- children: /* @__PURE__ */ k(g, { children: [/* @__PURE__ */ O("thead", { children: /* @__PURE__ */ k("tr", { children: [
75
- /* @__PURE__ */ O(b, { children: "Title" }),
76
- /* @__PURE__ */ O(b, { children: "Type" }),
77
- /* @__PURE__ */ O(b, { children: "Subject" }),
78
- /* @__PURE__ */ O(b, { children: "Due" }),
79
- /* @__PURE__ */ O(b, { children: "Status" }),
80
- /* @__PURE__ */ O(b, {
107
+ }) : /* @__PURE__ */ R(h, {
108
+ title: `${b.length} check${b.length === 1 ? "" : "s"}`,
109
+ children: /* @__PURE__ */ z(_, { children: [/* @__PURE__ */ R("thead", { children: /* @__PURE__ */ z("tr", { children: [
110
+ /* @__PURE__ */ R(x, { children: "Title" }),
111
+ /* @__PURE__ */ R(x, { children: "Type" }),
112
+ /* @__PURE__ */ R(x, { children: "Subject" }),
113
+ /* @__PURE__ */ R(x, { children: "Due" }),
114
+ /* @__PURE__ */ R(x, { children: "Status" }),
115
+ /* @__PURE__ */ R(x, {
81
116
  className: "text-right",
82
117
  children: "Actions"
83
118
  })
84
- ] }) }), /* @__PURE__ */ O("tbody", { children: y.map((e) => /* @__PURE__ */ k("tr", {
85
- className: "hover:bg-bg-sunken/50",
119
+ ] }) }), /* @__PURE__ */ R("tbody", { children: b.map((e) => /* @__PURE__ */ z("tr", {
120
+ className: "transition-colors hover:bg-bg-sunken/60",
86
121
  children: [
87
- /* @__PURE__ */ O(_, { children: /* @__PURE__ */ O("span", {
122
+ /* @__PURE__ */ R(v, { children: /* @__PURE__ */ R("span", {
88
123
  className: "font-medium text-text-primary",
89
124
  children: e.title
90
125
  }) }),
91
- /* @__PURE__ */ O(_, { children: C(e.type) }),
92
- /* @__PURE__ */ O(_, { children: C(e.subjectType) }),
93
- /* @__PURE__ */ O(_, { children: S(e.dueDate) }),
94
- /* @__PURE__ */ O(_, { children: /* @__PURE__ */ O(h, { status: e.status }) }),
95
- /* @__PURE__ */ O(_, {
126
+ /* @__PURE__ */ R(v, { children: /* @__PURE__ */ z("span", {
127
+ className: "inline-flex items-center gap-2 whitespace-nowrap",
128
+ children: [/* @__PURE__ */ R("span", {
129
+ className: "flex h-6 w-6 items-center justify-center rounded-md bg-bg-sunken text-accent",
130
+ children: W[e.type]
131
+ }), w(e.type)]
132
+ }) }),
133
+ /* @__PURE__ */ R(v, { children: w(e.subjectType) }),
134
+ /* @__PURE__ */ R(v, {
135
+ className: "whitespace-nowrap",
136
+ children: C(e.dueDate)
137
+ }),
138
+ /* @__PURE__ */ R(v, { children: /* @__PURE__ */ R(g, { status: e.status }) }),
139
+ /* @__PURE__ */ R(v, {
96
140
  className: "text-right",
97
- children: e.status === "PENDING" || e.status === "IN_REVIEW" ? /* @__PURE__ */ O(A, {
141
+ children: e.status === "PENDING" || e.status === "IN_REVIEW" ? /* @__PURE__ */ R(B, {
98
142
  variant: "ghost",
99
143
  size: "sm",
100
144
  onClick: () => l({
@@ -102,60 +146,60 @@ var j = [
102
146
  title: e.title
103
147
  }),
104
148
  children: "Resolve"
105
- }) : /* @__PURE__ */ O("span", {
149
+ }) : /* @__PURE__ */ R("span", {
106
150
  className: "text-xs text-text-tertiary",
107
- children: e.resolvedAt ? S(e.resolvedAt) : ""
151
+ children: e.resolvedAt ? C(e.resolvedAt) : ""
108
152
  })
109
153
  })
110
154
  ]
111
155
  }, e.id)) })] })
112
156
  }),
113
- r && /* @__PURE__ */ O(F, {
157
+ r && /* @__PURE__ */ R(K, {
114
158
  onClose: () => i(!1),
115
159
  onDone: () => {
116
- M(), v("Compliance check created.");
160
+ A(), y("Compliance check created.");
117
161
  }
118
162
  }),
119
- a && /* @__PURE__ */ O(I, {
163
+ a && /* @__PURE__ */ R(q, {
120
164
  check: a,
121
165
  onClose: () => l(null),
122
166
  onDone: () => {
123
- M(), v("Compliance check resolved.");
167
+ A(), y("Compliance check resolved.");
124
168
  }
125
169
  })
126
170
  ]
127
171
  });
128
- }, F = ({ onClose: t, onDone: a }) => {
129
- let s = n(), [c, u] = w({
172
+ }, K = ({ onClose: t, onDone: a }) => {
173
+ let s = n(), [c, u] = T({
130
174
  type: "ENGAGEMENT_ACCEPTANCE",
131
175
  subjectType: "ENGAGEMENT",
132
176
  subjectId: "",
133
177
  title: "",
134
178
  dueDate: "",
135
179
  details: ""
136
- }), [p, m] = w(null), h = (e) => (t) => u((n) => ({
180
+ }), [d, m] = T(null), h = (e) => (t) => u((n) => ({
137
181
  ...n,
138
182
  [e]: t.target.value
139
- })), g = e({ pagination: { limit: 100 } }), _ = r({ pagination: { limit: 100 } }), b = i({ pagination: { limit: 100 } }), S = c.subjectType === "CLIENT" ? (g.data?.items ?? []).map((e) => ({
183
+ })), g = e({ pagination: { limit: 100 } }), _ = r({ pagination: { limit: 100 } }), v = i({ pagination: { limit: 100 } }), x = c.subjectType === "CLIENT" ? (g.data?.items ?? []).map((e) => ({
140
184
  id: e.id,
141
185
  label: e.name
142
186
  })) : c.subjectType === "ENGAGEMENT" ? (_.data?.items ?? []).map((e) => ({
143
187
  id: e.id,
144
188
  label: e.name
145
- })) : (b.data?.items ?? []).map((e) => ({
189
+ })) : (v.data?.items ?? []).map((e) => ({
146
190
  id: e.id,
147
191
  label: e.title
148
192
  }));
149
- return /* @__PURE__ */ O(d, {
193
+ return /* @__PURE__ */ R(f, {
150
194
  open: !0,
151
195
  onClose: t,
152
196
  title: "New compliance check",
153
- footer: /* @__PURE__ */ k(D, { children: [/* @__PURE__ */ O(A, {
197
+ footer: /* @__PURE__ */ z(L, { children: [/* @__PURE__ */ R(B, {
154
198
  variant: "outline",
155
199
  onClick: t,
156
200
  disabled: s.isPending,
157
201
  children: "Cancel"
158
- }), /* @__PURE__ */ O(A, {
202
+ }), /* @__PURE__ */ R(B, {
159
203
  onClick: () => {
160
204
  if (m(null), !c.title.trim()) return m("Title is required.");
161
205
  if (!c.subjectId) return m("Select a subject.");
@@ -176,70 +220,70 @@ var j = [
176
220
  disabled: s.isPending,
177
221
  children: s.isPending ? "Creating…" : "Create check"
178
222
  })] }),
179
- children: /* @__PURE__ */ k("div", {
223
+ children: /* @__PURE__ */ z("div", {
180
224
  className: "space-y-3",
181
225
  children: [
182
- p && /* @__PURE__ */ O(o, {
226
+ d && /* @__PURE__ */ R(o, {
183
227
  tone: "danger",
184
- children: p
228
+ children: d
185
229
  }),
186
- /* @__PURE__ */ O(l, {
230
+ /* @__PURE__ */ R(l, {
187
231
  label: "Title",
188
232
  required: !0,
189
- children: /* @__PURE__ */ O(y, {
233
+ children: /* @__PURE__ */ R(b, {
190
234
  value: c.title,
191
235
  onChange: h("title"),
192
236
  placeholder: "Independence confirmation — FY26 audit"
193
237
  })
194
238
  }),
195
- /* @__PURE__ */ O(l, {
239
+ /* @__PURE__ */ R(l, {
196
240
  label: "Type",
197
- children: /* @__PURE__ */ O(f, {
241
+ children: /* @__PURE__ */ R(p, {
198
242
  value: c.type,
199
243
  onChange: h("type"),
200
- children: x(j)
244
+ children: S(V)
201
245
  })
202
246
  }),
203
- /* @__PURE__ */ k("div", {
247
+ /* @__PURE__ */ z("div", {
204
248
  className: "grid grid-cols-2 gap-3",
205
- children: [/* @__PURE__ */ O(l, {
249
+ children: [/* @__PURE__ */ R(l, {
206
250
  label: "Subject type",
207
- children: /* @__PURE__ */ O(f, {
251
+ children: /* @__PURE__ */ R(p, {
208
252
  value: c.subjectType,
209
253
  onChange: (e) => u((t) => ({
210
254
  ...t,
211
255
  subjectType: e.target.value,
212
256
  subjectId: ""
213
257
  })),
214
- children: x(N)
258
+ children: S(U)
215
259
  })
216
- }), /* @__PURE__ */ O(l, {
260
+ }), /* @__PURE__ */ R(l, {
217
261
  label: "Subject",
218
262
  required: !0,
219
- children: /* @__PURE__ */ k(f, {
263
+ children: /* @__PURE__ */ z(p, {
220
264
  value: c.subjectId,
221
265
  onChange: h("subjectId"),
222
- children: [/* @__PURE__ */ O("option", {
266
+ children: [/* @__PURE__ */ R("option", {
223
267
  value: "",
224
268
  children: "Select…"
225
- }), S.map((e) => /* @__PURE__ */ O("option", {
269
+ }), x.map((e) => /* @__PURE__ */ R("option", {
226
270
  value: e.id,
227
271
  children: e.label
228
272
  }, e.id))]
229
273
  })
230
274
  })]
231
275
  }),
232
- /* @__PURE__ */ O(l, {
276
+ /* @__PURE__ */ R(l, {
233
277
  label: "Due date",
234
- children: /* @__PURE__ */ O(y, {
278
+ children: /* @__PURE__ */ R(b, {
235
279
  type: "date",
236
280
  value: c.dueDate,
237
281
  onChange: h("dueDate")
238
282
  })
239
283
  }),
240
- /* @__PURE__ */ O(l, {
284
+ /* @__PURE__ */ R(l, {
241
285
  label: "Details",
242
- children: /* @__PURE__ */ O(v, {
286
+ children: /* @__PURE__ */ R(y, {
243
287
  value: c.details,
244
288
  onChange: h("details")
245
289
  })
@@ -247,18 +291,18 @@ var j = [
247
291
  ]
248
292
  })
249
293
  });
250
- }, I = ({ check: e, onClose: t, onDone: n }) => {
251
- let r = a(), [i, s] = w("PASSED"), [c, u] = w(""), [p, m] = w(null);
252
- return /* @__PURE__ */ O(d, {
294
+ }, q = ({ check: e, onClose: t, onDone: n }) => {
295
+ let r = a(), [i, s] = T("PASSED"), [c, u] = T(""), [d, m] = T(null);
296
+ return /* @__PURE__ */ R(f, {
253
297
  open: !0,
254
298
  onClose: t,
255
299
  title: `Resolve: ${e.title}`,
256
- footer: /* @__PURE__ */ k(D, { children: [/* @__PURE__ */ O(A, {
300
+ footer: /* @__PURE__ */ z(L, { children: [/* @__PURE__ */ R(B, {
257
301
  variant: "outline",
258
302
  onClick: t,
259
303
  disabled: r.isPending,
260
304
  children: "Cancel"
261
- }), /* @__PURE__ */ O(A, {
305
+ }), /* @__PURE__ */ R(B, {
262
306
  onClick: () => r.mutate({
263
307
  id: e.id,
264
308
  status: i,
@@ -272,27 +316,27 @@ var j = [
272
316
  disabled: r.isPending,
273
317
  children: r.isPending ? "Saving…" : "Resolve"
274
318
  })] }),
275
- children: /* @__PURE__ */ k("div", {
319
+ children: /* @__PURE__ */ z("div", {
276
320
  className: "space-y-3",
277
321
  children: [
278
- p && /* @__PURE__ */ O(o, {
322
+ d && /* @__PURE__ */ R(o, {
279
323
  tone: "danger",
280
- children: p
324
+ children: d
281
325
  }),
282
- /* @__PURE__ */ O(l, {
326
+ /* @__PURE__ */ R(l, {
283
327
  label: "Outcome",
284
- children: /* @__PURE__ */ O(f, {
328
+ children: /* @__PURE__ */ R(p, {
285
329
  value: i,
286
330
  onChange: (e) => s(e.target.value),
287
- children: M.map((e) => /* @__PURE__ */ O("option", {
331
+ children: H.map((e) => /* @__PURE__ */ R("option", {
288
332
  value: e,
289
- children: C(e)
333
+ children: w(e)
290
334
  }, e))
291
335
  })
292
336
  }),
293
- /* @__PURE__ */ O(l, {
337
+ /* @__PURE__ */ R(l, {
294
338
  label: "Notes",
295
- children: /* @__PURE__ */ O(v, {
339
+ children: /* @__PURE__ */ R(y, {
296
340
  value: c,
297
341
  onChange: (e) => u(e.target.value)
298
342
  })
@@ -302,6 +346,6 @@ var j = [
302
346
  });
303
347
  };
304
348
  //#endregion
305
- export { P as CompliancePage };
349
+ export { G as CompliancePage };
306
350
 
307
351
  //# sourceMappingURL=CompliancePage.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"CompliancePage.js","names":[],"sources":["../../../src/proserviceworld/pages/CompliancePage.tsx"],"sourcesContent":["import type { FC } from 'react';\nimport { useState } from 'react';\nimport { Button } from '@burdenoff/fe-libs/ui';\nimport { Plus, ShieldCheck } from 'lucide-react';\nimport {\n useComplianceChecks,\n useCreateComplianceCheck,\n useResolveComplianceCheck,\n useClients,\n useEngagements,\n useMatters,\n type PswComplianceStatus,\n} from '../hooks/useProServiceWorldApi';\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 TableWrap,\n Th,\n Td,\n enumOptions,\n fmtDate,\n humanize,\n} from '../components/ui';\n\nconst TYPES = [\n 'ENGAGEMENT_ACCEPTANCE',\n 'INDEPENDENCE',\n 'LICENSING',\n 'CONTINUING_EDUCATION',\n 'DATA_RETENTION',\n 'LEGAL_HOLD',\n] as const;\nconst RESOLVE_STATUSES: PswComplianceStatus[] = ['IN_REVIEW', 'PASSED', 'FAILED', 'WAIVED'];\nconst SUBJECT_TYPES = ['CLIENT', 'ENGAGEMENT', 'MATTER'] as const;\n\nexport const CompliancePage: FC = () => {\n const [statusFilter, setStatusFilter] = useState<PswComplianceStatus | ''>('');\n const [creating, setCreating] = useState(false);\n const [resolving, setResolving] = useState<{ id: string; title: string } | null>(null);\n const [banner, setBanner] = useState<string | null>(null);\n const { data, isLoading, error, refetch } = useComplianceChecks({\n status: statusFilter || undefined,\n });\n\n return (\n <div className=\"space-y-6\">\n <PageHeader\n title=\"Compliance\"\n subtitle=\"The duties that travel with the work — acceptance, independence, licensing, CE, retention and legal hold — as gates, not afterthoughts.\"\n icon={<ShieldCheck className=\"h-6 w-6\" />}\n actions={\n <Button onClick={() => setCreating(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n New check\n </Button>\n }\n />\n\n {banner && (\n <Banner tone=\"success\" onClose={() => setBanner(null)}>\n {banner}\n </Banner>\n )}\n\n <div className=\"flex justify-end\">\n <NativeSelect\n value={statusFilter}\n onChange={(e) => setStatusFilter(e.target.value as PswComplianceStatus | '')}\n className=\"sm:w-52\"\n >\n <option value=\"\">All statuses</option>\n {enumOptions(['PENDING', 'IN_REVIEW', 'PASSED', 'FAILED', 'WAIVED'])}\n </NativeSelect>\n </div>\n\n {isLoading ? (\n <LoadingBlock />\n ) : error ? (\n <ErrorState error={error} onRetry={() => void refetch()} />\n ) : !data || data.length === 0 ? (\n <Empty\n title=\"No compliance checks\"\n description=\"Raise a check to gate acceptance or track a professional obligation.\"\n icon={<ShieldCheck className=\"h-8 w-8\" />}\n action={\n <Button onClick={() => setCreating(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n New check\n </Button>\n }\n />\n ) : (\n <SectionCard title={`${data.length} check${data.length === 1 ? '' : 's'}`}>\n <TableWrap>\n <thead>\n <tr>\n <Th>Title</Th>\n <Th>Type</Th>\n <Th>Subject</Th>\n <Th>Due</Th>\n <Th>Status</Th>\n <Th className=\"text-right\">Actions</Th>\n </tr>\n </thead>\n <tbody>\n {data.map((c) => (\n <tr key={c.id} className=\"hover:bg-bg-sunken/50\">\n <Td>\n <span className=\"font-medium text-text-primary\">{c.title}</span>\n </Td>\n <Td>{humanize(c.type)}</Td>\n <Td>{humanize(c.subjectType)}</Td>\n <Td>{fmtDate(c.dueDate)}</Td>\n <Td>\n <StatusPill status={c.status} />\n </Td>\n <Td className=\"text-right\">\n {c.status === 'PENDING' || c.status === 'IN_REVIEW' ? (\n <Button\n variant=\"ghost\"\n size=\"sm\"\n onClick={() => setResolving({ id: c.id, title: c.title })}\n >\n Resolve\n </Button>\n ) : (\n <span className=\"text-xs text-text-tertiary\">\n {c.resolvedAt ? fmtDate(c.resolvedAt) : ''}\n </span>\n )}\n </Td>\n </tr>\n ))}\n </tbody>\n </TableWrap>\n </SectionCard>\n )}\n\n {creating && (\n <ComplianceModal\n onClose={() => setCreating(false)}\n onDone={() => {\n void refetch();\n setBanner('Compliance check created.');\n }}\n />\n )}\n {resolving && (\n <ResolveModal\n check={resolving}\n onClose={() => setResolving(null)}\n onDone={() => {\n void refetch();\n setBanner('Compliance check resolved.');\n }}\n />\n )}\n </div>\n );\n};\n\nconst ComplianceModal: FC<{ onClose: () => void; onDone: () => void }> = ({ onClose, onDone }) => {\n const create = useCreateComplianceCheck();\n const [form, setForm] = useState({\n type: 'ENGAGEMENT_ACCEPTANCE',\n subjectType: 'ENGAGEMENT',\n subjectId: '',\n title: '',\n dueDate: '',\n details: '',\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\n const clients = useClients({ pagination: { limit: 100 } });\n const engagements = useEngagements({ pagination: { limit: 100 } });\n const matters = useMatters({ pagination: { limit: 100 } });\n const subjects =\n form.subjectType === 'CLIENT'\n ? (clients.data?.items ?? []).map((c) => ({ id: c.id, label: c.name }))\n : form.subjectType === 'ENGAGEMENT'\n ? (engagements.data?.items ?? []).map((e) => ({ id: e.id, label: e.name }))\n : (matters.data?.items ?? []).map((m) => ({ id: m.id, label: m.title }));\n\n const submit = () => {\n setErr(null);\n if (!form.title.trim()) return setErr('Title is required.');\n if (!form.subjectId) return setErr('Select a subject.');\n create.mutate(\n {\n type: form.type,\n subjectType: form.subjectType,\n subjectId: form.subjectId,\n title: form.title.trim(),\n dueDate: form.dueDate ? new Date(form.dueDate).toISOString() : null,\n details: form.details.trim() || null,\n },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n };\n\n return (\n <Modal\n open\n onClose={onClose}\n title=\"New compliance check\"\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 ? 'Creating…' : 'Create check'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Title\" required>\n <TextInput\n value={form.title}\n onChange={set('title')}\n placeholder=\"Independence confirmation — FY26 audit\"\n />\n </Field>\n <Field label=\"Type\">\n <NativeSelect value={form.type} onChange={set('type')}>\n {enumOptions(TYPES)}\n </NativeSelect>\n </Field>\n <div className=\"grid grid-cols-2 gap-3\">\n <Field label=\"Subject type\">\n <NativeSelect\n value={form.subjectType}\n onChange={(e) =>\n setForm((f) => ({ ...f, subjectType: e.target.value, subjectId: '' }))\n }\n >\n {enumOptions(SUBJECT_TYPES)}\n </NativeSelect>\n </Field>\n <Field label=\"Subject\" required>\n <NativeSelect value={form.subjectId} onChange={set('subjectId')}>\n <option value=\"\">Select…</option>\n {subjects.map((s) => (\n <option key={s.id} value={s.id}>\n {s.label}\n </option>\n ))}\n </NativeSelect>\n </Field>\n </div>\n <Field label=\"Due date\">\n <TextInput type=\"date\" value={form.dueDate} onChange={set('dueDate')} />\n </Field>\n <Field label=\"Details\">\n <TextArea value={form.details} onChange={set('details')} />\n </Field>\n </div>\n </Modal>\n );\n};\n\nconst ResolveModal: FC<{\n check: { id: string; title: string };\n onClose: () => void;\n onDone: () => void;\n}> = ({ check, onClose, onDone }) => {\n const resolve = useResolveComplianceCheck();\n const [status, setStatus] = useState<PswComplianceStatus>('PASSED');\n const [details, setDetails] = useState('');\n const [err, setErr] = useState<string | null>(null);\n const submit = () =>\n resolve.mutate(\n { id: check.id, status, details: details.trim() || undefined },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n return (\n <Modal\n open\n onClose={onClose}\n title={`Resolve: ${check.title}`}\n footer={\n <>\n <Button variant=\"outline\" onClick={onClose} disabled={resolve.isPending}>\n Cancel\n </Button>\n <Button onClick={submit} disabled={resolve.isPending}>\n {resolve.isPending ? 'Saving…' : 'Resolve'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Outcome\">\n <NativeSelect\n value={status}\n onChange={(e) => setStatus(e.target.value as PswComplianceStatus)}\n >\n {RESOLVE_STATUSES.map((s) => (\n <option key={s} value={s}>\n {humanize(s)}\n </option>\n ))}\n </NativeSelect>\n </Field>\n <Field label=\"Notes\">\n <TextArea value={details} onChange={(e) => setDetails(e.target.value)} />\n </Field>\n </div>\n </Modal>\n );\n};\n"],"mappings":"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"}
1
+ {"version":3,"file":"CompliancePage.js","names":[],"sources":["../../../src/proserviceworld/pages/CompliancePage.tsx"],"sourcesContent":["import type { FC, ReactNode } from 'react';\nimport { useState } from 'react';\nimport { Button } from '@burdenoff/fe-libs/ui';\nimport {\n Plus,\n ShieldCheck,\n FileCheck,\n Scale,\n BadgeCheck,\n GraduationCap,\n Database,\n Lock,\n Clock,\n ListChecks,\n CheckCircle2,\n} from 'lucide-react';\nimport {\n useComplianceChecks,\n useCreateComplianceCheck,\n useResolveComplianceCheck,\n useClients,\n useEngagements,\n useMatters,\n type PswComplianceStatus,\n type PswComplianceType,\n} from '../hooks/useProServiceWorldApi';\nimport {\n PageHeader,\n SectionCard,\n MetricCard,\n LoadingBlock,\n ErrorState,\n Empty,\n StatusPill,\n Modal,\n Field,\n TextInput,\n TextArea,\n NativeSelect,\n Banner,\n TableWrap,\n Th,\n Td,\n enumOptions,\n fmtDate,\n humanize,\n} from '../components/ui';\n\nconst TYPES = [\n 'ENGAGEMENT_ACCEPTANCE',\n 'INDEPENDENCE',\n 'LICENSING',\n 'CONTINUING_EDUCATION',\n 'DATA_RETENTION',\n 'LEGAL_HOLD',\n] as const;\nconst RESOLVE_STATUSES: PswComplianceStatus[] = ['IN_REVIEW', 'PASSED', 'FAILED', 'WAIVED'];\nconst SUBJECT_TYPES = ['CLIENT', 'ENGAGEMENT', 'MATTER'] as const;\n\nconst TYPE_ICON: Record<PswComplianceType, ReactNode> = {\n ENGAGEMENT_ACCEPTANCE: <FileCheck className=\"h-3.5 w-3.5\" />,\n INDEPENDENCE: <Scale className=\"h-3.5 w-3.5\" />,\n LICENSING: <BadgeCheck className=\"h-3.5 w-3.5\" />,\n CONTINUING_EDUCATION: <GraduationCap className=\"h-3.5 w-3.5\" />,\n DATA_RETENTION: <Database className=\"h-3.5 w-3.5\" />,\n LEGAL_HOLD: <Lock className=\"h-3.5 w-3.5\" />,\n};\n\nexport const CompliancePage: FC = () => {\n const [statusFilter, setStatusFilter] = useState<PswComplianceStatus | ''>('');\n const [creating, setCreating] = useState(false);\n const [resolving, setResolving] = useState<{ id: string; title: string } | null>(null);\n const [banner, setBanner] = useState<string | null>(null);\n const { data, isLoading, error, refetch } = useComplianceChecks({\n status: statusFilter || undefined,\n });\n\n const checks = data ?? [];\n const pendingCount = checks.filter((c) => c.status === 'PENDING').length;\n const inReviewCount = checks.filter((c) => c.status === 'IN_REVIEW').length;\n const resolvedCount = checks.filter(\n (c) => c.status === 'PASSED' || c.status === 'FAILED' || c.status === 'WAIVED'\n ).length;\n\n return (\n <div className=\"space-y-6\">\n <PageHeader\n title=\"Compliance\"\n subtitle=\"The duties that travel with the work — acceptance, independence, licensing, CE, retention and legal hold — as gates, not afterthoughts.\"\n icon={<ShieldCheck className=\"h-6 w-6\" />}\n actions={\n <Button onClick={() => setCreating(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n New check\n </Button>\n }\n />\n\n {banner && (\n <Banner tone=\"success\" onClose={() => setBanner(null)}>\n {banner}\n </Banner>\n )}\n\n {data && data.length > 0 && (\n <div className=\"grid grid-cols-2 gap-3 lg:grid-cols-4\">\n <MetricCard\n label=\"Checks\"\n value={checks.length}\n icon={<ListChecks className=\"h-4 w-4\" />}\n />\n <MetricCard\n label=\"Pending\"\n value={pendingCount}\n icon={<Clock className=\"h-4 w-4\" />}\n tone={pendingCount ? 'warning' : 'neutral'}\n />\n <MetricCard\n label=\"In review\"\n value={inReviewCount}\n icon={<ShieldCheck className=\"h-4 w-4\" />}\n tone=\"info\"\n />\n <MetricCard\n label=\"Resolved\"\n value={resolvedCount}\n icon={<CheckCircle2 className=\"h-4 w-4\" />}\n tone=\"success\"\n />\n </div>\n )}\n\n <div className=\"flex justify-end\">\n <NativeSelect\n value={statusFilter}\n onChange={(e) => setStatusFilter(e.target.value as PswComplianceStatus | '')}\n className=\"sm:w-52\"\n >\n <option value=\"\">All statuses</option>\n {enumOptions(['PENDING', 'IN_REVIEW', 'PASSED', 'FAILED', 'WAIVED'])}\n </NativeSelect>\n </div>\n\n {isLoading ? (\n <LoadingBlock />\n ) : error ? (\n <ErrorState error={error} onRetry={() => void refetch()} />\n ) : !data || data.length === 0 ? (\n <Empty\n title=\"No compliance checks\"\n description=\"Raise a check to gate acceptance or track a professional obligation.\"\n icon={<ShieldCheck className=\"h-8 w-8\" />}\n action={\n <Button onClick={() => setCreating(true)}>\n <Plus className=\"mr-1.5 h-4 w-4\" />\n New check\n </Button>\n }\n />\n ) : (\n <SectionCard title={`${data.length} check${data.length === 1 ? '' : 's'}`}>\n <TableWrap>\n <thead>\n <tr>\n <Th>Title</Th>\n <Th>Type</Th>\n <Th>Subject</Th>\n <Th>Due</Th>\n <Th>Status</Th>\n <Th className=\"text-right\">Actions</Th>\n </tr>\n </thead>\n <tbody>\n {data.map((c) => (\n <tr key={c.id} className=\"transition-colors hover:bg-bg-sunken/60\">\n <Td>\n <span className=\"font-medium text-text-primary\">{c.title}</span>\n </Td>\n <Td>\n <span className=\"inline-flex items-center gap-2 whitespace-nowrap\">\n <span className=\"flex h-6 w-6 items-center justify-center rounded-md bg-bg-sunken text-accent\">\n {TYPE_ICON[c.type]}\n </span>\n {humanize(c.type)}\n </span>\n </Td>\n <Td>{humanize(c.subjectType)}</Td>\n <Td className=\"whitespace-nowrap\">{fmtDate(c.dueDate)}</Td>\n <Td>\n <StatusPill status={c.status} />\n </Td>\n <Td className=\"text-right\">\n {c.status === 'PENDING' || c.status === 'IN_REVIEW' ? (\n <Button\n variant=\"ghost\"\n size=\"sm\"\n onClick={() => setResolving({ id: c.id, title: c.title })}\n >\n Resolve\n </Button>\n ) : (\n <span className=\"text-xs text-text-tertiary\">\n {c.resolvedAt ? fmtDate(c.resolvedAt) : ''}\n </span>\n )}\n </Td>\n </tr>\n ))}\n </tbody>\n </TableWrap>\n </SectionCard>\n )}\n\n {creating && (\n <ComplianceModal\n onClose={() => setCreating(false)}\n onDone={() => {\n void refetch();\n setBanner('Compliance check created.');\n }}\n />\n )}\n {resolving && (\n <ResolveModal\n check={resolving}\n onClose={() => setResolving(null)}\n onDone={() => {\n void refetch();\n setBanner('Compliance check resolved.');\n }}\n />\n )}\n </div>\n );\n};\n\nconst ComplianceModal: FC<{ onClose: () => void; onDone: () => void }> = ({ onClose, onDone }) => {\n const create = useCreateComplianceCheck();\n const [form, setForm] = useState({\n type: 'ENGAGEMENT_ACCEPTANCE',\n subjectType: 'ENGAGEMENT',\n subjectId: '',\n title: '',\n dueDate: '',\n details: '',\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\n const clients = useClients({ pagination: { limit: 100 } });\n const engagements = useEngagements({ pagination: { limit: 100 } });\n const matters = useMatters({ pagination: { limit: 100 } });\n const subjects =\n form.subjectType === 'CLIENT'\n ? (clients.data?.items ?? []).map((c) => ({ id: c.id, label: c.name }))\n : form.subjectType === 'ENGAGEMENT'\n ? (engagements.data?.items ?? []).map((e) => ({ id: e.id, label: e.name }))\n : (matters.data?.items ?? []).map((m) => ({ id: m.id, label: m.title }));\n\n const submit = () => {\n setErr(null);\n if (!form.title.trim()) return setErr('Title is required.');\n if (!form.subjectId) return setErr('Select a subject.');\n create.mutate(\n {\n type: form.type,\n subjectType: form.subjectType,\n subjectId: form.subjectId,\n title: form.title.trim(),\n dueDate: form.dueDate ? new Date(form.dueDate).toISOString() : null,\n details: form.details.trim() || null,\n },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n };\n\n return (\n <Modal\n open\n onClose={onClose}\n title=\"New compliance check\"\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 ? 'Creating…' : 'Create check'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Title\" required>\n <TextInput\n value={form.title}\n onChange={set('title')}\n placeholder=\"Independence confirmation — FY26 audit\"\n />\n </Field>\n <Field label=\"Type\">\n <NativeSelect value={form.type} onChange={set('type')}>\n {enumOptions(TYPES)}\n </NativeSelect>\n </Field>\n <div className=\"grid grid-cols-2 gap-3\">\n <Field label=\"Subject type\">\n <NativeSelect\n value={form.subjectType}\n onChange={(e) =>\n setForm((f) => ({ ...f, subjectType: e.target.value, subjectId: '' }))\n }\n >\n {enumOptions(SUBJECT_TYPES)}\n </NativeSelect>\n </Field>\n <Field label=\"Subject\" required>\n <NativeSelect value={form.subjectId} onChange={set('subjectId')}>\n <option value=\"\">Select…</option>\n {subjects.map((s) => (\n <option key={s.id} value={s.id}>\n {s.label}\n </option>\n ))}\n </NativeSelect>\n </Field>\n </div>\n <Field label=\"Due date\">\n <TextInput type=\"date\" value={form.dueDate} onChange={set('dueDate')} />\n </Field>\n <Field label=\"Details\">\n <TextArea value={form.details} onChange={set('details')} />\n </Field>\n </div>\n </Modal>\n );\n};\n\nconst ResolveModal: FC<{\n check: { id: string; title: string };\n onClose: () => void;\n onDone: () => void;\n}> = ({ check, onClose, onDone }) => {\n const resolve = useResolveComplianceCheck();\n const [status, setStatus] = useState<PswComplianceStatus>('PASSED');\n const [details, setDetails] = useState('');\n const [err, setErr] = useState<string | null>(null);\n const submit = () =>\n resolve.mutate(\n { id: check.id, status, details: details.trim() || undefined },\n {\n onSuccess: () => {\n onDone();\n onClose();\n },\n onError: (e) => setErr(e instanceof Error ? e.message : 'Failed.'),\n }\n );\n return (\n <Modal\n open\n onClose={onClose}\n title={`Resolve: ${check.title}`}\n footer={\n <>\n <Button variant=\"outline\" onClick={onClose} disabled={resolve.isPending}>\n Cancel\n </Button>\n <Button onClick={submit} disabled={resolve.isPending}>\n {resolve.isPending ? 'Saving…' : 'Resolve'}\n </Button>\n </>\n }\n >\n <div className=\"space-y-3\">\n {err && <Banner tone=\"danger\">{err}</Banner>}\n <Field label=\"Outcome\">\n <NativeSelect\n value={status}\n onChange={(e) => setStatus(e.target.value as PswComplianceStatus)}\n >\n {RESOLVE_STATUSES.map((s) => (\n <option key={s} value={s}>\n {humanize(s)}\n </option>\n ))}\n </NativeSelect>\n </Field>\n <Field label=\"Notes\">\n <TextArea value={details} onChange={(e) => setDetails(e.target.value)} />\n </Field>\n </div>\n </Modal>\n );\n};\n"],"mappings":"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"}