@medusajs/dashboard 2.12.3-snapshot-20251217081413 → 2.12.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 (23) hide show
  1. package/dist/add-locales-GGNZCABB.mjs +81 -0
  2. package/dist/app.css +10 -0
  3. package/dist/app.js +483 -374
  4. package/dist/app.mjs +1 -1
  5. package/dist/{store-add-locales-I4GX3KAY.mjs → chunk-IKTGFXWR.mjs} +1 -66
  6. package/dist/{chunk-FJR3D6EM.mjs → chunk-LWYKUORZ.mjs} +14 -11
  7. package/dist/en.json +1 -2
  8. package/dist/{product-attributes-S535VXSC.mjs → product-attributes-STD47BGC.mjs} +1 -1
  9. package/dist/{product-create-DKBLOS3M.mjs → product-create-LVGWVQAT.mjs} +1 -1
  10. package/dist/{product-detail-D2PJ64Q3.mjs → product-detail-OYVHJH3D.mjs} +1 -1
  11. package/dist/{product-edit-K6CAQD5H.mjs → product-edit-3SIUUIW4.mjs} +1 -1
  12. package/dist/{product-organization-IQFN54D2.mjs → product-organization-3PQ45C4B.mjs} +1 -1
  13. package/dist/store-add-locales-GWCGIXHU.mjs +81 -0
  14. package/dist/{translation-list-KSM4QA3K.mjs → translation-list-FK7XYLHX.mjs} +182 -109
  15. package/package.json +9 -9
  16. package/src/dashboard-app/routes/get-route.map.tsx +4 -0
  17. package/src/i18n/translations/en.json +1 -2
  18. package/src/i18n/translations/es.json +1 -1
  19. package/src/routes/translations/add-locales/add-locales.tsx +29 -0
  20. package/src/routes/translations/add-locales/index.tsx +1 -0
  21. package/src/routes/translations/translation-list/components/active-locales-section/active-locales-section.tsx +41 -16
  22. package/src/routes/translations/translation-list/components/translation-list-section/translation-list-section.tsx +5 -1
  23. package/src/routes/translations/translation-list/components/translations-completion-section/translations-completion-section.tsx +144 -103
@@ -51,9 +51,16 @@ import { useTranslation as useTranslation4 } from "react-i18next";
51
51
 
52
52
  // src/routes/translations/translation-list/components/active-locales-section/active-locales-section.tsx
53
53
  import { PencilSquare, Language } from "@medusajs/icons";
54
- import { Container, Heading, IconButton, InlineTip, Text } from "@medusajs/ui";
54
+ import {
55
+ Container,
56
+ Heading,
57
+ IconButton,
58
+ InlineTip,
59
+ Text,
60
+ Tooltip
61
+ } from "@medusajs/ui";
55
62
  import { useTranslation } from "react-i18next";
56
- import { useCallback } from "react";
63
+ import { useCallback, useState } from "react";
57
64
  import { useNavigate } from "react-router-dom";
58
65
  import { jsx, jsxs } from "react/jsx-runtime";
