Phase 4.5+4.6: Modul-Konfiguration pro Workspace + Sidebar useMemo Fix
4.5 Modul-Konfiguration pro Workspace: - WorkspaceManager: Config-Editor pro Modul (JSON textarea) - Pro Modul kann JSON config bearbeitet werden (z.B. sichtbare Ordner-IDs) - Generisch: jedes Modul definiert selbst was in seiner config steht 4.6 Bugfixes: - Sidebar useMemo: isModuleVisible zu Abhaengigkeiten hinzugefuegt - Bei Workspacewechsel wird Sidebar jetzt sofort neu berechnet Tests: 17 Backend + 13 Frontend = 30/30 bestanden
This commit is contained in:
@@ -133,7 +133,7 @@ export function Sidebar() {
|
|||||||
if (a.order !== b.order) return a.order - b.order;
|
if (a.order !== b.order) return a.order - b.order;
|
||||||
return a.label.localeCompare(b.label);
|
return a.label.localeCompare(b.label);
|
||||||
});
|
});
|
||||||
}, [manifests, menuOrderData, user]);
|
}, [manifests, menuOrderData, user, isModuleVisible]);
|
||||||
|
|
||||||
const [expandedItems, setExpandedItems] = useState<Set<string>>(new Set());
|
const [expandedItems, setExpandedItems] = useState<Set<string>>(new Set());
|
||||||
|
|
||||||
|
|||||||
@@ -45,6 +45,7 @@ export function WorkspaceManager() {
|
|||||||
|
|
||||||
const [moduleWsId, setModuleWsId] = useState<string | null>(null);
|
const [moduleWsId, setModuleWsId] = useState<string | null>(null);
|
||||||
const [moduleConfig, setModuleConfig] = useState<WorkspaceModule[]>([]);
|
const [moduleConfig, setModuleConfig] = useState<WorkspaceModule[]>([]);
|
||||||
|
const [configEditingKey, setConfigEditingKey] = useState<string | null>(null);
|
||||||
|
|
||||||
const workspaces = wsData?.items || [];
|
const workspaces = wsData?.items || [];
|
||||||
|
|
||||||
@@ -156,14 +157,43 @@ export function WorkspaceManager() {
|
|||||||
{moduleConfig.map(m => {
|
{moduleConfig.map(m => {
|
||||||
const mod = availableModules.find(a => a.key === m.module_key);
|
const mod = availableModules.find(a => a.key === m.module_key);
|
||||||
return (
|
return (
|
||||||
<label key={m.module_key} className="flex items-center gap-2 p-2 border border-gray-200 dark:border-gray-700 rounded-md cursor-pointer hover:bg-gray-50 dark:hover:bg-gray-800">
|
<div key={m.module_key} className={`p-2 border rounded-md ${m.is_visible ? 'border-blue-300 dark:border-blue-700 bg-blue-50 dark:bg-blue-900/10' : 'border-gray-200 dark:border-gray-700'}`}>
|
||||||
<input
|
<label className="flex items-center gap-2 cursor-pointer hover:bg-gray-50 dark:hover:bg-gray-800 rounded p-1">
|
||||||
type="checkbox"
|
<input
|
||||||
checked={m.is_visible}
|
type="checkbox"
|
||||||
onChange={() => toggleModule(m.module_key)}
|
checked={m.is_visible}
|
||||||
/>
|
onChange={() => toggleModule(m.module_key)}
|
||||||
<span className="text-sm">{mod?.label || m.module_key}</span>
|
/>
|
||||||
</label>
|
<span className="text-sm flex-1">{mod?.label || m.module_key}</span>
|
||||||
|
{m.is_visible && (
|
||||||
|
<button
|
||||||
|
onClick={(e) => { e.preventDefault(); setModuleConfig(prev => prev.map(x => x.module_key === m.module_key ? { ...x, config: x.config } : x)); setConfigEditingKey(configEditingKey === m.module_key ? null : m.module_key); }}
|
||||||
|
className="text-xs px-1.5 py-0.5 border rounded hover:bg-gray-100 dark:hover:bg-gray-700"
|
||||||
|
title="Konfiguration bearbeiten"
|
||||||
|
>
|
||||||
|
⚙
|
||||||
|
</button>
|
||||||
|
)}
|
||||||
|
</label>
|
||||||
|
{m.is_visible && configEditingKey === m.module_key && (
|
||||||
|
<div className="mt-2 space-y-1">
|
||||||
|
<textarea
|
||||||
|
className="w-full text-xs font-mono p-1.5 border border-gray-300 dark:border-gray-600 rounded bg-white dark:bg-gray-900 h-20"
|
||||||
|
placeholder='{"visible_folder_ids": []}'
|
||||||
|
value={JSON.stringify(m.config || {}, null, 2)}
|
||||||
|
onChange={(e) => {
|
||||||
|
try {
|
||||||
|
const parsed = JSON.parse(e.target.value);
|
||||||
|
setModuleConfig(prev => prev.map(x => x.module_key === m.module_key ? { ...x, config: parsed } : x));
|
||||||
|
} catch {
|
||||||
|
// Invalid JSON — keep raw text for editing
|
||||||
|
}
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
<p className="text-xs text-gray-400">JSON-Konfiguration für dieses Modul (z.B. sichtbare Ordner-IDs)</p>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
Reference in New Issue
Block a user