Я действительно использую сервер только несколько часов в день несколько дней в неделю.
Это резервный сервер, он запрашивает данные резервного копирования у клиентов.
Об этой части позаботятся, она просыпается через запланированный волшебный пакет и делает свое дело. Все хорошо. Я могу разбудить его, чтобы использовать не по расписанию, это тоже нормально.
Как мне просто узнать, что сеть не использовалась какое-то время, и чтобы он заснул? Сетевой трафик, который я хотел бы записывать, - это SSH, SFTP, rsync и обновления от Canonical. Весь остальной трафик - это просто болтовня, которая меня не волнует.
Я хотел бы, может быть, добавить следующий псевдокод в качестве cron-скрипта ... который проверяет каждые 15 минут или около того. Я не беспокоюсь о добавлении функционала cron, чувствую себя в этом уверенно.
if [ lastSignificantNetworkActivity > 3h ] { hibernate }
У меня может быть проблема X-> Y. Я просто хочу перевести свой сервер в режим пониженного энергопотребления в режиме диска на обычные 18 часов, иначе он бы ничего не делал. Я думаю, сетевая активность была хорошим показателем для проверки. Я открыт для более развитых и надежных решений или присущих свойств сервера, чтобы проверить их наличие.
(Я не уверен, что ежедневное включение и выключение питания будет хуже, чем постоянный износ от ZFS, выполняющей проверки целостности данных в течение всего дня ... просто не уверен.)
Возможная реализация для обнаружения признаков сетевого трафика, генерируемого сеансами SSH, - через правила брандмауэра:
Этот подход также будет обнаруживать трафик, генерируемый SFTP и RSYNC, поскольку оба приложения работают по протоколу SSH.
Обнаружение обновлений через брандмауэр будет сложно выполнить, поскольку при загрузке пакетов используются протоколы FTP, HTTP и HTTPS, а правила брандмауэра необходимо настроить, чтобы отличать обновления программного обеспечения от записанного HTTP-трафика. По этой причине я предлагаю обнаруживать обновления программного обеспечения, проверяя время модификации /var/lib/apt/lists
, /var/cache/apt/archives
и /var/lib/dpkg/lock
.
Мое предложение по реализации выглядит следующим образом:
Эти командные строки настроили iptables
и ip6tables
правила.
# apt-get install iptables-persistent
# iptables -w -N fwstats
# iptables -w -A fwstats
# iptables -w -A INPUT -p tcp --dport 22 -m state --state ESTABLISHED -j fwstats
# iptables -w -A OUTPUT -p tcp --dport 22 -m state --state ESTABLISHED -j fwstats
# iptables-save > /etc/iptables/rules.v4
# ip6tables -w -N fwstats
# ip6tables -w -A fwstats
# ip6tables -w -A INPUT -p tcp --dport 22 -m state --state ESTABLISHED -j fwstats
# ip6tables -w -A OUTPUT -p tcp --dport 22 -m state --state ESTABLISHED -j fwstats
# ip6tables-save > /etc/iptables/rules.v6
Это эквивалентная установка для nftables
:
# apt-get install nftables
# nft add chain inet filter fwstats
# nft add rule inet filter fwstats counter
# nft add rule inet filter input tcp dport ssh ct state established jump fwstats
# nft add rule inet filter output tcp dport ssh ct state established jump fwstats
# echo -e \#\!`which nft` -f\\nflush ruleset > /etc/nftables.conf
# nft list ruleset >> /etc/nftables.conf
А это шаблон скрипта мониторинга. В getStats
функция должна быть настроена в соответствии с используемым межсетевым экраном.
#!/bin/bash
getStats () {
if using_nftables; then
nft list chain inet filter fwstats | grep counter
elif using_xtables; then
for xtable in iptables ip6tables; do
"${xtable}" -w -xnvL fwstats | egrep '^([[:space:]]+[0-9]+){2,2}'
done
fi
}
stateFile="/run/hibernation_state"
currentStats="`getStats`"
if [ "x${currentStats}" != "x" ]; then
previousStats="`cat \"${stateFile}\"`"
if [ "x${currentStats}" == "x${previousStats}" ]; then
# No network traffic has been detected. Check files related do DPKG and APT
clearToHibernate='true'
now="`date '+%s'`"
for path in "${stateFile}" \
'/var/lib/apt/lists' \
'/var/cache/apt/archives' \
'/var/lib/dpkg/lock' ; do
pathModTime="`stat -c '%Y' "${path}"`"
# 10800 seconds = 3 hours
if [ "$((now-10800))" -lt "${pathModTime}" ]; then
clearToHibernate='false'
fi
done
if "${clearToHibernate}"; then
# OK to hibernate.
systemctl hibernate
fi
else
# Network traffic has been detected. Refresh stats.
echo "${currentStats}" > "${stateFile}"
fi
fi
Ужасное время идеи! Давайте кататься сами!
Истекать запущенные сеансы SSH
cat > /etc/ssh/sshd_config <<__CONFIG__
AcceptEnv LANG LC_*
Banner none
ChallengeResponseAuthentication no
ClientAliveCountMax 0
ClientAliveInterval 1800
PasswordAuthentication yes
PrintMotd no
Subsystem sftp /usr/lib/openssh/sftp-server
UsePAM yes
X11Forwarding yes
__CONFIG__
Установить спящий режим
apt install hibernate
Установите общесистемный формат журнала, для развлечения
echo "HISTTIMEFORMAT=\"%Y-%m-%d %T \"" > /etc/environment
Начни работу cron!
echo "0,12,24,36,48 * * * * root bash /usr/local/sbin/hibernation" >> /etc/crontab
А теперь скроенные ужасные:
cat <<-EOF > /usr/local/sbin/hibernation
#!/bin/bash -i
# The hibernation delay script
echo "----------------------" >> /tmp/justchecking.txt
EXTEND=0
SCRIPTTIME=$(date +%s)
echo $(date) >> /tmp/justchecking.txt
echo "script timetamp" $SCRIPTTIME >> /tmp/justchecking.txt
# Make sure there is a hibernation time file
if [ ! -f /var/run/hibernation.time.txt ]
then
echo $SCRIPTTIME > /var/run/hibernation.time.txt
echo "created hibernation.time.txt sbin script" >> /tmp/justchecking.txt
fi
SLEEPTIME=$(</var/run/hibernation.time.txt)
if [ $SLEEPTIME -eq 999999999999 ]
then
echo "just came out of suspend, set extend to 360" >> /tmp/justchecking.txt
EXTEND=360
fi
# Check the logs for recent activity
HISTTIMEFORMAT="%Y-%m-%d %T "
HISTFILE=/root/.bash_history
set -o history
history 75 > /tmp/recenthistory.txt
set +o history
unset HISTFILE
ece
echo $(tail -n5 /var/log/apt/history.log | head -n1) "apt" >> /tmp/recenthistory.txt
LASTACTIVITY=$(grep -e apt -e dpkg -e chebackup /tmp/recenthistory.txt | tail -n1 | awk '{print $2" "$3}')
echo "last activity" $LASTACTIVITY >> /tmp/justchecking.txt
#LASTACTIVITYDATE="$(</tmp/recenthistory.txt)"
#echo "last activity date"$LASTACTIVITYDATE"." >> /tmp/justchecking.txt
# Store last activity date time as a timestamp
ACTIVITYTIMESTAMP=$(date -d "$LASTACTIVITY" +%s)
echo "activity time stamp" $ACTIVITYTIMESTAMP >> /tmp/justchecking.txt
# Calculate
ACTIVITYCOOLDOWNTIME=$(( 3960 - ( $SCRIPTTIME - $ACTIVITYTIMESTAMP ) ))
echo "activity cool down time" $ACTIVITYCOOLDOWNTIME >> /tmp/justchecking.txt
(($ACTIVITYCOOLDOWNTIME > 0)) && EXTEND=$ACTIVITYCOOLDOWNTIME
echo "extend variable after activity cool down command" $EXTEND >> /tmp/justchecking.txt
#if [ $ACTIVITYCOOLDOWNTIME > 0 ]
# then
# echo "activity was recent, adding cooldowntime to extend" >> /tmp/justchecking.txt
# EXTEND = $ACTIVITYCOOLDOWNTIME
#fi
# Check for updates or backup currently running
if [ $(ps -aux | grep -e apt -e dpkg -e chebackup | wc -l) -gt 1 ]
then
EXTEND=3960
SLEEPTIME=$(($SCRIPTTIME + $EXTEND))
echo $(ps -aux | grep -e apt -e dpkg -e chebackup | wc -l) > /tmp/justchecking.txt
echo "activity actively running, extended 3960" >> /tmp/justchecking.txt
fi
# Check for any users logged in
if [ $(who -u | wc -l) -gt 0 ]
then
EXTEND=10800
#EXTEND=180
echo $(who -u) >> /tmp/justchecking.txt
echo "extended 10800" >> /tmp/justchecking.txt
#echo "extend 180" >> /tmp/justchecking.txt
fi
echo "sleeptime" $SLEEPTIME >> /tmp/justchecking.txt
if [ $EXTEND -gt 0 ]
then
SLEEPTIME=$(($SCRIPTTIME + $EXTEND))
fi
if [ $SLEEPTIME -lt $SCRIPTTIME ]
then
echo "hibernate" >> /tmp/justchecking.txt
echo $(date +%s) >> /tmp/justchecking.txt
echo "hibernate" >> /tmp/justchecking.txt
echo "999999999999" > /var/run/hibernation.time.txt
hibernate &
disown
else
echo $SLEEPTIME > /var/run/hibernation.time.txt
echo "update sleeptime" $SLEEPTIME >> /tmp/justchecking.txt
fi
tail -n100 /tmp/justchecking.txt > /tmp/justchecking.txt
wc -l /tmp/justchecking.txt >> /tmp/justchicking.txt
exit 0
EOF
Не забудьте изменить разрешения
chmod 500 /usr/local/sbin/hibernation