fix: A27 lint terminé — eslint 0/0 (285 warnings nettoyés) (v7.25.0)
FlowDeck CI / test (push) Failing after 3h9m51s
FlowDeck CI / lint (push) Successful in 1m54s
FlowDeck CI / docker (push) Skipped

3 familles, 13 fichiers (+153/−167) :

1. no-empty ×70 = TOUS des `catch (x) {}` vides → `catch { /* volontaire */ }`
   (binding optionnel ES2019 + commentaire : passe no-empty ET
   no-unused-vars, zéro changement de comportement).

2. no-unused-vars ×171 :
   - bindings de catch inutilisés retirés (e/err/ex/e2/e3)
   - 24 lignes mortes déterministes, chaque suppression validée par assert
     sur le texte exact (`var self = this` ×8, `var lang`, `var acc`,
     `var today`, `var path/restored/files/resolved/items/clickEl`,
     `uid()`/`propName()` sans un seul appel, `.then` + `resolved++`
     compteurs jamais lus)
   - `/* exported */` sur les 10 fonctions appelées depuis les attributs
     HTML des templates (vérifiées par grep : 1 template chacune) :
     setActiveTab/kanbanBoard/filterSystem/sortSystem/newIssueForm/
     showNewIssue, importWizard, libraryPage, workspacesPage, settingsInit

3. no-undef ×44 = vrais globaux déclarés dans eslint.config.mjs
   (getSvgIcon = script inline de base.html, TextDecoder = API navigateur,
   Prism = CDN) + 2 vrais correctifs :
   - settings.js : `typeof toast === 'function'` = guard TOUJOURS faux
     (pas de toast global) → les toasts timezone/SAML ne s'affichaient
     jamais → `window.showToast` (2 sites)
   - local_workspace.js : `_wsInitData = window._wsInitData`
     (auto-affectation sans effet, global implicite) supprimé

