LinuxForum.Fans
Тема

email оповешения при подлючении клиента к OpenVPN серверу

Автор: NewbieUNIX 21 сообщений 4599 просмотров
#288507

Добрового времени суток друзья. Я столкнулся с маленькои проблемой, которая никак не решается. Может вы сможете помочь.
У меня написан следуюший скрипт:

text
#!/bin/bash
log="/etc/openvpn/openvpn.log"
msg="Peer Connection Initiated with"
tmp_file="/etc/openvpn/log.tmp"
mailbox="myemail@whatever.com"
while [ : ]
do
                tac $log | while read line; do
                        if [[ $line =~ "^checkAndSend" ]] ;then
                                break;
                        else
                                echo $line >> $tmp_file;
                        fi
                done
                echo "checkAndSend" >> $log
#----------------------------------------------------------------
                data=`egrep -wi "$msg" $tmp_file`
                if [ -n "$data" ] ; then
                        echo "$data"|mail -s "`echo $data|head -n1|awk {'print($7" connected by VPN from "$6)'}| sed 's/openvpn-//g'| cut -d: -f1`" $mailbox
                fi
                :> $tmp_file
sleep 30
done

Этот скрипт присылает мэил, когда кто-то из работников подсоединяется к OpenVPN серверу при помощи клиента.
На CentOS release 5.5 (Final) этот скрипт работал без проблем, но при переходе на CentOS release 6.2 (Final) он подвисает и отсылает одно и тоже уведомление снова и снова. Может кто-нибудь видит в чем проблема или предложит лучший способ?
Заранее спасибо.

#288521

Если ты предоставишь примеры файлов, будет проще проверить.
И что делает оператор =~?

#288523
Lupo Alberto написал:
[quote="Vascom"]И что делает оператор =~?

http://tldp.org/LDP/abs/html/bashver3.html#REGEXMATCHREF[/quote]
Замечательно :)
Там же написано

text
# NOTE: As of version 3.2 of Bash, expression to match no longer quoted.

Это оно? Надо кавычки убрать?

#288524
"Vascom" написал:
Это оно? Надо кавычки убрать?

Насколько я понял, при проверке соответствия значения переменной регулярному выражению в двойных квадратных скобках это регулярное выражение уже необязательно заключать в двойные кавычки.

#288663

Cпасибо за ответ друзья. Очень помогли.

#288669

Так в чём была проблема?

#288670
Vascom написал:
Так в чём была проблема?

кавычки =)

#288727

С вашего разрешения, друзья, посветим эту тему скриптам =)
Я пытаюсь написать скрипт, который будет отсылать email если количество соединений превысит установленный предел.
Т.е. один пользователь пытается закидать сервак запросами. Вот что у меня получилось:

text
#!/bin/bash
while [ : ]
do
        netstat -ntu | awk '{print $5}' | awk '!/[A-Z]/' | cut -d: -f1 | sort | uniq -c | sort -n 
                if [[ $line > 30 ]] ;then
                        break;
                else
                        echo $line >> result2;
                fi
done
#-------------------------------------------------------------------------------------------
                        cat result2 | mail -s "Some gay hit API limit" myemail@whatever.com
:> result2
done

Строго не судите, только учусь
Я использую команду netstat, для того чтобы получить список IP адресов и сколько соединений установленно с каждым IP:

text
 netstat -ntu | awk '{print $5}' | awk '!/[A-Z]/' | cut -d: -f1 | sort | uniq -c | sort -n 

Получается вот что:

text
      1 149.152.191.3
      1 164.50.244.203
      2 173.164.45.221
      4 173.64.11.26

Затем(вот тут вопрос):

text
if [[ $line > 1 ]] ;then
                        break;
                else
                        echo $line >> result2;
                fi
done

Как лучше проверить есть ли в первом столбике число, например, больше 30. И если такая линия имеется, то переместить её в отдельный фаил вместе с IP адресом. Естественно я понимаю, что if [[ $line > 1 ]] ;then .... совершенно не правильно, просто пытался кое-что изобразить, но вообше не получилось, пардоньте.