59
66
  var ActiveLocalesSection = ({
@@ -61,8 +68,9 @@ var ActiveLocalesSection = ({
61
68
  }) => {
62
69
  const { t } = useTranslation();
63
70
  const navigate = useNavigate();
71
+ const [isHovered, setIsHovered] = useState(false);
64
72
  const handleManageLocales = useCallback(() => {
65
- navigate("/settings/store/locales");
73
+ navigate("/settings/translations/add-locales");
66
74
  }, [navigate]);
67
75
  const renderLocales = useCallback(() => {
68
76
  const maxLocalesToDetail = 2;
@@ -77,13 +85,28 @@ var ActiveLocalesSection = ({
77
85
  /* @__PURE__ */ jsx(Heading, { level: "h2", children: t("translations.activeLocales.heading") }),
78
86
  /* @__PURE__ */ jsx(IconButton, { variant: "transparent", onClick: handleManageLocales, children: /* @__PURE__ */ jsx(PencilSquare, {}) })
79
87
  ] }),
80
- /* @__PURE__ */ jsx("div", { className: "px-1 pb-1", children: hasLocales ? /* @__PURE__ */ jsxs(Container, { className: "bg-ui-bg-component flex items-center gap-x-4 px-6 py-2", children: [
81
- /* @__PURE__ */ jsx(IconAvatar, { children: /* @__PURE__ */ jsx(Language, {}) }),
82
- /* @__PURE__ */ jsxs("div", { className: "flex flex-col", children: [
83
- /* @__PURE__ */ jsx(Text, { size: "small", weight: "plus", children: t("translations.activeLocales.subtitle") }),
84
- /* @__PURE__ */ jsx(Text, { className: "text-ui-fg-subtle", size: "small", children: renderLocales() })
85
- ] })
86
- ] }) : /* @__PURE__ */ jsx(InlineTip, { label: "Tip", children: t("translations.activeLocales.noLocalesTip") }) })
88
+ /* @__PURE__ */ jsx("div", { className: "px-1 pb-1", children: hasLocales ? /* @__PURE__ */ jsx(
89
+ Tooltip,
90
+ {
91
+ open: isHovered,
92
+ content: /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-y-1 p-1", children: locales.map((locale) => /* @__PURE__ */ jsx(Text, { size: "small", weight: "plus", children: locale.name }, locale.code)) }),
93
+ children: /* @__PURE__ */ jsxs(
94
+ Container,
95
+ {
96
+ className: "bg-ui-bg-component border-r-1 flex items-center gap-x-4 px-[19px] py-2",
97
+ onMouseEnter: () => setIsHovered(true),
98
+ onMouseLeave: () => setIsHovered(false),
99
+ children: [
100
+ /* @__PURE__ */ jsx(IconAvatar, { className: "border-ui-border-base border", children: /* @__PURE__ */ jsx(Language, {}) }),
101
+ /* @__PURE__ */ jsxs("div", { className: "flex flex-col", children: [
102
+ /* @__PURE__ */ jsx(Text, { size: "small", weight: "plus", children: t("translations.activeLocales.subtitle") }),
103
+ /* @__PURE__ */ jsx(Text, { className: "text-ui-fg-subtle", size: "small", children: renderLocales() })
104
+ ] })
105
+ ]
106
+ }
107
+ )
108
+ }
109
+ ) : /* @__PURE__ */ jsx(InlineTip, { label: "Tip", children: t("translations.activeLocales.noLocalesTip") }) })
87
110
  ] });
88
111
  };
89
112
 
@@ -111,7 +134,15 @@ var TranslationListSection = ({
111
134
  Link,
112
135
  {
113
136
  to: `/settings/translations/edit?reference=${entity.reference}`,
114
- children: /* @__PURE__ */ jsx2(Button, { variant: "secondary", size: "small", disabled: !hasLocales, children: "Edit" })
137
+ children: /* @__PURE__ */ jsx2(
138
+ Button,
139
+ {
140
+ variant: "secondary",
141
+ size: "small",
142
+ disabled: !hasLocales || !entity.totalCount,
143
+ children: "Edit"
144
+ }
145
+ )
115
146
  }
116
147
  )
117
148
  ]
