chore: remove i18n migration helper scripts
This commit is contained in:
-190
@@ -1,190 +0,0 @@
|
||||
"""Batch i18n: replace all remaining French strings in JS modules with t() calls."""
|
||||
import re, json
|
||||
|
||||
BASE = "frontend"
|
||||
|
||||
# ── Load locale to build reverse map ──
|
||||
with open(f"{BASE}/locales/fr.json", encoding="utf-8") as f:
|
||||
fr = json.load(f)
|
||||
text_to_key = {}
|
||||
for k, v in fr.items():
|
||||
if k.startswith("_"): continue
|
||||
if v not in text_to_key or len(k) < len(text_to_key[v]):
|
||||
text_to_key[v] = k
|
||||
|
||||
# ── Helper: quote for replacement ──
|
||||
def esc(s):
|
||||
return s.replace('\\', '\\\\').replace('"', '\\"')
|
||||
|
||||
# ── Replacements: (file, old_pattern, new_pattern) ──
|
||||
# Each old_pattern must be UNIQUE in the file
|
||||
replacements = []
|
||||
|
||||
# === ui.js ===
|
||||
f = f"{BASE}/js/ui.js"
|
||||
|
||||
# Delete dir modal template
|
||||
r = replacements # shorthand
|
||||
|
||||
# Delete dir action
|
||||
r.append((f,
|
||||
"confirmBtn.disabled = true;\n confirmBtn.textContent = 'Suppression...';\n \n try {\n const result = await api(`/api/directory",
|
||||
"confirmBtn.disabled = true;\n confirmBtn.textContent = t('modal.creating');\n \n try {\n const result = await api(`/api/directory"))
|
||||
|
||||
r.append((f,
|
||||
"showToast(`Dossier supprimé (${result.deleted_count} fichiers)`, 'success');",
|
||||
"showToast(t('toast.dir_deleted', {count: result.deleted_count}), 'success');"))
|
||||
|
||||
r.append((f,
|
||||
"showToast(err.message || 'Erreur lors de la suppression', 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = 'Supprimer définitivement';",
|
||||
"showToast(err.message || t('toast.delete_error'), 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = t('modal.delete_permanently');"))
|
||||
|
||||
# Rename toasts
|
||||
r.append((f,
|
||||
"showToast(type === 'directory' ? 'Dossier renommé' : 'Fichier renommé', 'success');",
|
||||
"showToast(type === 'directory' ? t('toast.dir_renamed') : t('toast.file_renamed'), 'success');"))
|
||||
|
||||
r.append((f,
|
||||
"showToast(err.message || 'Erreur lors du renommage', 'error');",
|
||||
"showToast(err.message || t('toast.rename_error'), 'error');"))
|
||||
|
||||
# Copy path toast
|
||||
r.append((f,
|
||||
"showToast(`Chemin copié : ${path}`, 'success');",
|
||||
"showToast(t('toast.path_copied', {path: path}), 'success');"))
|
||||
|
||||
r.append((f,
|
||||
"showToast('Erreur lors de la copie', 'error');",
|
||||
"showToast(t('toast.copy_error'), 'error');"))
|
||||
|
||||
# Bookmark toast
|
||||
r.append((f,
|
||||
'showToast(data.bookmarked ? "Ajouté aux bookmarks" : "Retiré des bookmarks", "success");',
|
||||
'showToast(data.bookmarked ? t("toast.bookmark_added") : t("toast.bookmark_removed"), "success");'))
|
||||
|
||||
# Dir saved search toast
|
||||
r.append((f,
|
||||
'showToast("Repertoire sauvegarde dans les recherches", "success");',
|
||||
'showToast(t("toast.dir_saved_search"), "success");'))
|
||||
|
||||
# Viewer error toast
|
||||
r.append((f,
|
||||
'showToast("Erreur lors du chargement du viewer: " + err.message, "error");',
|
||||
'showToast(t("toast.viewer_error") + ": " + err.message, "error");'))
|
||||
|
||||
|
||||
# === palette.js ===
|
||||
f = f"{BASE}/js/palette.js"
|
||||
pal = text_to_key
|
||||
|
||||
# Confirm dialogs
|
||||
r.append((f,
|
||||
'confirm(`Supprimer le fichier \\"${path}\\" ?`)',
|
||||
'confirm(t("confirm.delete_file_named", {path: path}))'))
|
||||
|
||||
r.append((f,
|
||||
'confirm(`Supprimer \\"${path}\\" et TOUT son contenu ?`)',
|
||||
'confirm(t("confirm.delete_dir_named", {path: path}))'))
|
||||
|
||||
# Show toasts
|
||||
r.append((f,
|
||||
"showToast('Erreur de création','error')",
|
||||
"showToast(t('toast.create_error'),'error')"))
|
||||
|
||||
r.append((f,
|
||||
"showToast('Erreur','error')",
|
||||
"showToast(t('common.error'),'error')"))
|
||||
|
||||
# === config.js ===
|
||||
f = f"{BASE}/js/config.js"
|
||||
|
||||
# About sections
|
||||
r.append((f,
|
||||
'title: "Application",',
|
||||
'title: t("about.section_app"),'))
|
||||
r.append((f,
|
||||
'title: "Environnement",',
|
||||
'title: t("about.section_env"),'))
|
||||
r.append((f,
|
||||
'title: "Composants",',
|
||||
'title: t("about.section_components"),'))
|
||||
|
||||
# About rows - these are data, not labels per se, but let's translate the labels
|
||||
for old_label, key in [
|
||||
('"Nom"', "about.name"), ('"Version"', "about.version"),
|
||||
('"Version API"', "about.api_version"), ('"Statut"', "about.status"),
|
||||
('"Vaults configurés"', "about.vaults_configured"),
|
||||
('"Fichiers indexés"', "about.files_indexed"),
|
||||
('"Navigateur"', "about.browser"), ('"Plateforme"', "about.platform"),
|
||||
('"Langue"', "about.language"), ('"Backend"', "about.backend"),
|
||||
('"Rendu Markdown"', "about.markdown_renderer"),
|
||||
('"Surveillance fichiers"', "about.file_watcher"),
|
||||
('"Frontend"', "about.frontend"), ('"Icônes"', "about.icons"),
|
||||
('"Coloration syntaxe"', "about.syntax_highlight"),
|
||||
('"Éditeur"', "about.editor"),
|
||||
]:
|
||||
r.append((f, f'[{old_label},', f'[t("{key}"),'))
|
||||
|
||||
# Admin-only / no webhooks
|
||||
r.append((f,
|
||||
"list.innerHTML = '<div class=\"config-description\">Admin uniquement</div>';",
|
||||
"list.innerHTML = '<div class=\"config-description\">' + t('common.loading') + '</div>';"))
|
||||
r.append((f,
|
||||
"list.innerHTML = '<div class=\"config-description\">Aucun webhook configuré.</div>';",
|
||||
"list.innerHTML = '<div class=\"config-description\">' + t('common.none') + '</div>';"))
|
||||
|
||||
# === auth.js ===
|
||||
f = f"{BASE}/js/auth.js"
|
||||
r.append((f,
|
||||
'Administration — Utilisateurs',
|
||||
"' + t('admin.title') + '"))
|
||||
r.append((f,
|
||||
'+ Nouvel utilisateur',
|
||||
"' + t('admin.new_user') + '"))
|
||||
r.append((f,
|
||||
"title=\"Fermer\"",
|
||||
"title=\"' + t('common.close') + '\""))
|
||||
|
||||
# === viewer.js ===
|
||||
f = f"{BASE}/js/viewer.js"
|
||||
r.append((f,
|
||||
"titleInp.placeholder = 'Titre...'",
|
||||
"titleInp.placeholder = t('forge.title_placeholder')"))
|
||||
r.append((f,
|
||||
"title: \"Ouvrir dans une nouvelle fenetre\"",
|
||||
"title: t('forge.popout')"))
|
||||
r.append((f,
|
||||
'document.createTextNode("pop-out")',
|
||||
'document.createTextNode(t("forge.popout_label"))'))
|
||||
|
||||
# === dashboard.js ===
|
||||
f = f"{BASE}/js/dashboard.js"
|
||||
r.append((f,
|
||||
'"Copier"',
|
||||
't("dashboard.copy_btn")'))
|
||||
r.append((f,
|
||||
'"Ouvrir"',
|
||||
't("dashboard.open_btn")'))
|
||||
|
||||
# === search.js ===
|
||||
f = f"{BASE}/js/search.js"
|
||||
r.append((f,
|
||||
"summaryText.textContent = `${data.total} résultat(s)",
|
||||
"summaryText.textContent = t('search.results_count', {count: data.total})"))
|
||||
|
||||
# ── Apply all replacements ──
|
||||
for filepath, old, new in replacements:
|
||||
with open(filepath, "r", encoding="utf-8") as fh:
|
||||
content = fh.read()
|
||||
count = content.count(old)
|
||||
if count == 0:
|
||||
print(f"SKIP {filepath}: pattern not found: {old[:60]}...")
|
||||
continue
|
||||
if count > 1:
|
||||
print(f"WARN {filepath}: {count} matches for: {old[:60]}...")
|
||||
content = content.replace(old, new)
|
||||
with open(filepath, "w", encoding="utf-8") as fh:
|
||||
fh.write(content)
|
||||
print(f"OK {filepath}: {count} replacement(s)")
|
||||
|
||||
print(f"\nTotal replacements applied: {len(replacements)}")
|
||||
-202
@@ -1,202 +0,0 @@
|
||||
"""One-pass i18n: replace all French strings in all JS modules."""
|
||||
import re
|
||||
|
||||
BASE = "frontend/js"
|
||||
|
||||
# All replacements as (file, find_unique_snippet, replacement)
|
||||
# Each 'find' must be UNIQUE in the file
|
||||
R = []
|
||||
|
||||
# ═══════ ui.js ═══════
|
||||
F = f"{BASE}/ui.js"
|
||||
|
||||
# Create file modal template
|
||||
R.append((F,
|
||||
'<h3 class="obsigate-modal-title">Créer un fichier</h3>',
|
||||
'<h3 class="obsigate-modal-title">${t(\'modal.create_file\')}</h3>'))
|
||||
R.append((F,
|
||||
'<label class="modal-label">Nom du fichier</label>',
|
||||
'<label class="modal-label">${t(\'modal.file_name\')}</label>'))
|
||||
R.append((F,
|
||||
'<div class="modal-hint">Dans: ${parentPath',
|
||||
'<div class="modal-hint">${t(\'modal.in_folder\', {path: parentPath'))
|
||||
R.append((F,
|
||||
'<label class="modal-label">Type de fichier</label>',
|
||||
'<label class="modal-label">${t(\'modal.file_type\')}</label>'))
|
||||
R.append((F,
|
||||
'<button class="modal-btn" id="file-cancel-btn">Annuler</button>',
|
||||
'<button class="modal-btn" id="file-cancel-btn">${t(\'common.cancel\')}</button>'))
|
||||
R.append((F,
|
||||
'<button class="modal-btn primary" id="file-create-btn">Créer</button>',
|
||||
'<button class="modal-btn primary" id="file-create-btn">${t(\'modal.create_btn\')}</button>'))
|
||||
|
||||
# Create file action (toasts, textContent)
|
||||
R.append((F,
|
||||
"createBtn.textContent = 'Création...';\n \n try {\n await api(`/api/file",
|
||||
"createBtn.textContent = t('modal.creating');\n \n try {\n await api(`/api/file"))
|
||||
R.append((F,
|
||||
'showToast(`Fichier "${name}" créé`, \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n openFile(vault, path);',
|
||||
'showToast(t(\'toast.file_created\', {name: name}), \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n openFile(vault, path);'))
|
||||
R.append((F,
|
||||
"showToast(err.message || 'Erreur lors de la création', 'error');\n createBtn.disabled = false;\n createBtn.textContent = 'Créer';\n }\n };\n \n createBtn.addEventListener('click', create);",
|
||||
"showToast(err.message || t('toast.create_error'), 'error');\n createBtn.disabled = false;\n createBtn.textContent = t('modal.create_btn');\n }\n };\n \n createBtn.addEventListener('click', create);"))
|
||||
|
||||
# Create dir action
|
||||
R.append((F,
|
||||
"createBtn.textContent = 'Création...';\n \n try {\n await api(`/api/directory",
|
||||
"createBtn.textContent = t('modal.creating');\n \n try {\n await api(`/api/directory"))
|
||||
R.append((F,
|
||||
'showToast(`Dossier "${name}" créé`, \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();',
|
||||
'showToast(t(\'toast.dir_created\', {name: name}), \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();'))
|
||||
R.append((F,
|
||||
"showToast(err.message || 'Erreur lors de la création', 'error');\n createBtn.disabled = false;\n createBtn.textContent = 'Créer';\n }\n };\n \n createBtn.addEventListener('click', create);\n cancelBtn.addEventListener('click', () => this._closeModal(overlay));\n \n input.addEventListener('keydown', (e) => {\n if (e.key === 'Enter') create();\n if (e.key === 'Escape') this._closeModal(overlay);\n });\n },\n\n showCreateFileModal",
|
||||
"showToast(err.message || t('toast.create_error'), 'error');\n createBtn.disabled = false;\n createBtn.textContent = t('modal.create_btn');\n }\n };\n \n createBtn.addEventListener('click', create);\n cancelBtn.addEventListener('click', () => this._closeModal(overlay));\n \n input.addEventListener('keydown', (e) => {\n if (e.key === 'Enter') create();\n if (e.key === 'Escape') this._closeModal(overlay);\n });\n },\n\n showCreateFileModal"))
|
||||
|
||||
# Delete dir modal template
|
||||
R.append((F,
|
||||
'<h3 class="obsigate-modal-title">Supprimer le dossier</h3>',
|
||||
'<h3 class="obsigate-modal-title">${t(\'modal.delete_dir\')}</h3>'))
|
||||
R.append((F,
|
||||
'<strong>Attention !</strong> Cette action est irréversible.\n <br>Tous les fichiers et sous-dossiers seront supprimés définitivement.',
|
||||
'<strong>${t(\'modal.delete_warning\')}</strong> ${t(\'modal.delete_irreversible\')}\n <br>${t(\'modal.delete_dir_warning\')}'))
|
||||
R.append((F,
|
||||
'<label class="modal-label">Dossier à supprimer:</label>',
|
||||
'<label class="modal-label">${t(\'modal.dir_to_delete\')}</label>'))
|
||||
|
||||
# Delete dir action
|
||||
R.append((F,
|
||||
"confirmBtn.textContent = 'Suppression...';\n \n try {\n const result = await api(`/api/directory",
|
||||
"confirmBtn.textContent = t('modal.creating');\n \n try {\n const result = await api(`/api/directory"))
|
||||
R.append((F,
|
||||
"showToast(`Dossier supprimé (${result.deleted_count} fichiers)`, 'success');",
|
||||
"showToast(t('toast.dir_deleted', {count: result.deleted_count}), 'success');"))
|
||||
R.append((F,
|
||||
"showToast(err.message || 'Erreur lors de la suppression', 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = 'Supprimer définitivement';\n }\n };\n \n confirmBtn.addEventListener('click', deleteDir);",
|
||||
"showToast(err.message || t('toast.delete_error'), 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = t('modal.delete_permanently');\n }\n };\n \n confirmBtn.addEventListener('click', deleteDir);"))
|
||||
|
||||
# Delete file modal template
|
||||
R.append((F,
|
||||
'<h3 class="obsigate-modal-title">Supprimer le fichier</h3>',
|
||||
'<h3 class="obsigate-modal-title">${t(\'modal.delete_file\')}</h3>'))
|
||||
R.append((F,
|
||||
'<strong>Attention !</strong> Cette action est irréversible.\n </div>\n </div>\n <div class="modal-form-group">\n <label class="modal-label">Fichier à supprimer:',
|
||||
'<strong>${t(\'modal.delete_warning\')}</strong> ${t(\'modal.delete_irreversible\')}\n </div>\n </div>\n <div class="modal-form-group">\n <label class="modal-label">${t(\'modal.file_to_delete\')}'))
|
||||
|
||||
# Delete file action
|
||||
R.append((F,
|
||||
"confirmBtn.textContent = 'Suppression...';\n \n try {\n await api(`/api/file/${encodeURIComponent(vault)}",
|
||||
"confirmBtn.textContent = t('modal.creating');\n \n try {\n await api(`/api/file/${encodeURIComponent(vault)}"))
|
||||
R.append((F,
|
||||
"showToast('Fichier supprimé', 'success');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n \n if (state.currentVault === vault",
|
||||
"showToast(t('toast.file_deleted'), 'success');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n \n if (state.currentVault === vault"))
|
||||
|
||||
# ═══════ palette.js ═══════
|
||||
F = f"{BASE}/palette.js"
|
||||
R.append((F,
|
||||
"confirm(`Supprimer le fichier \\\"${path}\\\" ?`)",
|
||||
"confirm(t('confirm.delete_file_named', {path: path}))"))
|
||||
R.append((F,
|
||||
"confirm(`Supprimer \\\"${path}\\\" et TOUT son contenu ?`)",
|
||||
"confirm(t('confirm.delete_dir_named', {path: path}))"))
|
||||
R.append((F,
|
||||
"showToast('Erreur de création','error')",
|
||||
"showToast(t('toast.create_error'),'error')"))
|
||||
R.append((F,
|
||||
"showToast('Erreur','error')",
|
||||
"showToast(t('common.error'),'error')"))
|
||||
R.append((F,
|
||||
"showToast('Aucun fichier ouvert','error')",
|
||||
"showToast(t('toast.no_open_file'),'error')"))
|
||||
|
||||
# ═══════ search.js ═══════
|
||||
F = f"{BASE}/search.js"
|
||||
R.append((F,
|
||||
"summaryText.textContent = `${data.total} résultat(s) pour \"${freeText}\" avec filtres`;",
|
||||
"summaryText.textContent = t('search.results_filtered', {count: data.total, query: freeText});"))
|
||||
R.append((F,
|
||||
"summaryText.textContent = `${data.total} résultat(s) pour \"${freeText}\"`;",
|
||||
"summaryText.textContent = t('search.results_for', {count: data.total, query: freeText});"))
|
||||
R.append((F,
|
||||
"summaryText.textContent = `${data.total} fichier(s) avec filtres`;",
|
||||
"summaryText.textContent = t('search.files_filtered', {count: data.total});"))
|
||||
R.append((F,
|
||||
"summaryText.textContent = `${data.total} résultat(s)`;",
|
||||
"summaryText.textContent = t('search.results_count', {count: data.total});"))
|
||||
R.append((F,
|
||||
"timeBadge.textContent = `(${data.query_time_ms} ms)`;",
|
||||
"timeBadge.textContent = t('search.query_time', {time: data.query_time_ms});"))
|
||||
|
||||
# ═══════ config.js ═══════
|
||||
F = f"{BASE}/config.js"
|
||||
R.append((F,
|
||||
'title: "Application",',
|
||||
'title: t("about.section_app"),'))
|
||||
R.append((F,
|
||||
'title: "Environnement",',
|
||||
'title: t("about.section_env"),'))
|
||||
R.append((F,
|
||||
'title: "Composants",',
|
||||
'title: t("about.section_components"),'))
|
||||
for old_lbl, key in [
|
||||
('"Nom"', "about.name"), ('"Version"', "about.version"),
|
||||
('"Version API"', "about.api_version"), ('"Statut"', "about.status"),
|
||||
('"Vaults configurés"', "about.vaults_configured"),
|
||||
('"Fichiers indexés"', "about.files_indexed"),
|
||||
('"Navigateur"', "about.browser"), ('"Plateforme"', "about.platform"),
|
||||
('"Langue"', "about.language"), ('"Backend"', "about.backend"),
|
||||
('"Rendu Markdown"', "about.markdown_renderer"),
|
||||
('"Surveillance fichiers"', "about.file_watcher"),
|
||||
('"Frontend"', "about.frontend"), ('"Icônes"', "about.icons"),
|
||||
('"Coloration syntaxe"', "about.syntax_highlight"),
|
||||
('"Éditeur"', "about.editor"),
|
||||
]:
|
||||
R.append((F, f'[{old_lbl},', f'[t("{key}"),'))
|
||||
|
||||
# ═══════ auth.js ═══════
|
||||
F = f"{BASE}/auth.js"
|
||||
R.append((F,
|
||||
"Administration — Utilisateurs",
|
||||
"' + t('admin.title') + '"))
|
||||
R.append((F,
|
||||
"+ Nouvel utilisateur",
|
||||
"' + t('admin.new_user') + '"))
|
||||
|
||||
# ═══════ viewer.js ═══════
|
||||
F = f"{BASE}/viewer.js"
|
||||
R.append((F,
|
||||
"titleInp.placeholder = 'Titre...'",
|
||||
"titleInp.placeholder = t('forge.title_placeholder')"))
|
||||
R.append((F,
|
||||
'title: "Ouvrir dans une nouvelle fenetre"',
|
||||
'title: t("forge.popout")'))
|
||||
R.append((F,
|
||||
'document.createTextNode("pop-out")',
|
||||
'document.createTextNode(t("forge.popout_label"))'))
|
||||
|
||||
# ═══════ dashboard.js ═══════
|
||||
F = f"{BASE}/dashboard.js"
|
||||
R.append((F,
|
||||
'📋 Copier',
|
||||
"' + t('dashboard.copy_btn') + '"))
|
||||
R.append((F,
|
||||
'📂 Ouvrir',
|
||||
"' + t('dashboard.open_btn') + '"))
|
||||
|
||||
# ── EXECUTE ──
|
||||
ok = 0
|
||||
skip = 0
|
||||
for filepath, find, repl in R:
|
||||
with open(filepath, "r", encoding="utf-8") as fh:
|
||||
content = fh.read()
|
||||
count = content.count(find)
|
||||
if count == 0:
|
||||
print(f"SKIP {filepath.split('/')[-1]}: not found — {find[:50]}...")
|
||||
skip += 1
|
||||
continue
|
||||
content = content.replace(find, repl)
|
||||
with open(filepath, "w", encoding="utf-8") as fh:
|
||||
fh.write(content)
|
||||
ok += 1
|
||||
print(f"OK {filepath.split('/')[-1]}: {count}× {find[:40]}...")
|
||||
|
||||
print(f"\nDone: {ok} applied, {skip} skipped")
|
||||
-159
@@ -1,159 +0,0 @@
|
||||
"""Robust one-pass i18n: read once, replace all, write once per file."""
|
||||
import re, collections
|
||||
|
||||
BASE = "frontend/js"
|
||||
|
||||
# All replacements grouped by file
|
||||
R = collections.defaultdict(list)
|
||||
|
||||
def add(f, find, repl):
|
||||
R[f].append((find, repl))
|
||||
|
||||
F = f"{BASE}/ui.js"
|
||||
|
||||
# Create file modal
|
||||
add(F, '<h3 class="obsigate-modal-title">Créer un fichier</h3>', '<h3 class="obsigate-modal-title">${t(\'modal.create_file\')}</h3>')
|
||||
add(F, '<label class="modal-label">Nom du fichier</label>', '<label class="modal-label">${t(\'modal.file_name\')}</label>')
|
||||
add(F, '<div class="modal-hint">Dans: ${parentPath', '<div class="modal-hint">${t(\'modal.in_folder\', {path: parentPath')
|
||||
add(F, '<label class="modal-label">Type de fichier</label>', '<label class="modal-label">${t(\'modal.file_type\')}</label>')
|
||||
add(F, '<button class="modal-btn" id="file-cancel-btn">Annuler</button>', '<button class="modal-btn" id="file-cancel-btn">${t(\'common.cancel\')}</button>')
|
||||
add(F, '<button class="modal-btn primary" id="file-create-btn">Créer</button>', '<button class="modal-btn primary" id="file-create-btn">${t(\'modal.create_btn\')}</button>')
|
||||
|
||||
# Create file action (toasts, textContent)
|
||||
add(F, "createBtn.textContent = 'Création...';\n \n try {\n await api(`/api/file",
|
||||
"createBtn.textContent = t('modal.creating');\n \n try {\n await api(`/api/file")
|
||||
add(F, 'showToast(`Fichier "${name}" créé`, \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n openFile(vault, path);',
|
||||
'showToast(t(\'toast.file_created\', {name: name}), \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n openFile(vault, path);')
|
||||
add(F, "showToast(err.message || 'Erreur lors de la création', 'error');\n createBtn.disabled = false;\n createBtn.textContent = 'Créer';\n }\n };\n \n createBtn.addEventListener('click', create);",
|
||||
"showToast(err.message || t('toast.create_error'), 'error');\n createBtn.disabled = false;\n createBtn.textContent = t('modal.create_btn');\n }\n };\n \n createBtn.addEventListener('click', create);")
|
||||
|
||||
# Create dir action
|
||||
add(F, "createBtn.textContent = 'Création...';\n \n try {\n await api(`/api/directory",
|
||||
"createBtn.textContent = t('modal.creating');\n \n try {\n await api(`/api/directory")
|
||||
add(F, 'showToast(`Dossier "${name}" créé`, \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();',
|
||||
'showToast(t(\'toast.dir_created\', {name: name}), \'success\');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();')
|
||||
add(F, "showToast(err.message || 'Erreur lors de la création', 'error');\n createBtn.disabled = false;\n createBtn.textContent = 'Créer';\n }\n };\n \n createBtn.addEventListener('click', create);\n cancelBtn.addEventListener('click', () => this._closeModal(overlay));\n \n input.addEventListener('keydown', (e) => {\n if (e.key === 'Enter') create();\n if (e.key === 'Escape') this._closeModal(overlay);\n });\n },\n\n showCreateFileModal",
|
||||
"showToast(err.message || t('toast.create_error'), 'error');\n createBtn.disabled = false;\n createBtn.textContent = t('modal.create_btn');\n }\n };\n \n createBtn.addEventListener('click', create);\n cancelBtn.addEventListener('click', () => this._closeModal(overlay));\n \n input.addEventListener('keydown', (e) => {\n if (e.key === 'Enter') create();\n if (e.key === 'Escape') this._closeModal(overlay);\n });\n },\n\n showCreateFileModal")
|
||||
|
||||
# Delete dir modal template
|
||||
add(F, '<h3 class="obsigate-modal-title">Supprimer le dossier</h3>', '<h3 class="obsigate-modal-title">${t(\'modal.delete_dir\')}</h3>')
|
||||
add(F, '<strong>Attention !</strong> Cette action est irréversible.\n <br>Tous les fichiers et sous-dossiers seront supprimés définitivement.',
|
||||
'<strong>${t(\'modal.delete_warning\')}</strong> ${t(\'modal.delete_irreversible\')}\n <br>${t(\'modal.delete_dir_warning\')}')
|
||||
add(F, '<label class="modal-label">Dossier à supprimer:</label>', '<label class="modal-label">${t(\'modal.dir_to_delete\')}</label>')
|
||||
|
||||
# Delete dir action
|
||||
add(F, "confirmBtn.textContent = 'Suppression...';\n \n try {\n const result = await api(`/api/directory",
|
||||
"confirmBtn.textContent = t('modal.creating');\n \n try {\n const result = await api(`/api/directory")
|
||||
add(F, "showToast(`Dossier supprimé (${result.deleted_count} fichiers)`, 'success');",
|
||||
"showToast(t('toast.dir_deleted', {count: result.deleted_count}), 'success');")
|
||||
add(F, "showToast(err.message || 'Erreur lors de la suppression', 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = 'Supprimer définitivement';\n }\n };\n \n confirmBtn.addEventListener('click', deleteDir);",
|
||||
"showToast(err.message || t('toast.delete_error'), 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = t('modal.delete_permanently');\n }\n };\n \n confirmBtn.addEventListener('click', deleteDir);")
|
||||
|
||||
# Delete file modal template + action
|
||||
add(F, '<h3 class="obsigate-modal-title">Supprimer le fichier</h3>', '<h3 class="obsigate-modal-title">${t(\'modal.delete_file\')}</h3>')
|
||||
add(F, '<strong>Attention !</strong> Cette action est irréversible.\n </div>\n </div>\n <div class="modal-form-group">\n <label class="modal-label">Fichier à supprimer:',
|
||||
'<strong>${t(\'modal.delete_warning\')}</strong> ${t(\'modal.delete_irreversible\')}\n </div>\n </div>\n <div class="modal-form-group">\n <label class="modal-label">${t(\'modal.file_to_delete\')}')
|
||||
add(F, 'data-i18n="common.cancel"', 'data-i18n="common.cancel"') # no-op, placeholder
|
||||
|
||||
# Replace all buttons in delete modals
|
||||
add(F, '<button class="modal-btn" id="del-cancel-btn">Annuler</button>', '<button class="modal-btn" id="del-cancel-btn">${t(\'common.cancel\')}</button>')
|
||||
add(F, '<button class="modal-btn danger" id="del-confirm-btn">Supprimer définitivement</button>', '<button class="modal-btn danger" id="del-confirm-btn">${t(\'modal.delete_permanently\')}</button>')
|
||||
|
||||
# Delete file action
|
||||
add(F, "confirmBtn.textContent = 'Suppression...';\n \n try {\n await api(`/api/file/${encodeURIComponent(vault)}",
|
||||
"confirmBtn.textContent = t('modal.creating');\n \n try {\n await api(`/api/file/${encodeURIComponent(vault)}")
|
||||
add(F, "showToast('Fichier supprimé', 'success');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n \n if (state.currentVault === vault",
|
||||
"showToast(t('toast.file_deleted'), 'success');\n this._closeModal(overlay);\n await refreshSidebarTreePreservingState();\n \n if (state.currentVault === vault")
|
||||
add(F, "showToast(err.message || 'Erreur lors de la suppression', 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = 'Supprimer définitivement';\n }\n };\n \n confirmBtn.addEventListener('click', deleteFile);",
|
||||
"showToast(err.message || t('toast.delete_error'), 'error');\n confirmBtn.disabled = false;\n confirmBtn.textContent = t('modal.delete_permanently');\n }\n };\n \n confirmBtn.addEventListener('click', deleteFile);")
|
||||
|
||||
# Rename toasts
|
||||
add(F, "showToast(type === 'directory' ? 'Dossier renommé' : 'Fichier renommé', 'success');",
|
||||
"showToast(type === 'directory' ? t('toast.dir_renamed') : t('toast.file_renamed'), 'success');")
|
||||
add(F, "showToast(err.message || 'Erreur lors du renommage', 'error');",
|
||||
"showToast(err.message || t('toast.rename_error'), 'error');")
|
||||
|
||||
# Copy path
|
||||
add(F, "showToast(`Chemin copié : ${path}`, 'success');",
|
||||
"showToast(t('toast.path_copied', {path: path}), 'success');")
|
||||
add(F, "showToast('Erreur lors de la copie', 'error');",
|
||||
"showToast(t('toast.copy_error'), 'error');")
|
||||
|
||||
# Bookmark + dir saved search + viewer error
|
||||
add(F, 'showToast(data.bookmarked ? "Ajouté aux bookmarks" : "Retiré des bookmarks", "success");',
|
||||
'showToast(data.bookmarked ? t("toast.bookmark_added") : t("toast.bookmark_removed"), "success");')
|
||||
add(F, 'showToast("Repertoire sauvegarde dans les recherches", "success");',
|
||||
'showToast(t("toast.dir_saved_search"), "success");')
|
||||
add(F, 'showToast("Erreur lors du chargement du viewer: " + err.message, "error");',
|
||||
'showToast(t("toast.viewer_error") + ": " + err.message, "error");')
|
||||
|
||||
# ═══════ palette.js ═══════
|
||||
F = f"{BASE}/palette.js"
|
||||
add(F, 'confirm(`Supprimer le fichier \\"${path}\\" ?`)', 'confirm(t(\'confirm.delete_file_named\', {path: path}))')
|
||||
add(F, 'confirm(`Supprimer \\"${path}\\" et TOUT son contenu ?`)', 'confirm(t(\'confirm.delete_dir_named\', {path: path}))')
|
||||
add(F, "showToast('Erreur de création','error')", "showToast(t('toast.create_error'),'error')")
|
||||
add(F, "showToast('Erreur','error')", "showToast(t('common.error'),'error')")
|
||||
add(F, "showToast('Aucun fichier ouvert','error')", "showToast(t('toast.no_open_file'),'error')")
|
||||
|
||||
# ═══════ search.js ═══════
|
||||
F = f"{BASE}/search.js"
|
||||
add(F, 'summaryText.textContent = `${data.total} résultat(s) pour "${freeText}" avec filtres`;',
|
||||
'summaryText.textContent = t(\'search.results_filtered\', {count: data.total, query: freeText});')
|
||||
add(F, 'summaryText.textContent = `${data.total} résultat(s) pour "${freeText}"`;',
|
||||
'summaryText.textContent = t(\'search.results_for\', {count: data.total, query: freeText});')
|
||||
add(F, 'summaryText.textContent = `${data.total} fichier(s) avec filtres`;',
|
||||
'summaryText.textContent = t(\'search.files_filtered\', {count: data.total});')
|
||||
add(F, 'summaryText.textContent = `${data.total} résultat(s)`;',
|
||||
'summaryText.textContent = t(\'search.results_count\', {count: data.total});')
|
||||
add(F, 'timeBadge.textContent = `(${data.query_time_ms} ms)`;',
|
||||
'timeBadge.textContent = t(\'search.query_time\', {time: data.query_time_ms});')
|
||||
|
||||
# ═══════ config.js ═══════
|
||||
F = f"{BASE}/config.js"
|
||||
add(F, 'title: "Application",', 'title: t("about.section_app"),')
|
||||
add(F, 'title: "Environnement",', 'title: t("about.section_env"),')
|
||||
add(F, 'title: "Composants",', 'title: t("about.section_components"),')
|
||||
for old_lbl, key in [('"Nom"',"about.name"),('"Version"',"about.version"),('"Version API"',"about.api_version"),
|
||||
('"Statut"',"about.status"),('"Vaults configurés"',"about.vaults_configured"),
|
||||
('"Fichiers indexés"',"about.files_indexed"),('"Navigateur"',"about.browser"),
|
||||
('"Plateforme"',"about.platform"),('"Langue"',"about.language"),('"Backend"',"about.backend"),
|
||||
('"Rendu Markdown"',"about.markdown_renderer"),('"Surveillance fichiers"',"about.file_watcher"),
|
||||
('"Frontend"',"about.frontend"),('"Icônes"',"about.icons"),
|
||||
('"Coloration syntaxe"',"about.syntax_highlight"),('"Éditeur"',"about.editor")]:
|
||||
add(F, f'[{old_lbl},', f'[t("{key}"),')
|
||||
|
||||
# ═══════ auth.js ═══════
|
||||
F = f"{BASE}/auth.js"
|
||||
add(F, 'Administration — Utilisateurs', "' + t('admin.title') + '")
|
||||
add(F, '+ Nouvel utilisateur', "' + t('admin.new_user') + '")
|
||||
|
||||
# ═══════ viewer.js ═══════
|
||||
F = f"{BASE}/viewer.js"
|
||||
add(F, "titleInp.placeholder = 'Titre...'", "titleInp.placeholder = t('forge.title_placeholder')")
|
||||
add(F, 'title: "Ouvrir dans une nouvelle fenetre"', 'title: t("forge.popout")')
|
||||
add(F, 'document.createTextNode("pop-out")', 'document.createTextNode(t("forge.popout_label"))')
|
||||
|
||||
# ═══════ dashboard.js ═══════
|
||||
F = f"{BASE}/dashboard.js"
|
||||
add(F, '\ud83d\udccb Copier', "' + t('dashboard.copy_btn') + '")
|
||||
add(F, '\ud83d\udcc2 Ouvrir', "' + t('dashboard.open_btn') + '")
|
||||
|
||||
# ── APPLY (one read + write per file) ──
|
||||
print("Applying replacements per file...")
|
||||
for filepath in R:
|
||||
with open(filepath, "r", encoding="utf-8") as fh:
|
||||
content = fh.read()
|
||||
changed = False
|
||||
for find, repl in R[filepath]:
|
||||
count = content.count(find)
|
||||
if count == 0:
|
||||
print(f" SKIP {filepath.split('/')[-1]}: {find[:50]}...")
|
||||
continue
|
||||
content = content.replace(find, repl)
|
||||
changed = True
|
||||
print(f" OK {filepath.split('/')[-1]}: {count}× {find[:40]}")
|
||||
if changed:
|
||||
with open(filepath, "w", encoding="utf-8") as fh:
|
||||
fh.write(content)
|
||||
|
||||
print("Done.")
|
||||
Reference in New Issue
Block a user