Add active user session tracking from agent user :0 2026-07-16 15:46
user pts/0 2026-07-16 15:50 (:0) user pts/1 2026-07-16 16:46 (:0) user pts/2 2026-07-17 09:05 (:0) to server UI
This commit is contained in:
+60
-1
@@ -7,6 +7,7 @@ import getpass
|
||||
import json
|
||||
import requests
|
||||
import logging
|
||||
import subprocess
|
||||
from pathlib import Path
|
||||
|
||||
logging.basicConfig(
|
||||
@@ -70,6 +71,62 @@ def get_disk_info():
|
||||
return disks
|
||||
|
||||
|
||||
def get_active_sessions():
|
||||
"""Return active user sessions similar to the `who` command.
|
||||
|
||||
Each session is a dict with keys: username, tty, login_time, origin.
|
||||
Falls back to the current process user if `who` is unavailable.
|
||||
"""
|
||||
try:
|
||||
result = subprocess.run(
|
||||
["who", "-u"],
|
||||
capture_output=True,
|
||||
text=True,
|
||||
timeout=5,
|
||||
check=False,
|
||||
)
|
||||
if result.returncode != 0:
|
||||
return []
|
||||
sessions = []
|
||||
for line in result.stdout.strip().splitlines():
|
||||
line = line.strip()
|
||||
if not line:
|
||||
continue
|
||||
parts = line.split()
|
||||
if len(parts) < 5:
|
||||
continue
|
||||
username = parts[0]
|
||||
tty = parts[1]
|
||||
# login time is usually "YYYY-MM-DD HH:MM" (parts[2] and parts[3])
|
||||
login_time = " ".join(parts[2:4]) if len(parts) >= 4 else ""
|
||||
# The last field may be a comment in parentheses, e.g. (192.168.255.50)
|
||||
origin = ""
|
||||
if parts[-1].startswith("(") and parts[-1].endswith(")"):
|
||||
origin = parts[-1][1:-1]
|
||||
sessions.append({
|
||||
"username": username,
|
||||
"tty": tty,
|
||||
"login_time": login_time,
|
||||
"origin": origin,
|
||||
})
|
||||
return sessions
|
||||
except Exception:
|
||||
return []
|
||||
|
||||
|
||||
def get_display_username(sessions):
|
||||
"""Return a short username representation for the dashboard.
|
||||
|
||||
Single user -> username
|
||||
Multiple -> comma-separated usernames
|
||||
No sessions -> fallback to process user
|
||||
"""
|
||||
usernames = [s["username"] for s in sessions if s.get("username")]
|
||||
if not usernames:
|
||||
return getpass.getuser()
|
||||
return ", ".join(dict.fromkeys(usernames))
|
||||
|
||||
|
||||
def get_cpu_temp():
|
||||
try:
|
||||
temps = psutil.sensors_temperatures()
|
||||
@@ -108,9 +165,11 @@ def get_top_processes(limit=10):
|
||||
|
||||
def collect():
|
||||
cfg = load_config()
|
||||
sessions = get_active_sessions()
|
||||
payload = {
|
||||
"hostname": socket.gethostname(),
|
||||
"username": getpass.getuser(),
|
||||
"username": get_display_username(sessions),
|
||||
"sessions": sessions,
|
||||
"os_info": f"{platform.system()} {platform.release()}",
|
||||
"local_ip": get_local_ip(),
|
||||
"public_ip": get_public_ip() if cfg.get("send_public_ip") else None,
|
||||
|
||||
Reference in New Issue
Block a user