8
8
9
9
"""CPU percent stats shared between CPU and Quicklook plugins."""
10
10
11
+ from typing import List , Optional , TypedDict
12
+
11
13
import psutil
12
14
13
15
from glances .logger import logger
14
16
from glances .timer import Timer
15
17
18
+ __all__ = ["cpu_percent" ]
19
+
20
+
21
+ class CpuInfo (TypedDict ):
22
+ cpu_name : str
23
+ cpu_hz : Optional [float ]
24
+ cpu_hz_current : Optional [float ]
25
+
26
+
27
+ class PerCpuPercentInfo (TypedDict ):
28
+ key : str
29
+ cpu_number : int
30
+ total : float
31
+ user : float
32
+ system : float
33
+ idle : float
34
+ nice : Optional [float ]
35
+ iowait : Optional [float ]
36
+ irq : Optional [float ]
37
+ softirq : Optional [float ]
38
+ steal : Optional [float ]
39
+ guest : Optional [float ]
40
+ guest_nice : Optional [float ]
41
+
16
42
17
43
class CpuPercent :
18
44
"""Get and store the CPU percent."""
19
45
20
- def __init__ (self , cached_timer_cpu = 2 ):
46
+ def __init__ (self , cached_timer_cpu : int = 2 ):
21
47
# cached_timer_cpu is the minimum time interval between stats updates
22
48
# since last update is passed (will retrieve old cached info instead)
23
49
self .cached_timer_cpu = cached_timer_cpu
@@ -27,21 +53,21 @@ def __init__(self, cached_timer_cpu=2):
27
53
28
54
# Get CPU name
29
55
self .timer_cpu_info = Timer (0 )
30
- self .cpu_info = {'cpu_name' : self .__get_cpu_name (), 'cpu_hz_current' : None , 'cpu_hz' : None }
56
+ self .cpu_info : CpuInfo = {'cpu_name' : self .__get_cpu_name (), 'cpu_hz_current' : None , 'cpu_hz' : None }
31
57
32
58
# Warning from PsUtil documentation
33
59
# The first time this function is called with interval = 0.0 or None
34
60
# it will return a meaningless 0.0 value which you are supposed to ignore.
35
61
self .timer_cpu = Timer (0 )
36
- self .cpu_percent = self .get_cpu ()
62
+ self .cpu_percent = self ._compute_cpu ()
37
63
self .timer_percpu = Timer (0 )
38
- self .percpu_percent = self .get_percpu ()
64
+ self .percpu_percent = self ._compute_percpu ()
39
65
40
66
def get_key (self ):
41
67
"""Return the key of the per CPU list."""
42
68
return 'cpu_number'
43
69
44
- def get_info (self ):
70
+ def get_info (self ) -> CpuInfo :
45
71
"""Get additional information about the CPU"""
46
72
# Never update more than 1 time per cached_timer_cpu_info
47
73
if self .timer_cpu_info .finished () and hasattr (psutil , 'cpu_freq' ):
@@ -63,70 +89,67 @@ def get_info(self):
63
89
self .timer_cpu_info .reset (duration = self .cached_timer_cpu_info )
64
90
return self .cpu_info
65
91
66
- def __get_cpu_name (self ):
92
+ @staticmethod
93
+ def __get_cpu_name () -> str :
67
94
# Get the CPU name once from the /proc/cpuinfo file
68
95
# Read the first line with the "model name" ("Model" for Raspberry Pi)
69
- ret = None
70
96
try :
71
- cpuinfo_file = open ('/proc/cpuinfo' ).readlines ()
97
+ cpuinfo_lines = open ('/proc/cpuinfo' ).readlines ()
72
98
except (FileNotFoundError , PermissionError ):
73
- pass
74
- else :
75
- for line in cpuinfo_file :
76
- if line .startswith ('model name' ) or line .startswith ('Model' ) or line .startswith ('cpu model' ):
77
- ret = line .split (':' )[1 ].strip ()
78
- break
79
- return ret if ret else 'CPU'
80
-
81
- def get_cpu (self ):
99
+ logger .debug ("No permission to read '/proc/cpuinfo'" )
100
+ return 'CPU'
101
+
102
+ for line in cpuinfo_lines :
103
+ if line .startswith ('model name' ) or line .startswith ('Model' ) or line .startswith ('cpu model' ):
104
+ return line .split (':' )[1 ].strip ()
105
+
106
+ return 'CPU'
107
+
108
+ def get_cpu (self ) -> float :
82
109
"""Update and/or return the CPU using the psutil library."""
83
110
# Never update more than 1 time per cached_timer_cpu
84
111
if self .timer_cpu .finished ():
85
112
# Reset timer for cache
86
113
self .timer_cpu .reset (duration = self .cached_timer_cpu )
87
114
# Update the stats
88
- self .cpu_percent = psutil . cpu_percent ( interval = 0.0 )
115
+ self .cpu_percent = self . _compute_cpu ( )
89
116
return self .cpu_percent
90
117
91
- def get_percpu (self ):
118
+ @staticmethod
119
+ def _compute_cpu () -> float :
120
+ return psutil .cpu_percent (interval = 0.0 )
121
+
122
+ def get_percpu (self ) -> List [PerCpuPercentInfo ]:
92
123
"""Update and/or return the per CPU list using the psutil library."""
93
124
# Never update more than 1 time per cached_timer_cpu
94
125
if self .timer_percpu .finished ():
95
126
# Reset timer for cache
96
127
self .timer_percpu .reset (duration = self .cached_timer_cpu )
97
- # Get stats
98
- percpu_percent = []
99
- psutil_percpu = enumerate (psutil .cpu_times_percent (interval = 0.0 , percpu = True ))
100
- for cpu_number , cputimes in psutil_percpu :
101
- cpu = {
102
- 'key' : self .get_key (),
103
- 'cpu_number' : cpu_number ,
104
- 'total' : round (100 - cputimes .idle , 1 ),
105
- 'user' : cputimes .user ,
106
- 'system' : cputimes .system ,
107
- 'idle' : cputimes .idle ,
108
- }
109
- # The following stats are for API purposes only
110
- if hasattr (cputimes , 'nice' ):
111
- cpu ['nice' ] = cputimes .nice
112
- if hasattr (cputimes , 'iowait' ):
113
- cpu ['iowait' ] = cputimes .iowait
114
- if hasattr (cputimes , 'irq' ):
115
- cpu ['irq' ] = cputimes .irq
116
- if hasattr (cputimes , 'softirq' ):
117
- cpu ['softirq' ] = cputimes .softirq
118
- if hasattr (cputimes , 'steal' ):
119
- cpu ['steal' ] = cputimes .steal
120
- if hasattr (cputimes , 'guest' ):
121
- cpu ['guest' ] = cputimes .guest
122
- if hasattr (cputimes , 'guest_nice' ):
123
- cpu ['guest_nice' ] = cputimes .guest_nice
124
- # Append new CPU to the list
125
- percpu_percent .append (cpu )
126
128
# Update stats
127
- self .percpu_percent = percpu_percent
129
+ self .percpu_percent = self . _compute_percpu ()
128
130
return self .percpu_percent
129
131
132
+ def _compute_percpu (self ) -> List [PerCpuPercentInfo ]:
133
+ psutil_percpu = enumerate (psutil .cpu_times_percent (interval = 0.0 , percpu = True ))
134
+ return [
135
+ {
136
+ 'key' : self .get_key (),
137
+ 'cpu_number' : cpu_number ,
138
+ 'total' : round (100 - cpu_times .idle , 1 ),
139
+ 'user' : cpu_times .user ,
140
+ 'system' : cpu_times .system ,
141
+ 'idle' : cpu_times .idle ,
142
+ 'nice' : cpu_times .nice if hasattr (cpu_times , 'nice' ) else None ,
143
+ 'iowait' : cpu_times .iowait if hasattr (cpu_times , 'iowait' ) else None ,
144
+ 'irq' : cpu_times .irq if hasattr (cpu_times , 'irq' ) else None ,
145
+ 'softirq' : cpu_times .softirq if hasattr (cpu_times , 'softirq' ) else None ,
146
+ 'steal' : cpu_times .steal if hasattr (cpu_times , 'steal' ) else None ,
147
+ 'guest' : cpu_times .guest if hasattr (cpu_times , 'guest' ) else None ,
148
+ 'guest_nice' : cpu_times .steal if hasattr (cpu_times , 'guest_nice' ) else None ,
149
+ }
150
+ for cpu_number , cpu_times in psutil_percpu
151
+ ]
152
+
130
153
131
154
# CpuPercent instance shared between plugins
132
155
cpu_percent = CpuPercent ()
0 commit comments