Fix: 同步文件时顺便同步更新结构
This commit is contained in:
parent
b51da785af
commit
bf1a7dde48
|
|
@ -16,7 +16,7 @@ import {
|
||||||
} from "@/lib/db";
|
} from "@/lib/db";
|
||||||
import { FolderOpen, Settings } from "lucide-react";
|
import { FolderOpen, Settings } from "lucide-react";
|
||||||
import { useTranslationInlineEdit } from "@/hooks/biz/use-translation-inline-edit";
|
import { useTranslationInlineEdit } from "@/hooks/biz/use-translation-inline-edit";
|
||||||
import { buildStructureFromObject, flattenEntries, flattenValues, type FlatEntry, insertEntrySibling, removeEntryAtPath, renameEntryAtPath, moveEntryByOffset } from "@/lib/i18n-structure";
|
import { buildStructureFromObject, flattenEntries, flattenValues, unflattenValues, type FlatEntry, insertEntrySibling, removeEntryAtPath, renameEntryAtPath, moveEntryByOffset } from "@/lib/i18n-structure";
|
||||||
import { ImportLanguageModal } from "@/components/biz/import-language-modal";
|
import { ImportLanguageModal } from "@/components/biz/import-language-modal";
|
||||||
import { ExportLanguageModal } from "@/components/biz/export-language-modal";
|
import { ExportLanguageModal } from "@/components/biz/export-language-modal";
|
||||||
import { EntryNameModal } from "@/components/biz/entry-name-modal";
|
import { EntryNameModal } from "@/components/biz/entry-name-modal";
|
||||||
|
|
@ -215,18 +215,74 @@ export default function Editor({ projectId }: EditorProps) {
|
||||||
}
|
}
|
||||||
}, [projectId, setSourcesMeta]);
|
}, [projectId, setSourcesMeta]);
|
||||||
|
|
||||||
|
const updateStructureFromDefaultLanguage = useCallback(
|
||||||
|
async (opts?: { silent?: boolean }) => {
|
||||||
|
if (!projectId) return false;
|
||||||
|
|
||||||
|
// 获取默认语言
|
||||||
|
const defaultLang = sourcesState.defaultLanguage;
|
||||||
|
if (!defaultLang) {
|
||||||
|
if (!opts?.silent) {
|
||||||
|
toast.error("未配置默认语言,无法更新翻译结构");
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取默认语言的翻译内容
|
||||||
|
const translations = valuesByLang[defaultLang];
|
||||||
|
if (!translations || Object.keys(translations).length === 0) {
|
||||||
|
if (!opts?.silent) {
|
||||||
|
toast.error(`默认语言 ${defaultLang} 的翻译内容为空`);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
// 从扁平结构转换为嵌套对象
|
||||||
|
const nestedObj = unflattenValues(translations);
|
||||||
|
// 从嵌套对象构建结构树
|
||||||
|
const root = buildStructureFromObject(nestedObj);
|
||||||
|
// 保存到数据库
|
||||||
|
await upsertStructure({ projectId, root });
|
||||||
|
setStructure({ projectId, root });
|
||||||
|
|
||||||
|
if (!opts?.silent) {
|
||||||
|
toast.success("翻译结构已更新");
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
} catch (err) {
|
||||||
|
const message = (err as Error)?.message ?? "更新结构失败";
|
||||||
|
if (!opts?.silent) {
|
||||||
|
toast.error(message);
|
||||||
|
}
|
||||||
|
console.error("更新结构失败", err);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
[projectId, sourcesState.defaultLanguage, valuesByLang]
|
||||||
|
);
|
||||||
|
|
||||||
const syncExternalSources = useCallback(
|
const syncExternalSources = useCallback(
|
||||||
async (opts?: { silent?: boolean; reloadConfig?: boolean }) => {
|
async (opts?: { silent?: boolean; reloadConfig?: boolean; updateStructure?: boolean }) => {
|
||||||
let preloaded: LoadedProjectSources | null = null;
|
let preloaded: LoadedProjectSources | null = null;
|
||||||
if (opts?.reloadConfig) {
|
if (opts?.reloadConfig) {
|
||||||
preloaded = await bootstrapSources();
|
preloaded = await bootstrapSources();
|
||||||
}
|
}
|
||||||
|
let syncResult: boolean;
|
||||||
if (preloaded) {
|
if (preloaded) {
|
||||||
return applyLoadedSources(preloaded, opts);
|
syncResult = await applyLoadedSources(preloaded, opts);
|
||||||
|
} else {
|
||||||
|
syncResult = await syncFromAdapter(opts);
|
||||||
}
|
}
|
||||||
return syncFromAdapter(opts);
|
|
||||||
|
// 如果同步成功且需要更新结构,则从默认语言更新结构
|
||||||
|
if (syncResult && opts?.updateStructure) {
|
||||||
|
await updateStructureFromDefaultLanguage({ silent: opts.silent });
|
||||||
|
}
|
||||||
|
|
||||||
|
return syncResult;
|
||||||
},
|
},
|
||||||
[applyLoadedSources, bootstrapSources, syncFromAdapter]
|
[applyLoadedSources, bootstrapSources, syncFromAdapter, updateStructureFromDefaultLanguage]
|
||||||
);
|
);
|
||||||
|
|
||||||
const refresh = useCallback(
|
const refresh = useCallback(
|
||||||
|
|
@ -482,7 +538,7 @@ export default function Editor({ projectId }: EditorProps) {
|
||||||
void syncExternalSources({ silent: false });
|
void syncExternalSources({ silent: false });
|
||||||
break;
|
break;
|
||||||
case "read-all":
|
case "read-all":
|
||||||
void syncExternalSources({ silent: false, reloadConfig: true });
|
void syncExternalSources({ silent: false, reloadConfig: true, updateStructure: true });
|
||||||
break;
|
break;
|
||||||
case "save":
|
case "save":
|
||||||
void handleSaveAllConnected();
|
void handleSaveAllConnected();
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue