[文章作者:张宴 本文版本:v1.0 最后修改:2008.06.25 转载请注明原文链接:http://blog.zyan.cc/read.php/354.htm]

  最近,在我原有的“Linux服务器系统监控程序”基础上,完善了HTTP、TCP、MySQL主动监控与MSN、E-mail、手机短信报警。监控程序以shell和PHP程序编写,以下为主要框架与部分代码:

  一、系统监控接口程序(interface.php)具有的报警方式
  1、MSN实时报警
  ①、监控程序每次检测到故障存在、或者故障恢复,都会发送短消息到管理员的MSN。
  点击在新窗口中浏览此图片

  点击在新窗口中浏览此图片

  发送MSN短消息用了一个PHP类:sendMsg,使用该PHP类发消息,必须将发送、接收双方的MSN加为联系人,发送中文时,先用iconv将字符集转为UTF-8:
引用
$sendMsg->sendMessage(iconv("GBK", "UTF-8", $message), 'Times New Roman', '008000');




  2、手机短信报警
  ①、工作日早上10点之前,晚上6点之后,以及周六、周日,监控程序检测到故障,会调用手机短信接口,发送短信给管理员的手机。
  ②、如果监控程序多次检测到同一台服务器的同一类故障,只会在第一次检测到故障时发送一条“故障报警”短信。服务器故障恢复后,监控程序会再发送一条“故障恢复”短信。

  如果没有手机短信网关接口,可以试试中国移动通信的www.139.com邮箱,具有免费的邮件到达手机短信通知功能,可以将收到的邮件标题以短信的形式发送到手机上。



  3、电子邮件报警
  ①、如果监控程序多次检测到同一台服务器的同一类故障,只会在第一次检测到故障时发送一封“故障报警”邮件。服务器故障恢复后,监控程序会再发送一封“故障恢复”邮件。

  系统监控接口程序interface.php(核心部分,仅提供部分代码):


  二、主动探测监控(“监控机”主动探测“被监控机”)
  1、HTTP服务器监控
  脚本:/data0/monitor/http.sh
引用
#!/bin/sh
LANG=C

#被监控服务器、端口列表
server_all_list=(\
192.168.1.1:80 \
192.168.1.2:80 \
192.168.1.3:80 \
)

date=$(date -d "today" +"%Y-%m-%d_%H:%M:%S")

#采用HTTP POST方式发送检测信息给接口程序interface.php,接口程序负责分析信息,决定是否发送报警MSN消息、手机短信、电子邮件。
send_msg_to_interface()
{
   /usr/bin/curl -m 600 -d menu=http -d date=$date -d ip=$server_ip -d port=$server_port -d status=$status http://127.0.0.1:8888/interface.php
}

server_all_len=${#server_all_list[*]}
i=0
while  [ $i -lt $server_all_len ]
do
   server_ip=$(echo ${server_all_list[$i]} | awk -F ':' '{print $1}')
   server_port=$(echo ${server_all_list[$i]} | awk -F ':' '{print $2}')
   if curl -m 10 -G http://${server_all_list[$i]}/ > /dev/null 2>&1
   then
     #status:    0,http down    1,http ok    2,http down but ping ok
     status=1
           echo "服务器${server_ip},端口${server_port}能够正常访问!"
   else
       if curl -m 30 -G http://${server_all_list[$i]}/ > /dev/null 2>&1
       then
           status=1
           echo "服务器${server_ip},端口${server_port}能够正常访问!"
       else
           if ping -c 1 $server_ip > /dev/null 2>&1
           then
               status=2
               echo "服务器${server_ip},端口${server_port}无法访问,但是能够Ping通!"
           else
               status=0
               echo "服务器${server_ip},端口${server_port}无法访问,并且无法Ping通!"
           fi
       fi
   fi
 send_msg_to_interface
   let i++
done



  2、TCP服务器监控
  脚本:/data0/monitor/tcp.sh
引用
#!/bin/sh
LANG=C

#被监控服务器、端口列表
server_all_list=(\
192.168.1.4:11211 \
192.168.1.5:11211 \
192.168.1.6:25 \
192.168.1.7:25 \
)

date=$(date -d "today" +"%Y-%m-%d_%H:%M:%S")

#采用HTTP POST方式发送检测信息给接口程序interface.php,接口程序负责分析信息,决定是否发送报警MSN消息、手机短信、电子邮件。
send_msg_to_interface()
{
   /usr/bin/curl -m 600 -d menu=tcp -d date=$date -d ip=$server_ip -d port=$server_port -d status=$status http://127.0.0.1:8888/interface.php
}

server_all_len=${#server_all_list[*]}
i=0
while  [ $i -lt $server_all_len ]
do
   server_ip=$(echo ${server_all_list[$i]} | awk -F ':' '{print $1}')
   server_port=$(echo ${server_all_list[$i]} | awk -F ':' '{print $2}')
   if nc -vv -z -w 3 $server_ip $server_port > /dev/null 2>&1
   then
       #status:    0,http down    1,http ok    2,http down but ping ok
       status=1
       echo "服务器${server_ip},端口${server_port}能够正常访问!"
   else
       if nc -vv -z -w 10 $server_ip $server_port > /dev/null 2>&1
       then
           status=1
           echo "服务器${server_ip},端口${server_port}能够正常访问!"
       else
           if ping -c 1 $server_ip > /dev/null 2>&1
           then
               status=2
               echo "服务器${server_ip},端口${server_port}无法访问,但是能够Ping通!"
           else
               status=0
               echo "服务器${server_ip},端口${server_port}无法访问,并且无法Ping通!"
           fi
       fi
   fi
   send_msg_to_interface
   let i++
done



  3、MySQL服务器监控
  ①、MySQL是否能够连接
  ②、MySQL是否发生表损坏等错误
  ③、MySQL活动连接数是否过多
  ④、MySQL从库是否同步正常
  ⑤、MySQL从库同步延迟时间是否过大
  脚本:/data0/monitor/mysql.php


  4、主动监控守护进程
  脚本:/data0/monitor/monitor.sh
引用
#!/bin/sh
while true
do
   /bin/sh /data0/monitor/http.sh > /dev/null 2>&1
   /bin/sh /data0/monitor/tcp.sh > /dev/null 2>&1
   /usr/local/php/bin/php /data0/monitor/mysql.php > /dev/null 2>&1
   sleep 10
done


  启动主动监控守护进程:
/usr/bin/nohup /bin/sh /data0/monitor/monitor.sh 2>&1 > /dev/null &



  三、被动报告监控(“被监控机”采集数据发送给“监控机”)
  1、磁盘空间使用量监控
  2、磁盘Inode使用量监控
  3、Swap交换空间使用量监控
  4、系统负载监控
  5、Apache进程数监控

  被动监控这部分,在我的文章《写完“Linux服务器监控系统 ServMon V1.1” 》中已经实现,就不再详细写出。



Tags: , , , ,



技术大类 » 其他Unix技术 | 评论(66) | 引用(1) | 阅读(140603)
xooass Email Homepage
2008-6-25 10:22
惊叹,做网管就应该做到张老师这样grin
lhmwzy
2008-6-25 10:29
能否开源?嘿嘿
agg
2008-6-25 10:47
MSN的这个有点酷
Robin
2008-6-25 11:29
就一msn机器人,要是能QQ就完美了
张宴 回复于 2008-6-25 20:36
QQ没有公开通讯协议,而且经常改协议,就是为了不互通,保持它的垄断优势。所以还不能支持QQ
linuxtone Homepage
2008-6-25 14:34
非常感谢分享!一直在用gtalk和msn配合使用。
彩火
2008-6-25 19:27
你的servmon是基于什么开发的?
张宴 回复于 2008-6-25 20:35
shell + PHP
未命名日志
[2008-6-25 21:57]
来源:wh111
内容:Linux服务器系统监控框架与MSN、E-mail、手机短信报警的实现
gurudk
2008-6-26 09:27
佩服,你的文章大多一板一眼,风格不错,值得学习!
..
2008-6-27 11:21
nagios不是现有的监控么?何必这么费劲呢?不过自己写的脚本倒也不错,很值得赞赏。
dj Email Homepage
2008-6-28 15:27
不错!!!!!!!
fcicq Email Homepage
2008-6-28 16:57
杀鸡用牛刀了. 写 script 简单输出 error message, 然后用 curl 扔到 fanfou/jiwai.de 就可以了.
再加上这根本就不是完整的方案, 应该在日志服务器上分析日志再发. 每个 server 应该把 status 报告到日志服务器.
redblade
2008-6-28 17:51
宴哥,如果我没有看错的话,您的那个监控应该无法做到这一点:

②、MySQL是否发生表损坏等错误


而我看到官网在说 检测 MyISAM 表是否损坏(MySQL启动状况下),用 CHECK TABLE table_name 命令,而监控一次就要执行全库的表检查,是非常耗时的,尤其数据量非常大的时候。

有什么办法吗?您是这方面的专家了,请教一下!
张宴 回复于 2008-6-30 09:02
用CHECK TABLE table_name检查表,会比较消耗资源,使用show slave status\G查看同步是否有错,不会消耗很大资源。
检查出Last_SQL_Error的内容(其中有损坏的表名),然后自动使用REPAIR TABLE table_name修复指定表。
小小啊咭 Email
2008-6-28 20:13
宴兄.强悍,经常看你的文章,二个字佩服
希望和你交朋友!

以后多交流!
todayboy Email
2008-6-29 00:36
不错,学习中!!!!!!!!!!!!!!!!!!!
lasu Homepage
2008-6-30 09:37
受益匪浅
zxp
2008-6-30 14:05
只会手机和email通知还不会msn通知。
看来要学习了~
redblade
2008-6-30 15:03
多谢宴哥回复!
宴哥,在主从库结构中,是可以通过Last_SQL_Error进行检查,但是在非主从库或者主从库的主库中呢?
怎么检查表的坏掉?
检查日志?
无解也~
plane
2008-6-30 16:26
shock

好强大!!
我也想做,但是一直都不会!
暗里着迷
2008-7-6 09:45
张宴大哥,这语句的第二次判断能够正常访问语句是不是有点重复,还是为了再一次确定是否能够正常访问?(if nc -vv -z -w 10 $server_ip $server_port > /dev/null 2>&1
      then
          status=1
          echo \"服务器${server_ip},端口${server_port}能够正常访问!\"
)您是怎么个想法?

if nc -vv -z -w 3 $server_ip $server_port > /dev/null 2>&1
  then
      #status:    0,http down    1,http ok    2,http down but ping ok
      status=1
      echo \"服务器${server_ip},端口${server_port}能够正常访问!\"
  else
      if nc -vv -z -w 10 $server_ip $server_port > /dev/null 2>&1
      then
          status=1
          echo \"服务器${server_ip},端口${server_port}能够正常访问!\"
      else
          if ping -c 1 $server_ip > /dev/null 2>&1
          then
              status=2
              echo \"服务器${server_ip},端口${server_port}无法访问,但是能够Ping通!\"
          else
              status=0
              echo \"服务器${server_ip},端口${server_port}无法访问,并且无法Ping通!\"
          fi
      fi
  fi
张宴 回复于 2008-7-6 10:22
后一次是为了再次确认是否能正常访问,第一次的等待时间为3秒,第二次为10秒。
我是游客
2008-7-9 10:31
能不能提供打包下载呀?哈哈。
分页: 1/4 第一页 1 2 3 4 下页 最后页
发表评论
表情
emotemotemotemotemot
emotemotemotemotemot
emotemotemotemotemot
emotemotemotemotemot
emotemotemotemotemot
打开HTML
打开UBB
打开表情
隐藏
记住我
昵称   密码   游客无需密码
网址   电邮   [注册]