import React, { useEffect, useState } from 'react'; import { useTranslation } from 'react-i18next'; import { useAppContext } from '../context/AppContext'; import { useUI } from '../context/UIContext'; const Memory: React.FC = () => { const { t } = useTranslation(); const ui = useUI(); const { q } = useAppContext(); const [files, setFiles] = useState([]); const [active, setActive] = useState(''); const [content, setContent] = useState(''); async function loadFiles() { const r = await fetch(`/webui/api/memory${q}`); if (!r.ok) { await ui.notify({ title: t('requestFailed'), message: await r.text() }); return; } const j = await r.json(); setFiles(Array.isArray(j.files) ? j.files : []); } const qp = (k: string, v: string) => `${q}${q ? '&' : '?'}${k}=${encodeURIComponent(v)}`; async function openFile(path: string) { const r = await fetch(`/webui/api/memory${qp('path', path)}`); if (!r.ok) { await ui.notify({ title: t('requestFailed'), message: await r.text() }); return; } const j = await r.json(); setActive(path); setContent(j.content || ''); } async function saveFile() { if (!active) return; try { await ui.withLoading(async () => { const r = await fetch(`/webui/api/memory${q}`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ path: active, content }), }); if (!r.ok) { throw new Error(await r.text()); } await loadFiles(); }, t('saving')); await ui.notify({ title: t('saved'), message: t('memoryFileSaved') }); } catch (e) { await ui.notify({ title: t('requestFailed'), message: String(e) }); } } async function removeFile(path: string) { const ok = await ui.confirmDialog({ title: t('memoryDeleteConfirmTitle'), message: t('memoryDeleteConfirmMessage', { path }), danger: true, confirmText: t('delete'), }); if (!ok) return; try { await ui.withLoading(async () => { const r = await fetch(`/webui/api/memory${qp('path', path)}`, { method: 'DELETE' }); if (!r.ok) { throw new Error(await r.text()); } if (active === path) { setActive(''); setContent(''); } await loadFiles(); }, t('deleting')); } catch (e) { await ui.notify({ title: t('requestFailed'), message: String(e) }); } } async function createFile() { const name = await ui.promptDialog({ title: t('memoryCreateTitle'), message: t('memoryFileNamePrompt'), confirmText: t('create'), initialValue: `note-${Date.now()}.md`, inputPlaceholder: 'note.md', }); if (!name) return; try { await ui.withLoading(async () => { const r = await fetch(`/webui/api/memory${q}`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ path: name, content: '' }), }); if (!r.ok) { throw new Error(await r.text()); } await loadFiles(); await openFile(name); }, t('creating')); } catch (e) { await ui.notify({ title: t('requestFailed'), message: String(e) }); } } useEffect(() => { loadFiles().catch(() => {}); }, [q]); return (

{active || t('noFileSelected')}