[glm-grade=B+] feat(i18n): complete card/filter/action translation keys for 31 languages

Full language display names + RTL set (ar/fa/ur) on /i18n/languages;
card.internet/auth/tailscale/dashca, status pills, filter bar and
batch-operation strings added to every language dictionary. Frontend:
English now loads the server dictionary too (keys are semantic ids,
not fallback copy), failed loads keep existing DOM text instead of
exposing raw keys, isLoaded() gate for pre-load renders. Rebuilt
status/dist. Tests: i18n-cards 9/9, full suite 1837/1837.
This commit is contained in:
Krystie
2026-08-15 00:01:17 -07:00
parent bd40fb1c17
commit ef685e515e
11 changed files with 495 additions and 167 deletions
+8 -3
View File
@@ -169,6 +169,11 @@
'4h': '4 hours', '8h': '8 hours', '12h': '12 hours', '24h': '24 hours', 'never': 'Disabled'
};
function translated(key, fallback) {
const i18n = window.DCI18n;
return i18n && i18n.isLoaded() ? i18n.t(key) : fallback;
}
function updateAuthCard(active, duration) {
const card = document.getElementById('auth-card');
const pill = document.getElementById('auth-pill');
@@ -179,15 +184,15 @@
if (active) {
card.setAttribute('data-status', 'on');
pill.className = 'badge on';
pill.textContent = 'YES';
pill.textContent = translated('card.status.yes', 'YES');
dot.className = 'dot ok at-bl';
statusText.textContent = 'Session: ' + (DURATION_LABELS[duration] || duration);
} else {
card.setAttribute('data-status', 'off');
pill.className = 'badge off';
pill.textContent = 'NO';
pill.textContent = translated('card.status.no', 'NO');
dot.className = 'dot bad at-bl';
statusText.textContent = 'Not configured';
statusText.textContent = translated('card.auth.not_configured', 'Not configured');
}
}