eslint static/js : **0 erreur / 0 warning** (285 → 0) · node --check vert
sur tous les fichiers · suite **1089/1089** · ruff OK · docs à jour
This commit is contained in:
2026-10-01 21:30:37 -04:00
parent 103bc57418
commit 8d0d69e7b8
19 changed files with 189 additions and 173 deletions
+30
View File
@@ -1,5 +1,35 @@
# Changelog - FlowDeck
## v7.25.0 (2026-10-01) — Audit : A27 CLOSED (eslint 0/0)
### Fixed
- **Toasts settings jamais affichés** : `settings.js` appelait
`typeof toast === 'function'` — guard **toujours faux** (le `toast` global
n'existait pas) → les retours « Timezone saved » / « SP metadata URL
copiée » ne s'affichaient jamais. → `window.showToast` (global `base.html`)
- `_wsInitData = window._wsInitData` (auto-affectation d'un nom non déclaré,
sans effet observable car `window._wsInitData` existe depuis L4) supprimé
### Changed
- **A27 lint terminé : `eslint static/js` = 0 erreur / 0 warning** (285 → 0,
22 fichiers) :
· no-empty ×70 = `catch (x) {}` vides → `catch { /* volontaire */ }`
(binding optionnel ES2019 ; zéro changement de comportement)
· no-unused-vars ×171 = bindings de catch retirés + 24 lignes mortes
déterministes (assert sur texte exact avant suppression) +
`/* exported */` sur les 10 fonctions appelées depuis les attributs
HTML des templates (vérifiées par grep)
· no-undef ×44 = vrais globaux déclarés dans `eslint.config.mjs`
(getSvgIcon = inline base.html, TextDecoder = API, Prism = CDN)
### Notes
- `node --check` vert sur tous les fichiers ; suite complète **1089/1089**
- A27 reste ouvert uniquement pour : `base` 1 523 L structurel (inline par
nature, décision assumée) + ~500 L de petits blocs hors cibles
## v7.24.0 (2026-10-01) — Audit : A27 extraction TERMINÉE (bilan -85 %)
### Changed
+2 -2
View File
File diff suppressed because one or more lines are too long
+1 -1
View File
@@ -1 +1 @@
7.24.0
7.25.0
+1 -1
View File
@@ -1,6 +1,6 @@
# WORKLOAD — FlowDeck Notion Clone
> **Début**: 2026-07-08 | **Version**: v7.24.0 (audit — A27 extraction TERMINÉE : 11 874 L, -85 % inline) | **Statut**: EN COURS 🔄
> **Début**: 2026-07-08 | **Version**: v7.25.0 (audit — A27 CLOSED : eslint 0/0, 285 warnings nettoyés) | **Statut**: EN COURS 🔄
> **Cible**: parité Notion + intégration forge · **Follow-ups v7.3 livrés**: sidebar teamspaces, notif `page.updated`, charts `number` + dashboards multi-DB, unfurl forge, UI Settings → Audit — voir `ROADMAP.md § v7.3.0`
## Avancement Global
+1 -1
View File
@@ -185,7 +185,7 @@ async def lifespan(_app: FastAPI):
app = FastAPI(
title="FlowDeck",
version="7.24.0",
version="7.25.0",
docs_url="/docs",
redoc_url="/redoc",
lifespan=lifespan,
+1 -1
View File
@@ -2,7 +2,7 @@
"openapi": "3.1.0",
"info": {
"title": "FlowDeck",
"version": "7.24.0"
"version": "7.25.0"
},
"paths": {
"/auth/register": {
+3
View File
@@ -40,6 +40,9 @@ const browserGlobals = {
Alpine: "readonly", htmx: "readonly", Sortable: "readonly",
// Globals exposed on window by app.js
openModal: "readonly", closeModal: "readonly",
// getSvgIcon : script inline de base.html (nonce) ; Prism : CDN des vues ;
// TextDecoder : API navigateur (ES2015)
getSvgIcon: "readonly", Prism: "readonly", TextDecoder: "readonly",
};
export default [
+2 -2
View File
@@ -61,7 +61,7 @@
self._place();
var el = document.querySelector('.fd-ctx-menu');
if (el && window.ResizeObserver) {
if (self._ro) { try { self._ro.disconnect(); } catch (e) {} }
if (self._ro) { try { self._ro.disconnect(); } catch { /* volontaire */ } }
self._ro = new ResizeObserver(function () { self._place(); });
self._ro.observe(el);
}
@@ -95,7 +95,7 @@
this.maxH = Math.max(120, vh - ny - 8);
},
close() {
if (this._ro) { try { this._ro.disconnect(); } catch (e) {} this._ro = null; }
if (this._ro) { try { this._ro.disconnect(); } catch { /* volontaire */ } this._ro = null; }
this.open = false;
this.node = null;
this.handlers = {};
+6 -6
View File
@@ -126,7 +126,7 @@
remove() {
var fn = this.onRemove || this.onPick;
if (fn) { try { fn(''); } catch (e) {} }
if (fn) { try { fn(''); } catch { /* volontaire */ } }
this.close();
},
@@ -143,7 +143,7 @@
loadRecent() {
try { this.recent = JSON.parse(localStorage.getItem('fd_icon_recent') || '[]'); }
catch (e) { this.recent = []; }
catch { this.recent = []; }
},
pushRecent(e) {
try {
@@ -151,7 +151,7 @@
r.unshift(e);
this.recent = r.slice(0, 32);
localStorage.setItem('fd_icon_recent', JSON.stringify(this.recent));
} catch (err) {}
} catch { /* volontaire */ }
},
async loadCustom() {
@@ -160,7 +160,7 @@
var d = await r.json();
this.custom = (d && d.emojis) || [];
this.customLoaded = true;
} catch (e) { this.custom = []; }
} catch { this.custom = []; }
},
openCustomModal() {
@@ -196,7 +196,7 @@
this.customModal = false;
this.pick(d.emoji.url);
}
} catch (e) {
} catch {
if (window.showToast) window.showToast('Emoji upload failed', 'error');
}
this.customBusy = false;
@@ -206,7 +206,7 @@
var csrf = (document.cookie.match(/csrf_token=([^;]+)/) || [])[1] || '';
await fetch('/api/custom-emojis/' + id, { method: 'DELETE', headers: { 'X-CSRF-Token': csrf }, credentials: 'same-origin' });
this.custom = this.custom.filter(function (e) { return e.id !== id; });
} catch (e) {}
} catch { /* volontaire */ }
}
});
});
+20 -24
View File
@@ -430,7 +430,7 @@
if(!lastAsst) return;
var steps = acts.map(function(a){
var res = null;
try{ res = a.result_json ? JSON.parse(a.result_json) : {}; }catch(e){ res = {}; }
try{ res = a.result_json ? JSON.parse(a.result_json) : {}; }catch{ res = {}; }
var msg = (res && res.message) ? res.message : '';
return agentPanel._actionStep({
tool: a.tool_name, status: a.status, target_id: a.target_id,
@@ -672,7 +672,7 @@
r.insertNode(br);
r.setStartAfter(br); r.collapse(true);
this.input = this.composerText();
}catch(e){}
}catch { /* volontaire */ }
this.resizeInput();
},
_caretQuery(){
@@ -687,7 +687,7 @@
if(i > 0 && s[i-1] === '@' && (i === 1 || /\s/.test(s[i-2]))){
return {node: node, at: i-1, raw: s.slice(i, off)};
}
}catch(e){}
}catch { /* volontaire */ }
return null;
},
_expandToAt(range){
@@ -727,14 +727,14 @@
useRange.setStartAfter(span); useRange.collapse(true);
useRange.insertNode(sp);
useRange.setStart(sp, 1); useRange.setEnd(sp, 1);
try{ var s2 = window.getSelection(); if(s2){ s2.removeAllRanges(); s2.addRange(useRange); } }catch(e2){}
try{ var s2 = window.getSelection(); if(s2){ s2.removeAllRanges(); s2.addRange(useRange); } }catch { /* volontaire */ }
} else {
if(el.textContent) el.appendChild(document.createTextNode(' '));
el.appendChild(span);
el.appendChild(document.createTextNode(' '));
try{ var r2 = document.createRange(); r2.selectNodeContents(el); r2.collapse(false); var s3 = window.getSelection(); if(s3){ s3.removeAllRanges(); s3.addRange(r2); } }catch(e3){}
try{ var r2 = document.createRange(); r2.selectNodeContents(el); r2.collapse(false); var s3 = window.getSelection(); if(s3){ s3.removeAllRanges(); s3.addRange(r2); } }catch { /* volontaire */ }
}
}catch(e){}
}catch { /* volontaire */ }
this.input = this.composerText();
this.resizeInput();
this._emptyCheck();
@@ -753,7 +753,7 @@
this._insertToken(item, r);
return;
}
}catch(e){}
}catch { /* volontaire */ }
}
this._insertToken(item);
},
@@ -803,12 +803,12 @@
onPaste(e){
e.preventDefault();
var text = '';
try{ if(e.clipboardData) text = e.clipboardData.getData('text/plain') || ''; }catch(err){ }
try{ if(e.clipboardData) text = e.clipboardData.getData('text/plain') || ''; }catch { /* volontaire */ }
if(!text) return;
try{
var sel = window.getSelection();
if(sel && sel.rangeCount){ sel.getRangeAt(0).deleteContents(); document.execCommand('insertText', false, text); }
}catch(err){}
}catch { /* volontaire */ }
this.input = this.composerText();
this.resizeInput();
},
@@ -889,7 +889,6 @@
return null;
},
useSuggestion(c){
var self = this;
if(!c || c._sep) return;
if(c._admin){
this.setComposerText(c.cmd.replace(/\s*<[^>]*>\s*$/, ' '));
@@ -926,7 +925,6 @@
this.scrollBottom();
},
handleCommand(text){
var self = this;
var parts = text.replace(/^\/+/, '').trim().split(/\s+/);
var cmd = (parts.shift() || '').toLowerCase();
var arg = parts.join(' ').trim();
@@ -1164,7 +1162,7 @@
if(tok){ e.preventDefault(); this._removeTokenDom(tok); return; }
}
}
}catch(err){}
}catch { /* volontaire */ }
}
if(key === 'Escape'){
if(this.mentionOpen){ e.preventDefault(); e.stopPropagation(); this.mentionOpen = false; this._mentionFrom = null; this._atNode = null; return; }
@@ -1219,7 +1217,6 @@
// Render agent markdown responses (headings, tables, code, lists, …) to
// HTML so the panel displays content like Notion (no raw `##` / `**`).
renderMarkdown(md){
var self = this;
function escHtml(s){ return String(s==null?'':s).replace(/&/g,'&amp;').replace(/</g,'&lt;').replace(/>/g,'&gt;'); }
function inline(t){
t = escHtml(t);
@@ -1261,7 +1258,6 @@
var t = raw.trim();
// Fenced code block
if(t.startsWith('```')){
var lang = t.substring(3).trim();
var code = [];
i++;
while(i < lines.length && !lines[i].trim().startsWith('```')){
@@ -1351,7 +1347,7 @@
var ok = document.execCommand('copy');
document.body.removeChild(ta);
self.toast(ok ? 'Réponse copiée.' : 'Copie impossible.', !ok);
}catch(err){ self.toast('Copie impossible.', true); }
}catch{ self.toast('Copie impossible.', true); }
}
if(navigator.clipboard && navigator.clipboard.writeText){
navigator.clipboard.writeText(text).then(function(){ self.toast('Réponse copiée.'); }).catch(function(){ fallback(); });
@@ -1418,7 +1414,7 @@
if(ment.length){ text = 'Analyse le contexte référencé.'; }
else if(!hasSkills){ return; }
}
try { await self.ensureConversation(); } catch(e){ return; }
try { await self.ensureConversation(); } catch{ return; }
var rawText = text;
// La requête est composée EN ARRIÈRE-PLAN (hors de la boîte d'édition) :
// contexte1 + contexte2 + skill-1 + skill-2 + texte.
@@ -1505,7 +1501,7 @@
fph.steps = runSteps.slice();
fph.stepsOpen = false;
fph.model = self.autoLabel || '';
if(window.__fdInsertAI){ try{ var h=window.__fdInsertAI; window.__fdInsertAI=null; h(ev.content||''); }catch(e){} }
if(window.__fdInsertAI){ try{ var h=window.__fdInsertAI; window.__fdInsertAI=null; h(ev.content||''); }catch { /* volontaire */ } }
}
else if(ev.type==='notice'){ self.notice = ev.message; }
else if(ev.type==='error'){
@@ -1515,7 +1511,7 @@
eph.steps = runSteps.slice();
self.errorMsg = ev.message;
}
}catch(e){}
}catch { /* volontaire */ }
});
self.scrollBottom();
return read();
@@ -1631,7 +1627,7 @@
var out = title ? ('Titre du document : ' + title) : 'Document ouvert';
if(text) out += '\n\n' + text;
return out.slice(0, 9000);
}catch(e){ return ''; }
}catch{ return ''; }
};
if(!window.fdGetPageContext) window.fdGetPageContext = window.fdReadPageContext;
@@ -1644,7 +1640,7 @@
try{
var m = (window.location.pathname || '').match(new RegExp('^\\/?' + prefix + '\\/(\\d+)'));
return m ? m[1] : null;
}catch(e){ return null; }
}catch{ return null; }
}
function labelFromTitle(){
try{
@@ -1652,7 +1648,7 @@
t = t.replace(/^\s*FlowDeck\s*-\s*/i, '');
t = t.replace(/\s*[-|]\s*FlowDeck\s*$/i, '');
if(t && t.toLowerCase() !== 'home' && t.toLowerCase() !== 'flowdeck') return t;
}catch(e){}
}catch { /* volontaire */ }
return '';
}
function docContext(){
@@ -1671,7 +1667,7 @@
refType: pid ? 'document' : null
};
}
}catch(e){}
}catch { /* volontaire */ }
return null;
}
function marker(){
@@ -1686,7 +1682,7 @@
var lbl = b.getAttribute('data-fd-context');
return {kind:'section', icon:'📍', label:lbl, text:'', key:'marker'};
}
}catch(e){}
}catch { /* volontaire */ }
return null;
}
function byPath(){
@@ -1777,7 +1773,7 @@
if(E.autoSave) E.autoSave();
if(E.render) E.render();
return true;
}catch(e){ return false; }
}catch{ return false; }
};
// Backward-compatible detection hooks (banner + Ask AI)
+2 -1
View File
@@ -1,4 +1,5 @@
const BD=(()=>{try{const el=document.getElementById('bd-config');return el?JSON.parse(el.textContent):{}}catch(e){return {}}})();
/* exported setActiveTab, kanbanBoard, filterSystem, sortSystem, newIssueForm, showNewIssue -- appeles depuis les attributs HTML des templates */
const BD=(()=>{try{const el=document.getElementById('bd-config');return el?JSON.parse(el.textContent):{}}catch{return {}}})();
var owner = BD.owner;
var repo = BD.repo;
+3 -6
View File
@@ -1,4 +1,4 @@
const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=el?JSON.parse(el.textContent):null;return v===undefined?null:v}catch(e){return null}})();
const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=el?JSON.parse(el.textContent):null;return v===undefined?null:v}catch{return null}})();
(function() {
'use strict';
@@ -47,7 +47,7 @@ const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=
var PALETTE = {gray:'#8b8b8b',brown:'#9f6b53',orange:'#d9730d',yellow:'#cb912f',green:'#448361',blue:'#337ea9',purple:'#9065b0',pink:'#c14c8a',red:'#d44c47'};
function escHtml(s) { return String(s==null?'':s).replace(/&/g,'&amp;').replace(/</g,'&lt;').replace(/>/g,'&gt;').replace(/"/g,'&quot;'); }
function parseJSON(s, d) { try { return typeof s === 'string' ? JSON.parse(s) : (s || d); } catch(e) { return d; } }
function parseJSON(s, d) { try { return typeof s === 'string' ? JSON.parse(s) : (s || d); } catch { return d; } }
function parseOpts(prop) {
var o = parseJSON(prop.options_json, []);
if (!Array.isArray(o)) o = [];
@@ -57,7 +57,6 @@ const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=
var found = parseOpts(prop).filter(function(o){ return o.name === name; })[0];
return (found && PALETTE[found.color]) || '#8b8b8b';
}
function uid() { return 'dbx' + Math.random().toString(36).slice(2,9); }
function getCsrf() { var m = document.cookie.match(/csrf_token=([^;]+)/); return m ? m[1] : ''; }
function toast(msg, kind) {
if (typeof window.showToast === 'function') window.showToast(msg, kind);
@@ -167,7 +166,6 @@ const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=
if (ref === undefined || ref === null || ref === '') return null;
return state.properties.filter(function(p){ return String(p.id) === String(ref) || p.name === ref; })[0] || null;
}
function propName(ref) { var p = findProp(ref); return p ? p.name : ''; }
function firstPropOfTypes(types) {
return state.properties.filter(function(p){ return types.indexOf(p.prop_type) >= 0; })[0] || null;
}
@@ -321,7 +319,7 @@ const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=
h += '<th class="db-th db-th-handle" style="width:32px;min-width:32px"></th>';
props.forEach(function(prop){
var w = state.colWidths[prop.id] || 200;
var groupIdx = 0; var acc = 0;
var groupIdx = 0;
groups.forEach(function(g, gi){ if (g.props.indexOf(prop) >= 0) groupIdx = gi; });
var collapsed = hasGroups && state.collapsedGroups[groupIdx];
h += '<th class="db-th db-th-property" data-colgroup="'+groupIdx+'" style="'+(collapsed?'display:none;':'')+'min-width:'+w+'px;width:'+w+'px" data-prop-id="'+prop.id+'">';
@@ -523,7 +521,6 @@ const DB_CONFIG=(()=>{try{const el=document.getElementById('db-config');const v=
if (!dp) return '<div style="padding:24px;color:var(--text-dim)">Add a Date property to use the calendar view.</div>';
var mode = calMode();
var cur = state.calCursor;
var today = new Date();
var h = '<div class="db-cal-head">';
h += '<div class="db-cal-nav"><button data-cal-prev="1">\u2039</button><button data-cal-next="1">\u203a</button></div>';
var title;
+9 -9
View File
@@ -63,7 +63,7 @@ document.addEventListener('alpine:init', () => {
var d = await r.json();
this.treeItems = d.tree || [];
this._sortTree();
} catch(e) { this.treeItems = []; this.sortedTreeItems = []; }
} catch { this.treeItems = []; this.sortedTreeItems = []; }
finally { this.treeLoading = false; }
},
@@ -267,7 +267,7 @@ document.addEventListener('alpine:init', () => {
ul.appendChild(li);
});
el.appendChild(ul);
} catch(e) {}
} catch { /* volontaire */ }
},
async openFile(path, sha) {
@@ -286,7 +286,7 @@ document.addEventListener('alpine:init', () => {
} else {
this.fileContent = '[Error loading file]';
}
} catch(e) {
} catch {
this.fileContent = '[Error loading file]';
}
this.fileLoading = false;
@@ -343,7 +343,7 @@ document.addEventListener('alpine:init', () => {
var d = await r.json();
window.showToast('Failed to save: ' + (d.error || 'Unknown error'), 'error');
}
} catch(e) { window.showToast('Network error', 'error'); }
} catch { window.showToast('Network error', 'error'); }
},
async deleteCurrentFile() {
@@ -358,7 +358,7 @@ document.addEventListener('alpine:init', () => {
this.filePath = '';
await this.refreshTree();
}
} catch(e) {}
} catch { /* volontaire */ }
},
async refreshTree() {
@@ -380,7 +380,7 @@ document.addEventListener('alpine:init', () => {
try {
var r = await fetch('/api/gitea/projects/' + this.owner + '/' + this.repo + '/private-pages');
if (r.ok) { var d = await r.json(); this.privatePages = d.pages || []; }
} catch(e) {}
} catch { /* volontaire */ }
},
newPrivate() {
@@ -398,7 +398,7 @@ document.addEventListener('alpine:init', () => {
this.editingPrivateTitle = d.page.title;
this.editingPrivateContent = d.page.content;
}
} catch(e) {}
} catch { /* volontaire */ }
},
async savePrivate() {
@@ -419,7 +419,7 @@ document.addEventListener('alpine:init', () => {
this.editingPrivateContent = '';
await this.loadPrivatePages();
}
} catch(e) {}
} catch { /* volontaire */ }
},
// Create new file
@@ -477,7 +477,7 @@ document.addEventListener('alpine:init', () => {
method: 'DELETE', headers: {'X-CSRF-Token': this.getCsrfToken ? this.getCsrfToken() : ''}
});
if (r.ok) await this.loadPrivatePages();
} catch(e) {}
} catch { /* volontaire */ }
},
getCsrfToken() {
+7 -6
View File
@@ -1,3 +1,4 @@
/* exported importWizard -- appeles depuis les attributs HTML des templates */
function importWizard() {
return {
@@ -25,11 +26,11 @@ function importWizard() {
try {
const r = await fetch('/api/import/sources');
this.sources = (await r.json()).sources || [];
} catch(e) {}
} catch { /* volontaire */ }
try {
const c = await fetch('/api/csrf-token');
this.csrf = (await c.json()).csrf_token;
} catch(e) {}
} catch { /* volontaire */ }
},
humanSize(n) { return n > 1048576 ? (n/1048576).toFixed(1)+' Mo' : Math.max(1, Math.round(n/1024))+' Ko'; },
addFiles(list) {
@@ -61,7 +62,7 @@ function importWizard() {
this.preview = merged;
this.mapping = {};
(merged ? merged.pages : []).forEach(p => (p.schema||[]).forEach(c => { this.mapping[c.name]=c.type; }));
} catch(e) { this.error = 'Erreur réseau'; }
} catch { this.error = 'Erreur réseau'; }
finally { this.busy = false; setTimeout(()=>{this.progress=0;},800); }
},
async importOne(f) {
@@ -82,7 +83,7 @@ function importWizard() {
if (!r.ok) { f.status='error'; f.error=d.detail||'Erreur'; return null; }
f.status = (d.status==='partial' ? 'partial' : 'done');
return d;
} catch(e) { f.status='error'; f.error='Erreur réseau'; return null; }
} catch { f.status='error'; f.error='Erreur réseau'; return null; }
},
async doImport() {
this.busy = true; this.error=''; this.report=null; this.progress=0;
@@ -115,7 +116,7 @@ function importWizard() {
const d = await r.json();
if (!r.ok) { this.urlError = d.detail || 'Erreur'; return; }
this.report = d; this.progress = 100;
} catch(e) { this.urlError = 'Erreur réseau'; }
} catch { this.urlError = 'Erreur réseau'; }
finally { this.busy = false; }
},
async doForge(kind) {
@@ -132,7 +133,7 @@ function importWizard() {
const d = await r.json();
if (!r.ok) { this.forgeError = d.detail || 'Erreur'; return; }
this.report = d; this.progress = 100;
} catch(e) { this.forgeError = 'Erreur réseau'; }
} catch { this.forgeError = 'Erreur réseau'; }
finally { this.busy = false; }
},
async pollJob(jobId, f) {
+15 -15
View File
@@ -1,3 +1,4 @@
/* exported libraryPage -- appeles depuis les attributs HTML des templates */
function libraryPage() {
return {
@@ -298,7 +299,7 @@ function libraryPage() {
} else {
if (window.showToast) window.showToast('Not a text file', 'error');
}
} catch (e) {
} catch {
if (window.showToast) window.showToast('Copy failed', 'error');
}
},
@@ -389,7 +390,7 @@ function libraryPage() {
headers: {'Content-Type':'application/json', 'X-CSRF-Token': csrf},
body: JSON.stringify({ parent_id: parentId || 0 })
});
} catch(e) {}
} catch { /* volontaire */ }
}
this.clearSelection();
this.loadTab();
@@ -537,7 +538,6 @@ function libraryPage() {
doSort() {
var s = this.sortBy;
if (!s) return;
var self = this;
function sortNodes(nodes) {
if (!nodes) return;
nodes.sort(function(a,b){
@@ -574,7 +574,7 @@ function libraryPage() {
item.children = d.items || [];
// Mark the tree for depth calculation
this._markChildren(item.children, (item.depth || 0) + 1);
} catch(e) {
} catch {
item.children = [];
}
}
@@ -701,7 +701,7 @@ function libraryPage() {
item.page_icon = icon;
this._renderTable();
if (window.showToast) window.showToast('Icon updated', 'success');
} catch(e) {
} catch {
if (window.showToast) window.showToast('Failed to update icon', 'error');
}
},
@@ -712,7 +712,7 @@ function libraryPage() {
var r = await fetch('/api/settings/tags/all');
var d = await r.json();
this.workspaceTags = d.tags || [];
} catch(e) { this.workspaceTags = []; }
} catch { this.workspaceTags = []; }
},
toggleTagFilter(tagName) {
@@ -771,7 +771,7 @@ function libraryPage() {
this._ctxRefreshAvail();
this._recomputeFlatItems();
}
} catch(e) {}
} catch { /* volontaire */ }
},
async toggleFavoriteItem(item) {
@@ -809,7 +809,7 @@ function libraryPage() {
this.loadTab();
this._syncSidebar();
if (window.showToast) window.showToast('Page duplicated', 'success');
} catch(e) {
} catch {
if (window.showToast) window.showToast('Failed to duplicate page', 'error');
}
},
@@ -828,7 +828,7 @@ function libraryPage() {
var all = (d.items || []).filter(function(it) { return ids.indexOf(it.id) === -1; });
this._moveAllCandidates = all;
this.moveCandidates = all.slice(0, 30);
} catch(e) {
} catch {
this._moveAllCandidates = [];
this.moveCandidates = [];
}
@@ -881,7 +881,7 @@ function libraryPage() {
if (r.ok) {
item.title = newName;
}
} catch(e) {}
} catch { /* volontaire */ }
this._renderTable();
this._syncSidebar();
},
@@ -908,7 +908,7 @@ function libraryPage() {
var cr = await fetch('/api/library/children/' + parentId);
var cd = await cr.json();
parent.children = cd.items || [];
} catch(e) {}
} catch { /* volontaire */ }
this._recomputeFlatItems();
this._renderTable();
return;
@@ -917,7 +917,7 @@ function libraryPage() {
if (window.fdNavigate) window.fdNavigate('/pages/' + d.id);
else window.location.href = '/pages/' + d.id;
}
} catch(e) {
} catch {
if (window.showToast) window.showToast('Failed to create page', 'error');
}
},
@@ -996,7 +996,7 @@ function libraryPage() {
if (days < 7) return days + 'd ago';
if (days < 30) return Math.floor(days/7) + 'w ago';
return dt.toLocaleDateString('en-US',{month:'short',day:'numeric',year:'numeric'});
} catch(e) { return d; }
} catch { return d; }
}
};
}
@@ -1029,11 +1029,11 @@ function libraryPage() {
if (el && el.__x) { el.__x.$data.peekItem = null; }
}
dragging = false;
try { localStorage.setItem('fd_peek_width', panel.style.width); } catch(ex) {}
try { localStorage.setItem('fd_peek_width', panel.style.width); } catch { /* volontaire */ }
handle.releasePointerCapture(e.pointerId);
});
try {
var saved = localStorage.getItem('fd_peek_width');
if (saved) panel.style.width = saved;
} catch(ex) {}
} catch { /* volontaire */ }
})();
+22 -35
View File
@@ -1,4 +1,4 @@
const LW=(()=>{try{const el=document.getElementById('lw-config');return el?JSON.parse(el.textContent):{}}catch(e){return {}}})();
const LW=(()=>{try{const el=document.getElementById('lw-config');return el?JSON.parse(el.textContent):{}}catch{return {}}})();
console.log('FLOWDECK v2.4.6 — IIFE running, about to set _wsInitData');
window._wsInitData = (function() {
@@ -17,7 +17,7 @@ window._wsInitData = (function() {
target:null,
expanded: (function() {
try { return JSON.parse(localStorage.getItem('fd_ws_expanded') || '{}'); }
catch(e) { return {}; }
catch { return {}; }
})(),
currentFolder: LW.current_folder_id,
searchQuery: '',
@@ -118,7 +118,7 @@ window._wsInitData = (function() {
pendingSyncCount: 0,
pinnedIds: (function() {
try { return JSON.parse(localStorage.getItem('fd_ws_pinned') || '[]'); }
catch(e) { return []; }
catch { return []; }
})(),
// Navigation history
@@ -223,13 +223,13 @@ window._wsInitData = (function() {
window._wsData.closePreviewPanel();
}
dragging = false;
try { localStorage.setItem('fd_peek_width', panel.style.width); } catch(ex) {}
try { localStorage.setItem('fd_peek_width', panel.style.width); } catch { /* volontaire */ }
handle.releasePointerCapture(e.pointerId);
});
try {
var saved = localStorage.getItem('fd_peek_width');
if (saved) panel.style.width = saved;
} catch(ex) {}
} catch { /* volontaire */ }
},
_recompute() {
@@ -252,7 +252,7 @@ window._wsInitData = (function() {
if (idx === -1) this.pinnedIds.push(id);
else this.pinnedIds.splice(idx, 1);
try { localStorage.setItem('fd_ws_pinned', JSON.stringify(this.pinnedIds)); }
catch(e) {}
catch { /* volontaire */ }
this._haptic();
},
isPinned(id) {
@@ -380,7 +380,6 @@ window._wsInitData = (function() {
_getItemPath(id) {
// Build folder path by walking up parent chain via tree
var path = [];
var found = this._findInTree(this.tree, id);
if (!found) return '—';
return '/' + found.path.reverse().join('/');
@@ -515,7 +514,7 @@ window._wsInitData = (function() {
} else {
preview = '<div style="text-align:center;padding:30px;color:var(--text-tertiary)">Empty document</div>';
}
} catch(e) {
} catch {
preview = '<pre style="background:var(--bg-tertiary);padding:14px;border-radius:6px;overflow:auto;font-size:12px;font-family:monospace;white-space:pre-wrap;">' + this._escHtml(String(content).substring(0, 3000)) + '</pre>';
}
@@ -533,7 +532,7 @@ window._wsInitData = (function() {
}
}
body.innerHTML = preview || '<div style="color:var(--text-tertiary);text-align:center;padding:20px">(empty)</div>';
} catch(e) {
} catch {
body.innerHTML = '<div style="text-align:center;padding:20px;color:var(--text-tertiary)">Preview not available</div>';
}
},
@@ -602,7 +601,7 @@ window._wsInitData = (function() {
} else {
if (window.showToast) window.showToast('Not a text file', 'error');
}
} catch (e) {
} catch {
if (window.showToast) window.showToast('Copy failed', 'error');
}
},
@@ -634,7 +633,7 @@ window._wsInitData = (function() {
if (window.appState && window.appState.refreshFavorites) window.appState.refreshFavorites();
if (window.showToast) window.showToast(node.favorited ? 'Added to Favorites' : 'Removed from Favorites', 'success');
}
} catch(e) {}
} catch { /* volontaire */ }
},
async setItemIcon(node, icon) {
@@ -652,7 +651,7 @@ window._wsInitData = (function() {
this.displayTree = [...this.tree];
this._reloadAfterAction();
if (window.showToast) window.showToast('Icon updated', 'success');
} catch(e) {
} catch {
if (window.showToast) window.showToast('Failed to update icon', 'error');
}
},
@@ -741,7 +740,7 @@ window._wsInitData = (function() {
this._computeFilteredTableItems();
this._ctxRefreshAvail();
}
} catch(e) {}
} catch { /* volontaire */ }
},
_markTree(nodes, depth) {
@@ -873,7 +872,7 @@ window._wsInitData = (function() {
if (node) { node.name = newName; }
this._reloadAfterAction();
}
} catch(e) {}
} catch { /* volontaire */ }
},
esc(s) {
@@ -1012,7 +1011,7 @@ window._wsInitData = (function() {
_saveExpandedState() {
try { localStorage.setItem('fd_ws_expanded', JSON.stringify(this.expanded)); }
catch(e) {}
catch { /* volontaire */ }
},
_reloadAfterAction() {
this._saveExpandedState();
@@ -1051,7 +1050,6 @@ window._wsInitData = (function() {
this._saveExpandedState();
if (window.appState && window.appState.refreshSidebarTree) window.appState.refreshSidebarTree();
if (window.FlowDeck && window.FlowDeck.syncPageTitle) window.FlowDeck.syncPageTitle(node.id, n);
var self = this;
if (this.folderStack && this.folderStack.length) {
this.folderStack.forEach(function(f) { if (String(f.id) === String(node.id)) f.name = n; });
}
@@ -1155,7 +1153,6 @@ window._wsInitData = (function() {
if (!ids.length || !ids[0]) return;
// Restore via API (soft-delete undo) — single or bulk
var self = this;
var restored = 0;
var total = ids.length;
function restoreOne(i) {
if (i >= total) {
@@ -1163,7 +1160,6 @@ window._wsInitData = (function() {
return;
}
fetch('/api/local-workspace/items/' + ids[i] + '/restore', {headers: {'X-CSRF-Token': (document.cookie.match(/csrf_token=([^;]+)/)||[])[1]||''}, method: 'POST' })
.then(function(r) { if (r.ok) restored++; })
.finally(function() { restoreOne(i + 1); });
}
restoreOne(0);
@@ -1274,7 +1270,6 @@ window._wsInitData = (function() {
_fetchRetry(url, json) {
var maxRetries = 2;
var delay = 300;
var self = this;
return new Promise(function(resolve, reject) {
function attempt(n) {
fetch(url).then(function(r) {
@@ -1432,7 +1427,7 @@ window._wsInitData = (function() {
}
return lines.join('\n').substring(0, 500) || '(empty)';
}
} catch(e) {}
} catch { /* volontaire */ }
}
// Fallback: raw text
return String(content).substring(0, 500);
@@ -1575,7 +1570,6 @@ window._wsInitData = (function() {
// Find parent node id from the onclick attribute or data
var li = parentFolder.closest('.ws-tree-item');
if (li) {
var clickEl = li.querySelector('.name.folder');
// Try to extract ID from onclick or the onclick handler
// Use data attributes if available, otherwise fall back
}
@@ -1646,7 +1640,6 @@ window._wsInitData = (function() {
var items = ev.dataTransfer.items;
if (!items) return;
var self = this;
var dtFiles = ev.dataTransfer.files;
// Check if any item is a directory (WebKit only)
@@ -1700,7 +1693,6 @@ window._wsInitData = (function() {
function doUpload() {
// Build structure
var structure = [];
var files = [];
for (var i = 0; i < allItems.length; i++) {
structure.push({path: allItems[i].path, type: allItems[i].type});
}
@@ -1711,7 +1703,6 @@ window._wsInitData = (function() {
if (allItems[i].type === 'file') fileEntries.push(allItems[i]);
}
var resolved = 0;
var formData = new FormData();
formData.append('structure', JSON.stringify(structure));
if (parentId) formData.append('parent_id', parentId);
@@ -1725,10 +1716,8 @@ window._wsInitData = (function() {
var fe = fileEntries[idx];
fe.entry.file(function(file) {
formData.append('files', file, fe.path);
resolved++;
addFile(idx + 1);
}, function() {
resolved++;
addFile(idx + 1);
});
}
@@ -1779,7 +1768,6 @@ window._wsInitData = (function() {
if (r.ok) {
this.uploadStatus = '✓ ' + d.items.length + ' item(s) uploaded';
this.uploadProgress = 100;
var items = d.items || [];
setTimeout(function() {
self.uploading = false;
self._reloadAfterAction();
@@ -1789,7 +1777,7 @@ window._wsInitData = (function() {
this.uploadProgress = 0;
setTimeout(function() { self.uploading = false; }, 2000);
}
} catch(e) {
} catch {
this.uploadStatus = '✗ Network error';
this.uploadProgress = 0;
setTimeout(function() { self.uploading = false; }, 2000);
@@ -1802,7 +1790,7 @@ window._wsInitData = (function() {
var r = await fetch('/api/local-workspace/tags', { cache: 'no-store' });
var d = await r.json();
this.workspaceTags = d.tags || [];
} catch(e) { this.workspaceTags = []; }
} catch { this.workspaceTags = []; }
},
// Mise à jour OPTIMISTE du compteur d'un tag dans la barre de tags :
@@ -1859,7 +1847,7 @@ window._wsInitData = (function() {
await this.loadWorkspaceTags();
this._computeFilteredTableItems();
}
} catch(e) {}
} catch { /* volontaire */ }
this.tagInputId = null;
},
@@ -1876,7 +1864,7 @@ window._wsInitData = (function() {
await this.loadWorkspaceTags();
this._computeFilteredTableItems();
}
} catch(e) {}
} catch { /* volontaire */ }
},
_updateNodeTags(nodes, itemId, tag, action, removeTagId) {
@@ -1983,7 +1971,7 @@ window._wsInitData = (function() {
this._collectFolders(d.tree || [], folders, 0);
this._moveAllCandidates = folders;
this.moveCandidates = folders.slice(0, 50);
} catch(e) {
} catch {
this._moveAllCandidates = [];
this.moveCandidates = [];
}
@@ -2014,7 +2002,7 @@ window._wsInitData = (function() {
headers: {'X-CSRF-Token': (document.cookie.match(/csrf_token=([^;]+)/)||[])[1]||'', 'Content-Type':'application/json'},
body: JSON.stringify({ parent_id: parentId || null })
});
} catch(e) {}
} catch { /* volontaire */ }
}
this.clearSelection();
this._reloadAfterAction();
@@ -2026,7 +2014,6 @@ window._wsInitData = (function() {
// Injecter toutes les props comme globales pour Alpine (résout les 36 erreurs de scope)
var _wsKeys = Object.keys(window._wsInitData);
for (var _i = 0; _i < _wsKeys.length; _i++) {
try { window[_wsKeys[_i]] = window._wsInitData[_wsKeys[_i]]; } catch(e) {}
try { window[_wsKeys[_i]] = window._wsInitData[_wsKeys[_i]]; } catch { /* volontaire */ }
}
_wsInitData = window._wsInitData;
console.log('FLOWDECK v2.4.6 — IIFE done, _wsInitData keys:', Object.keys(window._wsInitData).length);
+1 -1
View File
@@ -1,4 +1,4 @@
const RT=(()=>{try{const el=document.getElementById('rt-config');return el?JSON.parse(el.textContent):{}}catch(e){return {}}})();
const RT=(()=>{try{const el=document.getElementById('rt-config');return el?JSON.parse(el.textContent):{}}catch{return {}}})();
/* eslint-disable */
/* ═══════════ v5.13.0 Realtime — WS gateway, présence, curseurs, merge LWW ═══════════ */
+58 -58
View File
@@ -1,4 +1,5 @@
const ST=(()=>{try{const el=document.getElementById('st-config');return el?JSON.parse(el.textContent):{}}catch(e){return {}}})();
/* exported settingsInit -- appeles depuis les attributs HTML des templates */
const ST=(()=>{try{const el=document.getElementById('st-config');return el?JSON.parse(el.textContent):{}}catch{return {}}})();
function settingsInit() {
return {
@@ -107,13 +108,13 @@ function settingsInit() {
var r = await fetch('/api/notifications/prefs', {credentials:'same-origin'});
var d = await r.json();
this.notifPrefs = Object.assign({comments:true, mentions:true, reminders:true, assignments:true}, d.prefs || {});
} catch(e) {}
} catch { /* volontaire */ }
try {
var tz = await fetch('/api/notifications/timezone', {credentials:'same-origin'});
var td = await tz.json();
this.userTimezone = td.timezone || '';
this.userZones = td.zones || [];
} catch(e) {}
} catch { /* volontaire */ }
},
async saveNotifPrefs() {
try {
@@ -121,7 +122,7 @@ function settingsInit() {
method: 'POST', headers: {'Content-Type':'application/json','X-CSRF-Token': this.getCsrfToken()},
body: JSON.stringify(this.notifPrefs)
});
} catch(e) {}
} catch { /* volontaire */ }
},
async saveTimezone() {
try {
@@ -129,8 +130,8 @@ function settingsInit() {
method: 'POST', headers: {'Content-Type':'application/json','X-CSRF-Token': this.getCsrfToken()},
body: JSON.stringify({timezone: this.userTimezone})
});
if (r.ok && typeof toast === 'function') toast('Timezone saved');
} catch(e) {}
if (r.ok && typeof window.showToast === 'function') window.showToast('Timezone saved');
} catch { /* volontaire */ }
},
async loadTags() {
@@ -138,7 +139,7 @@ function settingsInit() {
var r = await fetch('/api/settings/tags/all');
var d = await r.json();
this.allTags = d.tags || [];
} catch(e) { this.allTags = []; }
} catch { this.allTags = []; }
},
async createTag() {
@@ -169,7 +170,6 @@ function settingsInit() {
this.renamingTag = tag;
this.renameValue = tag.name;
// Focus the input after Alpine renders the modal
var self = this;
this.$nextTick(function() {
var input = document.querySelector('.modal-box input[type=text]');
if (input) { input.focus(); input.select(); }
@@ -213,7 +213,7 @@ function settingsInit() {
var r = await this.adminFetch('/api/admin/users');
var d = await r.json();
this.adminUsers = d.users || [];
} catch(e) { this.adminUsers = []; }
} catch { this.adminUsers = []; }
await this.loadAdminStats();
},
@@ -221,7 +221,7 @@ function settingsInit() {
try {
var r = await this.adminFetch('/api/admin/stats');
this.adminStats = await r.json();
} catch(e) { this.adminStats = {}; }
} catch { this.adminStats = {}; }
},
async loadAdminAudit() {
@@ -249,7 +249,7 @@ function settingsInit() {
const logs = d.logs || [];
this.auditLogs = (reset !== false) ? logs : this.auditLogs.concat(logs);
this.auditHasMore = logs.length >= this.auditPageSize;
} catch(e) {
} catch {
if (reset !== false) this.auditLogs = [];
this.auditHasMore = false;
}
@@ -278,7 +278,7 @@ function settingsInit() {
var d = await r.json();
window.showToast(d.error || 'Failed to create user', 'error');
}
} catch(e) { window.showToast('Network error', 'error'); }
} catch { window.showToast('Network error', 'error'); }
},
async adminUpdateUser() {
@@ -295,7 +295,7 @@ function settingsInit() {
this.editingUser = null;
await this.loadAdminUsers();
}
} catch(e) {}
} catch { /* volontaire */ }
},
async adminDeleteUser(id) {
@@ -303,7 +303,7 @@ function settingsInit() {
try {
await this.adminFetch('/api/admin/users/' + id, { method: 'DELETE' });
await this.loadAdminUsers();
} catch(e) {}
} catch { /* volontaire */ }
},
// ── LLM / Agent ──
@@ -447,7 +447,7 @@ function settingsInit() {
}
if (this.selectedProviderId) this.keyForm(this.selectedProviderId);
this.syncLlmStatus();
} catch(e) {}
} catch { /* volontaire */ }
},
async loadProviderModels(id) {
var f = this.keyForm(id);
@@ -474,7 +474,7 @@ function settingsInit() {
} else {
f.msg = 'Erreur: ' + (d.error || 'échec de connexion');
}
} catch(e) { f.msg = 'Erreur réseau'; }
} catch { f.msg = 'Erreur réseau'; }
finally { f.modelLoading = false; }
},
async saveUserKey(id) {
@@ -505,7 +505,7 @@ function settingsInit() {
} else {
f.msg = d.detail || 'Erreur lors de l\'enregistrement';
}
} catch(e) { f.msg = 'Erreur réseau'; }
} catch { f.msg = 'Erreur réseau'; }
finally { f.saving = false; }
},
globalNeedsKeyFor(id) {
@@ -534,7 +534,7 @@ function settingsInit() {
this._setProviderState(id, false, d.error || 'échec de connexion');
f.msg = '✗ Test échoué : ' + (d.error || 'échec de connexion');
}
} catch(e) {
} catch {
this._setProviderState(id, false, 'Erreur réseau');
f.msg = 'Erreur réseau';
}
@@ -559,7 +559,7 @@ function settingsInit() {
} else {
f.msg = d.detail || 'Erreur lors de la suppression';
}
} catch(e) { f.msg = 'Erreur réseau'; }
} catch { f.msg = 'Erreur réseau'; }
finally { f.deleting = false; }
},
async loadLlmConfig() {
@@ -576,7 +576,7 @@ function settingsInit() {
api_base: d.api_base || (defp && defp.base_url) || ''};
this.applyLlmModels();
this.syncLlmStatus();
} catch(e) {}
} catch { /* volontaire */ }
},
applyLlmModels() {
var p = this.providerById(this.llmForm.provider);
@@ -619,7 +619,7 @@ function settingsInit() {
} else {
this.llmMsg = d.detail || 'Erreur lors de l\'enregistrement';
}
} catch(e) { this.llmMsg = 'Erreur réseau'; }
} catch { this.llmMsg = 'Erreur réseau'; }
finally { this.llmSaving = false; }
},
async resetGlobalLlm() {
@@ -644,7 +644,7 @@ function settingsInit() {
} else {
this.llmMsg = d.detail || 'Erreur lors de la réinitialisation';
}
} catch(e) { this.llmMsg = 'Erreur réseau'; }
} catch { this.llmMsg = 'Erreur réseau'; }
finally { this.llmSaving = false; }
},
async testLlm() {
@@ -669,7 +669,7 @@ function settingsInit() {
this._setProviderState(this.llmForm.provider, d.ok, d.error || '');
if (d.ok) cur.verified_model = d.model || '';
}
} catch(e) { this.llmTestOk = false; this.llmTestMsg = 'Erreur réseau'; }
} catch { this.llmTestOk = false; this.llmTestMsg = 'Erreur réseau'; }
finally { this.llmTesting = false; }
},
getCompletedLlmTest() { return this.llmTestMsg; },
@@ -698,7 +698,7 @@ function settingsInit() {
} else {
this.accountMsg = '✗ ' + (d.error || 'Error');
}
} catch(e) { this.accountMsg = '✗ Network error'; }
} catch { this.accountMsg = '✗ Network error'; }
this.accountSaving = false;
},
@@ -737,7 +737,7 @@ function settingsInit() {
var r = await fetch('/api/gitea/status');
var d = await r.json();
this.giteaLinked = d.linked || false;
} catch(e) { this.giteaLinked = false; }
} catch { this.giteaLinked = false; }
},
async disconnectGitea() {
@@ -745,41 +745,41 @@ function settingsInit() {
try {
var r = await fetch('/api/gitea/disconnect', { method: 'DELETE', headers: {'X-CSRF-Token': this.getCsrfToken()} });
if (r.ok) { this.giteaLinked = false; }
} catch(e) {}
} catch { /* volontaire */ }
},
async loadGithubStatus() {
try {
var r = await fetch('/api/github/status');
var d = await r.json();
this.githubLinked = d.linked || false;
} catch(e) { this.githubLinked = false; }
} catch { this.githubLinked = false; }
},
async disconnectGithub() {
if (!confirm('Disconnect GitHub? You can reconnect anytime.')) return;
try {
var r = await fetch('/api/github/disconnect', { method: 'DELETE', headers: {'X-CSRF-Token': this.getCsrfToken()} });
if (r.ok) { this.githubLinked = false; }
} catch(e) {}
} catch { /* volontaire */ }
},
async loadAutomations() {
try { await this.loadCollectionsForForm(); } catch(e) {}
try { await this.loadCollectionsForForm(); } catch { /* volontaire */ }
try {
var r = await fetch('/workspace/automations', {credentials:'same-origin'});
var d = await r.json();
this.automations = d.automations || [];
} catch(e) { this.automations = []; }
} catch { this.automations = []; }
},
async loadCollectionsForForm() {
try {
var r = await fetch('/db/api', {credentials:'same-origin'});
var d = await r.json();
this.globalCollections = d.collections || [];
} catch(e) { this.globalCollections = []; }
} catch { this.globalCollections = []; }
},
async saveAutomation() {
if (!this.af.name.trim()) { window.showToast && window.showToast('Nom requis', 'error'); return; }
try { JSON.parse(this.af.condition_json || '[]'); } catch(e) { window.showToast && window.showToast('Conditions JSON invalide', 'error'); return; }
try { JSON.parse(this.af.actions_json || '[]'); } catch(e) { window.showToast && window.showToast('Actions JSON invalide', 'error'); return; }
try { JSON.parse(this.af.condition_json || '[]'); } catch { window.showToast && window.showToast('Conditions JSON invalide', 'error'); return; }
try { JSON.parse(this.af.actions_json || '[]'); } catch { window.showToast && window.showToast('Actions JSON invalide', 'error'); return; }
var payload = {
name: this.af.name,
trigger_type: this.af.trigger_type,
@@ -801,7 +801,7 @@ function settingsInit() {
window.showToast && window.showToast(this.editAutomationId ? 'Automation mise à jour' : 'Automation créée');
this.cancelEditAutomation();
await this.loadAutomations();
} catch(e) { window.showToast && window.showToast('Erreur réseau', 'error'); }
} catch { window.showToast && window.showToast('Erreur réseau', 'error'); }
},
editAutomation(a) {
this.editAutomationId = a.id;
@@ -837,7 +837,7 @@ function settingsInit() {
headers: {'Content-Type':'application/json','X-CSRF-Token': this.getCsrfToken()},
body: JSON.stringify(payload) });
if (r.ok) await this.loadAutomations();
} catch(e) {}
} catch { /* volontaire */ }
},
async runAutomation(id) {
try {
@@ -850,7 +850,7 @@ function settingsInit() {
this.autoRuns.push({ created_at: new Date().toLocaleString(), trigger_source: 'manual', status: d.status || 'fired', detail: d.detail || '' });
window.showToast && window.showToast('Résultat : ' + (d.status || '') + ' — ' + (d.detail || ''));
await this.loadAutomations();
} catch(e) {}
} catch { /* volontaire */ }
},
async deleteAutomation(id) {
if (!confirm('Supprimer cette automation ?')) return;
@@ -858,7 +858,7 @@ function settingsInit() {
var r = await fetch('/workspace/automations/' + id, { method:'DELETE', credentials:'same-origin',
headers: {'X-CSRF-Token': this.getCsrfToken()} });
if (r.ok) await this.loadAutomations();
} catch(e) {}
} catch { /* volontaire */ }
},
// ── v5.2.0 API tokens ──
async loadApiTokens() {
@@ -866,7 +866,7 @@ function settingsInit() {
var r = await fetch('/api/settings/tokens', {headers: {'X-CSRF-Token': (document.cookie.match(/csrf_token=([^;]+)/)||[])[1]||''}, credentials:'same-origin'});
var d = await r.json();
this.apiTokens = d.tokens || [];
} catch(e) { this.apiTokens = []; }
} catch { this.apiTokens = []; }
},
async createApiToken() {
var name = this.tokenName.trim();
@@ -879,12 +879,12 @@ function settingsInit() {
this.newToken = d;
this.tokenName = '';
await this.loadApiTokens();
} catch(e) { window.showToast && window.showToast('Erreur réseau', 'error'); }
} catch { window.showToast && window.showToast('Erreur réseau', 'error'); }
},
async copyNewToken() {
if (!this.newToken) return;
try { await navigator.clipboard.writeText(this.newToken.token); window.showToast && window.showToast('Token copié'); }
catch(e) { window.showToast && window.showToast(this.newToken.token, 'error'); }
catch { window.showToast && window.showToast(this.newToken.token, 'error'); }
},
async revokeApiToken(t) {
if (!confirm('Révoquer le token « ' + t.name + ' » ? Il ne fonctionnera plus immédiatement.')) return;
@@ -892,7 +892,7 @@ function settingsInit() {
var r = await fetch('/api/settings/tokens/' + t.id, {method:'DELETE', credentials:'same-origin',
headers: {'X-CSRF-Token': this.getCsrfToken()} });
if (r.ok) await this.loadApiTokens();
} catch(e) {}
} catch { /* volontaire */ }
},
// ── v5.2.0 Sessions ──
async loadSessions() {
@@ -900,7 +900,7 @@ function settingsInit() {
var r = await fetch('/api/settings/sessions', {credentials:'same-origin'});
var d = await r.json();
this.sessions = d.sessions || [];
} catch(e) { this.sessions = []; }
} catch { this.sessions = []; }
},
async revokeSession(s) {
var msg = s.is_current ? 'Déconnecter cet appareil ?' : 'Révoquer cette session ?';
@@ -912,7 +912,7 @@ function settingsInit() {
if (s.is_current) window.location = '/auth/login?provider=local';
await this.loadSessions();
}
} catch(e) {}
} catch { /* volontaire */ }
},
// ── v6.2.0 Web Clipper ──
async loadClipperDevices() {
@@ -920,14 +920,14 @@ function settingsInit() {
var r = await fetch('/api/v2/web-clipper/devices', {credentials:'same-origin'});
var d = await r.json();
this.clipperDevices = d.devices || [];
} catch(e) { this.clipperDevices = []; }
} catch { this.clipperDevices = []; }
},
async revokeClipperDevice(d) {
if (!confirm('Révoquer l\'extension « ' + (d.device_name || d.device_id) + ' » ?')) return;
try {
var r = await fetch('/api/v2/web-clipper/devices/' + d.id, {method:'DELETE', credentials:'same-origin', headers: {'X-CSRF-Token': this.getCsrfToken()}});
if (r.ok) await this.loadClipperDevices();
} catch(e) {}
} catch { /* volontaire */ }
},
async testClip() {
this.clipTesting = true; this.clipTestMsg = ''; this.clipTestOk = false;
@@ -940,7 +940,7 @@ function settingsInit() {
var d = await r.json();
if (r.ok) { this.clipTestOk = true; this.clipTestMsg = '✓ Page créée : #' + d.page_id + ' — ' + d.title; await this.loadClipperDevices(); }
else this.clipTestMsg = d.detail || 'Erreur';
} catch(e) { this.clipTestMsg = 'Erreur réseau'; }
} catch { this.clipTestMsg = 'Erreur réseau'; }
finally { this.clipTesting = false; }
},
// ── v6.7.0 SSO / Enterprise (admin) ──
@@ -957,8 +957,8 @@ function settingsInit() {
async copySsoMetadata() {
try {
await navigator.clipboard.writeText(this.ssoMetadataUrl());
if (typeof toast === 'function') toast('SP metadata URL copiée');
} catch(e) {}
if (typeof window.showToast === 'function') window.showToast('SP metadata URL copiée');
} catch { /* volontaire */ }
},
async loadSsoConfig() {
this.ssoMsg = '';
@@ -994,7 +994,7 @@ function settingsInit() {
this.ssoGroups = (d.groups_mapping || []).map(function(g){ return {sso_group: g.sso_group || '', workspace_role: g.workspace_role || 'editor', workspace_id: g.workspace_id || ''}; });
}
}
} catch(e) {}
} catch { /* volontaire */ }
try {
var w = await fetch('/api/v2/sso/workspaces', {credentials:'same-origin'});
if (w.ok) {
@@ -1002,13 +1002,13 @@ function settingsInit() {
this.ssoWorkspaces = wd.workspaces || [];
this.ssoProvisioned = wd.provisioned_users || this.ssoProvisioned;
}
} catch(e) {}
} catch { /* volontaire */ }
},
async saveSsoConfig() {
this.ssoMsg = '';
var amap = {};
try { amap = JSON.parse(this.ssoAttrJson || '{}'); }
catch(e) { this.ssoMsg = 'Attribute mapping : JSON invalide'; this.ssoOk = false; return; }
catch { this.ssoMsg = 'Attribute mapping : JSON invalide'; this.ssoOk = false; return; }
if (amap === null || typeof amap !== 'object' || Array.isArray(amap)) {
this.ssoMsg = 'Attribute mapping : doit être un objet JSON'; this.ssoOk = false; return;
}
@@ -1024,10 +1024,10 @@ function settingsInit() {
delete payload.id;
try {
var r = await this.adminFetch('/api/v2/sso/config', {method:'POST', headers:{'Content-Type':'application/json'}, body: JSON.stringify(payload)});
var d = null; try { d = await r.json(); } catch(e) {}
var d = null; try { d = await r.json(); } catch { /* volontaire */ }
if (!r.ok) { this.ssoMsg = (d && (d.detail || d.error)) || ('Erreur ' + r.status); this.ssoOk = false; }
else { this.ssoMsg = 'Configuration enregistrée'; this.ssoOk = true; await this.loadSsoConfig(); }
} catch(e) { this.ssoMsg = 'Erreur réseau'; this.ssoOk = false; }
} catch { this.ssoMsg = 'Erreur réseau'; this.ssoOk = false; }
finally { this.ssoSaving = false; }
},
async disableSso() {
@@ -1037,16 +1037,16 @@ function settingsInit() {
var r = await this.adminFetch('/api/v2/sso/config', {method:'DELETE'});
if (r.ok) { this.ssoMsg = 'SSO désactivé'; this.ssoOk = true; await this.loadSsoConfig(); }
else { this.ssoMsg = 'Erreur ' + r.status; this.ssoOk = false; }
} catch(e) { this.ssoMsg = 'Erreur réseau'; this.ssoOk = false; }
} catch { this.ssoMsg = 'Erreur réseau'; this.ssoOk = false; }
},
async syncSsoGroups() {
this.ssoMsg = '';
try {
var r = await this.adminFetch('/api/v2/sso/sync', {method:'POST', headers:{'Content-Type':'application/json'}, body:'{}'});
var d = null; try { d = await r.json(); } catch(e) {}
var d = null; try { d = await r.json(); } catch { /* volontaire */ }
if (r.ok) { this.ssoMsg = 'Groupes re-synchronisés — ' + (d && d.updated || 0) + '/' + (d && d.users || 0) + ' utilisateur(s)'; this.ssoOk = true; await this.loadSsoConfig(); }
else { this.ssoMsg = (d && d.detail) || ('Erreur ' + r.status); this.ssoOk = false; }
} catch(e) { this.ssoMsg = 'Erreur réseau'; this.ssoOk = false; }
} catch { this.ssoMsg = 'Erreur réseau'; this.ssoOk = false; }
},
addSsoGroup() { this.ssoGroups.push({sso_group:'', workspace_role:'editor', workspace_id: this.ssoCfg.default_workspace_id || ''}); },
removeSsoGroup(i) { this.ssoGroups.splice(i, 1); },
@@ -1056,7 +1056,7 @@ function settingsInit() {
var r = await this.adminFetch('/api/settings/backups');
var d = await r.json();
this.backups = d.backups || [];
} catch(e) { this.backups = []; }
} catch { this.backups = []; }
},
async runBackup() {
this.backupRunning = true; this.backupMsg = ''; this.backupOk = false;
@@ -1065,7 +1065,7 @@ function settingsInit() {
var d = await r.json();
if (r.ok) { this.backupOk = true; this.backupMsg = '✓ Sauvegarde créée : ' + d.filename; await this.loadBackups(); }
else { this.backupMsg = d.detail || 'Erreur'; }
} catch(e) { this.backupMsg = 'Erreur réseau'; }
} catch { this.backupMsg = 'Erreur réseau'; }
finally { this.backupRunning = false; }
},
closeSettings() {
+5 -4
View File
@@ -1,3 +1,4 @@
/* exported workspacesPage -- appeles depuis les attributs HTML des templates */
function workspacesPage() {
return {
@@ -105,7 +106,7 @@ function workspacesPage() {
myLogin = meData.user?.login || 'Me';
if (myLogin.includes('_')) myLogin = myLogin.split('_').pop(); // strip gitea_ prefix if present
}
} catch(e) {}
} catch { /* volontaire */ }
// User repos (no org filter)
try {
@@ -117,7 +118,7 @@ function workspacesPage() {
groups.push({org: myLogin, avatar: '', projects: repos.map(r => ({...r, owner: r.owner || {login: myLogin}}))});
}
}
} catch(e) {}
} catch { /* volontaire */ }
// Org repos
for (const org of orgs) {
@@ -129,13 +130,13 @@ function workspacesPage() {
groups.push({org: org.username || org.login || org.name, avatar: org.avatar_url || '', projects: d.projects});
}
}
} catch(e) {}
} catch { /* volontaire */ }
}
this.giteaGroups = groups;
this.giteaTotal = groups.reduce((sum, g) => sum + g.projects.length, 0);
this.giteaStatus = 'ok';
} catch(e) {
} catch {
this.giteaStatus = 'error';
}
},