監控告警之elastalert部署及配置全解

1、安裝elastalert

環境

  • CentOS:7.4
  • Python:3.6.9
  • pip:19.3
  • elastalert:0.2.1
  • elk:7.3.2

二、配置Python3.6.9環境

安裝依賴包html

yum -y install wget openssl openssl-devel gcc gcc-c++

下載包node

wget https://www.python.org/ftp/python/3.6.9/Python-3.6.9.tgz

安裝python

tar xf Python-3.6.9.tgz
cd Python-3.6.9./configure --prefix=/usr/local/python --with-openssl
make && make install

配置nginx

mv /usr/bin/python /usr/bin/python_old
ln -s /usr/local/python/bin/python3 /usr/bin/python
ln -s /usr/local/python/bin/pip3 /usr/bin/pip
pip install --upgrade pip

注意,全部依賴python2的腳本或者命令,須要更改成python2.7,由於如今默認的python版本爲3.6,例如

sed -i '1s/python/python2.7/g' /usr/bin/yum
sed -i '1s/python/python2.7/g' /usr/libexec/urlgrabber-ext-down

驗證c++

$ python -V
    Python 3.6.9
$ pip -V 
	pip 19.3 from /usr/local/python/lib/python3.6/site-packages/pip (python 3.6)

三、安裝elastalert

下載包git

git clone https://github.com/Yelp/elastalert.git
cd elastalert

安裝github

pip install "elasticsearch<7,>6"
pip install -r requirements.txt
python setup.py install

安裝成功後能夠看到四個命令web

ll /usr/local/python/bin/elastalert*
	/usr/local/python/bin/elastalert
	/usr/local/python/bin/elastalert-create-index
	/usr/local/python/bin/elastalert-rule-from-kibana
	/usr/local/python/bin/elastalert-test-rule

軟鏈接到/usr/bin下,方便使用sql

ln -s /usr/local/python/bin/elastalert* /usr/bin
  • elastalert 報警執行的命令,會根據報警規則執行相應操做。
  • elastalert-create-index會建立一個索引,ElastAlert會把執行記錄存放到這個索引中,默認狀況下,索引名叫elastalert_status。其中有4個_type,都有本身的@timestamp字段,因此一樣也能夠用kibana來查看這個索引的日誌記錄狀況。
  • elastalert-rule-from-kibana從Kibana3已保存的儀表盤中讀取Filtering設置,幫助生成config.yaml裏的配置。不過注意,它只會讀取filtering,不包括queries。
  • elastalert-test-rule測試自定義配置中的rule設置。

2、使用

官方文檔:https://elastalert.readthedocs.ioshell

規則文檔:https://elastalert.readthedocs.io/en/latest/ruletypes.html

一、主配置文件

首先是主配置文件的模板爲config.yaml.example,生成全局配置
vim config.yaml

# 用來加載rule的目錄,默認是example_rules
rules_folder: rules
# 用來設置定時向elasticsearch發送請求,也就是告警執行的頻率
run_every:
  seconds: 30
# 用來設置請求裏時間字段的範圍
buffer_time:
  seconds: 30
# elasticsearch的host地址,端口
es_host: node01
es_port: 9200
# elastalert產生的日誌在elasticsearch中的建立的索引
writeback_index: elastalert_status
writeback_alias: elastalert_alerts
# 失敗重試的時間限制
alert_time_limit:
  days: 2

二、建立告警索引

執行elastalert-create-index命令在ES建立索引,這不是必須的步驟,可是強烈建議建立。由於對於審計和測試頗有用,而且重啓ES不影響計數和發送alert。

Elastic Version: 7.3.2
Reading Elastic 6 index mappings:
Reading index mapping 'es_mappings/6/silence.json'
Reading index mapping 'es_mappings/6/elastalert_status.json'
Reading index mapping 'es_mappings/6/elastalert.json'
Reading index mapping 'es_mappings/6/past_elastalert.json'
Reading index mapping 'es_mappings/6/elastalert_error.json'
New index elastalert_status created
Done!

看到這個輸出,就說明建立成功了,也能夠請求一下看看:

curl 127.0.0.1:9200/_cat/indices?v

health status index                     uuid                   pri rep docs.count docs.deleted store.size pri.store.size
green  open   elastalert_status_status  lh8LL4iCQeSn0afyzxBX7w   1   1          0            0       460b           230b
green  open   elastalert_status         i7B7IfCuSb2Sex8U5KoTZg   1   1          0            0       460b           230b
green  open   elastalert_status_past    et2aF44VR4WQnxB8T7zD4Q   1   1          0            0       460b           230b
green  open   elastalert_status_silence lhXHEsuUQeGZaW3cRLp5pQ   1   1          0            0       460b           230b
green  open   elastalert_status_error   zykwk4KtSyyOY7ckxQTrkA   1   1          0            0       460b           230b