Ну и финальная стадия, отправить содержимое фаила на определеный email и очистить фаил.
Подскажите пожалуиста как дописать скрипт, либо может эту задачу можно решить иным способом.
Спасибо.

#288738

На коленке можно так сделать, правда пришлось избавляться от пробелов, но их точно так же можно и вернуть, если надо:

text
#!/bin/bash

#Удаляем старый файл rm flame_file.log #Задаём порог срабатывания thr=1

full_line=`netstat -ntu | awk '{print $5}' | awk '!/[A-Z]/' | cut -d: -f1 | sort | uniq -c | sort -n`

#Заменяем пробелы на ",", чтобы проще было обрабатывать в цикле for full_line_s=`echo "$full_line" | sed 's/ /,/g'`

for line in $full_line_s do #Вычленяем нужные числа check=`echo "$line" | cut -d "," -f7`

#Проверяем превышение порога if (( $check > $thr )) then echo "$line" >> flame_file.log fi done

Как отправить письмо ты уже знаешь, файл очищается rm (в моём примере), либо через echo "" > flame_file.log.

Этот вариант написан за пару минут, можно доработать и вылизать его.

#288748
"NewbieUNIX" написал:
Как лучше проверить есть ли в первом столбике число, например, больше 30. И если такая линия имеется, то переместить её в отдельный фаил вместе с IP адресом.

Команда

text
netstat -ntu | awk '$5 ~ /[0-9]/ {print $5}' | cut -d: -f1 | sort | uniq -c | sort -n | awk '$1 > 30 {print $2}'

покажет только адреса, встречающиеся больше 30 раз. Ну и, разумеется, весь вывод можно перенаправить в файл.

#288753

Кстати, iptables может логировать (и при желании блокировать) превышение запросов за определённый промежуток времени.

#288939
Vascom написал:
На коленке можно так сделать, правда пришлось избавляться от пробелов, но их точно так же можно и вернуть, если надо:
text
#!/bin/bash

#Удаляем старый файл rm flame_file.log #Задаём порог срабатывания thr=1

full_line=`netstat -ntu | awk '{print $5}' | awk '!/[A-Z]/' | cut -d: -f1 | sort | uniq -c | sort -n`

#Заменяем пробелы на ",", чтобы проще было обрабатывать в цикле for full_line_s=`echo "$full_line" | sed 's/ /,/g'`

for line in $full_line_s do #Вычленяем нужные числа check=`echo "$line" | cut -d "," -f7`

#Проверяем превышение порога if (( $check > $thr )) then echo "$line" >> flame_file.log fi done

Как отправить письмо ты уже знаешь, файл очищается rm (в моём примере), либо через echo "" > flame_file.log.

Этот вариант написан за пару минут, можно доработать и вылизать его.

Скрипт интересный, спасибо большое.
На линии 19 он сравнивает IP с лимитом количества подключений, хотя должен сравнивать лимит подлючений и кол-во подключений с одного IP.

text
 line 19: ((: 209.40.97.5 > 1 : syntax error: invalid arithmetic operator (error token is ".40.97.5 > 1 ")

Или я чего-то не понимаю?
Спасибо

#289023

Да, это я коряво с пробелами разобрался :)
Конечно надо было через awk, как-то забываю про него.

Ну разберись в скрипте, если хочешь, там все команды элементарные.
Надо отредактировать строку
check=`echo "$line" | cut -d "," -f7`
подобрать нужное поле, то есть не -f7, а -f6 или -f5 или ещё меньше.

#289075
Vascom написал:
Да, это я коряво с пробелами разобрался :)
Конечно надо было через awk, как-то забываю про него.

Ну разберись в скрипте, если хочешь, там все команды элементарные.
Надо отредактировать строку
check=`echo "$line" | cut -d "," -f7`
подобрать нужное поле, то есть не -f7, а -f6 или -f5 или ещё меньше.

