@goodandready/dsh-russian-lang 0.3.15 → 0.3.16
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/client.js +38 -34
- package/lib/client.template.js +50 -44
- package/lib/locales.js +1 -1
- package/package.json +1 -1
package/lib/client.js
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
window.__ModuleLoader__.load({id: '@goodandready/dsh-russian-lang',factory: (require) => {var module = { exports: {} }
|
|
2
2
|
var React = null
|
|
3
|
-
try { React = require('react') } catch (e) { }
|
|
3
|
+
try { React = require('react') } catch (e) { void e; }
|
|
4
4
|
let isInspectorActive = false
|
|
5
5
|
let hoverBoxEl = null
|
|
6
6
|
let pillEl = null
|
|
7
|
+
let updateInspectorPill = () => {}
|
|
7
8
|
const numberFormat = new Intl.NumberFormat('ru-RU')
|
|
8
9
|
const compactNumberFormat = new Intl.NumberFormat('ru-RU', { notation: 'compact', compactDisplay: 'short' })
|
|
9
10
|
const relativeTimeFormat = new Intl.RelativeTimeFormat('ru-RU', { numeric: 'auto' })
|
|
@@ -396,8 +397,9 @@ RU['russian-lang'] = {"cardTitle":"Русская локализация","cardS
|
|
|
396
397
|
const SETTINGS_NS_NAME = 'russian-lang'
|
|
397
398
|
const FORM_NS = 'dsh-russian-lang'
|
|
398
399
|
const LEGACY_NS = 'russian-lang'
|
|
399
|
-
const ROW_CONFIG_KEY = '@goodandready/dsh-russian-lang#
|
|
400
|
+
const ROW_CONFIG_KEY = '@goodandready/dsh-russian-lang#' + FORM_NS
|
|
400
401
|
function apply(ctx) {const runtime = ctx.locale
|
|
402
|
+
const configForms = ctx && ctx.configForms
|
|
401
403
|
const resolveScope = (c) => {try {if (c && c.configForms) return c.configForms.get(FORM_NS)
|
|
402
404
|
if (c && c.settingsScope) return c.settingsScope.bind({ namespace: LEGACY_NS })
|
|
403
405
|
} catch (err) { void err }
|
|
@@ -416,7 +418,7 @@ if (typeof dict !== 'object' || !dict) continue
|
|
|
416
418
|
if (!RU[ns]) {RU[ns] = dict
|
|
417
419
|
ctx.effect(() => {try { return ctx.locale.register(ns, 'ru', dict) } catch (err) { return () => {} }}, 'dsh-russian-lang: ' + ns)
|
|
418
420
|
} else {Object.assign(RU[ns], dict)
|
|
419
|
-
try { ctx.locale.register(ns, 'ru', RU[ns]) } catch (_) {}}}}
|
|
421
|
+
try { ctx.locale.register(ns, 'ru', RU[ns]) } catch (_) { void _; }}}}
|
|
420
422
|
const CACHE_NAME = 'dsh-ru-cache-v1'
|
|
421
423
|
const loadLocalDict = (key) => {try {const raw = typeof localStorage !== 'undefined' ? localStorage.getItem('dsh_ru_' + key) : null
|
|
422
424
|
return raw ? JSON.parse(raw) : null
|
|
@@ -501,13 +503,13 @@ return value && value.overrides ? value.overrides : {}} catch (err) { return {}
|
|
|
501
503
|
const getPluginLocalizationStatus = makePluginLocalizationStatus(RU)
|
|
502
504
|
const lookupChain = () => {try {const chain = runtime.fallbackChain && runtime.fallbackChain(runtime.getLocale().active)
|
|
503
505
|
if (Array.isArray(chain) && chain.length) return chain
|
|
504
|
-
} catch (err) { }
|
|
506
|
+
} catch (err) { void err; }
|
|
505
507
|
return [runtime.getLocale().active]
|
|
506
508
|
}
|
|
507
509
|
const translationRegistry = new Map()
|
|
508
510
|
const lookup = (ns, key) => (runtime.lookup.length >= 3 ? runtime.lookup(ns, key, lookupChain()) : runtime.lookup(ns, key))
|
|
509
511
|
const syncLang = () => {try {if (typeof document !== 'undefined' && document.documentElement && runtime.getLocale().active === 'ru') document.documentElement.lang = 'ru-RU'
|
|
510
|
-
} catch (err) { }}
|
|
512
|
+
} catch (err) { void err; }}
|
|
511
513
|
const RUNTIME_PROP_NAMES = ['plural','pluralForm','formatDate','formatCompactNumber','formatTokens','formatNumber','formatRelativeTime','formatCurrency','inflect','getPluginLocalizationStatus','stemRussian','fuzzyMatchRu','humanizeError']
|
|
512
514
|
ctx.effect(() => {const origTranslate = runtime.translate
|
|
513
515
|
const origProps = {}
|
|
@@ -542,7 +544,7 @@ return () => {runtime.translate = origTranslate
|
|
|
542
544
|
for (const p of RUNTIME_PROP_NAMES) {if (origProps[p] !== undefined) runtime[p] = origProps[p]
|
|
543
545
|
else delete runtime[p]
|
|
544
546
|
}
|
|
545
|
-
if (typeof removeLang === 'function') { try { removeLang() } catch (_) { } }}}, 'dsh-russian-lang: runtime-lifecycle')
|
|
547
|
+
if (typeof removeLang === 'function') { try { removeLang() } catch (_) { void _; } }}}, 'dsh-russian-lang: runtime-lifecycle')
|
|
546
548
|
const syncFlag = () => {if (!legacyFlagMode) return
|
|
547
549
|
try {const wantRu = runtime.getLocale().active === 'ru'
|
|
548
550
|
const value = scope.getSnapshot().value || {}
|
|
@@ -558,7 +560,7 @@ runtime.setLocale('ru')
|
|
|
558
560
|
let booted = false
|
|
559
561
|
const tryBoot = () => {if (booted) return
|
|
560
562
|
try {const value = scope.getSnapshot().value
|
|
561
|
-
if (legacyFlagMode && value && value.enabled === true) { booted = true; activate() }} catch (err) { }}
|
|
563
|
+
if (legacyFlagMode && value && value.enabled === true) { booted = true; activate() }} catch (err) { void err; }}
|
|
562
564
|
ctx.effect(() => scope.subscribe(tryBoot), 'dsh-russian-lang: boot')
|
|
563
565
|
tryBoot()
|
|
564
566
|
const unsubscribeLang = runtime.subscribe(syncLang)
|
|
@@ -602,11 +604,11 @@ if (node.matches(EDITABLE)) spellOn(node)
|
|
|
602
604
|
node.querySelectorAll ? node.querySelectorAll(EDITABLE).forEach(spellOn) : null
|
|
603
605
|
}}})
|
|
604
606
|
spellObserver.observe(document.body, { childList: true, subtree: true })
|
|
605
|
-
} catch (err) { }}
|
|
607
|
+
} catch (err) { void err; }}
|
|
606
608
|
const unsubscribeSpell = runtime.subscribe(syncSpell)
|
|
607
609
|
ctx.effect(() => {return () => {unsubscribeSpell()
|
|
608
610
|
if (spellObserver) spellObserver.disconnect()
|
|
609
|
-
try { document.querySelectorAll('[' + SPELL_ON + ']').forEach(spellOff) } catch (err) { }}}, 'dsh-russian-lang: spellcheck')
|
|
611
|
+
try { document.querySelectorAll('[' + SPELL_ON + ']').forEach(spellOff) } catch (err) { void err; }}}, 'dsh-russian-lang: spellcheck')
|
|
610
612
|
syncSpell()
|
|
611
613
|
const ZH_CJK = /[\u3400-\u9fff\uf900-\ufaff]/
|
|
612
614
|
const ZH_RE_ESC = (s) => s.replace(/[.*+?^${}()|[\]\\]/g, '\\$&')
|
|
@@ -667,9 +669,10 @@ const trimmed = val.trim()
|
|
|
667
669
|
if (curOverrides[trimmed] !== undefined) {node.nodeValue = val.replace(trimmed, curOverrides[trimmed])
|
|
668
670
|
continue
|
|
669
671
|
}
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
if (
|
|
672
|
+
const p = node.parentElement
|
|
673
|
+
const isProtected = p && p.closest('code, pre, script, style, textarea, input, select, kbd, samp, [contenteditable="true"], [data-composer-input], [role="textbox"], .chat-message, .markdown-body')
|
|
674
|
+
if (trimmed.length >= 1 && ZH_CJK.test(val)) {if (!isProtected) hits.push(node)
|
|
675
|
+
} else if (trimmed.length >= 1 && DOM_EN_TEXT[trimmed]) {if (!isProtected) {node.nodeValue = val.replace(trimmed, DOM_EN_TEXT[trimmed])
|
|
673
676
|
}}}
|
|
674
677
|
for (const node of hits) {const next = zhTranslateText(node.nodeValue)
|
|
675
678
|
if (next && next !== node.nodeValue) node.nodeValue = next
|
|
@@ -685,7 +688,7 @@ if (root.getAttribute) {for (const attr of ['title', 'placeholder', 'aria-label'
|
|
|
685
688
|
if (v) {const tr = v.trim()
|
|
686
689
|
if (DOM_EN_TEXT[tr]) root.setAttribute(attr, v.replace(tr, DOM_EN_TEXT[tr]))
|
|
687
690
|
else if (DOM_EN_ATTRS[tr]) root.setAttribute(attr, v.replace(tr, DOM_EN_ATTRS[tr]))
|
|
688
|
-
}}}} catch (err) { }}
|
|
691
|
+
}}}} catch (err) { void err; }}
|
|
689
692
|
let zhObserver = null
|
|
690
693
|
let zhDebounceTimer = null
|
|
691
694
|
let zhWalking = false
|
|
@@ -715,7 +718,7 @@ document.addEventListener('pointerup', onInteraction, { passive: true })
|
|
|
715
718
|
document.addEventListener('click', onInteraction, { passive: true })
|
|
716
719
|
}
|
|
717
720
|
queueZhWalk()
|
|
718
|
-
} catch (err) { }}
|
|
721
|
+
} catch (err) { void err; }}
|
|
719
722
|
const unsubscribeZh = runtime.subscribe(syncZhDom)
|
|
720
723
|
ctx.effect(() => {return () => {unsubscribeZh()
|
|
721
724
|
if (zhObserver) zhObserver.disconnect()
|
|
@@ -759,7 +762,7 @@ for (const root of typoPending) {if (root.nodeType === 3) typoNode(root, conf)
|
|
|
759
762
|
else typoWalk(root, conf)
|
|
760
763
|
}
|
|
761
764
|
typoPending.clear()
|
|
762
|
-
} catch (err) { }}
|
|
765
|
+
} catch (err) { void err; }}
|
|
763
766
|
const typoPending = new Set()
|
|
764
767
|
const queueTypo = (roots) => {for (const r of roots) typoPending.add(r)
|
|
765
768
|
if (!typoQueued) typoQueued = requestAnimationFrame(flushTypo)
|
|
@@ -776,7 +779,7 @@ for (const record of records) {if (record.type === 'childList') {for (const adde
|
|
|
776
779
|
if (roots.length > 0) queueTypo(roots)
|
|
777
780
|
})
|
|
778
781
|
typoObserver.observe(document.body, { childList: true, subtree: true })
|
|
779
|
-
} catch (err) { }}
|
|
782
|
+
} catch (err) { void err; }}
|
|
780
783
|
const unsubscribeTypo = runtime.subscribe(syncTypo)
|
|
781
784
|
ctx.effect(() => {return () => {unsubscribeTypo()
|
|
782
785
|
if (typoObserver) typoObserver.disconnect()
|
|
@@ -951,7 +954,7 @@ if (c) { layoutShowHint(el, c.converted, 'ru'); return }}
|
|
|
951
954
|
if (cyrCount > 0 && latCount === 0 && value.trim().startsWith('/')) {const c = layoutFixCandidate(value, 'cyr2lat')
|
|
952
955
|
if (c) { layoutShowHint(el, c.converted, 'cmd'); return }}
|
|
953
956
|
layoutDismiss()
|
|
954
|
-
} catch (err) { }}
|
|
957
|
+
} catch (err) { void err; }}
|
|
955
958
|
const unsubscribeLayout = runtime.subscribe(layoutOnInput)
|
|
956
959
|
const layoutOnKeydown = (ev) => {const el = layoutCurrentInput(ev)
|
|
957
960
|
if (!el) return
|
|
@@ -1038,7 +1041,7 @@ document.body.appendChild(hoverBoxEl)
|
|
|
1038
1041
|
}
|
|
1039
1042
|
return hoverBoxEl
|
|
1040
1043
|
}
|
|
1041
|
-
|
|
1044
|
+
updateInspectorPill = () => {if (typeof document === 'undefined') return
|
|
1042
1045
|
if (!pillEl) {pillEl = document.createElement('div')
|
|
1043
1046
|
pillEl.id = 'dsh-ru-inspector-pill'
|
|
1044
1047
|
pillEl.className = 'rl-inspector-pill'
|
|
@@ -1051,7 +1054,7 @@ if (hoverBoxEl) hoverBoxEl.style.display = 'none'
|
|
|
1051
1054
|
document.body.appendChild(pillEl)
|
|
1052
1055
|
}
|
|
1053
1056
|
pillEl.style.display = isInspectorActive ? 'flex' : 'none'
|
|
1054
|
-
if (isInspectorActive) pillEl.classList.add('rl-inspector-pill-active')
|
|
1057
|
+
if (isInspectorActive && pillEl.classList) pillEl.classList.add('rl-inspector-pill-active')
|
|
1055
1058
|
}
|
|
1056
1059
|
const openInspectorModal = (meta, rawText, targetElement) => {if (typeof document === 'undefined') return
|
|
1057
1060
|
if (hoverBoxEl) hoverBoxEl.style.display = 'none'
|
|
@@ -1126,7 +1129,7 @@ setTimeout(() => { copyKeyBtn.textContent = '📋' }, 1500)
|
|
|
1126
1129
|
}}
|
|
1127
1130
|
const copyReportBtn = modal.querySelector('.rl-copy-report-btn')
|
|
1128
1131
|
if (copyReportBtn) {copyReportBtn.onclick = () => {const snippet = typeof generateBugReportSnippet === 'function'
|
|
1129
|
-
? generateBugReportSnippet({ key: k, ns, original: origText || rawText, current: rawText, override: textarea.value.trim(), pkgVersion: '0.3.
|
|
1132
|
+
? generateBugReportSnippet({ key: k, ns, original: origText || rawText, current: rawText, override: textarea.value.trim(), pkgVersion: '0.3.16' })
|
|
1130
1133
|
: ('### Репорт: ' + (k || rawText) + '\n- Исходный: ' + (origText || rawText) + '\n- Перевод: ' + textarea.value.trim())
|
|
1131
1134
|
try { navigator.clipboard.writeText(snippet) } catch (err) { void err; }
|
|
1132
1135
|
copyReportBtn.textContent = '✓ Скопировано'
|
|
@@ -1243,28 +1246,29 @@ if (!ctx.slots || !React) return
|
|
|
1243
1246
|
const toggleRu = (wantRu) => {try {if (runtime.getLocale().active === wantRu) return
|
|
1244
1247
|
runtime.setLocale(wantRu ? 'ru' : 'en')
|
|
1245
1248
|
} catch (err) { console.warn('dsh-russian-lang: toggle failed', err) }}
|
|
1246
|
-
|
|
1247
|
-
ctx.slots.register({name: 'plugins.item',id:
|
|
1249
|
+
const registerPluginsItem = () => {ctx.slots.inject('plugins.item', () =>
|
|
1250
|
+
ctx.slots.register({name: 'plugins.item',id: FORM_NS,order: 60,label: () => 'Russian language',locale: SETTINGS_NS_NAME,inject: () => ({ scope, runtime, toggleRu }),}, SettingsCard),)
|
|
1251
|
+
}
|
|
1252
|
+
if (typeof configForms?.whileServed === 'function') {ctx.effect(() => configForms.whileServed([FORM_NS], registerPluginsItem), 'dsh-russian-lang: plugins.item')
|
|
1253
|
+
} else {registerPluginsItem()
|
|
1254
|
+
}
|
|
1248
1255
|
ctx.slots.inject('plugins.row.config', () =>
|
|
1249
1256
|
ctx.slots.register({name: 'plugins.row.config',key: ROW_CONFIG_KEY,locale: SETTINGS_NS_NAME,inject: () => ({ scope, runtime, toggleRu }),}, SettingsCard),)
|
|
1250
|
-
ctx.slots.inject('settings.plugin.item', () =>
|
|
1251
|
-
ctx.slots.register({name: 'settings.plugin.item',key: SETTINGS_NS_NAME,locale: SETTINGS_NS_NAME,inject: () => ({ scope, runtime, toggleRu }),}, SettingsCard),)
|
|
1252
|
-
} catch (err) { console.warn('dsh-russian-lang: settings slot unavailable', err) }
|
|
1253
1257
|
try {ctx.slots.inject('conversation.session.header.utilities', () =>
|
|
1254
1258
|
ctx.slots.register({name: 'conversation.session.header.utilities',id: 'dsh-russian-lang-quick-switch',order: 100,locale: SETTINGS_NS_NAME,inject: () => ({ runtime, toggleRu }),}, QuickLangSwitch),)
|
|
1255
|
-
} catch (err) { }
|
|
1259
|
+
} catch (err) { void err; }
|
|
1256
1260
|
try {ctx.slots.inject('conversation.chat.assistant-actions', () =>
|
|
1257
1261
|
ctx.slots.register({name: 'conversation.chat.assistant-actions',id: 'dsh-russian-lang-translate-action',order: 50,locale: SETTINGS_NS_NAME,inject: () => ({ runtime }),}, TranslateTurnAction),)
|
|
1258
|
-
} catch (err) { }
|
|
1262
|
+
} catch (err) { void err; }
|
|
1259
1263
|
try {ctx.slots.inject('conversation.session.header.utilities', () =>
|
|
1260
1264
|
ctx.slots.register({name: 'conversation.session.header.utilities',id: 'dsh-russian-lang-md-export',order: 101,locale: SETTINGS_NS_NAME,inject: () => ({ runtime }),}, ExportMarkdownButton),)
|
|
1261
|
-
} catch (err) { }}
|
|
1265
|
+
} catch (err) { void err; }}
|
|
1262
1266
|
function QuickLangSwitch(props) {const inj = typeof props.inject === 'function' ? (props.inject() || {}) : (props.inject || {})
|
|
1263
1267
|
const runtime = props.runtime || inj.runtime
|
|
1264
1268
|
const toggleRu = props.toggleRu || inj.toggleRu
|
|
1265
1269
|
const [locale, setLocaleState] = React.useState(runtime ? (runtime.getLocale().active || 'en') : 'ru')
|
|
1266
1270
|
React.useEffect(() => {if (!runtime) return
|
|
1267
|
-
return runtime.subscribe(() => {try { setLocaleState(runtime.getLocale().active || 'en') } catch (e) { }})
|
|
1271
|
+
return runtime.subscribe(() => {try { setLocaleState(runtime.getLocale().active || 'en') } catch (e) { void e; }})
|
|
1268
1272
|
}, [runtime])
|
|
1269
1273
|
const isRu = locale === 'ru'
|
|
1270
1274
|
return React.createElement('button', {type: 'button',className: 'rl-lang-chip' + (isRu ? ' rl-lang-chip-active' : ''),title: isRu ? 'Интерфейс: Русский (нажмите для переключения на EN)' : 'Interface: English (click for RU)',onClick: () => { if (toggleRu) toggleRu(!isRu) },}, React.createElement('span', { className: 'rl-lang-text' }, isRu ? 'RU' : 'EN'))
|
|
@@ -1413,7 +1417,7 @@ const [snap, setSnap] = React.useState(() => (scope && scope.getSnapshot ? scope
|
|
|
1413
1417
|
const [ruActive, setRuActive] = React.useState(() => { try { return runtime.getLocale().active === 'ru' } catch (e) { return false } })
|
|
1414
1418
|
const [typo, setTypoState] = React.useState(() =>
|
|
1415
1419
|
(snap.value && snap.value.typography) || {})
|
|
1416
|
-
const [upStatus, setUpStatus] = React.useState({currentVersion: '0.3.
|
|
1420
|
+
const [upStatus, setUpStatus] = React.useState({currentVersion: '0.3.16',latestVersion: undefined,updateAvailable: false
|
|
1417
1421
|
})
|
|
1418
1422
|
const [upLoading, setUpLoading] = React.useState(false)
|
|
1419
1423
|
const [upMsg, setUpMsg] = React.useState(null)
|
|
@@ -1461,7 +1465,7 @@ if (s.value && s.value.typography) setTypoState(s.value.typography)
|
|
|
1461
1465
|
setSnap(scope.getSnapshot())
|
|
1462
1466
|
return un
|
|
1463
1467
|
}, [scope])
|
|
1464
|
-
React.useEffect(() => {try {const un = runtime.subscribe(() => {try { setRuActive(runtime.getLocale().active === 'ru') } catch (e) { }})
|
|
1468
|
+
React.useEffect(() => {try {const un = runtime.subscribe(() => {try { setRuActive(runtime.getLocale().active === 'ru') } catch (e) { void e; }})
|
|
1465
1469
|
return un
|
|
1466
1470
|
} catch (e) { return undefined }}, [runtime])
|
|
1467
1471
|
const status = snap.status || 'loading'
|
|
@@ -1506,7 +1510,7 @@ scope.set('agentPromptPreset', val)
|
|
|
1506
1510
|
} catch (err) { console.warn('dsh-russian-lang: set agentPromptPreset failed', err) }}},React.createElement('option', { value: 'technical_expert' }, t('presetExpert')),React.createElement('option', { value: 'tech_writer' }, t('presetWriter')),React.createElement('option', { value: 'concise' }, t('presetConcise')),React.createElement('option', { value: 'code_reviewer' }, t('presetReviewer')),React.createElement('option', { value: 'architect' }, t('presetArchitect')),React.createElement('option', { value: 'tutor' }, t('presetTutor')))),presetInfo ? React.createElement('div', { className: 'rl-preview-box' },React.createElement('div', { style: { fontWeight: 600, marginBottom: '4px', color: 'var(--dsw-alias-label-primary)' } }, '💬 ' + presetInfo.label + ':'),presetInfo.text
|
|
1507
1511
|
) : null
|
|
1508
1512
|
) : null
|
|
1509
|
-
),React.createElement('div', { className: 'rl-section-card' },React.createElement('div', { className: 'rl-section-title' },React.createElement('span', null, t('secUpdater')),React.createElement('span', { className: 'rl-badge ' + (upStatus.updateAvailable ? 'rl-badge-warn' : 'rl-badge-ok') },upStatus.updateAvailable ? t('badgeUpdateAvailable') : t('badgeUpToDate'))),React.createElement('div', { className: 'rl-section-desc' }, t('secUpdaterDesc')),React.createElement('div', { className: 'rl-item-card' },React.createElement('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', flexWrap: 'wrap', gap: '8px' } },React.createElement('div', null,React.createElement('div', { style: { fontWeight: 600, color: 'var(--dsw-alias-label-primary)' } },t('updaterCurrent').replace('{version}', upStatus.currentVersion || '0.3.
|
|
1513
|
+
),React.createElement('div', { className: 'rl-section-card' },React.createElement('div', { className: 'rl-section-title' },React.createElement('span', null, t('secUpdater')),React.createElement('span', { className: 'rl-badge ' + (upStatus.updateAvailable ? 'rl-badge-warn' : 'rl-badge-ok') },upStatus.updateAvailable ? t('badgeUpdateAvailable') : t('badgeUpToDate'))),React.createElement('div', { className: 'rl-section-desc' }, t('secUpdaterDesc')),React.createElement('div', { className: 'rl-item-card' },React.createElement('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', flexWrap: 'wrap', gap: '8px' } },React.createElement('div', null,React.createElement('div', { style: { fontWeight: 600, color: 'var(--dsw-alias-label-primary)' } },t('updaterCurrent').replace('{version}', upStatus.currentVersion || '0.3.16')),upStatus.updateAvailable
|
|
1510
1514
|
? React.createElement('div', { style: { color: 'var(--dsw-alias-state-warning-primary)', marginTop: '2px', fontWeight: 500 } },t('updaterLatest').replace('{version}', upStatus.latestVersion || ''))
|
|
1511
1515
|
: React.createElement('div', { style: { color: 'var(--dsw-alias-label-secondary)', marginTop: '2px' } },t('updaterUpToDate'))),upStatus.updateAvailable
|
|
1512
1516
|
? React.createElement('button', {type: 'button',className: 'rl-btn rl-btn-primary',disabled: upLoading,onClick: triggerUpdate,}, upLoading ? t('updaterUpdating') : t('updaterBtn').replace('{version}', upStatus.latestVersion || ''))
|
|
@@ -1539,12 +1543,12 @@ try { scope.set('overrides', next) } catch (_e) { void _e }},}, t('overrideDelet
|
|
|
1539
1543
|
updateInspectorPill()
|
|
1540
1544
|
},}, isInspectorActive ? '🔍 Инспектор перевода (включён)' : '🔍 Включить инспектор перевода (Alt+I)'),React.createElement('button', {type: 'button',className: 'rl-btn',style: { fontSize: '11px' },onClick: () => {try {navigator.clipboard.writeText(JSON.stringify(overrides, null, 2))
|
|
1541
1545
|
alert('Оверрайды скопированы в буфер обмена как JSON!')
|
|
1542
|
-
} catch (err) { void err; }}}, '📤 Экспорт JSON'),React.createElement('button', {type: 'button',className: 'rl-btn',style: { fontSize: '11px' },onClick: () => {const input = prompt('Вставьте JSON с оверрайдами:')
|
|
1546
|
+
} catch (err) { void err; }}}, '📤 Экспорт JSON'),React.createElement('button', {type: 'button',className: 'rl-btn',style: { fontSize: '11px' },onClick: () => {const input = typeof window !== 'undefined' && typeof window.prompt === 'function' ? window.prompt('Вставьте JSON с оверрайдами:') : null
|
|
1543
1547
|
if (!input) return
|
|
1544
1548
|
try {const parsed = JSON.parse(input)
|
|
1545
1549
|
if (parsed && typeof parsed === 'object') {const merged = Object.assign({}, overrides, parsed)
|
|
1546
1550
|
scope.set('overrides', merged)
|
|
1547
|
-
}} catch (err) { alert('Ошибка разбора JSON: ' + (err && err.message || err)) }}}, '📥 Импорт JSON'))),React.createElement('div', { className: 'rl-section-card' },React.createElement('div', { className: 'rl-section-title' },React.createElement('span', null, t('secSupport')),React.createElement('span', { className: 'rl-badge rl-badge-ok' }, '🟢 100.0%')),React.createElement('div', { className: 'rl-section-desc' }, t('secSupportDesc')),React.createElement('div', { className: 'rl-grid-3' },React.createElement('div', { className: 'rl-stat-box' },React.createElement('div', { className: 'rl-stat-val' }, '113'),React.createElement('div', { className: 'rl-stat-label' }, t('statNamespaces'))),React.createElement('div', { className: 'rl-stat-box' },React.createElement('div', { className: 'rl-stat-val' }, '1 225'),React.createElement('div', { className: 'rl-stat-label' }, t('statCoreKeys'))),React.createElement('div', { className: 'rl-stat-box' },React.createElement('div', { className: 'rl-stat-val' }, '5 924'),React.createElement('div', { className: 'rl-stat-label' }, t('statPluginKeys')))),React.createElement('div', { className: 'rl-actions-row' },React.createElement('a', {href: makeIssueUrl({}, '0.3.
|
|
1551
|
+
}} catch (err) { alert('Ошибка разбора JSON: ' + (err && err.message || err)) }}}, '📥 Импорт JSON'))),React.createElement('div', { className: 'rl-section-card' },React.createElement('div', { className: 'rl-section-title' },React.createElement('span', null, t('secSupport')),React.createElement('span', { className: 'rl-badge rl-badge-ok' }, '🟢 100.0%')),React.createElement('div', { className: 'rl-section-desc' }, t('secSupportDesc')),React.createElement('div', { className: 'rl-grid-3' },React.createElement('div', { className: 'rl-stat-box' },React.createElement('div', { className: 'rl-stat-val' }, '113'),React.createElement('div', { className: 'rl-stat-label' }, t('statNamespaces'))),React.createElement('div', { className: 'rl-stat-box' },React.createElement('div', { className: 'rl-stat-val' }, '1 225'),React.createElement('div', { className: 'rl-stat-label' }, t('statCoreKeys'))),React.createElement('div', { className: 'rl-stat-box' },React.createElement('div', { className: 'rl-stat-val' }, '5 924'),React.createElement('div', { className: 'rl-stat-label' }, t('statPluginKeys')))),React.createElement('div', { className: 'rl-actions-row' },React.createElement('a', {href: makeIssueUrl({}, '0.3.16'),target: '_blank',rel: 'noopener noreferrer',className: 'rl-btn rl-btn-primary'
|
|
1548
1552
|
}, '💬 ' + t('reportIssue')),React.createElement('div', { className: 'rl-hint-text', style: { flex: 1 } },t('exportMdHint')))))))
|
|
1549
1553
|
}
|
|
1550
1554
|
const RL_CSS = ['.rl-modal-mask{position:fixed;top:0;left:0;width:100vw;height:100vh;background:var(--dsw-alias-bg-mask);display:flex;align-items:center;justify-content:center;z-index:99999;backdrop-filter:blur(2px)}.rl-modal-box{background:var(--dsw-alias-bg-layer-2);color:var(--dsw-alias-label-primary);border:1px solid var(--dsw-alias-border-l1);border-radius:10px;width:calc(100vw - 40px);max-width:500px;box-shadow:var(--dsw-alias-shadow-l3);display:flex;flex-direction:column;gap:12px;padding:18px}.rl-card{border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);border-radius:12px;list-style:none;overflow:hidden;transition:border-color .15s ease}.rl-head{appearance:none;width:100%;font:inherit;color:inherit;text-align:left;cursor:pointer;background:0 0;border:0;border-radius:12px;display:flex;align-items:center;gap:12px;padding:14px 18px}.rl-head:hover{background:var(--dsw-alias-bg-layer-2)}.rl-head-main{flex:1;display:flex;flex-direction:column;gap:4px}.rl-title{color:var(--dsw-alias-label-primary);font-size:16px;font-weight:600;line-height:1.4;display:flex;align-items:center;flex-wrap:wrap;gap:8px}.rl-sub{color:var(--dsw-alias-label-secondary);font-size:13px}.rl-chev{margin-left:auto;flex:none;color:var(--dsw-alias-label-tertiary);display:inline-flex;transition:transform .16s}.rl-chev-open{transform:rotate(180deg)}.rl-body{border-top:1px solid var(--dsw-alias-border-l2);padding:18px}.rl-page{display:flex;flex-direction:column;gap:16px;max-width:960px}.rl-section-card{border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-2);border-radius:10px;padding:16px 18px;display:flex;flex-direction:column;gap:12px}.rl-section-title{font-size:14px;font-weight:600;color:var(--dsw-alias-label-primary);display:flex;align-items:center;justify-content:space-between;gap:8px}.rl-section-desc{font-size:12px;color:var(--dsw-alias-label-secondary);margin-top:-4px;line-height:1.4}.rl-grid-2{display:grid;grid-template-columns:repeat(auto-fit, minmax(280px, 1fr));gap:10px}.rl-grid-3{display:grid;grid-template-columns:repeat(auto-fit, minmax(140px, 1fr));gap:10px}.rl-badge{font-size:11px;padding:2px 8px;border-radius:999px;border:1px solid var(--dsw-alias-border-l2);display:inline-flex;align-items:center;gap:4px;font-weight:500}.rl-badge-ok{border-color:var(--dsw-alias-state-success-primary);color:var(--dsw-alias-state-success-primary);background:color-mix(in srgb, var(--dsw-alias-state-success-primary) 8%, transparent)}.rl-badge-warn{border-color:var(--dsw-alias-state-warning-primary);color:var(--dsw-alias-state-warning-primary);background:color-mix(in srgb, var(--dsw-alias-state-warning-primary) 8%, transparent)}.rl-badge-dim{border-color:var(--dsw-alias-border-l2);color:var(--dsw-alias-label-secondary);background:var(--dsw-alias-bg-layer-3)}.rl-item-card{border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);border-radius:8px;padding:10px 12px;display:flex;flex-direction:column;gap:4px}.rl-item-head{display:flex;align-items:center;justify-content:space-between;gap:8px}.rl-item-label{font-size:13px;font-weight:500;color:var(--dsw-alias-label-primary);display:flex;align-items:center;gap:8px;cursor:pointer}.rl-item-desc{font-size:11px;color:var(--dsw-alias-label-secondary);line-height:1.4}.rl-stat-box{border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);border-radius:8px;padding:10px 12px;display:flex;flex-direction:column;gap:2px}.rl-stat-val{font-size:16px;font-weight:700;color:var(--dsw-alias-label-primary)}.rl-stat-label{font-size:11px;color:var(--dsw-alias-label-secondary);letter-spacing:0.3px}.rl-hotkey-box{border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);border-radius:8px;padding:10px 12px;font-size:12px;color:var(--dsw-alias-label-secondary);line-height:1.4;display:flex;align-items:flex-start;gap:10px}.rl-hotkey-tag{font-size:11px;font-weight:700;padding:2px 6px;border-radius:4px;background:var(--dsw-alias-bg-layer-1);border:1px solid var(--dsw-alias-border-l2);color:var(--dsw-alias-label-primary);white-space:nowrap}.rl-preview-box{border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);border-radius:8px;padding:10px 12px;font-size:12px;color:var(--dsw-alias-label-secondary);line-height:1.4}.rl-btn{appearance:none;font:inherit;cursor:pointer;border:1px solid var(--dsw-alias-border-l2);border-radius:8px;padding:6px 12px;font-size:12px;background:var(--dsw-alias-bg-layer-3);color:var(--dsw-alias-label-primary);font-weight:500;display:inline-flex;align-items:center;justify-content:center;gap:6px;transition:all .15s ease;text-decoration:none}.rl-btn:hover:not(:disabled){background:var(--dsw-alias-bg-layer-1);border-color:var(--dsw-alias-label-secondary)}.rl-btn-primary{background:var(--dsw-alias-label-primary);color:var(--dsw-alias-bg-layer-3);border-color:transparent}.rl-btn-primary:hover:not(:disabled){opacity:0.9}.rl-select{height:32px;border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);color:var(--dsw-alias-label-primary);border-radius:6px;padding:0 8px;font-size:12px;outline:none;width:100%;max-width:380px}.rl-select:focus{border-color:var(--dsw-alias-state-brand-primary)}.rl-check{width:16px;height:16px;accent-color:var(--dsw-alias-label-primary);cursor:pointer;flex-shrink:0}.rl-hint-text{font-size:11px;color:var(--dsw-alias-label-secondary);line-height:1.4}.rl-actions-row{display:flex;flex-wrap:wrap;align-items:center;gap:12px;padding-top:4px}.rl-lang-chip{appearance:none;cursor:pointer;border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3);color:var(--dsw-alias-label-secondary);font-size:11px;font-weight:700;padding:2px 7px;border-radius:6px;display:inline-flex;align-items:center;transition:all .15s;margin:0 4px}.rl-lang-chip:hover{border-color:var(--dsw-alias-label-primary);color:var(--dsw-alias-label-primary)}.rl-lang-chip-active{color:var(--dsw-alias-label-primary);border-color:var(--dsw-alias-label-primary);background:var(--dsw-alias-bg-layer-2)}.rl-action-btn{appearance:none;background:0 0;border:1px solid transparent;border-radius:4px;color:var(--dsw-alias-label-secondary);cursor:pointer;font-size:11px;padding:2px 5px;display:inline-flex;align-items:center;transition:all .15s}.rl-action-btn:hover{color:var(--dsw-alias-label-primary);border-color:var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-3)}.rl-action-btn-active{color:var(--dsw-alias-label-primary);background:var(--dsw-alias-bg-layer-2);border-color:var(--dsw-alias-border-l2)}.rl-turn-translation{margin:8px 0;padding:10px 12px;border:1px solid var(--dsw-alias-border-l2);background:var(--dsw-alias-bg-layer-2);border-radius:8px;font-size:13px;line-height:1.5}.rl-trans-head{display:flex;justify-content:space-between;align-items:center;margin-bottom:6px;border-bottom:1px solid var(--dsw-alias-border-l2);padding-bottom:4px}.rl-trans-title{font-size:11px;font-weight:600;color:var(--dsw-alias-label-secondary);text-transform:uppercase;letter-spacing:0.5px}.rl-trans-tools{display:flex;gap:4px}.rl-trans-btn{appearance:none;background:var(--dsw-alias-bg-layer-3);border:1px solid var(--dsw-alias-border-l2);color:var(--dsw-alias-label-secondary);cursor:pointer;padding:2px 7px;border-radius:4px;font-size:11px}.rl-trans-btn:hover{background:var(--dsw-alias-bg-layer-1);color:var(--dsw-alias-label-primary)}.rl-trans-body{color:var(--dsw-alias-label-primary);white-space:pre-wrap;word-break:break-word;user-select:text}.rl-export-md-btn{appearance:none;border:1px solid var(--dsw-alias-border-l2);height:32px;color:var(--dsw-alias-label-primary);cursor:pointer;background:transparent;border-radius:18px;justify-content:center;align-items:center;gap:4px;padding:6px 12px;font-size:13px;font-weight:500;display:inline-flex;white-space:nowrap;margin-left:6px;transition:all .15s ease}.rl-export-md-btn:hover{background:var(--dsw-alias-interactive-bg-hover)}.rl-inspector-hover{position:absolute;pointer-events:none;border:2px solid var(--dsw-alias-state-brand-primary);border-radius:4px;background:color-mix(in srgb,var(--dsw-alias-state-brand-primary) 12%,transparent);box-shadow:0 0 10px color-mix(in srgb,var(--dsw-alias-state-brand-primary) 30%,transparent);z-index:99998;transition:all .06s ease;display:none}.rl-inspector-badge{position:absolute;bottom:calc(100% + 4px);left:0;background:var(--dsw-alias-state-brand-primary);color:var(--dsw-alias-label-inverse);font-size:10px;font-weight:600;padding:2px 6px;border-radius:4px;white-space:nowrap;box-shadow:var(--dsw-alias-shadow-l2);pointer-events:none}.rl-inspector-pill{position:fixed;bottom:18px;right:18px;background:var(--dsw-alias-bg-layer-2);color:var(--dsw-alias-label-primary);border:1px solid var(--dsw-alias-border-l1);border-radius:20px;padding:6px 12px;box-shadow:var(--dsw-alias-shadow-l3);display:none;align-items:center;gap:8px;font-size:12px;z-index:99990;user-select:none}.rl-inspector-pill-active{border-color:var(--dsw-alias-state-brand-primary);box-shadow:0 0 12px color-mix(in srgb,var(--dsw-alias-state-brand-primary) 35%,transparent)}'
|
package/lib/client.template.js
CHANGED
|
@@ -15,11 +15,12 @@ window.__ModuleLoader__.load({
|
|
|
15
15
|
factory: (require) => {
|
|
16
16
|
var module = { exports: {} }
|
|
17
17
|
var React = null
|
|
18
|
-
try { React = require('react') } catch (e) { /* карточка настроек необязательна */ }
|
|
18
|
+
try { React = require('react') } catch (e) { /* карточка настроек необязательна */ void e; }
|
|
19
19
|
|
|
20
20
|
let isInspectorActive = false
|
|
21
21
|
let hoverBoxEl = null
|
|
22
22
|
let pillEl = null
|
|
23
|
+
let updateInspectorPill = () => {}
|
|
23
24
|
|
|
24
25
|
//__PURE_JS__
|
|
25
26
|
|
|
@@ -39,10 +40,11 @@ window.__ModuleLoader__.load({
|
|
|
39
40
|
const FORM_NS = 'dsh-russian-lang'
|
|
40
41
|
const LEGACY_NS = 'russian-lang'
|
|
41
42
|
// Plugins page row seat (DSH 0.1.6-alpha.2): key = '<package name>#<row id>'.
|
|
42
|
-
const ROW_CONFIG_KEY = '@goodandready/dsh-russian-lang#
|
|
43
|
+
const ROW_CONFIG_KEY = '@goodandready/dsh-russian-lang#' + FORM_NS
|
|
43
44
|
|
|
44
45
|
function apply(ctx) {
|
|
45
46
|
const runtime = ctx.locale
|
|
47
|
+
const configForms = ctx && ctx.configForms
|
|
46
48
|
const resolveScope = (c) => {
|
|
47
49
|
try {
|
|
48
50
|
if (c && c.configForms) return c.configForms.get(FORM_NS)
|
|
@@ -84,7 +86,7 @@ window.__ModuleLoader__.load({
|
|
|
84
86
|
}, 'dsh-russian-lang: ' + ns)
|
|
85
87
|
} else {
|
|
86
88
|
Object.assign(RU[ns], dict)
|
|
87
|
-
try { ctx.locale.register(ns, 'ru', RU[ns]) } catch (_) {}
|
|
89
|
+
try { ctx.locale.register(ns, 'ru', RU[ns]) } catch (_) { /* bestEffort */ void _; }
|
|
88
90
|
}
|
|
89
91
|
}
|
|
90
92
|
}
|
|
@@ -248,7 +250,7 @@ window.__ModuleLoader__.load({
|
|
|
248
250
|
try {
|
|
249
251
|
const chain = runtime.fallbackChain && runtime.fallbackChain(runtime.getLocale().active)
|
|
250
252
|
if (Array.isArray(chain) && chain.length) return chain
|
|
251
|
-
} catch (err) { /* ignore */ }
|
|
253
|
+
} catch (err) { /* ignore */ void err; }
|
|
252
254
|
return [runtime.getLocale().active]
|
|
253
255
|
}
|
|
254
256
|
const translationRegistry = new Map()
|
|
@@ -256,7 +258,7 @@ window.__ModuleLoader__.load({
|
|
|
256
258
|
const syncLang = () => {
|
|
257
259
|
try {
|
|
258
260
|
if (typeof document !== 'undefined' && document.documentElement && runtime.getLocale().active === 'ru') document.documentElement.lang = 'ru-RU'
|
|
259
|
-
} catch (err) { /* ignore */ }
|
|
261
|
+
} catch (err) { /* ignore */ void err; }
|
|
260
262
|
}
|
|
261
263
|
const RUNTIME_PROP_NAMES = ['plural','pluralForm','formatDate','formatCompactNumber','formatTokens','formatNumber','formatRelativeTime','formatCurrency','inflect','getPluginLocalizationStatus','stemRussian','fuzzyMatchRu','humanizeError']
|
|
262
264
|
ctx.effect(() => {
|
|
@@ -305,7 +307,7 @@ window.__ModuleLoader__.load({
|
|
|
305
307
|
if (origProps[p] !== undefined) runtime[p] = origProps[p]
|
|
306
308
|
else delete runtime[p]
|
|
307
309
|
}
|
|
308
|
-
if (typeof removeLang === 'function') { try { removeLang() } catch (_) { /* bestEffort */ } }
|
|
310
|
+
if (typeof removeLang === 'function') { try { removeLang() } catch (_) { /* bestEffort */ void _; } }
|
|
309
311
|
}
|
|
310
312
|
}, 'dsh-russian-lang: runtime-lifecycle')
|
|
311
313
|
|
|
@@ -349,7 +351,7 @@ window.__ModuleLoader__.load({
|
|
|
349
351
|
try {
|
|
350
352
|
const value = scope.getSnapshot().value
|
|
351
353
|
if (legacyFlagMode && value && value.enabled === true) { booted = true; activate() }
|
|
352
|
-
} catch (err) { /* ignore */ }
|
|
354
|
+
} catch (err) { /* ignore */ void err; }
|
|
353
355
|
}
|
|
354
356
|
ctx.effect(() => scope.subscribe(tryBoot), 'dsh-russian-lang: boot')
|
|
355
357
|
tryBoot()
|
|
@@ -418,14 +420,14 @@ window.__ModuleLoader__.load({
|
|
|
418
420
|
}
|
|
419
421
|
})
|
|
420
422
|
spellObserver.observe(document.body, { childList: true, subtree: true })
|
|
421
|
-
} catch (err) { /* ignore */ }
|
|
423
|
+
} catch (err) { /* ignore */ void err; }
|
|
422
424
|
}
|
|
423
425
|
const unsubscribeSpell = runtime.subscribe(syncSpell)
|
|
424
426
|
ctx.effect(() => {
|
|
425
427
|
return () => {
|
|
426
428
|
unsubscribeSpell()
|
|
427
429
|
if (spellObserver) spellObserver.disconnect()
|
|
428
|
-
try { document.querySelectorAll('[' + SPELL_ON + ']').forEach(spellOff) } catch (err) { /* ignore */ }
|
|
430
|
+
try { document.querySelectorAll('[' + SPELL_ON + ']').forEach(spellOff) } catch (err) { /* ignore */ void err; }
|
|
429
431
|
}
|
|
430
432
|
}, 'dsh-russian-lang: spellcheck')
|
|
431
433
|
syncSpell()
|
|
@@ -795,11 +797,12 @@ window.__ModuleLoader__.load({
|
|
|
795
797
|
node.nodeValue = val.replace(trimmed, curOverrides[trimmed])
|
|
796
798
|
continue
|
|
797
799
|
}
|
|
800
|
+
const p = node.parentElement
|
|
801
|
+
const isProtected = p && p.closest('code, pre, script, style, textarea, input, select, kbd, samp, [contenteditable="true"], [data-composer-input], [role="textbox"], .chat-message, .markdown-body')
|
|
798
802
|
if (trimmed.length >= 1 && ZH_CJK.test(val)) {
|
|
799
|
-
hits.push(node)
|
|
803
|
+
if (!isProtected) hits.push(node)
|
|
800
804
|
} else if (trimmed.length >= 1 && DOM_EN_TEXT[trimmed]) {
|
|
801
|
-
|
|
802
|
-
if (p && !p.closest('code, pre, script, style, textarea, input, select, kbd, samp, [contenteditable="true"], [data-composer-input], [role="textbox"]')) {
|
|
805
|
+
if (!isProtected) {
|
|
803
806
|
node.nodeValue = val.replace(trimmed, DOM_EN_TEXT[trimmed])
|
|
804
807
|
}
|
|
805
808
|
}
|
|
@@ -834,7 +837,7 @@ window.__ModuleLoader__.load({
|
|
|
834
837
|
}
|
|
835
838
|
}
|
|
836
839
|
}
|
|
837
|
-
} catch (err) { /* ignore */ }
|
|
840
|
+
} catch (err) { /* ignore */ void err; }
|
|
838
841
|
}
|
|
839
842
|
|
|
840
843
|
let zhObserver = null
|
|
@@ -886,7 +889,7 @@ window.__ModuleLoader__.load({
|
|
|
886
889
|
document.addEventListener('click', onInteraction, { passive: true })
|
|
887
890
|
}
|
|
888
891
|
queueZhWalk()
|
|
889
|
-
} catch (err) { /* ignore */ }
|
|
892
|
+
} catch (err) { /* ignore */ void err; }
|
|
890
893
|
}
|
|
891
894
|
const unsubscribeZh = runtime.subscribe(syncZhDom)
|
|
892
895
|
ctx.effect(() => {
|
|
@@ -965,7 +968,7 @@ window.__ModuleLoader__.load({
|
|
|
965
968
|
else typoWalk(root, conf)
|
|
966
969
|
}
|
|
967
970
|
typoPending.clear()
|
|
968
|
-
} catch (err) { /* ignore */ }
|
|
971
|
+
} catch (err) { /* ignore */ void err; }
|
|
969
972
|
}
|
|
970
973
|
const typoPending = new Set()
|
|
971
974
|
const queueTypo = (roots) => {
|
|
@@ -993,7 +996,7 @@ window.__ModuleLoader__.load({
|
|
|
993
996
|
if (roots.length > 0) queueTypo(roots)
|
|
994
997
|
})
|
|
995
998
|
typoObserver.observe(document.body, { childList: true, subtree: true })
|
|
996
|
-
} catch (err) { /* ignore */ }
|
|
999
|
+
} catch (err) { /* ignore */ void err; }
|
|
997
1000
|
}
|
|
998
1001
|
const unsubscribeTypo = runtime.subscribe(syncTypo)
|
|
999
1002
|
ctx.effect(() => {
|
|
@@ -1274,7 +1277,7 @@ window.__ModuleLoader__.load({
|
|
|
1274
1277
|
if (c) { layoutShowHint(el, c.converted, 'cmd'); return }
|
|
1275
1278
|
}
|
|
1276
1279
|
layoutDismiss()
|
|
1277
|
-
} catch (err) { /* ignore */ }
|
|
1280
|
+
} catch (err) { /* ignore */ void err; }
|
|
1278
1281
|
}
|
|
1279
1282
|
const unsubscribeLayout = runtime.subscribe(layoutOnInput)
|
|
1280
1283
|
|
|
@@ -1438,7 +1441,7 @@ window.__ModuleLoader__.load({
|
|
|
1438
1441
|
return hoverBoxEl
|
|
1439
1442
|
}
|
|
1440
1443
|
|
|
1441
|
-
|
|
1444
|
+
updateInspectorPill = () => {
|
|
1442
1445
|
if (typeof document === 'undefined') return
|
|
1443
1446
|
if (!pillEl) {
|
|
1444
1447
|
pillEl = document.createElement('div')
|
|
@@ -1454,7 +1457,7 @@ window.__ModuleLoader__.load({
|
|
|
1454
1457
|
document.body.appendChild(pillEl)
|
|
1455
1458
|
}
|
|
1456
1459
|
pillEl.style.display = isInspectorActive ? 'flex' : 'none'
|
|
1457
|
-
if (isInspectorActive) pillEl.classList.add('rl-inspector-pill-active')
|
|
1460
|
+
if (isInspectorActive && pillEl.classList) pillEl.classList.add('rl-inspector-pill-active')
|
|
1458
1461
|
}
|
|
1459
1462
|
|
|
1460
1463
|
const openInspectorModal = (meta, rawText, targetElement) => {
|
|
@@ -1734,34 +1737,37 @@ window.__ModuleLoader__.load({
|
|
|
1734
1737
|
// ядро (0.1.6-alpha.2) рендерит как страницу плагина с настройками. label —
|
|
1735
1738
|
// статичная строка: он резолвится во время рендера страницы, и обращение к
|
|
1736
1739
|
// локали там роняет весь клиентский батч. Прежние посадки сохранены фолбэками.
|
|
1737
|
-
|
|
1740
|
+
// Посадочные места карточки настроек плагина.
|
|
1741
|
+
// DSH 0.2.0-rc.1:
|
|
1742
|
+
// - plugins.item (#388): id = FORM_NS ('dsh-russian-lang'), монтируется через whileServed([FORM_NS])
|
|
1743
|
+
// - plugins.row.config (#387): key = '@goodandready/dsh-russian-lang#' + FORM_NS
|
|
1744
|
+
// - settings-plugin-item (#389): устаревший слот упразднен в DSH 0.2.0-rc.1, удален
|
|
1745
|
+
const registerPluginsItem = () => {
|
|
1738
1746
|
ctx.slots.inject('plugins.item', () =>
|
|
1739
1747
|
ctx.slots.register({
|
|
1740
1748
|
name: 'plugins.item',
|
|
1741
|
-
id:
|
|
1749
|
+
id: FORM_NS,
|
|
1742
1750
|
order: 60,
|
|
1743
1751
|
label: () => 'Russian language',
|
|
1744
1752
|
locale: SETTINGS_NS_NAME,
|
|
1745
1753
|
inject: () => ({ scope, runtime, toggleRu }),
|
|
1746
1754
|
}, SettingsCard),
|
|
1747
1755
|
)
|
|
1748
|
-
|
|
1749
|
-
|
|
1750
|
-
|
|
1751
|
-
|
|
1752
|
-
|
|
1753
|
-
|
|
1754
|
-
|
|
1755
|
-
|
|
1756
|
-
ctx.slots.
|
|
1757
|
-
|
|
1758
|
-
|
|
1759
|
-
|
|
1760
|
-
|
|
1761
|
-
|
|
1762
|
-
|
|
1763
|
-
)
|
|
1764
|
-
} catch (err) { console.warn('dsh-russian-lang: settings slot unavailable', err) }
|
|
1756
|
+
}
|
|
1757
|
+
if (typeof configForms?.whileServed === 'function') {
|
|
1758
|
+
ctx.effect(() => configForms.whileServed([FORM_NS], registerPluginsItem), 'dsh-russian-lang: plugins.item')
|
|
1759
|
+
} else {
|
|
1760
|
+
registerPluginsItem()
|
|
1761
|
+
}
|
|
1762
|
+
|
|
1763
|
+
ctx.slots.inject('plugins.row.config', () =>
|
|
1764
|
+
ctx.slots.register({
|
|
1765
|
+
name: 'plugins.row.config',
|
|
1766
|
+
key: ROW_CONFIG_KEY,
|
|
1767
|
+
locale: SETTINGS_NS_NAME,
|
|
1768
|
+
inject: () => ({ scope, runtime, toggleRu }),
|
|
1769
|
+
}, SettingsCard),
|
|
1770
|
+
)
|
|
1765
1771
|
|
|
1766
1772
|
// #158: Быстрый переключатель RU ⇄ EN в шапке сессии
|
|
1767
1773
|
try {
|
|
@@ -1774,7 +1780,7 @@ window.__ModuleLoader__.load({
|
|
|
1774
1780
|
inject: () => ({ runtime, toggleRu }),
|
|
1775
1781
|
}, QuickLangSwitch),
|
|
1776
1782
|
)
|
|
1777
|
-
} catch (err) { /* ignore if slot not declared */ }
|
|
1783
|
+
} catch (err) { /* ignore if slot not declared */ void err; }
|
|
1778
1784
|
|
|
1779
1785
|
// #158: Кнопка перевода реплики на русский в действиях ассистента
|
|
1780
1786
|
try {
|
|
@@ -1787,7 +1793,7 @@ window.__ModuleLoader__.load({
|
|
|
1787
1793
|
inject: () => ({ runtime }),
|
|
1788
1794
|
}, TranslateTurnAction),
|
|
1789
1795
|
)
|
|
1790
|
-
} catch (err) { /* ignore if slot not declared */ }
|
|
1796
|
+
} catch (err) { /* ignore if slot not declared */ void err; }
|
|
1791
1797
|
|
|
1792
1798
|
// #158: Экспорт сессии в Markdown
|
|
1793
1799
|
try {
|
|
@@ -1800,7 +1806,7 @@ window.__ModuleLoader__.load({
|
|
|
1800
1806
|
inject: () => ({ runtime }),
|
|
1801
1807
|
}, ExportMarkdownButton),
|
|
1802
1808
|
)
|
|
1803
|
-
} catch (err) { /* ignore if slot not declared */ }
|
|
1809
|
+
} catch (err) { /* ignore if slot not declared */ void err; }
|
|
1804
1810
|
}
|
|
1805
1811
|
|
|
1806
1812
|
// Карточка настроек: React-компонент вне apply.
|
|
@@ -1820,7 +1826,7 @@ window.__ModuleLoader__.load({
|
|
|
1820
1826
|
React.useEffect(() => {
|
|
1821
1827
|
if (!runtime) return
|
|
1822
1828
|
return runtime.subscribe(() => {
|
|
1823
|
-
try { setLocaleState(runtime.getLocale().active || 'en') } catch (e) { /* ignore */ }
|
|
1829
|
+
try { setLocaleState(runtime.getLocale().active || 'en') } catch (e) { /* ignore */ void e; }
|
|
1824
1830
|
})
|
|
1825
1831
|
}, [runtime])
|
|
1826
1832
|
const isRu = locale === 'ru'
|
|
@@ -2166,7 +2172,7 @@ window.__ModuleLoader__.load({
|
|
|
2166
2172
|
React.useEffect(() => {
|
|
2167
2173
|
try {
|
|
2168
2174
|
const un = runtime.subscribe(() => {
|
|
2169
|
-
try { setRuActive(runtime.getLocale().active === 'ru') } catch (e) { /* ignore */ }
|
|
2175
|
+
try { setRuActive(runtime.getLocale().active === 'ru') } catch (e) { /* ignore */ void e; }
|
|
2170
2176
|
})
|
|
2171
2177
|
return un
|
|
2172
2178
|
} catch (e) { return undefined }
|
|
@@ -2586,7 +2592,7 @@ window.__ModuleLoader__.load({
|
|
|
2586
2592
|
className: 'rl-btn',
|
|
2587
2593
|
style: { fontSize: '11px' },
|
|
2588
2594
|
onClick: () => {
|
|
2589
|
-
const input = prompt('Вставьте JSON с оверрайдами:')
|
|
2595
|
+
const input = typeof window !== 'undefined' && typeof window.prompt === 'function' ? window.prompt('Вставьте JSON с оверрайдами:') : null
|
|
2590
2596
|
if (!input) return
|
|
2591
2597
|
try {
|
|
2592
2598
|
const parsed = JSON.parse(input)
|
package/lib/locales.js
CHANGED
|
@@ -79,7 +79,7 @@ export function getAllDictionaries() {
|
|
|
79
79
|
export function getZhRuMap() {
|
|
80
80
|
if (existsSync(ZH_RU_FILE)) {
|
|
81
81
|
try {
|
|
82
|
-
return JSON.parse(readFileSync(
|
|
82
|
+
return JSON.parse(readFileSync(ZH_RU_FILE, "utf8"))
|
|
83
83
|
} catch (_) { /* bestEffort */ void _; }
|
|
84
84
|
}
|
|
85
85
|
return {}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@goodandready/dsh-russian-lang",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.16",
|
|
4
4
|
"description": "Russian localization for DeepSeek Harness (DSH v0.1.7-rc.1+) web UI: adds Русский as native language option. 100.0% coverage across 11,295 keys (127 namespaces). Features full DSH v0.1.7-rc.1 core support (terminal, archive, command palette, Auto review, trajectory, PTC/Creator presets) and complete GoodAndReady plugin catalog (subscriptions, tts, image-gen, voice, key-limits, notify, commandcode, plugin-console).",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "lib/index.js",
|