152 lines
8.0 KiB
TypeScript
152 lines
8.0 KiB
TypeScript
import fs from "node:fs";
|
|
import path from "node:path";
|
|
|
|
import { describe, expect, it } from "vitest";
|
|
import DefaultKbsTemplate from "./DefaultKbsTemplate";
|
|
|
|
const sourcePath = path.resolve(process.cwd(), "apps/web/app/modules/knowledgeBase/utils/DefaultKbsTemplate.ts");
|
|
const enTranslationsPath = path.resolve(process.cwd(), "apps/web/public/locales/en/translations.json");
|
|
const deTranslationsPath = path.resolve(process.cwd(), "apps/web/public/locales/de/translations.json");
|
|
|
|
function readTranslations(localePath: string) {
|
|
return JSON.parse(fs.readFileSync(localePath, "utf8")) as {
|
|
knowledgeBase: {
|
|
defaultTemplates: {
|
|
sample: {
|
|
knowledgeBases: {
|
|
docs: { description: string; title: string };
|
|
center: { description: string; links: { backToSite: string }; title: string };
|
|
};
|
|
articles: {
|
|
exampleSiteKnowledgeBase: { description: string; content: { text: string } };
|
|
publishProductDocumentation: { description: string; content: { text: string } };
|
|
};
|
|
categories: {
|
|
introduction: { description: string };
|
|
kategorie1: { sections: { basics: { description: string } } };
|
|
};
|
|
};
|
|
};
|
|
};
|
|
};
|
|
}
|
|
|
|
describe("DefaultKbsTemplate content", () => {
|
|
it("keeps seeded knowledge-base copy free from placeholder junk and misspelled API names", () => {
|
|
const source = fs.readFileSync(sourcePath, "utf8");
|
|
|
|
expect(source).toContain("knowledgeBase.defaultTemplates.sample");
|
|
expect(source).not.toContain("knowlegeBase");
|
|
expect(source).not.toContain("asdf");
|
|
expect(source).not.toContain("Sample description");
|
|
expect(source).not.toContain("Category 1");
|
|
expect(source).not.toContain("Introduction category description sample");
|
|
expect(source).not.toContain("Example Site - Knowledge Base");
|
|
expect(source).not.toContain("loom.com");
|
|
expect(source).not.toContain("demo@toolctrl.local");
|
|
expect(source).not.toContain("Dynamic vs Static Knowledge Bases");
|
|
expect(source).not.toContain("apps/web/app/routes/docs/($lang).tsx");
|
|
expect(source).not.toContain("related articles to guide readers");
|
|
});
|
|
|
|
it("stores semantic locale keys for default knowledge-base seed copy", () => {
|
|
const source = fs.readFileSync(sourcePath, "utf8");
|
|
const en = readTranslations(enTranslationsPath);
|
|
const de = readTranslations(deTranslationsPath);
|
|
|
|
expect(source).toContain('templateKey("knowledgeBases.docs.title")');
|
|
expect(source).toContain('templateKey("articles.publishProductDocumentation.content.text")');
|
|
expect(source).not.toContain("ui.autogenerated");
|
|
|
|
expect(en.knowledgeBase.defaultTemplates.sample.knowledgeBases.docs.title).toBe("Docs");
|
|
expect(en.knowledgeBase.defaultTemplates.sample.articles.publishProductDocumentation.content.text).toContain("related articles");
|
|
expect(de.knowledgeBase.defaultTemplates.sample.knowledgeBases.center.links.backToSite).toBe("Zur Website");
|
|
expect(de.knowledgeBase.defaultTemplates.sample.articles.publishProductDocumentation.content.text).toContain("verwandte Artikel");
|
|
});
|
|
|
|
it("exposes locale-scoped admin import samples instead of mixed public chrome", () => {
|
|
for (const [template, language] of [
|
|
[DefaultKbsTemplate.SAMPLE_EN, "en"],
|
|
[DefaultKbsTemplate.SAMPLE_DE, "de"],
|
|
] as const) {
|
|
expect(Object.keys(template).sort()).toEqual(["articles", "categories", "knowledgeBases"]);
|
|
expect(template.knowledgeBases.every((kb) => kb.defaultLanguage === language)).toBe(true);
|
|
expect(template.knowledgeBases.every((kb) => kb.languages.length === 1 && kb.languages[0] === language)).toBe(true);
|
|
expect(template.categories.every((category) => category.language === language)).toBe(true);
|
|
expect(template.articles.every((article) => article.language === language)).toBe(true);
|
|
}
|
|
|
|
expect(DefaultKbsTemplate.SAMPLE_DE.knowledgeBases.map((kb) => kb.title)).toContain("Hilfe-Center");
|
|
expect(JSON.stringify(DefaultKbsTemplate.SAMPLE_DE)).not.toContain("Help Center");
|
|
expect(JSON.stringify(DefaultKbsTemplate.SAMPLE_DE)).not.toContain("Back to site");
|
|
});
|
|
|
|
it("keeps German knowledge-base copy generic while preserving the Hilfe-Center product title", () => {
|
|
const deSample = DefaultKbsTemplate.SAMPLE_DE;
|
|
const deCopy = JSON.stringify(deSample);
|
|
|
|
expect(deSample.knowledgeBases.find((kb) => kb.slug === "center")?.title).toBe("Hilfe-Center");
|
|
expect(deSample.categories.find((category) => category.slug === "kategorie-1")?.description).toBe(
|
|
"Grundlagen für die Einrichtung und Nutzung der Wissensdatenbank."
|
|
);
|
|
expect(deSample.articles.find((article) => article.slug === "beispiel-2")?.title).toBe("Wissensdatenbank strukturieren");
|
|
expect(deSample.articles.find((article) => article.slug === "beispiel-1")?.contentPublishedAsText).toContain("Diese Wissensdatenbank bündelt");
|
|
expect(deCopy).not.toContain("Nutzung des Hilfe-Centers");
|
|
expect(deCopy).not.toContain("Dieses Hilfe-Center bündelt");
|
|
});
|
|
|
|
it("keeps default category and article metadata useful for imported starter content", () => {
|
|
for (const template of [DefaultKbsTemplate.SAMPLE_EN, DefaultKbsTemplate.SAMPLE_DE]) {
|
|
for (const knowledgeBase of template.knowledgeBases) {
|
|
expect(knowledgeBase.title.trim()).not.toHaveLength(0);
|
|
expect(knowledgeBase.description.trim()).not.toHaveLength(0);
|
|
}
|
|
for (const category of template.categories) {
|
|
expect(category.title.trim()).not.toHaveLength(0);
|
|
expect(category.description.trim()).not.toHaveLength(0);
|
|
for (const section of category.sections) {
|
|
expect(section.title.trim()).not.toHaveLength(0);
|
|
expect(section.description.trim()).not.toHaveLength(0);
|
|
}
|
|
}
|
|
for (const article of template.articles) {
|
|
expect(article.title.trim()).not.toHaveLength(0);
|
|
expect(article.description.trim()).not.toHaveLength(0);
|
|
}
|
|
}
|
|
|
|
expect(DefaultKbsTemplate.SAMPLE_EN.knowledgeBases.find((kb) => kb.slug === "docs")?.description).toBe(
|
|
"Public product documentation and starter guides for your team."
|
|
);
|
|
expect(DefaultKbsTemplate.SAMPLE_EN.knowledgeBases.find((kb) => kb.slug === "center")?.description).toBe(
|
|
"Customer-facing help articles, setup guidance, and account support."
|
|
);
|
|
expect(
|
|
DefaultKbsTemplate.SAMPLE_DE.categories.find((category) => category.slug === "kategorie-1")?.sections.find((section) => section.order === 1)
|
|
?.description
|
|
).toBe("Wichtige Einrichtungshinweise, um hilfreiche Startinhalte zu strukturieren.");
|
|
|
|
expect(DefaultKbsTemplate.SAMPLE_EN.categories.find((category) => category.slug === "introduction")?.description).toBe(
|
|
"Start here for an overview of the documentation structure."
|
|
);
|
|
const starterArticle = DefaultKbsTemplate.SAMPLE_EN.articles.find((article) => article.slug === "example-site-knowledge-base");
|
|
expect(starterArticle?.description).toBe("A short starter article for the public docs knowledge base.");
|
|
expect(starterArticle?.contentPublishedAsText).toContain("neutral starting point");
|
|
expect(starterArticle?.createdByUserEmail).toBeNull();
|
|
|
|
const publishingArticle = DefaultKbsTemplate.SAMPLE_EN.articles.find((article) => article.slug === "publish-product-documentation");
|
|
expect(publishingArticle?.description).toBe("A practical checklist for turning draft articles into useful public documentation.");
|
|
expect(publishingArticle?.contentPublishedAsText).toContain("answers a real user question");
|
|
expect(publishingArticle?.contentPublishedAsText).not.toContain("route files");
|
|
});
|
|
|
|
it("keeps imported sample articles self-contained and attributed to the importing admin", () => {
|
|
for (const template of [DefaultKbsTemplate.SAMPLE_EN, DefaultKbsTemplate.SAMPLE_DE]) {
|
|
const serialized = JSON.stringify(template);
|
|
expect(serialized).not.toContain("loom.com");
|
|
expect(serialized).not.toContain("demo@toolctrl.local");
|
|
expect(template.articles.every((article) => article.createdByUserEmail === null)).toBe(true);
|
|
}
|
|
});
|
|
});
|