|
1
|
|
|
# |
|
2
|
|
|
# This file is part of Glances. |
|
3
|
|
|
# |
|
4
|
|
|
# SPDX-FileCopyrightText: 2025 Nicolas Hennion <[email protected]> |
|
5
|
|
|
# |
|
6
|
|
|
# SPDX-License-Identifier: LGPL-3.0-only |
|
7
|
|
|
# |
|
8
|
|
|
|
|
9
|
|
|
"""Fetch mode interface class.""" |
|
10
|
|
|
|
|
11
|
|
|
import jinja2 |
|
12
|
|
|
|
|
13
|
|
|
from glances import api |
|
14
|
|
|
from glances.logger import logger |
|
15
|
|
|
|
|
16
|
|
|
DEFAULT_FETCH_TEMPLATE = """ |
|
17
|
|
|
|
|
18
|
|
|
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ |
|
19
|
|
|
✨ {{ gl.system['hostname'] }}{{ ' | ' + gl.ip['address'] if gl.ip['address'] else '' }} | Uptime: {{ gl.uptime }} |
|
20
|
|
|
⚙️ {{ gl.system['hr_name'] }} |
|
21
|
|
|
|
|
22
|
|
|
💡 LOAD {{ '%0.2f'| format(gl.load['min1']) }}/min1 |\ |
|
23
|
|
|
{{ '%0.2f'| format(gl.load['min5']) }}/min5 |\ |
|
24
|
|
|
{{ '%0.2f'| format(gl.load['min15']) }}/min15 |
|
25
|
|
|
⚡ CPU {{ gl.bar(gl.cpu['total']) }} {{ gl.cpu['total'] }}% of {{ gl.core['log'] }} cores |
|
26
|
|
|
🧠 MEM {{ gl.bar(gl.mem['percent']) }} {{ gl.mem['percent'] }}% ({{ gl.auto_unit(gl.mem['used']) }} /\ |
|
27
|
|
|
{{ gl.auto_unit(gl.mem['total']) }}) |
|
28
|
|
|
{% for fs in gl.fs.keys() %}\ |
|
29
|
|
|
💾 {% if loop.index == 1 %}DISK{% else %} {% endif %}\ |
|
30
|
|
|
{{ gl.bar(gl.fs[fs]['percent']) }} {{ gl.fs[fs]['percent'] }}% ({{ gl.auto_unit(gl.fs[fs]['used']) }} /\ |
|
31
|
|
|
{{ gl.auto_unit(gl.fs[fs]['size']) }}) for {{ fs }} |
|
32
|
|
|
{% endfor %}\ |
|
33
|
|
|
{% for net in gl.network.keys() %}\ |
|
34
|
|
|
📡 {% if loop.index == 1 %}NET{% else %} {% endif %}\ |
|
35
|
|
|
↓ {{ gl.auto_unit(gl.network[net]['bytes_recv_rate_per_sec']) }}b/s\ |
|
36
|
|
|
↑ {{ gl.auto_unit(gl.network[net]['bytes_sent_rate_per_sec']) }}b/s for {{ net }} |
|
37
|
|
|
{% endfor %}\ |
|
38
|
|
|
|
|
39
|
|
|
🔥 TOP PROCESS by CPU |
|
40
|
|
|
{% for process in gl.top_process() %}\ |
|
41
|
|
|
{{ loop.index }}️⃣ {{ process['name'][:20] }}{{ ' ' * (20 - process['name'][:20] | length) }}\ |
|
42
|
|
|
⚡ {{ process['cpu_percent'] }}% CPU\ |
|
43
|
|
|
{{ ' ' * (8 - (gl.auto_unit(process['cpu_percent']) | length)) }}\ |
|
44
|
|
|
🧠 {{ gl.auto_unit(process['memory_info']['rss']) }}B MEM |
|
45
|
|
|
{% endfor %}\ |
|
46
|
|
|
🔥 TOP PROCESS by MEM |
|
47
|
|
|
{% for process in gl.top_process(sorted_by='memory_percent', sorted_by_secondary='cpu_percent') %}\ |
|
48
|
|
|
{{ loop.index }}️⃣ {{ process['name'][:20] }}{{ ' ' * (20 - process['name'][:20] | length) }}\ |
|
49
|
|
|
🧠 {{ gl.auto_unit(process['memory_info']['rss']) }}B MEM\ |
|
50
|
|
|
{{ ' ' * (7 - (gl.auto_unit(process['memory_info']['rss']) | length)) }}\ |
|
51
|
|
|
⚡ {{ process['cpu_percent'] }}% CPU |
|
52
|
|
|
{% endfor %}\ |
|
53
|
|
|
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ |
|
54
|
|
|
|
|
55
|
|
|
""" |
|
56
|
|
|
|
|
57
|
|
|
|
|
58
|
|
|
class GlancesStdoutFetch: |
|
59
|
|
|
"""This class manages the Stdout JSON display.""" |
|
60
|
|
|
|
|
61
|
|
|
def __init__(self, config=None, args=None): |
|
62
|
|
|
# Init |
|
63
|
|
|
self.config = config |
|
64
|
|
|
self.args = args |
|
65
|
|
|
self.gl = api.GlancesAPI(self.config, self.args) |
|
66
|
|
|
|
|
67
|
|
|
def end(self): |
|
68
|
|
|
pass |
|
69
|
|
|
|
|
70
|
|
|
def update(self, stats, duration=3, cs_status=None, return_to_browser=False): |
|
71
|
|
|
"""Display fetch from the template file to stdout.""" |
|
72
|
|
|
if self.args.fetch_template == "": |
|
73
|
|
|
fetch_template = DEFAULT_FETCH_TEMPLATE |
|
74
|
|
|
else: |
|
75
|
|
|
logger.info("Using fetch template file: " + self.args.fetch_template) |
|
76
|
|
|
# Load the template from the file given in the self.args.fetch_template argument |
|
77
|
|
|
with open(self.args.fetch_template) as f: |
|
78
|
|
|
fetch_template = f.read() |
|
79
|
|
|
|
|
80
|
|
|
# Create a Jinja2 environment |
|
81
|
|
|
jinja_env = jinja2.Environment(loader=jinja2.BaseLoader()) |
|
82
|
|
|
template = jinja_env.from_string(fetch_template) |
|
83
|
|
|
output = template.render(gl=self.gl) |
|
84
|
|
|
print(output) |
|
85
|
|
|
|
|
86
|
|
|
# Return True to exit directly (no refresh) |
|
87
|
|
|
return True |
|
88
|
|
|
|