Да конечно :) Ещё раз огромное спасибо *THUMBSUP*
Просто хотел убедиться, что понимаю о чём речь.
Позже виложу конечный вариант.

#289132

Вот что получилось. Vascom и Lupo Alberto огромное спасибо.

text
#!/bin/bash

thr=30

full_line=`netstat -ntu | awk '{print $5}' | awk '!/[A-Za-z]/' | cut -d: -f1 | sort | uniq -c | sort -n`

full_line_s=`echo "$full_line" | awk '{print $1}'`

for line in $full_line_s do

check=`echo "$line" | awk '{print $1}'` ############################################################### host=`hostname` mailbox="myemail@whatever.com" data=`netstat -ntu | awk '$5 ~ /[0-9]/ {print $5}' | cut -d: -f1 | sort | uniq -c | sort -n | awk '$1 > 30 {print $2}'` ############################################################### #check limits if (( $check > $thr )) then echo "Some text here: $data"|mail -s "Some text here $host" $mailbox fi done

#290013

Помогите пожалуйста оптимизировать:

text
date | awk '{print $3,$2,$6,$4}' | sed 's/ /\//' | sed 's/ /\//' | sed 's/ /\:/' | cut -d: -f1,2,3

Пытаюсь вывод команды "date" трансформировать, вместо

text
Tue Dec 11 13:35:32 EST 2012

получить следующее:

text
11/Dec/2012:13:35

Мой вариант работает, но я понимаю что можно сделать проще, только не знаю как. Буду очень благодарен за подсказку.
Спасибо.

#290017
Lupo Alberto написал:
text
date +%d/%b/%Y:%H:%M

Спасибо.

#290651

Добрового времени суток. Помогите дописать скрипт пожалуйста.

1шаг: Проверяю еррор логи на наличие ошибки, на выходе из команды получаю название домена

text
grep "$min_1" $log_er | grep limiting | awk '{print $16}' | sed 's/,/ /g' 

2шаг: Потом сравниваю с именами домена. Если какои-то домен подходит, то проверяю другие логи, чтобы узнать количество соединений

text
     if [[ $line =~ ^domain1.com ]] ;then
                                full_line=`grep "$min_2" $log_2 | awk '{print $3}' | sort | uniq -c | sort -n `
                                full_line_s=`echo "$full_line" |  awk '{print $1}'`
                                for line in $full_line_s
                        fi
                        do
                                check=`echo "$line"`
                #check limits
                        if (( $check > $thr ))
                then
                        echo "Some text: $data"|mail -s "Some text on $host" $mailbox
                        fi
#-----------------------------------------------------------------------------------------------------
                        elif [[ $line =~ ^domain2.com ]] ;then
                                full_line=`grep "$min_2" $log_2 | awk '{print $3}' | sort | uniq -c | sort -n `
                                full_line_s=`echo "$full_line" |  awk '{print $1}'`
                                for line in $full_line_s
                        do
                                check=`echo "$line"`
                #check limits
                        if (( $check > $thr ))
                then
                        echo "Some text: $data"|mail -s "Some text on $host" $mailbox
                        fi
#-----------------------------------------------------------------------------------------------------
                         elif [[ $line =~ ^domain3.com ]] ;then
                                full_line=`grep "$min_2" $log_3 | awk '{print $3}' | sort | uniq -c | sort -n `
                                full_line_s=`echo "$full_line" |  awk '{print $1}'`
                                for line in $full_line_s
                        do
                                check=`echo "$line"`
                #check limits
                        if (( $check > $thr ))
                then
                        echo "Some text: $data"|mail -s "Some text on $host" $mailbox
                        fi