@@ -121,8 +152,8 @@ var TranslationListSection = ({
121
152
  };
122
153
 
123
154
  // src/routes/translations/translation-list/components/translations-completion-section/translations-completion-section.tsx
124
- import { Container as Container3, Heading as Heading2, Text as Text3, Tooltip } from "@medusajs/ui";
125
- import { useMemo, useState } from "react";
155
+ import { Container as Container3, Divider, Heading as Heading2, Text as Text3, Tooltip as Tooltip2 } from "@medusajs/ui";
156
+ import { useMemo, useState as useState2 } from "react";
126
157
  import { useTranslation as useTranslation3 } from "react-i18next";
127
158
  import { Fragment, jsx as jsx3, jsxs as jsxs3 } from "react/jsx-runtime";
128
159
  var TranslationsCompletionSection = ({
@@ -130,7 +161,7 @@ var TranslationsCompletionSection = ({
130
161
  locales
131
162
  }) => {
132
163
  const { t } = useTranslation3();
133
- const [hoveredLocale, setHoveredLocale] = useState(null);
164
+ const [hoveredLocale, setHoveredLocale] = useState2(null);
134
165
  const { translatedCount, totalCount } = Object.values(statistics).reduce(
135
166
  (acc, curr) => ({
136
167
  translatedCount: acc.translatedCount + curr.translated,
@@ -193,7 +224,8 @@ var TranslationsCompletionSection = ({
193
224
  className: "mr-0.5 h-full rounded-sm transition-all",
194
225
  style: {
195
226
  width: `${percentage}%`,
196
- backgroundColor: "var(--bg-interactive)"
227
+ backgroundColor: "var(--tag-blue-icon)",
228
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)"
197
229
  }
198
230
  }
199
231
  ),
@@ -202,8 +234,8 @@ var TranslationsCompletionSection = ({
202
234
  {
203
235
  className: "h-full flex-1 rounded-sm",
204
236
  style: {
205
- backgroundColor: "var(--bg-interactive)",
206
- opacity: 0.3
237
+ backgroundColor: "var(--tag-blue-border)",
238
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)"
207
239
  }
208
240
  }
209
241
  )
@@ -212,8 +244,8 @@ var TranslationsCompletionSection = ({
212
244
  {
213
245
  className: "h-full w-full rounded-sm",
214
246
  style: {
215
- backgroundColor: "var(--bg-interactive)",
216
- opacity: 0.3
247
+ backgroundColor: "var(--tag-blue-border)",
248
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)"
217
249
  }
218
250
  }
219
251
  ) }),
@@ -229,117 +261,158 @@ var TranslationsCompletionSection = ({
229
261
  ] })
230
262
  ] })
231
263
  ] }),