三、Rule配置

全部的告警規則,經過在rule目下建立配置文件進行定義,這裏簡單建立一個來做爲演示。

首先我已經在elk集羣中配置了一個NGINX日誌採集的流水線,如今去kibana中利用檢索規則,過濾出我想要的告警內容,好比我想讓狀態碼是404的請求,觸發告警通知,就用以下語句進行查詢:

response: 404

其中group是kafka裏邊定義的組,後邊是狀態碼,還能夠寫更多條件進行匹配。

而後來到服務器添加一條規則:

vim nginx_404.yaml

name: Nginx_err
use_strftine_index: true
index: nginx_info*
type: any
aggregation:
 seconds: 10
filter:
- query:
    query_string:
      query: "response: 404"
alert:
- "email"
email:
 - "test@qq.com"
smtp_host: smtp.163.com
smtp_port: 25
smtp_auth_file: /opt/elastalert/smtp_auth_file.yaml
from_addr: test01@163.com
email_reply_to: teast02@163.com

注意裏邊在配置郵件通知的時候,還須要引用外部的一個文件,這個文件裏用於存放對應郵箱的用戶名密碼。

vim /opt/elastalert/smtp_auth_file.yaml

user: "test01@163.com"
password: "xxxxxxx"

四、規則測試

剛剛已經添加了一條規則,如今能夠用自身的命令測試一下剛剛添加的規則。

elastalert-test-rule --config config.yaml nginx_404.yaml

INFO:elastalert:Note: In debug mode, alerts will be logged to console but NOT actually sent.
            To send them but remain verbose, use --verbose instead.
Didn't get any results.
INFO:elastalert:Note: In debug mode, alerts will be logged to console but NOT actually sent.
                To send them but remain verbose, use --verbose instead.
1 rules loaded
.........
elastalert_status - {'rule_name': 'Nginx_err', 'endtime': datetime.datetime(2020, 1, 11, 7, 30, 59, 793352, tzinfo=tzutc()), 'starttime': datetime.datetime(2020, 1, 10, 7, 30, 59, 793352, tzinfo=tzutc()), 'matches': 0, 'hits': 0, '@timestamp': datetime.datetime(2020, 1, 11, 7, 31, 0, 76042, tzinfo=tzutc()), 'time_taken': 0.24003815650939941}

若是沒有報錯,則說明可用。

五、啓動

啓動方式有兩種

(1)指定規則文件路徑

python -m elastalert.elastalert --verbose --config config.yaml --rule rules/nginx_404.yaml

(2)在全局路徑config.yaml下,配置規則存放在加載規則rules目錄下

python -m elastalert.elastalert --verbose

六、驗證

服務啓動以後,日誌可以很清晰看到整個過程,此時能夠在剛剛的索引原點請求幾個不存在的接口,造一些404狀態,過一下子應該能夠看到日誌中的說明,有告警發出,郵箱應該也能收到了。

3、優化

一、啓動方式

上邊的啓動命令只是在前臺啓動,並不給力,可使用nohup啓動,或者是經過supervisord管理,會更加方便。
supervisord如何安裝就不說了.

建立配置文件:

$cat /etc/supervisord.d/elastalert1.ini
[program:elastalert1]
directory=/data/elastalert1/
command=python -m elastalert.elastalert --verbose --config /data/elastalert1/config.yaml
process_name=elastalert1
autorestart=true
startsecs=15
stopsignal=INT
stopasgroup=true
killasgroup=true
redirect_stderr=true
stdout_logfile=/data/log/elastalert1.log
stdout_logfile_maxbytes=5MB

而後啓動便可

supervisorctl update 
supervisorctl start elastalert1

二、報警方式

elastalert的報警方式有不少種,像郵件、微信、釘釘、post等等,咱們主要介紹如下幾種經常使用的

(1)郵件報警

alert:
- "email"
email:
 - "test@qq.com"
smtp_host: smtp.163.com
smtp_port: 25
smtp_auth_file: /opt/elastalert/smtp_auth_file.yaml
from_addr: test01@163.com
email_reply_to: teast02@163.com

修改/opt/elastalert/smtp_auth_file.yaml信息

(2)微信機器人報警

微信報警模板

