feat: reliability, ops hooks, security checks, daily report
This commit is contained in:
@@ -0,0 +1,2 @@
|
|||||||
|
.DS_Store
|
||||||
|
CalculatorApp/
|
||||||
@@ -0,0 +1,167 @@
|
|||||||
|
# ssh-monitor
|
||||||
|
|
||||||
|
Bash-скрипт мониторинга SSH/SUDO с уведомлениями в Telegram, опциональным резервным webhook, авто-блокировкой IP (IPv4 через `iptables`, IPv6 через `ip6tables` при наличии) и ежедневным отчётом.
|
||||||
|
|
||||||
|
## Конфигурация
|
||||||
|
|
||||||
|
Скрипт читает параметры из `/etc/ssh-monitor.conf` в формате `KEY="value"`.
|
||||||
|
|
||||||
|
1. Скопируйте пример:
|
||||||
|
- `sudo cp ./ssh-monitor.conf.example /etc/ssh-monitor.conf`
|
||||||
|
2. Ограничьте доступ:
|
||||||
|
- `sudo chmod 600 /etc/ssh-monitor.conf`
|
||||||
|
3. Заполните минимум:
|
||||||
|
- `TELEGRAM_BOT_TOKEN`
|
||||||
|
- `TELEGRAM_CHAT_ID`
|
||||||
|
|
||||||
|
Поддерживаемые параметры:
|
||||||
|
|
||||||
|
- `TELEGRAM_BOT_TOKEN`, `TELEGRAM_CHAT_ID`
|
||||||
|
- `BACKUP_WEBHOOK_URL` — резервная доставка JSON `{"text":"..."}` (например Slack Incoming Webhook), если Telegram недоступен или вернул ошибку
|
||||||
|
- `LOG_FILE`, `LAST_HEARTBEAT_FILE`, `LAST_REPORT_FILE`, `LAST_SSH_CHECK_FILE`, `LAST_SUDO_CHECK_FILE`, `LAST_SECURITY_EVENTS_FILE`, `BAN_LIST_FILE`
|
||||||
|
- `DAILY_REPORT_HOUR` (0..23), `DAILY_REPORT_TOP_IPS`
|
||||||
|
- `BRUTE_WINDOW_SEC`, `BRUTE_MIN_FAILS`, `BRUTE_NOTIFY_COOLDOWN_SEC`
|
||||||
|
- `PROMETHEUS_TEXTFILE_DIR` — каталог для `ssh_monitor.prom` (совместимость с node_exporter textfile collector)
|
||||||
|
- `HEALTHCHECK_STATUS_FILE` — путь к JSON-файлу с меткой последней итерации цикла
|
||||||
|
- `BAN_TIME`, `MAX_ATTEMPTS`, `BAN_CHECK_INTERVAL`, `MONITOR_INTERVAL`
|
||||||
|
- `WHITELIST_IPS`, `WHITELIST_SUBNETS` (CSV, например `ip1,ip2`)
|
||||||
|
- `WATCHDOG_MAX_HEARTBEAT_AGE`, `WATCHDOG_LOG_FILE`, `WATCHDOG_SERVICE_NAME`, `WATCHDOG_NOTIFY_ON_RECOVERY`
|
||||||
|
|
||||||
|
Если файл `/etc/ssh-monitor.conf` отсутствует или часть значений пустая, используются значения по умолчанию из скрипта.
|
||||||
|
|
||||||
|
### Описание переменных в `/etc/ssh-monitor.conf`
|
||||||
|
|
||||||
|
- `TELEGRAM_BOT_TOKEN` — токен Telegram-бота для отправки уведомлений.
|
||||||
|
- `TELEGRAM_CHAT_ID` — ID чата/пользователя, куда отправляются уведомления.
|
||||||
|
- `BACKUP_WEBHOOK_URL` — URL для резервной отправки (тело JSON `{"text":"..."}`).
|
||||||
|
- `LOG_FILE` — путь к основному лог-файлу скрипта.
|
||||||
|
- `LAST_HEARTBEAT_FILE` — файл с timestamp последнего heartbeat-сообщения.
|
||||||
|
- `LAST_REPORT_FILE` — дата последнего ежедневного отчёта в формате `YYYY-MM-DD` (старый формат Unix-времени при первом запуске будет автоматически интерпретирован).
|
||||||
|
- `LAST_SSH_CHECK_FILE` — файл с меткой времени последней проверки SSH-событий.
|
||||||
|
- `LAST_SUDO_CHECK_FILE` — файл с меткой времени последней проверки sudo-событий.
|
||||||
|
- `LAST_SECURITY_EVENTS_FILE` — метка последней проверки «тяжёлых» событий безопасности в журнале.
|
||||||
|
- `BAN_LIST_FILE` — файл состояния банов (IP, время окончания бана и метаданные).
|
||||||
|
- `DAILY_REPORT_HOUR` — локальный час (0..23), после наступления которого в текущих сутках отправляется не более одного ежедневного отчёта.
|
||||||
|
- `DAILY_REPORT_TOP_IPS` — сколько IP показывать в топе неудачных попыток за 24 часа.
|
||||||
|
- `BRUTE_WINDOW_SEC` — окно (секунды) для оценки «массового» брутфорса по `journalctl`.
|
||||||
|
- `BRUTE_MIN_FAILS` — минимум неудачных попыток за окно для тревоги.
|
||||||
|
- `BRUTE_NOTIFY_COOLDOWN_SEC` — пауза между повторными уведомлениями по одному и тому же IP.
|
||||||
|
- `PROMETHEUS_TEXTFILE_DIR` — если задан существующий каталог, на каждой итерации пишется `ssh_monitor.prom` с метрикой `ssh_monitor_last_loop_unixtime`.
|
||||||
|
- `HEALTHCHECK_STATUS_FILE` — если задан, на каждой итерации обновляется JSON `{ "ts", "hostname", "dry_run" }`.
|
||||||
|
- `BAN_TIME` — длительность бана IP в секундах.
|
||||||
|
- `MAX_ATTEMPTS` — число неудачных SSH-попыток до автоматического бана.
|
||||||
|
- `BAN_CHECK_INTERVAL` — интервал проверки просроченных банов и аудита согласованности бан-листа с firewall (секунды).
|
||||||
|
- `MONITOR_INTERVAL` — пауза между итерациями основного цикла мониторинга (секунды).
|
||||||
|
- `WHITELIST_IPS` — белый список IP через запятую (IPv4 и IPv6 — точное совпадение).
|
||||||
|
- `WHITELIST_SUBNETS` — белый список подсетей **только IPv4** CIDR через запятую (например `10.0.0.0/24`).
|
||||||
|
- `WATCHDOG_MAX_HEARTBEAT_AGE` — через сколько секунд heartbeat считается устаревшим.
|
||||||
|
- `WATCHDOG_LOG_FILE` — лог-файл watchdog-скрипта.
|
||||||
|
- `WATCHDOG_SERVICE_NAME` — имя systemd-сервиса, который контролирует watchdog (по умолчанию `ssh-monitor.service`).
|
||||||
|
- `WATCHDOG_NOTIFY_ON_RECOVERY` — `1` включает служебные сообщения watchdog при штатном состоянии, `0` отключает.
|
||||||
|
|
||||||
|
## Режимы запуска
|
||||||
|
|
||||||
|
Обычный запуск (root):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo bash ./ssh-monitor
|
||||||
|
```
|
||||||
|
|
||||||
|
Проверка конфигурации и синтаксиса **без** запуска цикла, **без** изменений `iptables` и без обязательного Telegram:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo bash ./ssh-monitor --check-config
|
||||||
|
```
|
||||||
|
|
||||||
|
Режим **dry-run** (правила firewall не меняются; уведомления выводятся в stderr вместо отправки):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo bash ./ssh-monitor --dry-run
|
||||||
|
```
|
||||||
|
|
||||||
|
## Проверка синтаксиса
|
||||||
|
|
||||||
|
```bash
|
||||||
|
bash -n ./ssh-monitor
|
||||||
|
```
|
||||||
|
|
||||||
|
## Автозапуск через systemd
|
||||||
|
|
||||||
|
1. Скопируйте скрипт в постоянное место:
|
||||||
|
- `sudo install -m 750 ./ssh-monitor /usr/local/bin/ssh-monitor`
|
||||||
|
2. Убедитесь, что конфиг есть:
|
||||||
|
- `sudo cp ./ssh-monitor.conf.example /etc/ssh-monitor.conf` (если еще не создан)
|
||||||
|
- `sudo chmod 600 /etc/ssh-monitor.conf`
|
||||||
|
3. Создайте unit-файл `/etc/systemd/system/ssh-monitor.service`:
|
||||||
|
|
||||||
|
```ini
|
||||||
|
[Unit]
|
||||||
|
Description=SSH Monitor with Telegram alerts
|
||||||
|
After=network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
ExecStart=/usr/local/bin/ssh-monitor
|
||||||
|
Restart=always
|
||||||
|
RestartSec=5
|
||||||
|
User=root
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
```
|
||||||
|
|
||||||
|
4. Включите и запустите сервис:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo systemctl daemon-reload
|
||||||
|
sudo systemctl enable ssh-monitor
|
||||||
|
sudo systemctl start ssh-monitor
|
||||||
|
```
|
||||||
|
|
||||||
|
5. Проверка состояния и логов:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo systemctl status ssh-monitor
|
||||||
|
sudo journalctl -u ssh-monitor -f
|
||||||
|
```
|
||||||
|
|
||||||
|
## Ротация логов
|
||||||
|
|
||||||
|
Пример для `logrotate` лежит в репозитории: `contrib/logrotate.d/ssh-monitor`. Скопируйте файл в `/etc/logrotate.d/` и при необходимости поправьте пути под ваши `LOG_FILE` / `WATCHDOG_LOG_FILE`.
|
||||||
|
|
||||||
|
## Статистика без systemd (`journalctl`)
|
||||||
|
|
||||||
|
Для корректного подсчёта событий за последние 24 часа по файлам `/var/log/auth.log*` рекомендуется наличие **Python 3** на сервере. При его отсутствии счётчики в ежедневном отчёте для «классического» syslog могут быть занижены (используется безопасный fallback).
|
||||||
|
|
||||||
|
## Watchdog (автоматическое восстановление)
|
||||||
|
|
||||||
|
Watchdog проверяет:
|
||||||
|
|
||||||
|
- активен ли `ssh-monitor.service`;
|
||||||
|
- не устарел ли heartbeat (`LAST_HEARTBEAT_FILE`).
|
||||||
|
|
||||||
|
Если сервис неактивен или heartbeat старше `WATCHDOG_MAX_HEARTBEAT_AGE`, watchdog выполняет `systemctl restart` и отправляет уведомление (Telegram и при сбое — `BACKUP_WEBHOOK_URL`, если задан).
|
||||||
|
|
||||||
|
### Установка watchdog
|
||||||
|
|
||||||
|
1. Установите watchdog-скрипт:
|
||||||
|
- `sudo install -m 750 ./ssh-monitor-watchdog /usr/local/bin/ssh-monitor-watchdog`
|
||||||
|
2. Создайте unit и timer из примеров:
|
||||||
|
- `sudo cp ./ssh-monitor-watchdog.service.example /etc/systemd/system/ssh-monitor-watchdog.service`
|
||||||
|
- `sudo cp ./ssh-monitor-watchdog.timer.example /etc/systemd/system/ssh-monitor-watchdog.timer`
|
||||||
|
3. Примените и запустите timer:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo systemctl daemon-reload
|
||||||
|
sudo systemctl enable ssh-monitor-watchdog.timer
|
||||||
|
sudo systemctl start ssh-monitor-watchdog.timer
|
||||||
|
```
|
||||||
|
|
||||||
|
4. Проверка:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo systemctl status ssh-monitor-watchdog.timer
|
||||||
|
sudo systemctl list-timers | grep ssh-monitor-watchdog
|
||||||
|
sudo journalctl -u ssh-monitor-watchdog.service -f
|
||||||
|
```
|
||||||
@@ -0,0 +1,19 @@
|
|||||||
|
# Пример для /etc/logrotate.d/ssh-monitor
|
||||||
|
# Установка: sudo cp contrib/logrotate.d/ssh-monitor /etc/logrotate.d/ssh-monitor
|
||||||
|
# Пути должны совпадать с LOG_FILE и WATCHDOG_LOG_FILE в /etc/ssh-monitor.conf
|
||||||
|
|
||||||
|
/var/log/ssh_monitor.log
|
||||||
|
/var/log/ssh_monitor_watchdog.log {
|
||||||
|
weekly
|
||||||
|
rotate 12
|
||||||
|
compress
|
||||||
|
delaycompress
|
||||||
|
missingok
|
||||||
|
notifempty
|
||||||
|
create 0640 root root
|
||||||
|
sharedscripts
|
||||||
|
postrotate
|
||||||
|
# При необходимости отправьте сигнал процессу (если добавите обработку HUP)
|
||||||
|
/bin/true
|
||||||
|
endscript
|
||||||
|
}
|
||||||
+1169
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,152 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
set -Eeuo pipefail
|
||||||
|
IFS=$'\n\t'
|
||||||
|
|
||||||
|
CONFIG_FILE="/etc/ssh-monitor.conf"
|
||||||
|
WATCHDOG_LOG_FILE="/var/log/ssh_monitor_watchdog.log"
|
||||||
|
LAST_HEARTBEAT_FILE="/var/log/last_heartbeat.txt"
|
||||||
|
WATCHDOG_MAX_HEARTBEAT_AGE=5400
|
||||||
|
WATCHDOG_SERVICE_NAME="ssh-monitor.service"
|
||||||
|
WATCHDOG_NOTIFY_ON_RECOVERY="0"
|
||||||
|
|
||||||
|
write_log() {
|
||||||
|
local message="$1"
|
||||||
|
local timestamp
|
||||||
|
timestamp="$(date '+%Y-%m-%d %H:%M:%S')"
|
||||||
|
echo "${timestamp} - ${message}" | tee -a "$WATCHDOG_LOG_FILE" >/dev/null
|
||||||
|
}
|
||||||
|
|
||||||
|
send_telegram_raw() {
|
||||||
|
local message="$1"
|
||||||
|
if [ -z "${TELEGRAM_BOT_TOKEN:-}" ] || [ -z "${TELEGRAM_CHAT_ID:-}" ]; then
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
local url="https://api.telegram.org/bot${TELEGRAM_BOT_TOKEN}/sendMessage"
|
||||||
|
local body
|
||||||
|
if ! body=$(curl -fsS -X POST "$url" \
|
||||||
|
--data-urlencode "chat_id=${TELEGRAM_CHAT_ID}" \
|
||||||
|
--data-urlencode "text=${message}" \
|
||||||
|
--data-urlencode "parse_mode=HTML" \
|
||||||
|
--max-time 10 2>/dev/null); then
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
if echo "$body" | grep -q '"ok":true'; then
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
send_backup_webhook_raw() {
|
||||||
|
local message="$1"
|
||||||
|
if [ -z "${BACKUP_WEBHOOK_URL:-}" ]; then
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
if ! command -v python3 >/dev/null 2>&1; then
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
local plain
|
||||||
|
plain="$(printf '%s' "$message" | sed 's/%0A/\n/g')"
|
||||||
|
local payload
|
||||||
|
payload="$(BACKUP_MSG="$plain" python3 - <<'PY'
|
||||||
|
import json, os
|
||||||
|
print(json.dumps({"text": os.environ.get("BACKUP_MSG", "")}))
|
||||||
|
PY
|
||||||
|
)"
|
||||||
|
if curl -fsS -m 12 -X POST "$BACKUP_WEBHOOK_URL" \
|
||||||
|
-H "Content-Type: application/json" \
|
||||||
|
-d "$payload" >/dev/null 2>&1; then
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
notify_send() {
|
||||||
|
local message="$1"
|
||||||
|
if send_telegram_raw "$message"; then
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
if send_backup_webhook_raw "$message"; then
|
||||||
|
write_log "WARN: Telegram недоступен, сообщение watchdog ушло в BACKUP_WEBHOOK_URL"
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
write_log "WARN: watchdog: не удалось отправить уведомление"
|
||||||
|
return 1
|
||||||
|
}
|
||||||
|
|
||||||
|
load_config() {
|
||||||
|
if [ -f "$CONFIG_FILE" ]; then
|
||||||
|
# shellcheck disable=SC1090
|
||||||
|
source "$CONFIG_FILE"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
is_service_active() {
|
||||||
|
systemctl is-active --quiet "$WATCHDOG_SERVICE_NAME"
|
||||||
|
}
|
||||||
|
|
||||||
|
heartbeat_age_seconds() {
|
||||||
|
if [ ! -f "$LAST_HEARTBEAT_FILE" ]; then
|
||||||
|
echo 999999
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
local hb now
|
||||||
|
hb="$(<"$LAST_HEARTBEAT_FILE")"
|
||||||
|
now="$(date '+%s')"
|
||||||
|
if [[ ! "$hb" =~ ^[0-9]+$ ]]; then
|
||||||
|
echo 999999
|
||||||
|
return 0
|
||||||
|
fi
|
||||||
|
echo $((now - hb))
|
||||||
|
}
|
||||||
|
|
||||||
|
restart_monitor() {
|
||||||
|
local reason="$1"
|
||||||
|
write_log "Watchdog: перезапуск $WATCHDOG_SERVICE_NAME, причина: $reason"
|
||||||
|
if systemctl restart "$WATCHDOG_SERVICE_NAME"; then
|
||||||
|
local msg=" ⚠️ WATCHDOG: монитор перезапущен %0A"
|
||||||
|
msg="${msg}Сервис: ${WATCHDOG_SERVICE_NAME}%0A"
|
||||||
|
msg="${msg}Причина: ${reason}%0A"
|
||||||
|
msg="${msg}Время: $(date '+%d.%m.%Y %H:%M:%S')"
|
||||||
|
notify_send "$msg"
|
||||||
|
else
|
||||||
|
write_log "Watchdog: ошибка перезапуска $WATCHDOG_SERVICE_NAME"
|
||||||
|
local msg=" ❌ WATCHDOG: не удалось перезапустить монитор %0A"
|
||||||
|
msg="${msg}Сервис: ${WATCHDOG_SERVICE_NAME}%0A"
|
||||||
|
msg="${msg}Причина: ${reason}%0A"
|
||||||
|
msg="${msg}Время: $(date '+%d.%m.%Y %H:%M:%S')"
|
||||||
|
notify_send "$msg"
|
||||||
|
return 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
main() {
|
||||||
|
if [ "$EUID" -ne 0 ]; then
|
||||||
|
echo "Запустите watchdog от root"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
load_config
|
||||||
|
mkdir -p "$(dirname "$WATCHDOG_LOG_FILE")"
|
||||||
|
touch "$WATCHDOG_LOG_FILE"
|
||||||
|
|
||||||
|
local reason=""
|
||||||
|
if ! is_service_active; then
|
||||||
|
reason="systemd reported inactive service"
|
||||||
|
else
|
||||||
|
local age
|
||||||
|
age="$(heartbeat_age_seconds)"
|
||||||
|
if [ "$age" -ge "${WATCHDOG_MAX_HEARTBEAT_AGE:-5400}" ]; then
|
||||||
|
reason="stale heartbeat (${age}s)"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ -n "$reason" ]; then
|
||||||
|
restart_monitor "$reason"
|
||||||
|
elif [ "${WATCHDOG_NOTIFY_ON_RECOVERY:-1}" = "1" ]; then
|
||||||
|
write_log "Watchdog: OK, сервис активен и heartbeat актуален"
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
main "$@"
|
||||||
@@ -0,0 +1,9 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=Watchdog for ssh-monitor service
|
||||||
|
After=network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=oneshot
|
||||||
|
ExecStart=/usr/local/bin/ssh-monitor-watchdog
|
||||||
|
User=root
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
[Unit]
|
||||||
|
Description=Run ssh-monitor watchdog every minute
|
||||||
|
|
||||||
|
[Timer]
|
||||||
|
OnBootSec=2min
|
||||||
|
OnUnitActiveSec=1min
|
||||||
|
Unit=ssh-monitor-watchdog.service
|
||||||
|
Persistent=true
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=timers.target
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
TELEGRAM_BOT_TOKEN="replace_with_telegram_bot_token"
|
||||||
|
TELEGRAM_CHAT_ID="replace_with_telegram_chat_id"
|
||||||
|
|
||||||
|
# Резервный webhook при недоступности Telegram (JSON {"text":"..."}, совместимо со Slack Incoming Webhook)
|
||||||
|
BACKUP_WEBHOOK_URL=""
|
||||||
|
|
||||||
|
LOG_FILE="/var/log/ssh_monitor.log"
|
||||||
|
LAST_HEARTBEAT_FILE="/var/log/last_heartbeat.txt"
|
||||||
|
LAST_REPORT_FILE="/var/log/last_daily_report.txt"
|
||||||
|
LAST_SSH_CHECK_FILE="/var/log/last_ssh_check"
|
||||||
|
LAST_SUDO_CHECK_FILE="/var/log/last_sudo_check"
|
||||||
|
LAST_SECURITY_EVENTS_FILE="/var/log/last_security_events_check"
|
||||||
|
BAN_LIST_FILE="/var/log/ssh_bans.txt"
|
||||||
|
|
||||||
|
DAILY_REPORT_HOUR="9"
|
||||||
|
DAILY_REPORT_TOP_IPS="5"
|
||||||
|
|
||||||
|
BAN_TIME="3600"
|
||||||
|
MAX_ATTEMPTS="3"
|
||||||
|
BAN_CHECK_INTERVAL="60"
|
||||||
|
MONITOR_INTERVAL="10"
|
||||||
|
|
||||||
|
# Окно и порог для уведомления о возможном массовом брутфорсе (journalctl)
|
||||||
|
BRUTE_WINDOW_SEC="900"
|
||||||
|
BRUTE_MIN_FAILS="30"
|
||||||
|
BRUTE_NOTIFY_COOLDOWN_SEC="3600"
|
||||||
|
|
||||||
|
# Директория для textfile collector Prometheus (node_exporter). Пусто — отключено.
|
||||||
|
PROMETHEUS_TEXTFILE_DIR=""
|
||||||
|
|
||||||
|
# JSON-снимок состояния на каждой итерации (timestamp, hostname, dry_run). Пусто — отключено.
|
||||||
|
HEALTHCHECK_STATUS_FILE=""
|
||||||
|
|
||||||
|
WATCHDOG_MAX_HEARTBEAT_AGE="5400"
|
||||||
|
WATCHDOG_LOG_FILE="/var/log/ssh_monitor_watchdog.log"
|
||||||
|
WATCHDOG_SERVICE_NAME="ssh-monitor.service"
|
||||||
|
WATCHDOG_NOTIFY_ON_RECOVERY="0"
|
||||||
|
|
||||||
|
WHITELIST_IPS="127.0.0.1,10.0.0.5"
|
||||||
|
WHITELIST_SUBNETS="10.0.0.0/24,192.168.1.0/24"
|
||||||
Reference in New Issue
Block a user