Swatch и други приложения
08.02.2013 Posted by Александър Христов
Swatch e система писана на Perl, която има за цел да следи записите в .log файловете и да реагира на определени записи.
Стандартно swatch се стартира по следния начин:
/usr/bin/swatch –config-file=/etc/swatch/swatch.conf –tail-file=/var/log/syslog –background и още няколко променливи. Отделно има и до конфигуриране на swatch.conf. Което предизвика в мен огромно чувство за мързел и във вследствие на което промених малко начина на работа.
Инсталация на swatch под Debian:
[code lang=“bash“]
$ aptitude install swatch
[/code]
трябва да имате инсталирани следните модули:
[code lang=“bash“]
Time::HiRes
Date::Calc
Date::Format
File::Tail
[/code]
С модулите на Perl може да имате малко проблеми, но има достатъчно информация из нета, че и аз да пиша 🙂
От няколко скрипта сглобих и допълних един init.d скрипт за swatch, който хем да върши достатъчно работа, хем да е прост за корекция и четене. Скрипта е /etc/init.d/swatch, ето го и самия скрипт:
[code lang=“bash“]
#!/bin/bash
#/etc/init.d/swatch
#
### BEGIN INIT INFO
# Provides: swatch
# Required-Start: $syslog
# Required-Stop:
# Default-Start: 2 3 5
# Default-Stop: 0 1 6
# Description: Start or stop the SWATCH daemon
### END INIT INFO
# Check for missing binaries (stale symlinks should not happen)
SWATCH_BIN=/usr/bin/swatch
test -x $SWATCH_BIN || exit 5
# Check for existence of needed config file
SWATCH_CONFIG=/etc/swatch/swatch.conf
test -r $SWATCH_CONFIG || exit 6
# Watch syslog or *log
FILE=/var/log/*log
# Miscellaneous parameters
RETVAL=0
prog=“swatch“
start() {
echo $“Starting $prog daemon“
$SWATCH_BIN -c $SWATCH_CONFIG –tail-file=$FILE –daemon
RETVAL=$?
echo
return $RETVAL
}
stop() {
echo $“Shutting down $prog“
id=`ps aux | grep /usr/bin/tail | grep /var/log | awk ‘{print $2}’`
if [ -z „$id“ ]; then
echo „No running process $prog“
else
echo „$prog (pid $id) is stop“
kill -9 $id
fi
RETVAL=$?
echo
return $RETVAL
}
rhstatus() {
pid=`ps aux | grep swatch | grep daemon | awk ‘{print $2}’`
if [ -z „$pid“ ]; then
echo „$prog is stopped“
RETVAL=1
else
echo „$prog (pid $pid) is running“
RETVAL=0
fi
}
restart() {
echo
echo „Please wait for the process to complete“
stop
sleep 5
start
}
case „$1″ in
start)
start
;;
stop)
stop
;;
status)
rhstatus
;;
restart)
restart
;;
reload)
reload
;;
*)
echo $“Usage: $0 {start|stop|status|restart}“
exit 1
esac
exit $?
[/code]
След като създадете файла и копирате скрипта в него изпълнете това:
[code lang=“bash“]
$ chmod 755 /etc/init.d/swatch
$ update-rc.d swatch defaults
[/code]
Във файла има променлива FILE=/var/log/syslog в случая swatch ще следи само записите в /var/log/syslog, ако искате да следите повече .log файлове подменете syslog с *log. Така на практика ще се следят всичко log файлове.
Лошото в случая е, че може да след само един или всички .log файлове. Поне това аз успях да направя. Което малко или много си е ресурс за системата. Но не няма как и вълка сит и агнето цяло. И така, след това вече трябва да се създаде watch.conf. В случая аз ще го ползвам да следи локалния UPS и след определено време да изключи компютрите който са в мрежата на UPS-и.
[code lang=“bash“]
watchfor /UPS ups\@localhost on battery/
mail addresses=35988xxxxxxx\@sms.mtel.net,subject=“Power\ is\ DOWN“
exec „/etc/swatch/shutdown_remote_servers.sh“
watchfor /UPS ups\@localhost on line power/
mail addrrees=35988xxxxxxx\@sms.mtel.net,subject=“Power\ is\ UP“
exec „/etc/swatch/kill_service_shutdows.sh“
[/code]
Като трябва много да се внимава с символа “@”, да има пред него ляво наклонена черта “\”, че почват едно грешки и се чудиш защо 🙂
При мен всички потребители с админ права са с една и съща парола, което ми позваля да направя следното във файла shutdown_remote_servers.sh:
[code lang=“bash“]
#!/bin/bash
###############################################################
IP=`cat /etc/swatch/ip_address`
user=“administrator“
pass=“password“
###############################################################
sleep 600
for server in $IP ;
do net rpc shutdown -I $server -U $user%$pass &
done
[/code]
Използвана е следната команда:
[code lang=“bash“]
net rpc shutdown -I IPADDRESS -U USERNAME%PASSWORD
[/code]
Тя има за цел да изключи директно windows машината.
Ето какво представлява и самия файл ip_address:
[code lang=“bash“]
192.168.xx.yy
192.168.xx.yy
192.168.xx.yy
192.168.xx.yy
192.168.xx.yy
192.168.xx.yy
192.168.xx.yy
[/code]
И на края остана последния скрипт който има за цел, ако случайно дойде токът а времето 600 (5 мин) заложено в командата sleep не е изтеколо. Ето го и самия скрипт, kill_service_shutdows.sh:
[code lang=“bash“]
#!/bin/bash
process=shutdown_remote_servers.sh
pid=`ps auNx | grep „$process“ | grep /bin/bash | awk ‘{print $2}’`
if [ -z „$pid“ ]; then
echo „No running process $process“
else
echo „$process (pid $pid) is stop“
kill -9 $pid
fi
[/code]
След известно време осъзнах няколко неща, въз основа на които се наложи да променя начина на работа на системата за автоматично изключване.
Нещата които осъзнах са следните:
- Ако мрежата ви е на UPS и той се самоизключи след известно време (по малко от заложеното в sleep), защото няма батерия няма да сработи системата. И всички машини се изключат некоректно.
- Ако имате клиентски компютри, с модифицирания вариант потребителите ще знаят колко време имат преди да им се изключат автоматично компютрите.
- Има начин да се прекъсне брояча за автоматично изключване.
За тази цел създадох 2 скрипта:
shutdown_remotely_servers.sh
[code lang=“bash“]
#!/bin/bash
###############################################################
IP=`cat /etc/swatch/ip_address`
user=“administrator“
pass=“password“
###############################################################
# shutdown other PC after 60 sec or 1 min
net rpc shutdown -C „Power DOWN, PC is shutting down“ -I XXX.XXX.XXX.XXX -U $user%$pass -t 60 &
# shutdown the Servers after 300 sec or 5 min
for server in $IP ;
do net rpc shutdown -C „Power DOWN, PC is shutting down“ -I $server -U $user%$pass -t 300 &
done
# shutdown Linux Server after 600 sec o 10 min
shutdown -t 900 -h
[/code]
abortshutdown_remotely_servers.sh
[code lang=“bash“]
#!/bin/bash
###############################################################
IP=`cat /etc/swatch/ip_address`
user=“administrator“
pass=“password“
###############################################################
#Abort shutdown other PC
net rpc abortshutdown -I XXX.XXX.XXX.XXX -U $user%$pass &
#Abort shutdown the Servers
for server in $IP ;
do net rpc abortshutdown -I $server -U $user%$pass &
done
#Abort shutdown Linux Server
shutdown -c
[/code]
За изключване на компютрите използвам следната команда:
net rpc shutdown -C „Power DOWN, PC is shutting down“ -I XXX.XXX.XXX.XXX -U $user%$pass -t xxx
За прекъсване на брояча следната команда:
net rpc abortshutdown -I XXX.XXX.XXX.XXX -U $user%$pass
Наблюдение на температура на сървърно помещение
15.09.2012 Posted by Александър Христов
Идеята се появи след като климатика в едно от сървърните помещения реши да има собствено мнение дали да работи и как да работи 🙂 . Трябваше ми скрипт който да следи температурата в помещението и над определена температура да ме известява с смс и да ми изпраща e-mail.
След търсене в интернет попаднах на тази схема. Информацията се от чипа се извлича с digitemp.
1 вия скрип DS18B20.pl го ползвам, да визуализира информацията в cacti и за скрипта ми.
[code lang=“perl“]
#!/usr/bin/perl
$temp0 = `digitemp -t 0 | grep „Sensor 0“ -m 1 | awk ‘{print \$7}’`;
printf(„%.0f\n“, $temp1);
[/code]
Следва самия скрипт monitor_temp_serv_room.sh който следи температурата.
[code lang=“bash“]
#!/bin/bash
######################
thermo_datchik=“../DS18B20.pl“
email=“admin@domain.com“
room=“DATA Center “
LOG=/usr/bin/logger
NORMAL_LEVEL=25
WARN_LEVEL=26
CRITICAL_LEVEL=35
error_datchik=85
time_sleep=300
######################
normal_level_r () {
(
date
echo „$room Temperature is Normal – $TEMP C*“
) | mail -s „$room monitoring“ $email
}
warn_level_u_r () {
(
date
echo „$room Temperature is UP – $TEMP C*“
) | mail -s „$room monitoring“ $email
}
warn_level_d_r () {
(
date
echo „$room Temperature is DOWN – $TEMP C*“
) | mail -s „$room monitoring“ $email
}
critical_level_r () {
(
date
echo „$room Temperature is CRITICAL – $TEMP C*, PLEASE SYSTEM DOWN“
) | mail -s „$room monitoring“ $email
#$LOG „$room Temperature is CRITICAL – $TEMP C*, SYSTEM DOWN“
sleep $time_sleep
begin_f
#halt exit 0
}
set_warn_level () {
newtemp=$TEMP
oldtemp=$TEMP
while (true) ; do
if [ „$oldtemp“ -eq „$newtemp“ ] ; then # $oldtemp = $newtemp
echo
else
if [ „$oldtemp“ -lt „$newtemp“ ] ; then # $oldtemp < $newtemp
warn_level_u_r
else
if [ "$oldtemp" -gt "$newtemp" ] ; then # $oldtemp > $newtemp
warn_level_d_r
if [ „$newtemp“ -le $NORMAL_LEVEL ] ; then # $oldtemp < = $NORMAL_LEVEL
normal_level_r
begin_f
fi
fi
fi
fi
oldtemp=$newtemp
sleep $time_sleep
TEMP=`$thermo_datchik`
newtemp=$TEMP
if [ "$newtemp" -ge $CRITICAL_LEVEL ] ; then
critical_level_r
fi
done
}
critical_level_f () {
if [ "$TEMP" -ge $CRITICAL_LEVEL ] ; then
critical_level_r
else
set_warn_level
fi
}
begin_f () {
TEMP=`$thermo_datchik`
if [ "$TEMP" -ge $WARN_LEVEL ] ; then # $TEMP >= $WARN_LEVEL
if [ „$TEMP“ -eq $error_datchik ] ; then # $TEMP = $error_datchik
sleep $time_sleep
begin_f
else
warn_level_u_r
critical_level_f
fi
else
sleep $time_sleep
begin_f
fi
}
#begin script
begin_f
[/code]
Идеята на скрипта е да следи температурата постоянно, като реагира само на промяна.
Т.е. задаваме следните температури:
NORMAL_LEVEL=25 – температура <= е нормална за сървърното помещение
WARN_LEVEL=26 – температура >= от NORMAL_LEVEL трябва да се обърне внимание
CRITICAL_LEVEL=35 – температура >= от NORMAL_LEVEL трябва да се обърне специално внимание и да се подготвят за изключване сървърите
error_datchik=85 – При недостатъчно напрежение от RS232 датчика репортува температура 85*
в един момент спира климатика, много сървъри в помещението и в момента когато сработва скрипта температурата е 29*. Време на изчакване е 300 сек или 5 минути. След 5 мин температурата пак е 29* и в този случай системата няма да прави SMS. След още 5 минути температурата е намаляла на 27* при което се получава SMS, че температурата спада. И така на татък до нормализиране на температурата.
По принцип в началото мислех след като премине критична температура, да изключва сървъра, но в момента е направен да изчаква и пак от начало ред 41 и 42, ако все пак някой реши да ползва тази опция нека размаркира ред 40 и 43 и да маркира 41 и 42.