git clone https://github.com/anjia0532/elastalert-wechat-plugin.git
cp elastalert-wechat-plugin/elastalert_modules/* elastalert_modules/

添加報警方式

alert:
 - "elastalert_modules.wechat_qiye_alert.WeChatAlerter"
#後臺登錄後【設置】->【權限管理】->【普通管理組】->【建立並設置通信錄和應用權限】->【CorpID,Secret】
#設置微信企業號的appid
corp_id: xxx
#設置微信企業號的Secret
secret: xxx
#後臺登錄後【應用中心】->【選擇應用】->【應用id】
#設置微信企業號應用id
agent_id: xx
#部門id
party_id: xx
#用戶微信號
user_id: xx
# 標籤id,多個用 | 分隔

(3)釘釘報警方式

釘釘報警模板

git clone https://github.com/xuyaoqiang/elastalert-dingtalk-plugin.git
cp elastalert-dingtalk-plugin/elastalert_modules/dingtalk_alert.py elastalert_modules/

添加報警方式

alert:
- "elastalert_modules.dingtalk_alert.DingTalkAlerter"
dingtalk_webhook: "https://oapi.dingtalk.com/robot/send?access_token=fb6500f4c85b8cfe66fa9586870f3ce16c848eab1e1cb23110388d6d443f1e"
dingtalk_msgtype: text

三、報警頻率

#限定時間內,發生事件次數
num_events: 3
#與上面參數結合使用,表示在2分鐘內發生3次就報警
timeframe:
  minutes: 2

四、避免重複告警

避免必定時間段中重複告警,能夠配置realertexponential_realert這兩個選項:

# 5分鐘內相同的報警不會重複發送
realert:
  minutes: 5
# 指數級擴大 realert 時間,中間若是有報警,
# 則按照5->10->20->40->60不斷增大報警時間到制定的最大時間,
# 若是以後報警減小,則會慢慢恢復原始realert時間
exponential_realert:
  hours: 1

五、聚合相同告警

# 根據報警的內容將相同的報警按照 name 來聚合
aggregation_key: name
# 聚合報警的內容,只展現 name 與 message
summary_table_fields:
  - name
  - message

六、告警內容格式化

能夠自定義告警內容,內部是使用Pythonformat來實現的。

alert_subject: "Error {1} @{2}"
alert_subject_args:
  - name
  - "@timestamp"
alert_text_type: alert_text_only
alert_text: |
  > Name: {1}
  > Message: {2}
  > Host: {3} ({4})
alert_text_args:
  - name
  - message
  - hostname
  - host

最後,整理了比較全的配置文件

name: test_err
use_strftine_index: true
index: filebeat-7.3.2-*
type: any

#將多個匹配項彙總到一個警報中。每次找到匹配項時,ElastAlert將等待該aggregation時間段,並將特定規則在該時間段內發生的全部匹配項一塊兒發送。
aggregation:
  seconds: 10
#限定時間內,發生事件次數
num_events: 3
#與上面參數結合使用,在幾分鐘內
timeframe:
  minutes: 2

realert:
# 5分鐘內相同的報警不會重複發送
  minutes: 5
   # 指數級擴大 realert 時間,中間若是有報警,
   # 則按照5->10->20->40->60不斷增大報警時間到制定的最大時間,
   # 若是以後報警減小,則會慢慢恢復原始realert時間
exponential_realert:
  hours: 1

filter:
- query:
    query_string:
      query: "404"

alert:
- "email"
#在郵件正文會顯示你定義的alert_text
alert_text: "You have a err message!"

#用戶認證文件,須要user和password兩個屬性
smtp_host: smtp.163.com
smtp_port: 25
smtp_auth_file: /opt/elastalert/smtp_auth_file.yaml

#從哪一個郵箱發送
from_addr: test@163.com
#回覆給那個郵箱
email_reply_to: test@163.com

email:
#接收報警郵件的郵箱
 - "test04@163.com"

4、示例

一、監控日誌Web攻擊行爲

1.1 修改nginx日誌格式

log_format logstash_json '{"time": "$time_local", '
         '"remote_addr": "$remote_addr", '
         '"remote_user": "$remote_user", '
         '"request": "$request", '
         '"status": "$status", '
         '"body_bytes_sent": "$body_bytes_sent", '
         '"http_referer": "$http_referer", '
         '"http_user_agent": "$http_user_agent", '
         '"http_x_forwarded_for": "$http_x_forwarded_for", '
         '"request_time": "$request_time", '
         '"request_length": "$request_length", '
         '"host": "$http_host"}';

1.2 編寫監控規則

name: web attack
realert:
  minutes: 5
index: logstash-*
type: frequency
num_events: 10
timeframe:
  minutes: 1

query_key:
  - name
realert:
  minutes: 5
exponential_realert:
  hours: 1
  
filter:
- query_string:
# sql insert  xss detect
        query: "request: select.+(from|limit) OR request: union(.*?)select OR request: into.+(dump|out)file OR
        request: (base64_decode|sleep|benchmark|and.+1=1|and.+1=2|or%20|exec|information_schema|where%20|union%20|%2ctable_name%20|cmdshell|table_schema) OR
        request: (iframe|script|body|img|layer|div|meta|style|base|object|input|onmouseover|onerror|onload) OR
        request: .+etc.+passwd OR http_user_agent:(HTTrack|harvest|audit|dirbuster|pangolin|nmap|sqln|-scan|hydra|Parser|libwww|BBBike|sqlmap|w3af|owasp|Nikto|fimap|havij|PycURL|zmeu|BabyKrokodil|netsparker|httperf|bench) OR
        status: (400|404|500|501)
        NOT (request:_health.html OR remote_addr:222.222.222.222  )
        "

smtp_host: smtp.qiye.163.com
smtp_port: 25
smtp_auth_file: /opt/elastalert/smtp_auth_file.yaml
email_reply_to: xxx@163.com
from_addr: xxx@163.com

alert:
- "email"
email:
- "shystartree@163.com"

alert_subject: "web attack may be by {0} at @{1}"
alert_subject_args:
  - remote_addr
  - time
alert_text_type: alert_text_only
alert_text: |
  你好,服務器({})可能正在受到web攻擊,請採起手段阻止!!!!
  ### 截止發郵件前匹配到的請求數:{}
  > 發生時間: {}
  > timestamp:{}
  > attacker's ip: {}
  > request: {}
  > status:{}
  > UA頭:{}
  >>> 參考來源:{}

alert_text_args:
  - host
  - num_hits
  - time
  - "@timestamp"
  - remote_addr
  - request
  - status
  - http_user_agent
  - source

二、五分鐘內流量總和超過200M就發郵件

run_every:
  minutes: 5

name: flow
type: metric_aggregation
index: nginx_info
buffer_time:
  minutes: 5

metric_agg_key: body_bytes_sent
metric_agg_type: sum
max_threshold: 209715200
use_run_every_query_size: true

alert_text_type: alert_text_only
alert_subject: "Alter 最近五分鐘流量超200M,請注意!!!"
alert_text: |
  最近五分鐘總流量: {0} B
  kibana url: http://xxxxx

alert_text_args:
  - metric_body_bytes_sent_sum

smtp_host: smtp.qq.com
smtp_port: 25
smtp_auth_file: /opt/elastalert/smtp_auth_file.yaml
from_addr: "xxxx@qq.com"
alert:
- "email"
email:
- "xxxx@qq.com"

三、對後端請求超過3秒的發送郵件

es_host: 192.168.20.6
es_port: 9200
run_every:
  seconds: 30
name: xxx_reponse_time
index: n-xxx-*
type: whitelist
compare_key: "request"
ignore_null: true
whitelist:
  - /index.html
  - /siteapp/ecsAuthentication/hasAuthentication

type: frequency
num_events: 1
timeframe:
    seconds: 30
filter:
- query_string:
   query: "upstream_response_time: >3 "

alert_text_type: alert_text_only
alert_subject: "Alter {0} 接口後端處理超過3秒!!!"
alert_subject_args:
- _index

html_table_title: "<h2>This is a heading</h2>"
alert_text: |
  timestamp: {0}
  request_method: {1}
  request: {2}
  request_body: {3}
  request_time: {4} s
  upstream_response_time: {5} s
  body_bytes_sent: {6} B
  status: {7}
  remote_addr: {8}
  http_x_forwarded_for: {9}
  upstream_addr: {10}
  agent: {11}

alert_text_args:
  - timestamp
  - request_method
  - request
  - request_body
  - request_time
  - upstream_response_time
  - body_bytes_sent
  - status
  - remote_addr
  - http_x_forwarded_for
  - upstream_addr
  - agent

smtp_host: smtp.qq.com
smtp_port: 25
smtp_auth_file: /opt/elastalert/rule_templates/smtp_auth_file.yaml
from_addr: "xxx@qq.com"
alert:
- "email"
email:
- "xxxxx@qq.com"
相關文章
相關標籤/搜索