feat(): Introduce translation module and preliminary application of them (#14189)

* feat(): Translation first steps

* feat(): locale middleware

* feat(): readonly links

* feat(): feature flag

* feat(): modules sdk

* feat(): translation module re export

* start adding workflows

* update typings

* update typings

* test(): Add integration tests

* test(): centralize filters preparation

* test(): centralize filters preparation

* remove unnecessary importy

* fix workflows

* Define StoreLocale inside Store Module

* Link definition to extend Store with supported_locales

* store_locale migration

* Add supported_locales handling in Store Module

* Tests

* Accept supported_locales in Store endpoints

* Add locales to js-sdk

* Include locale list and default locale in Store Detail section

* Initialize local namespace in js-sdk

* Add locales route

* Make code primary key of locale table to facilitate upserts

* Add locales routes

* Show locale code as is

* Add list translations api route

* Batch endpoint

* Types

* New batchTranslationsWorkflow and various updates to existent ones

* Edit default locale UI

* WIP

* Apply translation agnostically

* middleware

* Apply translation agnostically

* fix Apply translation agnostically

* apply translations to product list

* Add feature flag

* fetch translations by batches of 250 max

* fix apply

* improve and test util

* apply to product list

* dont manage translations if no locale

* normalize locale

* potential todo

* Protect translations routes with feature flag

* Extract normalize locale util to core/utils

* Normalize locale on write

* Normalize locale for read

* Use feature flag to guard translations UI across the board

* Avoid throwing incorrectly when locale_code not present in partial updates

* move applyTranslations util

* remove old tests

* fix util tests

* fix(): product end points

* cleanup

* update lock

* remove unused var

* cleanup

* fix apply locale

* missing new dep for test utils

* Change entity_type, entity_id to reference, reference_id

* Remove comment

* Avoid registering translations route if ff not enabled

* Prevent registering express handler for disabled route via defineFileConfig

* Add tests

* Add changeset

* Update test

* fix integration tests, module and internals

* Add locale id plus fixed

* Allow to pass array of reference_id

* fix unit tests

* fix link loading

* fix store route

* fix sales channel test

* fix tests

---------

Co-authored-by: Nicolas Gorga <nicogorga11@gmail.com>
Co-authored-by: Oli Juhl <59018053+olivermrbl@users.noreply.github.com>
This commit is contained in:
Adrien de Peretti
2025-12-08 19:33:08 +01:00
committed by GitHub
parent fea3d4ec49
commit 6dc0b8bed8
130 changed files with 5649 additions and 112 deletions
@@ -3,6 +3,7 @@ import { sdk } from "../../lib/client"
export type FeatureFlags = {
view_configurations?: boolean
translation?: boolean
[key: string]: boolean | undefined
}
@@ -10,13 +11,16 @@ export const useFeatureFlags = () => {
return useQuery<FeatureFlags>({
queryKey: ["admin", "feature-flags"],
queryFn: async () => {
const response = await sdk.client.fetch<{ feature_flags: FeatureFlags }>("/admin/feature-flags", {
method: "GET",
})
const response = await sdk.client.fetch<{ feature_flags: FeatureFlags }>(
"/admin/feature-flags",
{
method: "GET",
}
)
return response.feature_flags
},
staleTime: 5 * 60 * 1000, // Cache for 5 minutes
cacheTime: 10 * 60 * 1000, // Keep in cache for 10 minutes
})
}
}
@@ -11,6 +11,7 @@ export * from "./fulfillment-providers"
export * from "./fulfillment-sets"
export * from "./inventory"
export * from "./invites"
export * from "./locales"
export * from "./notification"
export * from "./orders"
export * from "./payment-collections"
@@ -0,0 +1,52 @@
import { FetchError } from "@medusajs/js-sdk"
import { HttpTypes } from "@medusajs/types"
import { QueryKey, UseQueryOptions, useQuery } from "@tanstack/react-query"
import { sdk } from "../../lib/client"
import { queryKeysFactory } from "../../lib/query-key-factory"
const LOCALES_QUERY_KEY = "locales" as const
const localesQueryKeys = queryKeysFactory(LOCALES_QUERY_KEY)
export const useLocales = (
query?: HttpTypes.AdminLocaleListParams,
options?: Omit<
UseQueryOptions<
HttpTypes.AdminLocaleListResponse,
FetchError,
HttpTypes.AdminLocaleListResponse,
QueryKey
>,
"queryFn" | "queryKey"
>
) => {
const { data, ...rest } = useQuery({
queryFn: () => sdk.admin.locale.list(query),
queryKey: localesQueryKeys.list(query),
...options,
})
return { ...data, ...rest }
}
export const useLocale = (
id: string,
query?: HttpTypes.AdminLocaleParams,
options?: Omit<
UseQueryOptions<
HttpTypes.AdminLocaleResponse,
FetchError,
HttpTypes.AdminLocaleResponse,
QueryKey
>,
"queryFn" | "queryKey"
>
) => {
const { data, ...rest } = useQuery({
queryKey: localesQueryKeys.detail(id),
queryFn: async () => sdk.admin.locale.retrieve(id, query),
...options,
})
return { ...data, ...rest }
}