import React, { useState, useEffect, useCallback } from 'react';
import { useSettings } from '../hooks/useSettings';
import { getServiceHealth } from '../api/orchestration';
export default function SettingsView({ onNavigate }) {
const { settings, saveSetting, saving } = useSettings();
return (
Settings
onNavigate('memory')}>Open →}
/>
saveSetting('recentEpisodeLimit', val)}
saving={saving}
/>
saveSetting('semanticLimit', val)}
saving={saving}
/>
saveSetting('scoreThreshold', val)}
saving={saving}
/>
} />
} />
} />
}
/>
v0.1.0}
/>
} />
);
}
function SettingsSection({ title, children }) {
return (
);
}
function NumberSetting({ label, description, value, min, max, step = 1, onSave, saving }) {
const [local, setLocal] = useState(value ?? '');
const isDirty = local !== '' && Number(local) !== value;
// Sync when settings load from API
useEffect(() => {
if (value !== undefined) setLocal(value);
}, [value]);
return (
setLocal(e.target.value)}
style={{
width: '64px', padding: '5px 8px', textAlign: 'center',
background: 'var(--bg-elevated)', border: '1px solid var(--border)',
borderRadius: 'var(--radius-md)', color: 'var(--text-primary)',
fontSize: '13px', outline: 'none',
}}
/>
{isDirty && (
)}
}
/>
);
}
function SettingsRow({ label, description, action }) {
return (
{label}
{description && {description}}
{action}
);
}
function ComingSoon() {
return Coming soon;
}
function ServiceHealth() {
const [services, setServices] = useState(null);
const [loading, setLoading] = useState(false);
const [lastChecked, setLastChecked] = useState(null);
const check = useCallback(async () => {
setLoading(true);
try {
setServices(await getServiceHealth());
setLastChecked(new Date());
} catch (err) {
console.error('[ServiceHealth]', err.message);
} finally {
setLoading(false);
}
}, []);
return (
{lastChecked && (
{lastChecked.toLocaleTimeString()}
)}
{services && (
{services.map((svc, i) => (
{/* Status dot */}
{/* Label */}
{svc.label}
{/* Detail — show model for inference, nothing extra for others */}
{svc.key === 'inference' && svc.detail?.model
? svc.detail.model
: svc.status === 'unreachable' ? 'Unreachable' : ''}
{/* Latency */}
{svc.latency}ms
))}
)}
);
}