@burdenoff/microfe-mybodyshield 2026.821.2 → 2026.830.1

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 (90) hide show
  1. package/dist/mybodyshield/MyBodyShieldRoot.d.ts.map +1 -1
  2. package/dist/mybodyshield/MyBodyShieldRoot.js +54 -56
  3. package/dist/mybodyshield/MyBodyShieldRoot.js.map +1 -1
  4. package/dist/mybodyshield/MyBodyShieldRoutes.d.ts.map +1 -1
  5. package/dist/mybodyshield/MyBodyShieldRoutes.js +121 -62
  6. package/dist/mybodyshield/MyBodyShieldRoutes.js.map +1 -1
  7. package/dist/mybodyshield/components/EvidenceUpload.d.ts.map +1 -1
  8. package/dist/mybodyshield/components/EvidenceUpload.js +46 -45
  9. package/dist/mybodyshield/components/EvidenceUpload.js.map +1 -1
  10. package/dist/mybodyshield/components/FileLink.d.ts.map +1 -1
  11. package/dist/mybodyshield/components/FileLink.js +27 -18
  12. package/dist/mybodyshield/components/FileLink.js.map +1 -1
  13. package/dist/mybodyshield/components/MybDiscussion.d.ts +1 -1
  14. package/dist/mybodyshield/components/MybDiscussion.d.ts.map +1 -1
  15. package/dist/mybodyshield/components/MybDiscussion.js +59 -58
  16. package/dist/mybodyshield/components/MybDiscussion.js.map +1 -1
  17. package/dist/mybodyshield/components/MybTags.d.ts +1 -1
  18. package/dist/mybodyshield/components/MybTags.d.ts.map +1 -1
  19. package/dist/mybodyshield/components/MybTags.js +83 -74
  20. package/dist/mybodyshield/components/MybTags.js.map +1 -1
  21. package/dist/mybodyshield/components/PageDisabled.d.ts.map +1 -1
  22. package/dist/mybodyshield/components/PageDisabled.js +16 -11
  23. package/dist/mybodyshield/components/PageDisabled.js.map +1 -1
  24. package/dist/mybodyshield/components/Pagination.d.ts.map +1 -1
  25. package/dist/mybodyshield/components/Pagination.js +36 -27
  26. package/dist/mybodyshield/components/Pagination.js.map +1 -1
  27. package/dist/mybodyshield/components/StateViews.d.ts.map +1 -1
  28. package/dist/mybodyshield/components/StateViews.js +42 -34
  29. package/dist/mybodyshield/components/StateViews.js.map +1 -1
  30. package/dist/mybodyshield/components/UserSearchSelect.d.ts.map +1 -1
  31. package/dist/mybodyshield/components/UserSearchSelect.js +66 -68
  32. package/dist/mybodyshield/components/UserSearchSelect.js.map +1 -1
  33. package/dist/mybodyshield/hooks/index.d.ts +1 -0
  34. package/dist/mybodyshield/hooks/index.d.ts.map +1 -1
  35. package/dist/mybodyshield/hooks/index.js +1 -0
  36. package/dist/mybodyshield/hooks/useTr.d.ts +5 -0
  37. package/dist/mybodyshield/hooks/useTr.d.ts.map +1 -0
  38. package/dist/mybodyshield/hooks/useTr.js +12 -0
  39. package/dist/mybodyshield/hooks/useTr.js.map +1 -0
  40. package/dist/mybodyshield/pages/DashboardPage.d.ts.map +1 -1
  41. package/dist/mybodyshield/pages/DashboardPage.js +157 -136
  42. package/dist/mybodyshield/pages/DashboardPage.js.map +1 -1
  43. package/dist/mybodyshield/pages/SettingsPage.d.ts.map +1 -1
  44. package/dist/mybodyshield/pages/SettingsPage.js +50 -59
  45. package/dist/mybodyshield/pages/SettingsPage.js.map +1 -1
  46. package/dist/mybodyshield/pages/_shared/visuals.d.ts +2 -1
  47. package/dist/mybodyshield/pages/_shared/visuals.d.ts.map +1 -1
  48. package/dist/mybodyshield/pages/_shared/visuals.js +91 -81
  49. package/dist/mybodyshield/pages/_shared/visuals.js.map +1 -1
  50. package/dist/mybodyshield/pages/ai/AiControlsPage.d.ts.map +1 -1
  51. package/dist/mybodyshield/pages/ai/AiControlsPage.js +279 -231
  52. package/dist/mybodyshield/pages/ai/AiControlsPage.js.map +1 -1
  53. package/dist/mybodyshield/pages/coaching/CoachingPage.d.ts.map +1 -1
  54. package/dist/mybodyshield/pages/coaching/CoachingPage.js +349 -258
  55. package/dist/mybodyshield/pages/coaching/CoachingPage.js.map +1 -1
  56. package/dist/mybodyshield/pages/goals/GoalsPage.d.ts.map +1 -1
  57. package/dist/mybodyshield/pages/goals/GoalsPage.js +247 -251
  58. package/dist/mybodyshield/pages/goals/GoalsPage.js.map +1 -1
  59. package/dist/mybodyshield/pages/insights/InsightsCharts.d.ts.map +1 -1
  60. package/dist/mybodyshield/pages/insights/InsightsCharts.js +216 -213
  61. package/dist/mybodyshield/pages/insights/InsightsCharts.js.map +1 -1
  62. package/dist/mybodyshield/pages/insights/InsightsPage.d.ts.map +1 -1
  63. package/dist/mybodyshield/pages/insights/InsightsPage.js +327 -220
  64. package/dist/mybodyshield/pages/insights/InsightsPage.js.map +1 -1
  65. package/dist/mybodyshield/pages/nutrition/NutritionPage.d.ts.map +1 -1
  66. package/dist/mybodyshield/pages/nutrition/NutritionPage.js +575 -529
  67. package/dist/mybodyshield/pages/nutrition/NutritionPage.js.map +1 -1
  68. package/dist/mybodyshield/pages/programs/ProgramDetailPage.d.ts.map +1 -1
  69. package/dist/mybodyshield/pages/programs/ProgramDetailPage.js +333 -275
  70. package/dist/mybodyshield/pages/programs/ProgramDetailPage.js.map +1 -1
  71. package/dist/mybodyshield/pages/programs/ProgramsPage.d.ts.map +1 -1
  72. package/dist/mybodyshield/pages/programs/ProgramsPage.js +258 -253
  73. package/dist/mybodyshield/pages/programs/ProgramsPage.js.map +1 -1
  74. package/dist/mybodyshield/pages/progress/ProgressPage.d.ts.map +1 -1
  75. package/dist/mybodyshield/pages/progress/ProgressPage.js +271 -254
  76. package/dist/mybodyshield/pages/progress/ProgressPage.js.map +1 -1
  77. package/dist/mybodyshield/pages/recovery/RecoveryPage.d.ts.map +1 -1
  78. package/dist/mybodyshield/pages/recovery/RecoveryPage.js +206 -200
  79. package/dist/mybodyshield/pages/recovery/RecoveryPage.js.map +1 -1
  80. package/dist/mybodyshield/pages/train/SessionDetailPage.d.ts.map +1 -1
  81. package/dist/mybodyshield/pages/train/SessionDetailPage.js +327 -294
  82. package/dist/mybodyshield/pages/train/SessionDetailPage.js.map +1 -1
  83. package/dist/mybodyshield/pages/train/SessionsPage.d.ts.map +1 -1
  84. package/dist/mybodyshield/pages/train/SessionsPage.js +180 -163
  85. package/dist/mybodyshield/pages/train/SessionsPage.js.map +1 -1
  86. package/dist/mybodyshield/utils/i18n.d.ts +1 -2
  87. package/dist/mybodyshield/utils/i18n.d.ts.map +1 -1
  88. package/dist/mybodyshield/utils/i18n.js +15 -0
  89. package/dist/mybodyshield/utils/i18n.js.map +1 -0
  90. package/package.json +1 -1
