@@ -26,6 +26,7 @@ import {
2626 MessageSquare ,
2727 Volume2 ,
2828 Database ,
29+ MemoryStick ,
2930} from "lucide-react" ;
3031import { Button } from "@/components/ui/button" ;
3132import { Badge } from "@/components/ui/badge" ;
@@ -59,6 +60,7 @@ import type {
5960 HfModelSummary ,
6061 HfGgufFile ,
6162 ScheduledTask ,
63+ AppActivity ,
6264} from "@/types/electron" ;
6365import { EXTRA_MODELS } from "@/lib/model-catalog" ;
6466import { OPENAI_MODELS , ANTHROPIC_MODELS , GEMINI_MODELS , formatModelRef , CUSTOM_PROVIDER_PRESETS } from "@/lib/providers" ;
@@ -136,6 +138,8 @@ export default function Settings() {
136138 const [ appVersion , setAppVersion ] = useState < string | null > ( null ) ;
137139 const [ diagnosticsCopied , setDiagnosticsCopied ] = useState ( false ) ;
138140 const [ userDataPath , setUserDataPath ] = useState < string | null > ( null ) ;
141+ const [ activity , setActivity ] = useState < AppActivity | null > ( null ) ;
142+ const [ activityLoading , setActivityLoading ] = useState ( false ) ;
139143 const [ importMessage , setImportMessage ] = useState < string | null > ( null ) ;
140144 const [ ollamaHostInput , setOllamaHostInput ] = useState ( "" ) ;
141145 const [ modelsDirStatus , setModelsDirStatus ] = useState < string | null > ( null ) ;
@@ -191,6 +195,7 @@ export default function Settings() {
191195 window . api . ollama . status ( ) . then ( setRunning ) ;
192196 window . api . system . getSpecs ( ) . then ( setSpecs ) ;
193197 window . api . system . getRecommendations ( ) . then ( setRecommendations ) ;
198+ window . api . system . getActivity ( ) . then ( setActivity ) ;
194199 window . api . settings . get ( ) . then ( ( s ) => {
195200 setSettings ( s ) ;
196201 setOllamaHostInput ( s . ollamaHost ) ;
@@ -338,6 +343,15 @@ export default function Settings() {
338343 await refreshSessions ( ) ;
339344 }
340345
346+ async function refreshActivity ( ) {
347+ setActivityLoading ( true ) ;
348+ try {
349+ setActivity ( await window . api . system . getActivity ( ) ) ;
350+ } finally {
351+ setActivityLoading ( false ) ;
352+ }
353+ }
354+
341355 async function handleCopyDiagnostics ( ) {
342356 const d = await window . api . app . getDiagnostics ( ) ;
343357 const text = [
@@ -2043,6 +2057,56 @@ export default function Settings() {
20432057 ) }
20442058 </ SettingsSection >
20452059
2060+ < SettingsSection
2061+ title = { t . appActivity }
2062+ description = { t . appActivityDescription }
2063+ action = {
2064+ < Button size = "sm" variant = "outline" onClick = { refreshActivity } className = "gap-1.5" disabled = { activityLoading } >
2065+ < RefreshCw className = { `size-3.5 ${ activityLoading ? "animate-spin" : "" } ` } /> { t . refresh }
2066+ </ Button >
2067+ }
2068+ >
2069+ { activity && (
2070+ < >
2071+ < SettingsRow label = "Ollama" >
2072+ < span className = "text-sm text-muted-foreground" >
2073+ { activity . ollamaRunning
2074+ ? activity . ollamaLoadedModels . length > 0
2075+ ? activity . ollamaLoadedModels . map ( ( m ) => m . name ) . join ( ", " )
2076+ : t . noModelsLoaded
2077+ : t . notRunning }
2078+ </ span >
2079+ </ SettingsRow >
2080+ < SettingsRow label = "llama.cpp" >
2081+ < span className = "text-sm text-muted-foreground" >
2082+ { activity . llamacppLoadedModels . length > 0
2083+ ? activity . llamacppLoadedModels . map ( ( p ) => p . split ( / [ / \\ ] / ) . pop ( ) ) . join ( ", " )
2084+ : t . noModelsLoaded }
2085+ </ span >
2086+ </ SettingsRow >
2087+ < SettingsRow label = { t . mcpServersLabel } >
2088+ { Object . keys ( activity . mcpServers ) . length > 0 ? (
2089+ < div className = "flex flex-wrap justify-end gap-1.5" >
2090+ { Object . entries ( activity . mcpServers ) . map ( ( [ id , status ] ) => (
2091+ < Badge key = { id } variant = { status . connected ? "secondary" : "outline" } >
2092+ { id } · { status . toolCount } { t . tools }
2093+ </ Badge >
2094+ ) ) }
2095+ </ div >
2096+ ) : (
2097+ < span className = "text-sm text-muted-foreground" > { t . noneConnected } </ span >
2098+ ) }
2099+ </ SettingsRow >
2100+ < SettingsRow label = { t . appMemoryUsage } >
2101+ < span className = "flex items-center gap-1.5 text-sm text-muted-foreground" >
2102+ < MemoryStick className = "size-3.5" />
2103+ { activity . memory . rssMB . toLocaleString ( ) } MB
2104+ </ span >
2105+ </ SettingsRow >
2106+ </ >
2107+ ) }
2108+ </ SettingsSection >
2109+
20462110 < SettingsSection title = { t . diagnostics } description = { t . diagnosticsDescription } >
20472111 < SettingsRow label = { t . copyDiagnosticInfo } >
20482112 < Button size = "sm" variant = "outline" onClick = { handleCopyDiagnostics } className = "gap-1.5" >
0 commit comments