1
1
import React , { useState , useCallback , useEffect , useRef } from 'react' ;
2
2
import { useTheme } from '../contexts/ThemeContext' ;
3
3
import ChainSettingsModal from './ChainSettingsModal' ;
4
- import './StatusLight.css' ; // Will create this next
4
+ import './StatusLight.css' ;
5
5
import ForceStopModal from './ForceStopModal' ;
6
6
import SettingsIcon from './SettingsIcon' ;
7
7
import Tooltip from './Tooltip' ;
@@ -24,50 +24,48 @@ const Card = ({
24
24
const [ lastActionTime , setLastActionTime ] = useState ( 0 ) ;
25
25
const [ tooltipVisible , setTooltipVisible ] = useState ( false ) ;
26
26
const [ tooltipPosition , setTooltipPosition ] = useState ( { x : 0 , y : 0 } ) ;
27
- const [ processHealth , setProcessHealth ] = useState ( 'healthy' ) ; // 'healthy', 'warning', 'error', 'offline'
27
+ const [ processHealth , setProcessHealth ] = useState ( 'offline' ) ; // 'healthy', 'warning', 'error', 'offline'
28
+ const [ blockCount , setBlockCount ] = useState ( - 1 ) ;
28
29
const buttonRef = useRef ( null ) ;
29
30
30
- // Demo effect to cycle through status colors
31
+ // Periodic chain status / health check
31
32
useEffect ( ( ) => {
32
- const statuses = [ 'healthy' , 'warning' , 'error' , 'offline' ] ;
33
- let currentIndex = 0 ;
34
-
35
- const interval = setInterval ( ( ) => {
36
- currentIndex = ( currentIndex + 1 ) % statuses . length ;
37
- setProcessHealth ( statuses [ currentIndex ] ) ;
38
- } , 2000 ) ;
33
+ const fetchBlockCount = async ( ) => {
34
+ try {
35
+ const count = await window . electronAPI . getChainBlockCount ( chain . id ) ;
36
+ console . log ( "new count: " , count )
37
+ setBlockCount ( count ) ;
38
+ } catch ( error ) {
39
+ setBlockCount ( - 1 )
40
+ console . error ( 'Failed to fetch block count:' , error ) ;
41
+ }
42
+ } ;
39
43
40
- return ( ) => clearInterval ( interval ) ;
41
- } , [ ] ) ;
44
+ // Initial fetch
45
+ fetchBlockCount ( ) ;
42
46
43
- // TODO: Set up IPC/RPC communication for real process health updates
44
- // Example implementation:
45
- /*
46
- useEffect(() => {
47
- // Subscribe to process health updates
48
- const unsubscribe = window.electronAPI.onProcessHealthUpdate(chain.id, (health) => {
49
- // health object might contain:
50
- // - memory usage
51
- // - CPU usage
52
- // - error counts
53
- // - response times
54
- // - connection status
55
-
56
- // Determine status based on health metrics
57
- if (health.error_count > threshold) {
58
- setProcessHealth('error');
59
- } else if (health.memory_usage > warningThreshold) {
60
- setProcessHealth('warning');
61
- } else if (!health.connected) {
47
+ const interval = setInterval ( ( ) => {
48
+ fetchBlockCount ( ) ;
49
+
50
+ if ( chain . status === 'stopping' || chain . status === 'stopped' ) {
62
51
setProcessHealth ( 'offline' ) ;
63
- } else {
64
- setProcessHealth('healthy');
52
+ }
53
+ else
54
+ if ( blockCount === - 1 ) {
55
+ setProcessHealth ( 'offline' ) ;
65
56
}
66
- });
57
+ else
58
+ if ( blockCount === 0 ) {
59
+ setProcessHealth ( 'warning' ) ;
60
+ }
61
+ else
62
+ if ( blockCount > 0 ) {
63
+ setProcessHealth ( 'healthy' ) ;
64
+ }
65
+ } , 1000 ) ;
67
66
68
- return () => unsubscribe();
69
- }, [chain.id]);
70
- */
67
+ return ( ) => clearInterval ( interval ) ;
68
+ } , [ chain . id , chain . status , blockCount ] ) ;
71
69
72
70
const checkDependencies = ( ) => {
73
71
if ( ! chain . dependencies || chain . dependencies . length === 0 ) return true ;
@@ -139,6 +137,7 @@ const Card = ({
139
137
console . log ( `Stopping chain ${ chain . id } ` ) ;
140
138
// Update UI immediately to show stopping state
141
139
onUpdateChain ( chain . id , { status : 'stopping' } ) ;
140
+ setProcessHealth ( 'offline' ) ;
142
141
await onStop ( chain . id ) ;
143
142
} catch ( error ) {
144
143
console . error ( 'Stop failed:' , error ) ;
@@ -240,9 +239,14 @@ const Card = ({
240
239
return (
241
240
< div style = { { display : 'flex' , flexDirection : 'column' , flex : 1 , minWidth : '300px' } } >
242
241
< div className = { `card ${ isDarkMode ? 'dark' : 'light' } ` } >
243
- < div className = "card-header" style = { { display : 'flex' , alignItems : 'center' , justifyContent : 'space-between' , position : 'relative' } } >
244
- < h2 style = { { margin : 0 , lineHeight : 1.2 } } > { chain . display_name } </ h2 >
245
- < div className = { `status-light ${ processHealth } ` } title = { `Process Status: ${ processHealth } ` } />
242
+ < div className = "card-header" style = { { position : 'relative' } } >
243
+ < div style = { { display : 'flex' , alignItems : 'center' } } >
244
+ < div className = { `status-light ${ processHealth } ` } title = { `Process Status: ${ processHealth } ` } style = { { marginRight : '10px' } } />
245
+ < h2 style = { { margin : 0 , lineHeight : 1.2 } } > { chain . display_name } </ h2 >
246
+ </ div >
247
+ < div style = { { fontSize : '1em' , color : isDarkMode ? '#fff' : '#333' , marginTop : '4px' , marginLeft : '24px' , fontWeight : 500 } } >
248
+ { processHealth === 'healthy' && blockCount >= 0 ? `#Blocks: ${ blockCount } ` : 'Chain not started' }
249
+ </ div >
246
250
</ div >
247
251
< div className = "card-content" >
248
252
< p > { chain . description } </ p >
0 commit comments