@@ -1,338 +1,386 @@
1
1
  import { PageLayout as e } from "../../components/PageLayout.js";
2
2
  import { MetricsCard as t } from "../../components/MetricsCard.js";
3
3
  import { formatDateTime as n, formatEnumLabel as r, formatRelativeTime as i } from "../../utils/formatters.js";
4
- import { ErrorView as a, LoadingView as o, Section as s } from "../../components/StateViews.js";
5
- import { DataTable as c } from "../../components/DataTable.js";
6
- import { useMybAiOperationLogs as l, useMybAiSettings as u, useMybUpdateAiSettings as d } from "../../hooks/useMyBodyShieldApi.js";
4
+ import { useMybAiOperationLogs as a, useMybAiProcessingConsent as o, useMybAiSettings as s, useMybSetAiProcessingConsent as c, useMybUpdateAiSettings as l } from "../../hooks/useMyBodyShieldApi.js";
5
+ import { useTr as u } from "../../hooks/useTr.js";
7
6
  import "../../hooks/index.js";
7
+ import { ErrorView as d, LoadingView as f, Section as p } from "../../components/StateViews.js";
8
+ import { DataTable as m } from "../../components/DataTable.js";
8
9
  import "../../components/index.js";
9
- import { useMemo as f, useState as p } from "react";
10
- import { Activity as m, Bot as h, KeyRound as g, Save as _, Sparkles as v } from "lucide-react";
11
- import { jsx as y, jsxs as b } from "react/jsx-runtime";
12
- import { Button as x, GlassCard as S, Input as C, Label as w, Select as T, SelectContent as E, SelectItem as D, SelectTrigger as O, SelectValue as k, Spinner as A } from "@burdenoff/fe-libs/ui";
10
+ import { IconChip as h } from "../_shared/visuals.js";
11
+ import { useMemo as g, useState as _ } from "react";
12
+ import { Activity as v, Bot as y, KeyRound as b, Save as x, ShieldCheck as S, ShieldOff as C, Sparkles as w } from "lucide-react";
13
+ import { jsx as T, jsxs as E } from "react/jsx-runtime";
14
+ import { Button as D, GlassCard as O, Input as k, Label as A, Select as j, SelectContent as M, SelectItem as N, SelectTrigger as P, SelectValue as F, Spinner as I, Switch as L } from "@burdenoff/fe-libs/ui";
13
15
  //#region src/mybodyshield/pages/ai/AiControlsPage.tsx
