window.LOGIN_LOCALE_DATA = { "zh-tw": { "name": "繁體中文(台灣)", "fontFamily": "\"Microsoft JhengHei\",\"SimHei\", \"Apple LiGothic Medium\", \"STHeiti\"", "strings": { "page/title": "ArozOS - 登入", "login/description": "", "login/signinButton": "登入", "login/oauthButton": "透過 OAuth 2.0 登入", "login/ldapButton": "透過 LDAP 登入", "login/rememberMe": "記住我", "login/signUp": "註冊", "login/forgotPassword": "忘記密碼", "login/createNewSession": "建立新工作階段", "login/resumableSession": "可恢復的工作階段", "login/errorIncorrect": "錯誤。使用者名稱或密碼不正確。", "login/requestTimestamp": "請求時間戳記", "locale/language-default-text": "語言", "locale/browser-default": "Default", "login/introPrefix": "使用您的使用者名稱及密碼登入 ", "login/introSuffix": "", "login/redirectMessage": "5 秒後導向組織登入頁面...", "login/cancel": "取消", "page/titleSuffix": "登入" }, "placeholder": { "Username": "使用者名稱", "Password": "密碼" } }, "zh-hk": { "name": "繁體中文(香港)", "fontFamily": "\"Microsoft JhengHei\",\"SimHei\", \"Apple LiGothic Medium\", \"STHeiti\"", "strings": { "page/title": "ArozOS - 登入", "login/description": "", "login/signinButton": "登入", "login/oauthButton": "透過 OAuth 2.0 登入", "login/ldapButton": "透過 LDAP 登入", "login/rememberMe": "記住我", "login/signUp": "註冊", "login/forgotPassword": "忘記密碼", "login/createNewSession": "建立新工作階段", "login/resumableSession": "可恢復的工作階段", "login/errorIncorrect": "錯誤。使用者名稱或密碼不正確。", "login/requestTimestamp": "請求時間戳記", "locale/language-default-text": "語言", "locale/browser-default": "Default", "login/introPrefix": "使用您的使用者名稱及密碼登入 ", "login/introSuffix": "", "login/redirectMessage": "5 秒後重新導向至組織登入頁面...", "login/cancel": "取消", "page/titleSuffix": "登入" }, "placeholder": { "Username": "使用者名稱", "Password": "密碼" } }, "zh-cn": { "name": "简体中文", "fontFamily": "\"Microsoft YaHei\", \"SimHei\", \"STHeiti\"", "strings": { "page/title": "ArozOS - 登录", "login/description": "", "login/signinButton": "登录", "login/oauthButton": "通过 OAuth 2.0 登录", "login/ldapButton": "通过 LDAP 登录", "login/rememberMe": "记住我", "login/signUp": "注册", "login/forgotPassword": "忘记密码", "login/createNewSession": "创建新会话", "login/resumableSession": "可恢复的会话", "login/errorIncorrect": "错误。用户名或密码不正确。", "login/requestTimestamp": "请求时间戳", "locale/language-default-text": "语言", "locale/browser-default": "Default", "login/introPrefix": "使用您的用户名和密码登录 ", "login/introSuffix": "", "login/redirectMessage": "5 秒后重定向到组织登录页面...", "login/cancel": "取消", "page/titleSuffix": "登录" }, "placeholder": { "Username": "用户名", "Password": "密码" } }, "en-us": { "name": "English (US)", "fontFamily": "\"Segoe UI\", \"Helvetica Neue\", Arial, sans-serif", "strings": { "page/title": "ArozOS - Login", "login/description": "with your username and password", "login/signinButton": "Sign In", "login/oauthButton": "Sign In via OAuth 2.0", "login/ldapButton": "Sign In via LDAP", "login/rememberMe": "Remember Me", "login/signUp": "Sign Up", "login/forgotPassword": "Forgot Password", "login/createNewSession": "Create New Session", "login/resumableSession": "Resumable Session", "login/errorIncorrect": "Error. Incorrect username or password.", "login/requestTimestamp": "Request Timestamp", "locale/language-default-text": "Language", "locale/browser-default": "Default", "login/introPrefix": "Sign in to ", "login/introSuffix": " ", "login/redirectMessage": "Redirecting to organization sign-in page in 5 seconds...", "login/cancel": "Cancel", "page/titleSuffix": "Sign In" }, "placeholder": { "Username": "Username", "Password": "Password" } }, "ja-jp": { "name": "日本語", "fontFamily": "\"Hiragino Sans\", \"Hiragino Kaku Gothic ProN\", \"Noto Sans JP\", sans-serif", "strings": { "page/title": "ArozOS - ログイン", "login/description": "", "login/signinButton": "ログイン", "login/oauthButton": "OAuth 2.0でログイン", "login/ldapButton": "LDAPでログイン", "login/rememberMe": "ログイン状態を保持する", "login/signUp": "新規登録", "login/forgotPassword": "パスワードをお忘れですか?", "login/createNewSession": "新しいセッションを作成", "login/resumableSession": "復元可能なセッション", "login/errorIncorrect": "エラー。ユーザー名またはパスワードが正しくありません。", "login/requestTimestamp": "リクエストタイムスタンプ", "locale/language-default-text": "言語", "locale/browser-default": "Default", "login/introPrefix": "ユーザー名とパスワードでサインイン ", "login/introSuffix": "", "login/redirectMessage": "5 秒後に組織のサインインページへリダイレクトします...", "login/cancel": "キャンセル", "page/titleSuffix": "ログイン" }, "placeholder": { "Username": "ユーザー名", "Password": "パスワード" } }, "ko-kr": { "name": "한국어", "fontFamily": "\"Apple SD Gothic Neo\", \"Malgun Gothic\", \"Noto Sans KR\", sans-serif", "strings": { "page/title": "ArozOS - 로그인", "login/description": "", "login/signinButton": "로그인", "login/oauthButton": "OAuth 2.0으로 로그인", "login/ldapButton": "LDAP으로 로그인", "login/rememberMe": "로그인 상태 유지", "login/signUp": "회원가입", "login/forgotPassword": "비밀번호 찾기", "login/createNewSession": "새 세션 만들기", "login/resumableSession": "복원 가능한 세션", "login/errorIncorrect": "오류. 사용자 이름 또는 비밀번호가 올바르지 않습니다.", "login/requestTimestamp": "요청 타임스탬프", "locale/language-default-text": "언어", "locale/browser-default": "Default", "login/introPrefix": "사용자 이름과 비밀번호로 로그인 ", "login/introSuffix": "", "login/redirectMessage": "5초 후 조직 로그인 페이지로 이동합니다...", "login/cancel": "취소", "page/titleSuffix": "로그인" }, "placeholder": { "Username": "사용자 이름", "Password": "비밀번호" } } }; (function () { var rawData = window.LOGIN_LOCALE_DATA || null; var FALLBACK_LANG = 'en-us'; var STORAGE_KEY = 'global_language'; var readyQueue = []; var currentLanguage = null; var currentDataset = null; function getAvailableLocales() { return rawData || {}; } function normalizeLanguageCandidate(candidate) { if (!candidate) { return null; } return candidate.replace(/_/g, '-').toLowerCase(); } function matchLanguageCandidate(candidate) { if (!candidate || candidate === 'default') { return null; } var normalized = normalizeLanguageCandidate(candidate); if (!normalized) { return null; } var availableKeys = Object.keys(getAvailableLocales()); for (var i = 0; i < availableKeys.length; i++) { if (availableKeys[i] === normalized) { return availableKeys[i]; } } var primary = normalized.split('-')[0]; for (var j = 0; j < availableKeys.length; j++) { if (availableKeys[j].split('-')[0] === primary) { return availableKeys[j]; } } return null; } function getBrowserLanguage() { var browserLangs = []; if (navigator.languages && navigator.languages.length) { browserLangs = navigator.languages; } else if (navigator.language) { browserLangs = [navigator.language]; } for (var i = 0; i < browserLangs.length; i++) { var match = matchLanguageCandidate(browserLangs[i]); if (match) { return match; } } return null; } function getQueryParam(name) { var regex = new RegExp('[?&]' + name + '=([^&]*)'); var results = regex.exec(window.location.search); if (!results || results.length < 2) { return null; } try { return decodeURIComponent(results[1].replace(/\+/g, ' ')); } catch (err) { return null; } } function getUrlLanguage() { var value = getQueryParam('lang'); return value ? value.toLowerCase() : null; } function getStoredLanguage() { try { if (window.localStorage) { var stored = localStorage.getItem(STORAGE_KEY); return stored ? stored.toLowerCase() : null; } } catch (err) { // Ignore storage errors } return null; } function resolveLanguage() { var availableKeys = Object.keys(getAvailableLocales()); if (!availableKeys.length) { return FALLBACK_LANG; } var overrideLang = getUrlLanguage(); var overrideMatch = matchLanguageCandidate(overrideLang); if (overrideMatch) { return overrideMatch; } var storedLang = getStoredLanguage(); if (storedLang && storedLang !== 'default') { var storedMatch = matchLanguageCandidate(storedLang); if (storedMatch) { return storedMatch; } } var browserLang = getBrowserLanguage(); if (browserLang) { return browserLang; } for (var i = 0; i < availableKeys.length; i++) { if (availableKeys[i] === FALLBACK_LANG) { return FALLBACK_LANG; } } return availableKeys[0]; } function ensureDataset() { var locales = getAvailableLocales(); currentDataset = locales[currentLanguage] || null; if (!currentDataset) { var keys = Object.keys(locales); if (keys.length) { currentLanguage = keys[0]; currentDataset = locales[currentLanguage]; } } } function forEachNode(list, handler) { if (!list || !handler) { return; } for (var i = 0; i < list.length; i++) { handler(list[i]); } } function translateDocument() { if (!currentDataset) { return; } var strings = currentDataset.strings || {}; var placeholders = currentDataset.placeholder || {}; var titles = currentDataset.titles || {}; forEachNode(document.querySelectorAll('[locale]'), function (el) { var key = el.getAttribute('locale'); if (!key || strings[key] === undefined) { return; } if (el.tagName === 'INPUT' || el.tagName === 'TEXTAREA') { el.value = strings[key]; } else { el.innerHTML = strings[key]; } }); forEachNode(document.querySelectorAll('[placeholder]'), function (el) { var placeholderKey = el.getAttribute('placeholder'); if (placeholderKey && placeholders[placeholderKey] !== undefined) { el.setAttribute('placeholder', placeholders[placeholderKey]); } }); forEachNode(document.querySelectorAll('[title]'), function (el) { var titleKey = el.getAttribute('title'); if (titleKey && titles[titleKey] !== undefined) { el.setAttribute('title', titles[titleKey]); } }); if (currentDataset.fontFamily && document.body) { document.body.style.fontFamily = currentDataset.fontFamily; } if (document.documentElement) { document.documentElement.setAttribute('lang', currentLanguage || 'en'); } if (strings['page/title']) { document.title = strings['page/title']; } } function flushReadyQueue() { while (readyQueue.length) { var callback = readyQueue.shift(); try { callback(currentDataset || {}); } catch (err) { console.error('[LoginLocale] callback error', err); } } } function init() { if (currentDataset || !rawData) { if (!currentDataset) { flushReadyQueue(); } return currentDataset; } currentLanguage = resolveLanguage(); ensureDataset(); var run = function () { translateDocument(); flushReadyQueue(); updateDropdownText(); }; if (document.readyState === 'loading') { var onDomReady = function () { document.removeEventListener('DOMContentLoaded', onDomReady); run(); }; document.addEventListener('DOMContentLoaded', onDomReady); } else { run(); } return currentDataset; } function onReady(callback) { if (typeof callback !== 'function') { return; } if (currentDataset) { callback(currentDataset); } else { readyQueue.push(callback); } } function getString(key, fallback) { if (!currentDataset || !currentDataset.strings || currentDataset.strings[key] === undefined) { return fallback; } return currentDataset.strings[key]; } function setLanguage(lang) { currentLanguage = lang; localStorage.setItem(STORAGE_KEY, lang); ensureDataset(); translateDocument(); updateDropdownText(); if (window.updateHostnameAndTitle) { window.updateHostnameAndTitle(); } } function updateDropdownText() { var text = 'Language'; if (currentLanguage === 'default') { text = 'Browser Default'; } else if (currentDataset && currentDataset.name) { text = currentDataset.name; } $('.selection.dropdown .text').text(text); } function getCurrentLanguage() { return currentLanguage; } function getAvailable() { return getAvailableLocales(); } window.LoginLocale = { init: init, translateDocument: translateDocument, getString: getString, getCurrentLanguage: getCurrentLanguage, getAvailableLocales: getAvailable, onReady: onReady, setLanguage: setLanguage }; })();