Skip to content

Commit e1d9216

Browse files
committed
Add site tests: language selector and RTL rendering
- tests/site.test.mjs validates the generated site: disabled menu entries for untranslated languages, links to existing translations, and dir=rtl/lang=fa on Persian pages - Wire test:site into the test-only chain
1 parent 4b6e744 commit e1d9216

2 files changed

Lines changed: 59 additions & 1 deletion

File tree

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,8 @@
4141
"seq": "bash -c 'for cmd in \"$@\"; do npm run $cmd || exit 1; done' - ",
4242
"serve": "npm run _serve",
4343
"test-and-fix": "npm run fix && npm run test-only",
44-
"test-only": "npm run check:links",
44+
"test-only": "npm run check:links && npm run test:site",
45+
"test:site": "node --test 'tests/**/*.test.mjs'",
4546
"test": "npm run test-and-fix",
4647
"update:docsy:main": "hugo mod get -u github.com/google/docsy/theme@main && hugo mod tidy",
4748
"update:docsy:mod": "hugo mod get -u github.com/google/docsy/theme && hugo mod tidy",

tests/site.test.mjs

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
import test from 'node:test';
2+
import assert from 'node:assert/strict';
3+
import { readFileSync } from 'node:fs';
4+
import { join } from 'node:path';
5+
import { fileURLToPath } from 'node:url';
6+
7+
// Validates the navbar language selector and RTL rendering in the generated
8+
// site (public/). Assumes the site has been built (`npm run build`); in the
9+
// `test-only` chain, the check:links prebuild takes care of that.
10+
11+
const publicDir = fileURLToPath(new URL('../public', import.meta.url));
12+
13+
function page(relPath) {
14+
return readFileSync(join(publicDir, relPath, 'index.html'), 'utf8');
15+
}
16+
17+
// Extract the language-menu markup from a page.
18+
function langMenu(html) {
19+
const m = html.match(
20+
/<div class="td-lang-menu dropdown">[\s\S]*?<\/ul>\s*<\/div>/,
21+
);
22+
assert.ok(m, 'page has a td-lang-menu language selector');
23+
return m[0];
24+
}
25+
26+
test('language selector marks untranslated languages as disabled', (t) => {
27+
// /docs/tasks/ exists only in English: the menu should show an active
28+
// entry (English) and disabled, link-less entries for no and fa.
29+
const menu = langMenu(page('docs/tasks'));
30+
const active = menu.match(/class="dropdown-item active"/g) ?? [];
31+
const disabled = menu.match(/class="dropdown-item disabled"/g) ?? [];
32+
assert.equal(active.length, 1, 'one active language entry');
33+
assert.equal(disabled.length, 2, 'two disabled (untranslated) entries');
34+
assert.ok(
35+
!/<a[^>]*class="dropdown-item (active|disabled)"/.test(menu),
36+
'active/disabled entries are not links',
37+
);
38+
t.diagnostic(`active: ${active.length}, disabled: ${disabled.length}`);
39+
});
40+
41+
test('language selector links to existing translations', (t) => {
42+
// /docs/overview/ has a Persian translation: the menu should link to it.
43+
const menu = langMenu(page('docs/overview'));
44+
assert.match(
45+
menu,
46+
/<a class="dropdown-item" href="\/fa\/docs\/overview\/"/,
47+
'links to the Persian translation',
48+
);
49+
t.diagnostic('fa translation link present on /docs/overview/');
50+
});
51+
52+
test('Persian pages render right-to-left', (t) => {
53+
const html = page('fa');
54+
assert.match(html, /<html[^>]*\bdir="rtl"/, 'html element has dir="rtl"');
55+
assert.match(html, /<html[^>]*\blang="fa"/, 'html element has lang="fa"');
56+
t.diagnostic('fa home page has dir="rtl" and lang="fa"');
57+
});

0 commit comments

Comments
 (0)