232
- localeStats.length > 0 && /* @__PURE__ */ jsxs3("div", { className: "border-ui-border-strong flex flex-col gap-y-3 border-t border-dashed px-6 pb-6 pt-4", children: [
233
- /* @__PURE__ */ jsx3("div", { className: "flex h-32 w-full items-end gap-1", children: localeStats.map((locale) => {
234
- const heightPercent = locale.total / maxTotal * 100;
235
- const translatedPercent = locale.total > 0 ? locale.translated / locale.total * 100 : 0;
236
- return /* @__PURE__ */ jsx3(
237
- Tooltip,
238
- {
239
- open: hoveredLocale === locale.code,
240
- content: /* @__PURE__ */ jsxs3("div", { className: "flex flex-col gap-y-1 p-1", children: [
241
- /* @__PURE__ */ jsx3(Text3, { size: "small", weight: "plus", children: locale.name }),
242
- /* @__PURE__ */ jsxs3("div", { className: "flex items-center justify-between", children: [
243
- /* @__PURE__ */ jsxs3("div", { className: "flex items-center gap-x-2", children: [
264
+ localeStats.length > 0 && /* @__PURE__ */ jsxs3(Fragment, { children: [
265
+ /* @__PURE__ */ jsx3(Divider, { variant: "dashed" }),
266
+ /* @__PURE__ */ jsxs3("div", { className: "flex flex-col gap-y-3 px-6 pb-6 pt-4", children: [
267
+ /* @__PURE__ */ jsx3("div", { className: "flex h-32 w-full items-end gap-1", children: localeStats.map((locale) => {
268
+ const heightPercent = locale.total / maxTotal * 100;
269
+ const translatedPercent = locale.total > 0 ? locale.translated / locale.total * 100 : 0;
270
+ return /* @__PURE__ */ jsx3(
271
+ Tooltip2,
272
+ {
273
+ open: hoveredLocale === locale.code,
274
+ content: /* @__PURE__ */ jsxs3("div", { className: "flex min-w-[150px] flex-col gap-y-1 p-1", children: [
275
+ /* @__PURE__ */ jsx3(Text3, { size: "small", weight: "plus", children: locale.name }),
276
+ /* @__PURE__ */ jsxs3("div", { className: "flex items-center justify-between", children: [
277
+ /* @__PURE__ */ jsxs3("div", { className: "flex items-center gap-x-2", children: [
278
+ /* @__PURE__ */ jsx3(
279
+ "div",
280
+ {
281
+ className: "h-2 w-2 rounded-full",
282
+ style: {
283
+ backgroundColor: "var(--tag-blue-icon)",
284
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)"
285
+ }
286
+ }
287
+ ),
288
+ /* @__PURE__ */ jsx3(
289
+ Text3,
290
+ {
291
+ size: "small",
292
+ weight: "plus",
293
+ className: "text-ui-fg-base",
294
+ children: t("translations.completion.translated")
295
+ }
296
+ )
297
+ ] }),
244
298
  /* @__PURE__ */ jsx3(
245
- "div",
299
+ Text3,
246
300
  {
247
- className: "h-2 w-2 rounded-full",
248
- style: { backgroundColor: "var(--bg-interactive)" }
301
+ size: "small",
302
+ weight: "plus",
303
+ className: "text-ui-fg-base",
304
+ children: locale.translated
249
305
  }
250
- ),
306
+ )
307
+ ] }),
308
+ /* @__PURE__ */ jsxs3("div", { className: "flex items-center justify-between", children: [
309
+ /* @__PURE__ */ jsxs3("div", { className: "flex items-center gap-x-2", children: [
310
+ /* @__PURE__ */ jsx3(
311
+ "div",
312
+ {
313
+ className: "h-2 w-2 rounded-full",
314
+ style: {
315
+ backgroundColor: "var(--tag-blue-border)",
316
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)"
317
+ }
318
+ }
319
+ ),
320
+ /* @__PURE__ */ jsx3(
321
+ Text3,
322
+ {
323
+ size: "small",
324
+ weight: "plus",
325
+ className: "text-ui-fg-base",
326
+ children: t("translations.completion.toTranslate")
327
+ }
328
+ )
329
+ ] }),
251
330
  /* @__PURE__ */ jsx3(
252
331
  Text3,
253
332
  {
254
333
  size: "small",
255
334
  weight: "plus",
256
- className: "text-ui-fg-subtle",
257
- children: t("translations.completion.translated")
335
+ className: "text-ui-fg-base",
336
+ children: locale.toTranslate
258
337
  }
259
338
  )
260
- ] }),
261
- /* @__PURE__ */ jsx3(Text3, { size: "small", weight: "plus", children: locale.translated })
339
+ ] })
262
340
  ] }),
263
- /* @__PURE__ */ jsxs3("div", { className: "flex items-center gap-x-2", children: [
264
- /* @__PURE__ */ jsx3(
265
- "div",
266
- {
267
- className: "h-2 w-2 rounded-full",
268
- style: {
269
- backgroundColor: "var(--bg-interactive)",
270
- opacity: 0.3
271
- }
272
- }
273
- ),
274
- /* @__PURE__ */ jsx3(
275
- Text3,
276
- {
277
- size: "small",
278
- weight: "plus",
279
- className: "text-ui-fg-subtle",
280
- children: t("translations.completion.toTranslate")
281
- }
282
- ),
283
- /* @__PURE__ */ jsx3(Text3, { size: "small", weight: "plus", children: locale.toTranslate })
284
- ] })
285
- ] }),
286
- children: /* @__PURE__ */ jsxs3(
287
- "div",
288
- {
289
- className: "flex min-w-2 flex-1 flex-col justify-end overflow-hidden rounded-t-sm transition-opacity",
290
- style: { height: `${heightPercent}%` },
291
- onMouseEnter: () => setHoveredLocale(locale.code),
292
- onMouseLeave: () => setHoveredLocale(null),
293
- children: [
294
- /* @__PURE__ */ jsx3(
341
+ children: /* @__PURE__ */ jsx3("div", { className: "flex h-full flex-1 items-end justify-center", children: /* @__PURE__ */ jsx3(
342
+ "div",
343
+ {
344
+ className: "flex w-full min-w-2 max-w-[96px] flex-col justify-end overflow-hidden rounded-t-sm transition-opacity",
345
+ style: { height: `${heightPercent}%` },
346
+ onMouseEnter: () => setHoveredLocale(locale.code),
347
+ onMouseLeave: () => setHoveredLocale(null),
348
+ children: translatedPercent === 0 ? /* @__PURE__ */ jsx3(
295
349
  "div",
296
350
  {
297
- className: "w-full rounded-t-sm",
351
+ className: "w-full rounded-sm",
298
352
  style: {
299
- height: `${100 - translatedPercent}%`,
300
- backgroundColor: "var(--bg-interactive)",
301
- opacity: 0.3,
302
- minHeight: locale.toTranslate > 0 ? "2px" : "0"
353
+ height: "100%",
354
+ backgroundColor: "var(--tag-neutral-bg)",
355
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)"
303
356
  }
304
357
  }
305
- ),
306
- translatedPercent > 0 && /* @__PURE__ */ jsx3(
307
- "div",
308
- {
309
- className: "mt-0.5 w-full rounded-sm",
310
- style: {
311
- height: `${translatedPercent}%`,
312
- backgroundColor: "var(--bg-interactive)",
313
- minHeight: locale.translated > 0 ? "2px" : "0"
358
+ ) : /* @__PURE__ */ jsxs3(Fragment, { children: [
359
+ /* @__PURE__ */ jsx3(
360
+ "div",
361
+ {
362
+ className: "w-full rounded-sm",
363
+ style: {
364
+ height: `${100 - translatedPercent}%`,
365
+ backgroundColor: "var(--tag-blue-border)",
366
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)",
367
+ minHeight: locale.toTranslate > 0 ? "2px" : "0"
368
+ }
314
369
  }
315
- }
316
- )
317
- ]
370
+ ),
371
+ translatedPercent > 0 && /* @__PURE__ */ jsx3(
372
+ "div",
373
+ {
374
+ className: "mt-0.5 w-full rounded-sm",
375
+ style: {
376
+ height: `${translatedPercent}%`,
377
+ backgroundColor: "var(--tag-blue-icon)",
378
+ boxShadow: "inset 0 0 0 0.5px var(--alpha-250)",
379
+ minHeight: locale.translated > 0 ? "2px" : "0"
380
+ }
381
+ }
382
+ )
383
+ ] })
384
+ }
385
+ ) })
386
+ },
387
+ locale.code
388
+ );
389
+ }) }),
390
+ localeStatsCount < 9 && /* @__PURE__ */ jsx3("div", { className: "flex w-full gap-1", children: localeStats.map((locale) => /* @__PURE__ */ jsx3(
391
+ "div",
392
+ {
393
+ className: "flex flex-1 items-center justify-center",
394
+ children: /* @__PURE__ */ jsx3(
395
+ Text3,
396
+ {
397
+ size: "xsmall",
398
+ weight: "plus",
399
+ className: "text-ui-fg-subtle min-w-2 whitespace-normal break-words text-center leading-tight",
400
+ children: localeStatsCount < 6 ? locale.name : locale.code
318
401
  }
319
402
  )
320
403
  },
321
404
  locale.code
322
- );
323
- }) }),
324
- localeStatsCount < 9 && /* @__PURE__ */ jsx3("div", { className: "flex w-full gap-1", children: localeStats.map((locale) => /* @__PURE__ */ jsx3(
325
- Text3,
326
- {
327
- size: "xsmall",
328
- weight: "plus",
329
- className: "text-ui-fg-subtle min-w-2 flex-1 whitespace-normal break-words text-center leading-tight",
330
- children: localeStatsCount < 6 ? locale.name : locale.code
331
- },
332
- locale.code
333
- )) }),
334
- localeStatsCount > 9 && /* @__PURE__ */ jsx3(
335
- Text3,
336
- {
337
- weight: "plus",
338
- size: "xsmall",
339
- className: "text-ui-fg-subtle text-center",
340
- children: t("translations.completion.footer")
341
- }
342
- )
405
+ )) }),
406
+ localeStatsCount > 9 && /* @__PURE__ */ jsx3(
407
+ Text3,
408
+ {
409
+ weight: "plus",
410
+ size: "xsmall",
411
+ className: "text-ui-fg-subtle text-center",
412
+ children: t("translations.completion.footer")
413
+ }
414
+ )
415
+ ] })
343
416
  ] })
344
417
  ] });
345
418
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@medusajs/dashboard",
3
- "version": "2.12.3-snapshot-20251217081413",
3
+ "version": "2.12.3",
4
4
  "scripts": {
5
5
  "generate:static": "node ./scripts/generate-currencies.js && prettier --write ./src/lib/currencies.ts",
6
6
  "dev": "../../../node_modules/.bin/vite",
@@ -46,10 +46,10 @@
46
46
  "@dnd-kit/utilities": "^3.2.2",
47
47
  "@hookform/error-message": "^2.0.1",
48
48
  "@hookform/resolvers": "3.4.2",
49
- "@medusajs/admin-shared": "2.12.3-snapshot-20251217081413",
50
- "@medusajs/icons": "2.12.3-snapshot-20251217081413",
51
- "@medusajs/js-sdk": "2.12.3-snapshot-20251217081413",
52
- "@medusajs/ui": "4.0.31-snapshot-20251217081413",
49
+ "@medusajs/admin-shared": "2.12.3",
50
+ "@medusajs/icons": "2.12.3",
51
+ "@medusajs/js-sdk": "2.12.3",
52
+ "@medusajs/ui": "4.0.31",
53
53
  "@radix-ui/react-dialog": "1.1.4",
54
54
  "@radix-ui/react-dismissable-layer": "1.1.4",
55
55
  "@tanstack/react-query": "5.64.2",
@@ -80,10 +80,10 @@
80
80
  "zod": "3.25.76"
81
81
  },
82
82
  "devDependencies": {
83
- "@medusajs/admin-shared": "2.12.3-snapshot-20251217081413",
84
- "@medusajs/admin-vite-plugin": "2.12.3-snapshot-20251217081413",
85
- "@medusajs/types": "2.12.3-snapshot-20251217081413",
86
- "@medusajs/ui-preset": "2.12.3-snapshot-20251217081413"
83
+ "@medusajs/admin-shared": "2.12.3",
84
+ "@medusajs/admin-vite-plugin": "2.12.3",
85
+ "@medusajs/types": "2.12.3",
86
+ "@medusajs/ui-preset": "2.12.3"
87
87
  },
88
88
  "packageManager": "yarn@3.2.1"
89
89
  }
@@ -1857,6 +1857,10 @@ export function getRouteMap({
1857
1857
  lazy: () =>
1858
1858
  import("../../routes/translations/translations-edit"),
1859
1859
  },
1860
+ {
1861
+ path: "add-locales",
1862
+ lazy: () => import("../../routes/translations/add-locales"),
1863
+ },
1860
1864
  ],
1861
1865
  },