#-----------------------------------------------------------------------------------------------------
                        elif [[ $line =~ ^domain4.com ]] ;then
                                full_line=`grep "$min_2" $log_4 | awk '{print $3}' | sort | uniq -c | sort -n `
                                full_line_s=`echo "$full_line" |  awk '{print $1}'`
                                for line in $full_line_s
                        do
                                check=`echo "$line"`
                #check limits
                        if (( $check > $thr ))
                then
                        echo "Some text: $data"|mail -s "Some text on $host" $mailbox
                        fi
#-----------------------------------------------------------------------------------------------------
                else
                        break;
        fi
                done

3шаг: Если лимит превышен, то отправляю емаил

text
do
                                check=`echo "$line"`
                #check limits
                        if (( $check > $thr ))
                then
                        echo "Some text: $data"|mail -s "Some text on $host" $mailbox
                        fi

Весь скрипт:

text
#!/bin/bash

#Setup limit thr=900 #----------------------------------------------------------------------------------------------------- #Time min_1=`date '+%G/%m/%d %H:%M'` min_2=`date +%d/%b/%Y:%H:%M` #----------------------------------------------------------------------------------------------------- #nginx error log file log_er="/var/log/nginx/error.log" #----------------------------------------------------------------------------------------------------- #log files log_1="/etc/nginx/logs/domain1.com.ssl.log" log_2="/etc/nginx/logs/domain2.com.ssl.log" log_3="/etc/nginx/logs/domain3.com.ssl.log" log_4="/etc/nginx/logs/domain4.com.ssl.log" #----------------------------------------------------------------------------------------------------- #Information for email #From hostname host=`hostname` #----------------------------------------------------------------------------------------------------- #To mailbox="myemail@whatever.com" #----------------------------------------------------------------------------------------------------- #Body data=`test message` #----------------------------------------------------------------------------------------------------- grep "$min_1" $log_er | grep limiting | awk '{print $16}' | sed 's/,/ /g' | while read line; do if [[ $line =~ ^domain1.com ]] ;then full_line=`grep "$min_2" $log_2 | awk '{print $3}' | sort | uniq -c | sort -n ` full_line_s=`echo "$full_line" | awk '{print $1}'` for line in $full_line_s fi do check=`echo "$line"` #check limits if (( $check > $thr )) then echo "Some text: $data"|mail -s "Some text on $host" $mailbox fi #----------------------------------------------------------------------------------------------------- elif [[ $line =~ ^domain2.com ]] ;then full_line=`grep "$min_2" $log_2 | awk '{print $3}' | sort | uniq -c | sort -n ` full_line_s=`echo "$full_line" | awk '{print $1}'` for line in $full_line_s do check=`echo "$line"` #check limits if (( $check > $thr )) then echo "Some text: $data"|mail -s "Some text on $host" $mailbox fi #----------------------------------------------------------------------------------------------------- elif [[ $line =~ ^domain3.com ]] ;then full_line=`grep "$min_2" $log_3 | awk '{print $3}' | sort | uniq -c | sort -n ` full_line_s=`echo "$full_line" | awk '{print $1}'` for line in $full_line_s do check=`echo "$line"` #check limits if (( $check > $thr )) then echo "Some text: $data"|mail -s "Some text on $host" $mailbox fi #----------------------------------------------------------------------------------------------------- elif [[ $line =~ ^domain4.com ]] ;then full_line=`grep "$min_2" $log_4 | awk '{print $3}' | sort | uniq -c | sort -n ` full_line_s=`echo "$full_line" | awk '{print $1}'` for line in $full_line_s do check=`echo "$line"` #check limits if (( $check > $thr )) then echo "Some text: $data"|mail -s "Some text on $host" $mailbox fi #----------------------------------------------------------------------------------------------------- else break; fi done

По частям скрипт работает, но связать все в один не получатся, особенно if fi не могу понять как работает, если там не один цикл, а четыре. Плюс еше if fi из шага 3 там мешаются. Короче завис я( Помогите пожалуйста, буду очень благодарен.
Спасибо.

Войдите или зарегистрируйтесь, чтобы ответить.