14
- var j = [
16
+ var R = [
15
17
  "GEMINI",
16
18
  "OPENAI",
17
19
  "ANTHROPIC"
18
- ], M = {
20
+ ], z = {
19
21
  GEMINI: "Google Gemini",
20
22
  OPENAI: "OpenAI",
21
23
  ANTHROPIC: "Anthropic"
22
- }, N = {
24
+ }, B = {
23
25
  GEMINI: "gemini-2.5-flash",
24
26
  OPENAI: "gpt-4o-mini",
25
27
  ANTHROPIC: "claude-3-5-haiku-latest"
26
- }, P = (e) => ({
28
+ }, V = (e) => ({
27
29
  provider: e.provider,
28
30
  modelName: e.modelName,
29
31
  dailyAllowance: String(e.dailyAllowance),
30
32
  providerKey: "",
31
33
  clearKey: !1
32
34
  });
33
- function F({ settings: l, logsQuery: u }) {
34
- let F = d(), [I, L] = p(() => P(l)), [R, z] = p(null), [B, V] = p(!1), H = f(() => {
35
- let { dailyAllowance: e, dailyAllowanceUsed: t } = l;
35
+ function H() {
36
+ let e = u(), t = o(), n = c();
37
+ if (t.isLoading) return /* @__PURE__ */ T(f, { label: e("mybodyshield.pages.aiControls.loadingConsent", "Loading AI-processing consent…") });
38
+ if (t.isError) return /* @__PURE__ */ T(d, {
39
+ message: e("mybodyshield.pages.aiControls.consentError", "We couldn't load your AI-processing consent."),
40
+ onRetry: () => t.refetch()
41
+ });
42
+ let r = t.data?.enabled ?? !1;
43
+ return /* @__PURE__ */ T(O, {
44
+ treatment: "plain",
45
+ className: "p-5",
46
+ children: /* @__PURE__ */ E("div", {
47
+ className: "flex flex-wrap items-start justify-between gap-4",
48
+ children: [/* @__PURE__ */ E("div", {
49
+ className: "flex min-w-0 items-start gap-3",
50
+ children: [/* @__PURE__ */ T(h, { icon: T(r ? S : C, { className: "h-5 w-5" }) }), /* @__PURE__ */ E("div", {
51
+ className: "min-w-0",
52
+ children: [
53
+ /* @__PURE__ */ T("p", {
54
+ className: "text-sm font-medium text-text-primary",
55
+ children: r ? e("mybodyshield.pages.aiControls.aiMayReadData", "AI may read your health data") : e("mybodyshield.pages.aiControls.aiWithdrawn", "AI processing is withdrawn — summaries will not run")
56
+ }),
57
+ /* @__PURE__ */ T("p", {
58
+ className: "mt-0.5 text-sm text-text-secondary",
59
+ children: r ? e("mybodyshield.pages.aiControls.aiEnabledDescription", "The provider and model below are used to turn your logged training, nutrition, recovery and body-metric data into plain-language summaries.") : e("mybodyshield.pages.aiControls.aiWithdrawnDescription", "The provider and model below are saved, but no AI summary is generated while consent is withdrawn. Rule-based guidance and every manual logging path keep working.")
60
+ }),
61
+ t.data?.withdrawnAt && !r && /* @__PURE__ */ T("p", {
62
+ className: "mt-1 text-xs text-text-tertiary",
63
+ children: e("mybodyshield.pages.aiControls.withdrawnAgo", "Withdrawn {{time}}.", { time: i(t.data.withdrawnAt) })
64
+ }),
65
+ t.data?.acceptedAt && r && /* @__PURE__ */ T("p", {
66
+ className: "mt-1 text-xs text-text-tertiary",
67
+ children: e("mybodyshield.pages.aiControls.consentGivenAgo", "Consent given {{time}}.", { time: i(t.data.acceptedAt) })
68
+ })
69
+ ]
70
+ })]
71
+ }), /* @__PURE__ */ T(L, {
72
+ checked: r,
73
+ onCheckedChange: (e) => n.mutate(e),
74
+ disabled: n.isPending,
75
+ "aria-label": e("mybodyshield.pages.aiControls.allowAiData", "Allow AI to read my health data")
76
+ })]
77
+ })
78
+ });
79
+ }
80
+ function U({ settings: a, logsQuery: o }) {
81
+ let s = u(), c = l(), [h, S] = _(() => V(a)), [C, L] = _(null), [U, W] = _(!1), G = g(() => {
82
+ let { dailyAllowance: e, dailyAllowanceUsed: t } = a;
36
83
  return e <= 0 ? 0 : Math.min(100, Math.round(t / e * 100));
37
- }, [l]), U = l.dailyAllowanceUsed >= l.dailyAllowance, W = (e) => {
38
- L((t) => ({
84
+ }, [a]), K = a.dailyAllowanceUsed >= a.dailyAllowance, q = (e) => {
85
+ S((t) => ({
39
86
  ...t,
40
87
  provider: e,
41
- modelName: t.modelName === N[t.provider] ? N[e] : t.modelName
88
+ modelName: t.modelName === B[t.provider] ? B[e] : t.modelName
42
89
  }));
43
- };
44
- return /* @__PURE__ */ b(e, {
45
- title: "AI controls",
46
- description: "Choose your AI provider, model and daily allowance.",
47
- actions: /* @__PURE__ */ b(x, {
90
+ }, J = async () => {
91
+ L(null), W(!1);
92
+ let e = Number(h.dailyAllowance);
93
+ if (!Number.isInteger(e) || e < 0 || e > 1e4) {
94
+ L(s("mybodyshield.pages.aiControls.allowanceRange", "Daily allowance must be an integer between 0 and 10,000."));
95
+ return;
96
+ }
97
+ if (!h.modelName.trim()) {
98
+ L(s("mybodyshield.pages.aiControls.modelRequired", "Model name is required."));
99
+ return;
100
+ }
101
+ let t = {
102
+ provider: h.provider,
103
+ modelName: h.modelName.trim(),
104
+ dailyAllowance: e
105
+ };
106
+ h.clearKey ? t.providerKey = "" : h.providerKey.trim() && (t.providerKey = h.providerKey.trim());
107
+ try {
108
+ await c.mutateAsync(t), W(!0), S((e) => ({
109
+ ...e,
110
+ providerKey: "",
111
+ clearKey: !1
112
+ }));
113
+ } catch (e) {
114
+ L(e instanceof Error ? e.message : s("mybodyshield.pages.aiControls.failedToSave", "Failed to save AI settings."));
115
+ }
116
+ }, Y = [
117
+ {
118
+ key: "createdAt",
119
+ header: s("mybodyshield.pages.aiControls.time", "Time"),
120
+ sortValue: (e) => new Date(e.createdAt).getTime(),
121
+ render: (e) => /* @__PURE__ */ E("div", {
122
+ className: "text-text-primary",
123
+ children: [/* @__PURE__ */ T("span", {
124
+ className: "block text-sm",
125
+ children: n(e.createdAt)
126
+ }), /* @__PURE__ */ T("span", {
127
+ className: "text-xs text-text-tertiary",
128
+ children: i(e.createdAt)
129
+ })]
130
+ })
131
+ },
132
+ {
133
+ key: "operationType",
134
+ header: s("mybodyshield.pages.aiControls.operation", "Operation"),
135
+ render: (e) => /* @__PURE__ */ T("span", {
136
+ className: "text-text-secondary",
137
+ children: r(e.operationType)
138
+ })
139
+ },
140
+ {
141
+ key: "provider",
142
+ header: s("mybodyshield.pages.aiControls.providerModel", "Provider / Model"),
143
+ render: (e) => /* @__PURE__ */ E("div", { children: [/* @__PURE__ */ T("span", {
144
+ className: "block text-sm text-text-primary",
145
+ children: z[e.provider]
146
+ }), /* @__PURE__ */ T("span", {
147
+ className: "text-xs text-text-tertiary",
148
+ children: e.modelName
149
+ })] })
150
+ },
151
+ {
152
+ key: "tokens",
153
+ header: s("mybodyshield.pages.aiControls.tokens", "Tokens"),
154
+ align: "right",
155
+ render: (e) => /* @__PURE__ */ E("span", {
156
+ className: "tabular-nums text-text-secondary",
157
+ children: [
158
+ e.inputTokens ?? "—",
159
+ " / ",
160
+ e.outputTokens ?? "—"
161
+ ]
162
+ })
163
+ },
164
+ {
165
+ key: "status",
166
+ header: s("mybodyshield.pages.aiControls.status", "Status"),
167
+ render: (e) => /* @__PURE__ */ T("span", {
168
+ className: `inline-flex items-center rounded-full px-2 py-0.5 text-xs font-medium ${e.status === "SUCCESS" ? "bg-status-success-bg text-status-success-text" : "bg-status-error-bg text-status-error-text"}`,
169
+ children: r(e.status)
170
+ })
171
+ },
172
+ {
173
+ key: "error",
174
+ header: s("mybodyshield.pages.aiControls.errorColumn", "Error"),
175
+ hideOnMobile: !0,
176
+ render: (e) => e.errorMessage ? /* @__PURE__ */ T("span", {
177
+ className: "text-xs text-status-error-text",
178
+ children: e.errorMessage
179
+ }) : /* @__PURE__ */ T("span", {
180
+ className: "text-text-tertiary",
181
+ children: "—"
182
+ })
183
+ }
184
+ ];
185
+ return /* @__PURE__ */ E(e, {
186
+ title: s("mybodyshield.pages.aiControls.title", "AI controls"),
187
+ description: s("mybodyshield.pages.aiControls.description", "Choose your AI provider, model and daily allowance."),
188
+ actions: /* @__PURE__ */ E(D, {
48
189
  className: "gap-2",
49
- onClick: async () => {
50
- z(null), V(!1);
51
- let e = Number(I.dailyAllowance);
52
- if (!Number.isInteger(e) || e < 0 || e > 1e4) {
53
- z("Daily allowance must be an integer between 0 and 10,000.");
54
- return;
55
- }
56
- if (!I.modelName.trim()) {
57
- z("Model name is required.");
58
- return;
59
- }
60
- let t = {
61
- provider: I.provider,
62
- modelName: I.modelName.trim(),
63
- dailyAllowance: e
64
- };
65
- I.clearKey ? t.providerKey = "" : I.providerKey.trim() && (t.providerKey = I.providerKey.trim());
66
- try {
67
- await F.mutateAsync(t), V(!0), L((e) => ({
68
- ...e,
69
- providerKey: "",
70
- clearKey: !1
71
- }));
72
- } catch (e) {
73
- z(e instanceof Error ? e.message : "Failed to save AI settings.");
74
- }
75
- },
76
- disabled: F.isPending,
77
- children: [F.isPending ? /* @__PURE__ */ y(A, { size: "sm" }) : /* @__PURE__ */ y(_, { className: "h-4 w-4" }), "Save settings"]
190
+ onClick: J,
191
+ disabled: c.isPending,
192
+ children: [c.isPending ? /* @__PURE__ */ T(I, { size: "sm" }) : /* @__PURE__ */ T(x, { className: "h-4 w-4" }), s("mybodyshield.pages.aiControls.saveSettings", "Save settings")]
78
193
  }),
79
194
  children: [
80
- /* @__PURE__ */ b("div", {
195
+ /* @__PURE__ */ T(p, {
196
+ title: s("mybodyshield.pages.aiControls.consentTitle", "AI-processing consent"),
197
+ description: s("mybodyshield.pages.aiControls.consentDescription", "AI summaries only run while you allow AI to read your health data."),
198
+ children: /* @__PURE__ */ T(H, {})
199
+ }),
200
+ /* @__PURE__ */ E("div", {
81
201
  className: "grid grid-cols-1 gap-4 sm:grid-cols-3",
82
202
  children: [
83
- /* @__PURE__ */ y(t, {
84
- icon: /* @__PURE__ */ y(v, { className: "h-5 w-5" }),
85
- value: l.provider,
86
- label: "Current provider"
203
+ /* @__PURE__ */ T(t, {
204
+ icon: /* @__PURE__ */ T(w, { className: "h-5 w-5" }),
205
+ value: a.provider,
206
+ label: s("mybodyshield.pages.aiControls.currentProvider", "Current provider")
87
207
  }),
88
- /* @__PURE__ */ y(t, {
89
- icon: /* @__PURE__ */ y(h, { className: "h-5 w-5" }),
90
- value: l.modelName,
91
- label: "Current model"
208
+ /* @__PURE__ */ T(t, {
209
+ icon: /* @__PURE__ */ T(y, { className: "h-5 w-5" }),
210
+ value: a.modelName,
211
+ label: s("mybodyshield.pages.aiControls.currentModel", "Current model")
92
212
  }),
93
- /* @__PURE__ */ y(t, {
94
- icon: /* @__PURE__ */ y(m, { className: "h-5 w-5" }),
95
- value: `${l.dailyAllowanceUsed} / ${l.dailyAllowance}`,
96
- label: "Daily allowance used",
97
- accent: U ? "error" : H >= 80 ? "warning" : "success",
98
- footer: /* @__PURE__ */ b("p", {
213
+ /* @__PURE__ */ T(t, {
214
+ icon: /* @__PURE__ */ T(v, { className: "h-5 w-5" }),
215
+ value: `${a.dailyAllowanceUsed} / ${a.dailyAllowance}`,
216
+ label: s("mybodyshield.pages.aiControls.dailyAllowanceUsed", "Daily allowance used"),
217
+ accent: K ? "error" : G >= 80 ? "warning" : "success",
218
+ footer: /* @__PURE__ */ T("p", {
99
219
  className: "text-xs text-text-tertiary",
100
- children: ["Resets ", i(l.allowanceResetAt)]
220
+ children: s("mybodyshield.pages.aiControls.resets", "Resets {{time}}", { time: i(a.allowanceResetAt) })
101
221
  })
102
222
  })
103
223
  ]
104
224
  }),
105
- /* @__PURE__ */ y(s, {
106
- title: "Configuration",
107
- description: "Changes apply to your account only.",
108
- children: /* @__PURE__ */ b(S, {
225
+ /* @__PURE__ */ T(p, {
226
+ title: s("mybodyshield.pages.aiControls.configuration", "Configuration"),
227
+ description: s("mybodyshield.pages.aiControls.configurationDescription", "Changes apply to your account only."),
228
+ children: /* @__PURE__ */ E(O, {
109
229
  treatment: "plain",
110
230
  className: "p-6",
111
231
  children: [
112
- /* @__PURE__ */ b("div", {
232
+ /* @__PURE__ */ E("div", {
113
233
  className: "grid gap-6 md:grid-cols-2",
114
234
  children: [
115
- /* @__PURE__ */ b("div", {
235
+ /* @__PURE__ */ E("div", {
116
236
  className: "space-y-1.5",
117
237
  children: [
118
- /* @__PURE__ */ y(w, {
238
+ /* @__PURE__ */ T(A, {
119
239
  htmlFor: "myb-ai-provider",
120
- children: "AI provider"
240
+ children: s("mybodyshield.pages.aiControls.aiProvider", "AI provider")
121
241
  }),
122
- /* @__PURE__ */ b(T, {
123
- value: I.provider,
124
- onValueChange: (e) => W(e),
125
- children: [/* @__PURE__ */ y(O, {
242
+ /* @__PURE__ */ E(j, {
243
+ value: h.provider,
244
+ onValueChange: (e) => q(e),
245
+ children: [/* @__PURE__ */ T(P, {
126
246
  id: "myb-ai-provider",
127
- children: /* @__PURE__ */ y(k, {})
128
- }), /* @__PURE__ */ y(E, { children: j.map((e) => /* @__PURE__ */ y(D, {
247
+ children: /* @__PURE__ */ T(F, {})
248
+ }), /* @__PURE__ */ T(M, { children: R.map((e) => /* @__PURE__ */ T(N, {
129
249
  value: e,
130
- children: M[e]
250
+ children: z[e]
131
251
  }, e)) })]
132
252
  }),
133
- /* @__PURE__ */ y("p", {
253
+ /* @__PURE__ */ T("p", {
134
254
  className: "text-xs text-text-tertiary",
135
- children: "The provider used for AI-generated guidance summaries."
255
+ children: s("mybodyshield.pages.aiControls.providerDescription", "The provider used for AI-generated guidance summaries.")
136
256
  })
137
257
  ]
138
258
  }),
139
- /* @__PURE__ */ b("div", {
259
+ /* @__PURE__ */ E("div", {
140
260
  className: "space-y-1.5",
141
261
  children: [
142
- /* @__PURE__ */ y(w, {
262
+ /* @__PURE__ */ T(A, {
143
263
  htmlFor: "myb-ai-model",
144
- children: "Model name"
264
+ children: s("mybodyshield.pages.aiControls.modelName", "Model name")
145
265
  }),
146
- /* @__PURE__ */ y(C, {
266
+ /* @__PURE__ */ T(k, {
147
267
  id: "myb-ai-model",
148
- value: I.modelName,
149
- onChange: (e) => L((t) => ({
268
+ value: h.modelName,
269
+ onChange: (e) => S((t) => ({
150
270
  ...t,
151
271
  modelName: e.target.value
152
272
  })),
153
- placeholder: N[I.provider]
273
+ placeholder: s("mybodyshield.pages.aiControls.modelPlaceholder", "e.g. {{model}}", { model: B[h.provider] })
154
274
  }),
155
- /* @__PURE__ */ b("p", {
275
+ /* @__PURE__ */ T("p", {
156
276
  className: "text-xs text-text-tertiary",
157
- children: [
158
- "e.g. ",
159
- N[I.provider],
160
- ". Must be valid for the chosen provider."
161
- ]
277
+ children: s("mybodyshield.pages.aiControls.modelHint", "Must be valid for the chosen provider.")
162
278
  })
163
279
  ]
164
280
  }),
165
- /* @__PURE__ */ b("div", {
281
+ /* @__PURE__ */ E("div", {
166
282
  className: "space-y-1.5",
167
283
  children: [
168
- /* @__PURE__ */ y(w, {
284
+ /* @__PURE__ */ T(A, {
169
285
  htmlFor: "myb-ai-allowance",
170
- children: "Daily allowance"
286
+ children: s("mybodyshield.pages.aiControls.dailyAllowance", "Daily allowance")
171
287
  }),
172
- /* @__PURE__ */ y(C, {
288
+ /* @__PURE__ */ T(k, {
173
289
  id: "myb-ai-allowance",
174
290
  type: "number",
175
291
  min: 0,
176
292
  max: 1e4,
177
293
  step: 1,
178
- value: I.dailyAllowance,
179
- onChange: (e) => L((t) => ({
294
+ value: h.dailyAllowance,
295
+ onChange: (e) => S((t) => ({
180
296
  ...t,
181
297
  dailyAllowance: e.target.value
182
298
  }))
183
299
  }),
184
- /* @__PURE__ */ y("p", {
300
+ /* @__PURE__ */ T("p", {
185
301
  className: "text-xs text-text-tertiary",
186
- children: "Maximum AI operations counted against your account per UTC day."
302
+ children: s("mybodyshield.pages.aiControls.dailyAllowanceHint", "Maximum AI operations counted against your account per UTC day.")
187
303
  })
188
304
  ]
189
305
  }),
190
- /* @__PURE__ */ b("div", {
306
+ /* @__PURE__ */ E("div", {
191
307
  className: "space-y-1.5",
192
308
  children: [
193
- /* @__PURE__ */ y(w, {
309
+ /* @__PURE__ */ T(A, {
194
310
  htmlFor: "myb-ai-key",
195
- children: /* @__PURE__ */ b("span", {
311
+ children: /* @__PURE__ */ E("span", {
196
312
  className: "inline-flex items-center gap-1.5",
197
- children: [/* @__PURE__ */ y(g, { className: "h-3.5 w-3.5" }), "Provider API key"]
313
+ children: [/* @__PURE__ */ T(b, { className: "h-3.5 w-3.5" }), s("mybodyshield.pages.aiControls.providerApiKey", "Provider API key")]
198
314
  })
199
315
  }),
200
- /* @__PURE__ */ y(C, {
316
+ /* @__PURE__ */ T(k, {
201
317
  id: "myb-ai-key",
202
318
  type: "password",
203
- value: I.providerKey,
204
- onChange: (e) => L((t) => ({
319
+ value: h.providerKey,
320
+ onChange: (e) => S((t) => ({
205
321
  ...t,
206
322
  providerKey: e.target.value,
207
323
  clearKey: !1
208
324
  })),
209
- placeholder: l.hasProviderKey ? "•••••••• (saved)" : "Optional",
210
- disabled: I.clearKey
325
+ placeholder: a.hasProviderKey ? s("mybodyshield.pages.aiControls.providerKeySaved", "•••••••• (saved)") : s("mybodyshield.pages.aiControls.providerKeyPlaceholder", "Optional"),
326
+ disabled: h.clearKey
211
327
  }),
212
- /* @__PURE__ */ b("div", {
328
+ /* @__PURE__ */ E("div", {
213
329
  className: "flex items-center gap-2",
214
- children: [/* @__PURE__ */ y("input", {
330
+ children: [/* @__PURE__ */ T("input", {
215
331
  id: "myb-ai-clear-key",
216
332
  type: "checkbox",
217
- checked: I.clearKey,
218
- onChange: (e) => L((t) => ({
333
+ checked: h.clearKey,
334
+ onChange: (e) => S((t) => ({
219
335
  ...t,
220
336
  clearKey: e.target.checked,
221
337
  providerKey: ""
222
338
  })),
223
339
  className: "h-4 w-4 rounded border-border-seam text-accent focus:ring-accent"
224
- }), /* @__PURE__ */ y(w, {
340
+ }), /* @__PURE__ */ T(A, {
225
341
  htmlFor: "myb-ai-clear-key",
226
342
  className: "text-xs font-normal text-text-secondary",
227
- children: "Clear saved key and fall back to the workspace default"
343
+ children: s("mybodyshield.pages.aiControls.clearKey", "Clear saved key and fall back to the workspace default")
228
344
  })]
229
345
  })
230
346
  ]
231
347
  })
232
348
  ]
233
349
  }),
234
- B && /* @__PURE__ */ y("p", {
350
+ U && /* @__PURE__ */ T("p", {
235
351
  className: "mt-4 text-sm text-status-success-text",
236
- children: "AI settings saved."
352
+ children: s("mybodyshield.pages.aiControls.settingsSaved", "AI settings saved.")
237
353
  }),
238
- R && /* @__PURE__ */ y("p", {
354
+ C && /* @__PURE__ */ T("p", {
239
355
  className: "mt-4 text-sm text-status-error-text",
240
- children: R
356
+ children: C
241
357
  })
242
358
  ]
243
359
  })
244
360
  }),
245
- /* @__PURE__ */ y(s, {
246
- title: "Operation history",
247
- description: "Redacted audit log of AI operations for your account.",
248
- children: u.isLoading ? /* @__PURE__ */ y(o, { label: "Loading operation history…" }) : u.isError ? /* @__PURE__ */ y(a, {
249
- message: "We couldn't load the operation log.",
250
- onRetry: () => u.refetch()
251
- }) : u.data?.items.length === 0 ? /* @__PURE__ */ b(S, {
361
+ /* @__PURE__ */ T(p, {
362
+ title: s("mybodyshield.pages.aiControls.operationHistory", "Operation history"),
363
+ description: s("mybodyshield.pages.aiControls.operationHistoryDescription", "Redacted audit log of AI operations for your account."),
364
+ children: o.isLoading ? /* @__PURE__ */ T(f, { label: s("mybodyshield.pages.aiControls.loadingHistory", "Loading operation history…") }) : o.isError ? /* @__PURE__ */ T(d, {
365
+ message: s("mybodyshield.pages.aiControls.historyError", "We couldn't load the operation log."),
366
+ onRetry: () => o.refetch()
367
+ }) : o.data?.items.length === 0 ? /* @__PURE__ */ E(O, {
252
368
  treatment: "plain",
253
369
  className: "p-8 text-center",
254
370
  children: [
255
- /* @__PURE__ */ y(v, { className: "mx-auto h-8 w-8 text-text-tertiary" }),
256
- /* @__PURE__ */ y("p", {
371
+ /* @__PURE__ */ T(w, { className: "mx-auto h-8 w-8 text-text-tertiary" }),
372
+ /* @__PURE__ */ T("p", {
257
373
  className: "mt-3 text-sm font-medium text-text-primary",
258
- children: "No AI operations yet"
374
+ children: s("mybodyshield.pages.aiControls.noOperations", "No AI operations yet")
259
375
  }),
260
- /* @__PURE__ */ y("p", {
376
+ /* @__PURE__ */ T("p", {
261
377
  className: "mt-1 text-xs text-text-tertiary",
262
- children: "Operations appear here once AI-generated guidance runs."
378
+ children: s("mybodyshield.pages.aiControls.noOperationsDescription", "Operations appear here once AI-generated guidance runs.")
263
379
  })
264
380
  ]
265
- }) : /* @__PURE__ */ y(c, {
266
- columns: [
267
- {
268
- key: "createdAt",
269
- header: "Time",
270
- sortValue: (e) => new Date(e.createdAt).getTime(),
271
- render: (e) => /* @__PURE__ */ b("div", {
272
- className: "text-text-primary",
273
- children: [/* @__PURE__ */ y("span", {
274
- className: "block text-sm",
275
- children: n(e.createdAt)
276
- }), /* @__PURE__ */ y("span", {
277
- className: "text-xs text-text-tertiary",
278
- children: i(e.createdAt)
279
- })]
280
- })
281
- },
282
- {
283
- key: "operationType",
284
- header: "Operation",
285
- render: (e) => /* @__PURE__ */ y("span", {
286
- className: "text-text-secondary",
287
- children: r(e.operationType)
288
- })
289
- },
290
- {
291
- key: "provider",
292
- header: "Provider / Model",
293
- render: (e) => /* @__PURE__ */ b("div", { children: [/* @__PURE__ */ y("span", {
294
- className: "block text-sm text-text-primary",
295
- children: M[e.provider]
296
- }), /* @__PURE__ */ y("span", {
297
- className: "text-xs text-text-tertiary",
298
- children: e.modelName
299
- })] })
300
- },
301
- {
302
- key: "tokens",
303
- header: "Tokens",
304
- align: "right",
305
- render: (e) => /* @__PURE__ */ b("span", {
306
- className: "tabular-nums text-text-secondary",
307
- children: [
308
- e.inputTokens ?? "—",
309
- " / ",
310
- e.outputTokens ?? "—"
311
- ]
312
- })
313
- },
314
- {
315
- key: "status",
316
- header: "Status",
317
- render: (e) => /* @__PURE__ */ y("span", {
318
- className: `inline-flex items-center rounded-full px-2 py-0.5 text-xs font-medium ${e.status === "SUCCESS" ? "bg-status-success-bg text-status-success-text" : "bg-status-error-bg text-status-error-text"}`,
319
- children: r(e.status)
320
- })
321
- },
322
- {
323
- key: "error",
324
- header: "Error",
325
- hideOnMobile: !0,
326
- render: (e) => e.errorMessage ? /* @__PURE__ */ y("span", {
327
- className: "text-xs text-status-error-text",
328
- children: e.errorMessage
329
- }) : /* @__PURE__ */ y("span", {
330
- className: "text-text-tertiary",
331
- children: "—"
332
- })
333
- }
334
- ],
335
- rows: u.data?.items ?? [],
381
+ }) : /* @__PURE__ */ T(m, {
382
+ columns: Y,
383
+ rows: o.data?.items ?? [],
336
384
  rowKey: (e) => e.id,
337
385
  defaultSort: {
338
386
  key: "createdAt",
@@ -343,36 +391,36 @@ function F({ settings: l, logsQuery: u }) {
343
391
  ]
344
392
  });
345
393
  }
346
- function I() {
347
- let t = u(), n = l();
348
- if (t.isLoading) return /* @__PURE__ */ y(e, {
349
- title: "AI controls",
350
- children: /* @__PURE__ */ y(o, { label: "Loading AI settings…" })
394
+ function W() {
395
+ let t = u(), n = s(), r = a();
396
+ if (n.isLoading) return /* @__PURE__ */ T(e, {
397
+ title: t("mybodyshield.pages.aiControls.title", "AI controls"),
398
+ children: /* @__PURE__ */ T(f, { label: t("mybodyshield.pages.aiControls.loadingSettings", "Loading AI settings…") })
351
399
  });
352
- if (t.isError) return /* @__PURE__ */ y(e, {
353
- title: "AI controls",
354
- children: /* @__PURE__ */ y(a, {
355
- title: "Could not load AI settings",
356
- message: "We couldn't fetch your AI configuration. Try again in a moment.",
357
- onRetry: () => t.refetch()
400
+ if (n.isError) return /* @__PURE__ */ T(e, {
401
+ title: t("mybodyshield.pages.aiControls.title", "AI controls"),
402
+ children: /* @__PURE__ */ T(d, {
403
+ title: t("mybodyshield.pages.aiControls.errorTitle", "Could not load AI settings"),
404
+ message: t("mybodyshield.pages.aiControls.error", "We couldn't fetch your AI configuration. Try again in a moment."),
405
+ onRetry: () => n.refetch()
358
406
  })
359
407
  });
360
- let r = t.data;
361
- if (!r) return /* @__PURE__ */ y(e, {
362
- title: "AI controls",
363
- children: /* @__PURE__ */ y(a, {
364
- title: "Could not load AI settings",
365
- message: "We couldn't fetch your AI configuration. Try again in a moment.",
366
- onRetry: () => t.refetch()
408
+ let i = n.data;
409
+ if (!i) return /* @__PURE__ */ T(e, {
410
+ title: t("mybodyshield.pages.aiControls.title", "AI controls"),
411
+ children: /* @__PURE__ */ T(d, {
412
+ title: t("mybodyshield.pages.aiControls.errorTitle", "Could not load AI settings"),
413
+ message: t("mybodyshield.pages.aiControls.error", "We couldn't fetch your AI configuration. Try again in a moment."),
414
+ onRetry: () => n.refetch()
367
415
  })
368
416
  });
369
- let i = `${r.id}:${r.updatedAt}`;
370
- return /* @__PURE__ */ y(F, {
371
- settings: r,
372
- logsQuery: n
373
- }, i);
417
+ let o = `${i.id}:${i.updatedAt}`;
418
+ return /* @__PURE__ */ T(U, {
419
+ settings: i,
420
+ logsQuery: r
421
+ }, o);
374
422
  }
375
423
  //#endregion
376
- export { I as AiControlsPage };
424
+ export { W as AiControlsPage };
377
425
 
378
426
  //# sourceMappingURL=AiControlsPage.js.map