diff --git a/src/components/pages/LanguagesPage.tsx b/src/components/pages/LanguagesPage.tsx index da49e1b..2ff1c83 100644 --- a/src/components/pages/LanguagesPage.tsx +++ b/src/components/pages/LanguagesPage.tsx @@ -1,7 +1,8 @@ import { useEffect, useState } from "react" -import { Languages, Plus } from "lucide-react" +import { Languages, Plus, Pencil } from "lucide-react" import { toast } from "sonner" import { languagesAPI } from "@/services/api" +import type { LanguageResponse } from "@/types" import { useLanguagesStore } from "@/stores/languagesStore" import { Button } from "@/components/ui/button" import { Input } from "@/components/ui/input" @@ -17,14 +18,17 @@ import { import { LoadingSpinner } from "@/components/common/LoadingSpinner" import { EmptyState } from "@/components/common/EmptyState" import { InfoTooltip } from "@/components/common/InfoTooltip" +import { useAuth } from "@/contexts/AuthContext" import { formatDate } from "@/utils/format" export default function LanguagesPage() { + const { isPlatformAdmin } = useAuth() const { languages, loading: storeLoading, lastFetched, fetch: fetchLanguages } = useLanguagesStore() const loading = storeLoading || (!lastFetched && languages.length === 0) const [dialogOpen, setDialogOpen] = useState(false) const [creating, setCreating] = useState(false) + const [editingLang, setEditingLang] = useState(null) const [name, setName] = useState("") const [code, setCode] = useState("") @@ -33,18 +37,34 @@ export default function LanguagesPage() { // eslint-disable-next-line react-hooks/exhaustive-deps }, []) - function openDialog() { + function openCreateDialog() { + setEditingLang(null) setName("") setCode("") setDialogOpen(true) } - async function handleCreate() { + function openEditDialog(lang: LanguageResponse) { + setEditingLang(lang) + setName(lang.name) + setCode(lang.code) + setDialogOpen(true) + } + + async function handleSave() { if (!name.trim() || code.trim().length !== 3) return setCreating(true) try { - await languagesAPI.create({ name: name.trim(), code: code.trim().toLowerCase() }) - toast.success("Language created") + if (editingLang) { + await languagesAPI.update(editingLang.id, { + name: name.trim(), + code: code.trim().toLowerCase(), + }) + toast.success("Language updated") + } else { + await languagesAPI.create({ name: name.trim(), code: code.trim().toLowerCase() }) + toast.success("Language created") + } setDialogOpen(false) useLanguagesStore.getState().invalidate() await fetchLanguages() @@ -53,7 +73,7 @@ export default function LanguagesPage() { if (status === 409) { toast.error("A language with this code already exists") } else { - toast.error("Failed to create language") + toast.error(editingLang ? "Failed to update language" : "Failed to create language") } } finally { setCreating(false) @@ -76,7 +96,7 @@ export default function LanguagesPage() { {languages.length} language{languages.length !== 1 ? "s" : ""} registered

- @@ -88,15 +108,26 @@ export default function LanguagesPage() { title="No languages yet" description="Languages define the translation targets for your projects. Create one to get started." actionLabel="Create Language" - onAction={openDialog} + onAction={openCreateDialog} /> ) : (
{languages.map((lang) => (
+ {isPlatformAdmin && ( + + )}
{lang.code} @@ -116,9 +147,11 @@ export default function LanguagesPage() { - Create Language + {editingLang ? "Edit Language" : "Create Language"} - Add a new target language for your translation projects. + {editingLang + ? "Update the language name or code." + : "Add a new target language for your translation projects."}
@@ -159,10 +192,16 @@ export default function LanguagesPage() { Cancel diff --git a/src/services/api.ts b/src/services/api.ts index d0f3a8c..4b88a9f 100644 --- a/src/services/api.ts +++ b/src/services/api.ts @@ -16,6 +16,7 @@ import type { AppRoleResponse, LanguageResponse, LanguageCreate, + LanguageUpdate, OrganizationResponse, OrganizationCreate, OrganizationUpdate, @@ -170,6 +171,8 @@ export const languagesAPI = { list: () => api.get("/languages"), create: (data: LanguageCreate) => api.post("/languages", data), + update: (languageId: string, data: LanguageUpdate) => + api.put(`/languages/${languageId}`, data), get: (languageId: string) => api.get(`/languages/${languageId}`), getByCode: (code: string) => diff --git a/src/types/index.ts b/src/types/index.ts index e343aa0..a4103a6 100644 --- a/src/types/index.ts +++ b/src/types/index.ts @@ -25,6 +25,7 @@ export type { export type { LanguageResponse, LanguageCreate, + LanguageUpdate, } from "./language" export type { diff --git a/src/types/language.ts b/src/types/language.ts index fb5a8bd..7fcf6d6 100644 --- a/src/types/language.ts +++ b/src/types/language.ts @@ -3,9 +3,15 @@ export interface LanguageResponse { name: string code: string created_at: string + updated_at: string } export interface LanguageCreate { name: string code: string } + +export interface LanguageUpdate { + name?: string + code?: string +}