Add hand-rolled English support (/en/*) alongside the Italian site
PocketBase gains optional, manually-authored English fields on articles and categories (same record, same slug), and the frontend serves an /en counterpart of every dynamic route via thin page wrappers around shared view components — no i18n library, consistent with the project's existing minimalism stance for a two-locale site with ~20 UI strings. An article/category with no translation 404s cleanly on its own /en detail page and is filtered out of /en listings, and the header's language-switch link falls back to the English blog index rather than a dead link; resolving that requires a global route middleware, since the layout's header renders before the page content in document order and so can't react to state a page component sets during its own async setup.
This commit is contained in:
@@ -53,6 +53,7 @@ describe('GET /content/articles/:slug', () => {
|
||||
expect(article.summary.length).toBeGreaterThan(0)
|
||||
expect(article.author).toBe('Redazione')
|
||||
expect(article.category?.slug).toBe('economia')
|
||||
expect(article.hasTranslation).toBe(true)
|
||||
})
|
||||
|
||||
it('404s for an unknown slug', async () => {
|
||||
@@ -62,6 +63,36 @@ describe('GET /content/articles/:slug', () => {
|
||||
it('404s for a draft (unpublished) slug', async () => {
|
||||
await expectStatus($fetch('/content/articles/articolo-bozza'), 404)
|
||||
})
|
||||
|
||||
it('reports hasTranslation false for an article with no English content', async () => {
|
||||
const article = await $fetch<Article>('/content/articles/secondo-articolo')
|
||||
expect(article.hasTranslation).toBe(false)
|
||||
})
|
||||
|
||||
it('returns the English fields when lang=en and a translation exists', async () => {
|
||||
const article = await $fetch<Article>('/content/articles/articolo-pubblicato', {
|
||||
query: { lang: 'en' },
|
||||
})
|
||||
expect(article.title).toBe('Published article')
|
||||
expect(article.html).toContain('<strong>markdown</strong>')
|
||||
})
|
||||
|
||||
it('404s for lang=en when no translation exists', async () => {
|
||||
await expectStatus(
|
||||
$fetch('/content/articles/secondo-articolo', { query: { lang: 'en' } }),
|
||||
404
|
||||
)
|
||||
})
|
||||
})
|
||||
|
||||
describe('GET /content/articles with lang=en', () => {
|
||||
it('only lists articles that have an English translation', async () => {
|
||||
const response = await $fetch<Paginated<ArticleSummary>>('/content/articles', {
|
||||
query: { lang: 'en' },
|
||||
})
|
||||
expect(response.items.map((a) => a.slug)).toEqual(['articolo-pubblicato'])
|
||||
expect(response.items[0]?.title).toBe('Published article')
|
||||
})
|
||||
})
|
||||
|
||||
describe('GET /content/categories', () => {
|
||||
@@ -69,6 +100,11 @@ describe('GET /content/categories', () => {
|
||||
const categories = await $fetch<Category[]>('/content/categories')
|
||||
expect(categories.map((c) => c.name)).toEqual(['Attualità', 'Economia'])
|
||||
})
|
||||
|
||||
it('only lists translated categories when lang=en', async () => {
|
||||
const categories = await $fetch<Category[]>('/content/categories', { query: { lang: 'en' } })
|
||||
expect(categories.map((c) => c.name)).toEqual(['Economy'])
|
||||
})
|
||||
})
|
||||
|
||||
describe('GET /content/categories/:slug', () => {
|
||||
@@ -80,6 +116,15 @@ describe('GET /content/categories/:slug', () => {
|
||||
it('404s for an unknown slug', async () => {
|
||||
await expectStatus($fetch('/content/categories/does-not-exist'), 404)
|
||||
})
|
||||
|
||||
it('returns the English name when lang=en and a translation exists', async () => {
|
||||
const category = await $fetch<Category>('/content/categories/economia', { query: { lang: 'en' } })
|
||||
expect(category.name).toBe('Economy')
|
||||
})
|
||||
|
||||
it('404s for lang=en when no translation exists', async () => {
|
||||
await expectStatus($fetch('/content/categories/attualita', { query: { lang: 'en' } }), 404)
|
||||
})
|
||||
})
|
||||
|
||||
describe('GET /admin', () => {
|
||||
|
||||
Reference in New Issue
Block a user