1862
1866
  ...(settingsRoutes?.[0]?.children || []),
@@ -2514,7 +2514,6 @@
2514
2514
  "manage": "Manage translations",
2515
2515
  "manageLocales": "Manage locales"
2516
2516
  },
2517
- "title": "Translation domains",
2518
2517
  "subtitle": "Manage translations of your data in Medusa",
2519
2518
  "list": {
2520
2519
  "metrics": "{{translated}} of {{total}} fields translated"
@@ -2538,7 +2537,7 @@
2538
2537
  "completion": {
2539
2538
  "heading": "Translated fields",
2540
2539
  "translated": "Translated",
2541
- "toTranslate": "To be translated",
2540
+ "toTranslate": "Missing",
2542
2541
  "footer": "Languages"
2543
2542
  }
2544
2543
  },
@@ -2477,7 +2477,7 @@
2477
2477
  "completion": {
2478
2478
  "heading": "Textos traducidos",
2479
2479
  "translated": "Traducidos",
2480
- "toTranslate": "Por traducir",
2480
+ "toTranslate": "Faltantes",
2481
2481
  "footer": "Idiomas"
2482
2482
  }
2483
2483
  },
@@ -0,0 +1,29 @@
1
+ import { RouteFocusModal } from "../../../components/modals/route-focus-modal"
2
+ import { useStore } from "../../../hooks/api"
3
+ import { useFeatureFlag } from "../../../providers/feature-flag-provider"
4
+ import { useNavigate } from "react-router-dom"
5
+ import { AddLocalesForm } from "../../store/store-add-locales/components/add-locales-form/add-locales-form"
6
+
7
+ export const TranslationsAddLocales = () => {
8
+ const isEnabled = useFeatureFlag("translation")
9
+ const navigate = useNavigate()
10
+
11
+ if (!isEnabled) {
12
+ navigate(-1)
13
+ return null
14
+ }
15
+
16
+ const { store, isPending, isError, error } = useStore()
17
+
18
+ const ready = !!store && !isPending
19
+
20
+ if (isError) {
21
+ throw error
22
+ }
23
+
24
+ return (
25
+ <RouteFocusModal>
26
+ {ready && <AddLocalesForm store={store} />}
27
+ </RouteFocusModal>
28
+ )
29
+ }
@@ -0,0 +1 @@
1
+ export { TranslationsAddLocales as Component } from "./add-locales"
@@ -1,9 +1,16 @@
1
1
  import { PencilSquare, Language } from "@medusajs/icons"
