Linux Server

Who Logged In to My Server? Audit SSH and aaPanel Logins and Get a Telegram Alert for Every Login

6 steps 13 min read 14 views 0
On this page

Most break-ins are discovered late because nobody looks at who logs in. An attacker with a stolen password logs in exactly like you do, and the log line looks normal unless you know which IPs and keys are yours. This guide shows how to audit SSH logins on a Linux server, map each login to a key, check aaPanel (BaoTa) panel logins, and send a Telegram message every time someone logs in, so a stranger stands out within seconds.

Step 1: Who Is Logged In Right Now

who                 # interactive sessions
ss -tnp | grep sshd # every SSH connection, including tunnels without a terminal
An SSH session used only for port forwarding (ssh -N) does not open a terminal, so it does not appear in who or w. Always check ss -tnp or ps -ef | grep "sshd:" as well. A connection from an IP you do not recognise that has been open for days is a serious warning sign.

Step 2: Review Login History

last -a | head -30          # successful logins (from /var/log/wtmp)
lastb -a | head -30         # failed logins (from /var/log/btmp)

# Successful SSH logins with the method used (password or key)
grep "Accepted" /var/log/auth.log | tail -50        # Debian / Ubuntu
grep "Accepted" /var/log/secure | tail -50          # Rocky / AlmaLinux / CentOS
journalctl -u ssh -u sshd --since "7 days ago" | grep Accepted

Each line shows the method, user, source IP and, for keys, the key fingerprint:

Accepted password for root from 198.51.100.7 port 51234 ssh2
Accepted publickey for root from 203.0.113.20 port 60122 ssh2: ED25519 SHA256:Xq3vR8...

Summarise them to see every source IP and method at a glance:

grep -h "Accepted" /var/log/auth.log* 2>/dev/null | awk '{for(i=1;i<=NF;i++){if($i=="Accepted")m=$(i+1); if($i=="from")ip=$(i+1)}; print m, ip}' | sort | uniq -c | sort -rn

If you only log in with keys, any Accepted password line is suspicious.

Step 3: Match Key Fingerprints to Your Keys

List the fingerprints of every key that may log in, then compare them with the fingerprints in the log:

ssh-keygen -lf /root/.ssh/authorized_keys
for h in /home/*; do [ -f "$h/.ssh/authorized_keys" ] && ssh-keygen -lf "$h/.ssh/authorized_keys"; done

Every key should have a comment you recognise (such as alice@laptop). Remove keys you cannot explain, and check that nobody added extra key files through AuthorizedKeysFile in /etc/ssh/sshd_config.

Step 4: Check aaPanel (BaoTa) Logins

In aaPanel, the home page shows the latest panel logins, and Logs → Panel logs lists every login with its IP. You can also read them from the command line:

sqlite3 /www/server/panel/data/default.db \
  "select addtime, log from logs where type in ('Login','用户登录') order by id desc limit 30"

After a login, check what that session did in the same logs (file uploads, downloads, cron jobs, new sites). Then turn on Google Authenticator (two-step verification) in Settings, set a security entrance and limit panel access by IP where you can, as described in the aaPanel security hardening guide.

Step 5: Get a Telegram Message for Every SSH Login

Create a Telegram bot with @BotFather, send it a message, and get your chat ID as shown in the AI daily server report guide. Then create the alert script:

cat > /usr/local/bin/ssh-login-alert.sh <<'EOF'
#!/bin/bash
# Called by PAM when an SSH session opens: send user, source IP and host to Telegram
[ "$PAM_TYPE" = "open_session" ] || exit 0
TG_TOKEN="123456789:replace-with-your-bot-token"
TG_CHAT="123456789"
TEXT="SSH login on $(hostname): user=${PAM_USER} from=${PAM_RHOST} at $(date '+%F %T %Z')"
curl -s -m 5 "https://api.telegram.org/bot${TG_TOKEN}/sendMessage" \
  --data-urlencode "chat_id=${TG_CHAT}" --data-urlencode "text=${TEXT}" >/dev/null 2>&1 &
exit 0
EOF
chmod 700 /usr/local/bin/ssh-login-alert.sh

Hook it into PAM so it runs for every SSH session, including key logins and tunnels:

echo "session optional pam_exec.so /usr/local/bin/ssh-login-alert.sh" >> /etc/pam.d/sshd
grep -i "^UsePAM" /etc/ssh/sshd_config   # must be "UsePAM yes" (the default on most systems)

Keep your current SSH window open, log in from a second window and check that the Telegram message arrives. The optional keyword and the 5-second timeout mean a Telegram outage never blocks your login.

To add the key fingerprint to the alert, read the latest Accepted line for that user from journalctl -u ssh -n 20 inside the script. Keep the script short: it runs on every login.

Step 6: Make Logins Hard to Steal

  • Use key login only and disable passwords: SSH key login on Linux.
  • Never reuse the same root password on several servers. One stolen password then opens every machine, including jump hosts and management servers.
  • Block brute force with Fail2ban and keep panel ports closed to the internet where possible.
  • If you find a login you cannot explain, follow checking whether a Linux server is hacked before changing anything else, and rotate every password and key the server could see.

FAQ

last shows nothing, but auth.log has logins

Non-interactive sessions (scp, sftp, tunnels) often do not write to wtmp. The SSH log and the PAM alert above catch them.

The log files rotate. How far back can I look?

Check /var/log/auth.log.1 and the compressed .gz files (zgrep Accepted /var/log/auth.log*). For longer history, send logs to another server or keep the Telegram alerts.

Still stuck after following these steps? Open a support ticket and the IMIDC 24/7 technical team will help. Include the server IP and the suspicious log lines so we can pinpoint the issue faster.

Was this answer helpful?

Related Tutorials