2
- import { Container, Heading, IconButton, InlineTip, Text } from "@medusajs/ui"
2
+ import {
3
+ Container,
4
+ Heading,
5
+ IconButton,
6
+ InlineTip,
7
+ Text,
8
+ Tooltip,
9
+ } from "@medusajs/ui"
3
10
  import { useTranslation } from "react-i18next"
4
11
  import { IconAvatar } from "../../../../../components/common/icon-avatar"
5
12
  import { HttpTypes } from "@medusajs/types"
6
- import { useCallback } from "react"
13
+ import { useCallback, useState } from "react"
7
14
  import { useNavigate } from "react-router-dom"
8
15
 
9
16
  type ActiveLocalesSectionProps = {
@@ -15,9 +22,10 @@ export const ActiveLocalesSection = ({
15
22
  }: ActiveLocalesSectionProps) => {
16
23
  const { t } = useTranslation()
17
24
  const navigate = useNavigate()
25
+ const [isHovered, setIsHovered] = useState(false)
18
26
 
19
27
  const handleManageLocales = useCallback(() => {
20
- navigate("/settings/store/locales")
28
+ navigate("/settings/translations/add-locales")
21
29
  }, [navigate])
22
30
 
23
31
  const renderLocales = useCallback(() => {
@@ -44,19 +52,36 @@ export const ActiveLocalesSection = ({
44
52
  </div>
45
53
  <div className="px-1 pb-1">
46
54
  {hasLocales ? (
47
- <Container className="bg-ui-bg-component flex items-center gap-x-4 px-6 py-2">
48
- <IconAvatar>
49
- <Language />
50
- </IconAvatar>
51
- <div className="flex flex-col">
52
- <Text size="small" weight="plus">
53
- {t("translations.activeLocales.subtitle")}
54
- </Text>
55
- <Text className="text-ui-fg-subtle" size="small">
56
- {renderLocales()}
57
- </Text>
58
- </div>
59
- </Container>
55
+ <Tooltip
56
+ open={isHovered}
57
+ content={
58
+ <div className="flex flex-col gap-y-1 p-1">
59
+ {locales.map((locale) => (
60
+ <Text key={locale.code} size="small" weight="plus">
61
+ {locale.name}
62
+ </Text>
63
+ ))}
64
+ </div>
65
+ }
66
+ >
67
+ <Container
68
+ className="bg-ui-bg-component border-r-1 flex items-center gap-x-4 px-[19px] py-2"
69
+ onMouseEnter={() => setIsHovered(true)}
70
+ onMouseLeave={() => setIsHovered(false)}
71
+ >
72
+ <IconAvatar className="border-ui-border-base border">
73
+ <Language />
74
+ </IconAvatar>
75
+ <div className="flex flex-col">
76
+ <Text size="small" weight="plus">
77
+ {t("translations.activeLocales.subtitle")}
78
+ </Text>
79
+ <Text className="text-ui-fg-subtle" size="small">
80
+ {renderLocales()}
81
+ </Text>
82
+ </div>
83
+ </Container>
84
+ </Tooltip>
60
85
  ) : (
61
86
  <InlineTip label="Tip">
62
87
  {t("translations.activeLocales.noLocalesTip")}
@@ -33,7 +33,11 @@ export const TranslationListSection = ({
33
33
  <Link
34
34
  to={`/settings/translations/edit?reference=${entity.reference}`}
35
35
  >
36
- <Button variant="secondary" size="small" disabled={!hasLocales}>
36
+ <Button
37
+ variant="secondary"
38
+ size="small"
39
+ disabled={!hasLocales || !entity.totalCount}
40
+ >
37
41
  Edit
38
42
  </Button>
39
43
  </Link>