dstat:一款简单直观的os实时监控工具
在oschina上闲逛,发现一款不错的os实时监控工具dstat,整合了vmstat, iostat, ifstat, netstat等常见os监控工具的优点,输出的结果简单直观,并且结果可以保存到csv文件,这样再写一个简单的perl脚本,就能将os的主要监控信息一次性全部抓取出来,保存到监控数据库中用于分析展示。试用了一下觉得非常不错,因此在这里分享一下这个用python写的工具。
$dstat ----total-cpu-usage---- -dsk/total- -net/total- ---paging-- ---system-- usr sys idl wai hiq siq| read writ| recv send| in out | int csw 2 0 98 0 0 0| 80k 54k| 0 0 | 335B 381B|1297 1301 22 2 74 0 0 2| 0 416k| 621k 219k| 0 0 |1158 26k 23 3 72 0 0 2| 64k 484k| 11k 11k| 0 0 |1109 30k 21 3 75 0 0 2|4096B 416k| 77k 77k| 0 0 |2104 25k 29 4 66 0 0 2| 0 1240k| 996k 425k| 0 0 |1350 28k
$dstat -ta --output osstat.csv -----time----- ----total-cpu-usage---- -dsk/total- -net/total- ---paging-- ---system-- date/time |usr sys idl wai hiq siq| read writ| recv send| in out | int csw 05-02 11:37:08| 2 0 98 0 0 0| 80k 54k| 0 0 | 335B 381B|1297 1301 05-02 11:37:09| 16 4 78 0 0 3| 0 1404k|1478k 939k| 0 0 |4316 33k 05-02 11:37:10| 20 2 76 0 0 2| 0 1144k|1109k 828k| 0 0 |5653 28k 05-02 11:37:11| 13 2 83 0 0 2| 0 588k|2590k 1684k| 0 0 |4256 23k
$dstat -h
Usage: dstat [-afv] [options..] [delay [count]]
Versatile tool for generating system resource statistics
Dstat options:
-c, --cpu enable cpu stats
-C 0,3,total include cpu0, cpu3 and total
-d, --disk enable disk stats
-D total,hda include hda and total
-g, --page enable page stats
-i, --int enable interrupt stats
-I 5,eth2 include int5 and interrupt used by eth2
-l, --load enable load stats
-m, --mem enable memory stats
-n, --net enable network stats
-N eth1,total include eth1 and total
-p, --proc enable process stats
-s, --swap enable swap stats
-S swap1,total include swap1 and total
-t, --time enable time/date output
-T, --epoch enable time counter (seconds since epoch)
-y, --sys enable system stats
--ipc enable ipc stats
--lock enable lock stats
--raw enable raw stats
--tcp enable tcp stats
--udp enable udp stats
--unix enable unix stats
-M stat1,stat2 enable external stats
--mods stat1,stat2
-a, --all equals -cdngy (default)
-f, --full expand -C, -D, -I, -N and -S discovery lists
-v, --vmstat equals -pmgdsc -D total
--integer show integer values
--nocolor disable colors (implies --noupdate)
--noheaders disable repetitive headers
--noupdate disable intermediate updates
--output file write CSV output to file
delay is the delay in seconds between each update
count is the number of updates to display before exiting
The default delay is 1 and count is unspecified (unlimited)
tbstat:实时监控数据库统计状态的小工具
用perl写了一个简单的工具,用于实时查看数据库的统计状态信息,展现信息主要来源于Oracle数据字典中v$systat和v$system_event。写这个工具的初衷,是因为目前我们对于数据库的监控,更多的是分钟级别抽样的数据来绘制的图形,粒度相对还比较粗,有一些比较深的问题,需要更加细粒度的数据。而如果把监控的粒度做到秒级,则收集的数据量就会非常大,因此需要一个平衡,平时采用分钟级别的抽样数据已经足够用于预警,而秒级的则用于某个具体问题的分析。
当前tbstat功能还比较简单,类似于iostat/vmstat等os工具,tbstat可以通过指定抽样间隔和抽样次数,来循环抓取Oracle的统计状态信息。tbstat支持三个参数 -i 表示间隔时间 -c 表示循环次数 -n 表示需要查看的统计信息的名字(使用前后%的like来查询)
- tbstat -i 2 -c 10 表示间隔时间2s,循环次数10次,展示经过人工筛选的36项统计信息
- tbstat -i 2 -c 10 -n parse 表示间隔时间2s,循环次数10次,展示所有名字包含parse的统计信息
- tbstat -i 2 -c 10 -n all 表示间隔时间2s,循环次数10次,展示所有不为零的统计信息
也可以使用简化的参数输入方法,第一位表示间隔时间,第二位表示循环次数,第三位表示统计信息名。直接敲入tbstat,则默认的参数为间隔时间10s,次数无限,经过挑选过滤的一些常用的v$sysstat中的统计信息。如果name参数传入的值是event,则展示v$system_event中的等待事件的信息。
$tbstat 1 0
--------------------------------------------------------------------------
-- tbstat v0.3.3 --- a tool for oracle system statistics and event.
-- Powered by NinGoo.net
--------------------------------------------------------------------------
CPU used by this session: 40 CR blocks created: 5
DBWR checkpoint buffers written: 569 DBWR undo block writes: 64
bytes received via SQL*Net from client: 314297 bytes sent via SQL*Net to client: 2761660
cleanouts only - consistent read gets: 4 consistent gets: 48855
db block changes: 2122 db block gets: 3714
enqueue requests: 900 enqueue waits: 7
execute count: 3145 free buffer requested: 1402
index crx upgrade (positioned): 3 index fast full scans (full): 0
leaf node 90-10 splits: 0 leaf node splits: 0
logons cumulative: 1 parse count (failures): 0
parse count (hard): 0 physical reads: 1546
physical reads cache prefetch: 0 physical writes: 603
redo size: 618436 redo synch time: 16
redo synch writes: 181 redo write time: 15
redo writes: 174 rollbacks only - consistent read gets: 0
sorts (disk): 0 sorts (memory): 259
table scans (long tables): 0 table scans (short tables): 9
transaction rollbacks: 0 user commits: 182
$tbstat 1 0 event
-------------------------------------------------------------------------------
-- tbstat v0.3.3 --- a tool for oracle system statistics and event.
-- Powered by NinGoo.net
-------------------------------------------------------------------------------
Event Name: waits time Event Name: waits time
--------------------------------------------------------------------------------------------
LGWR wait for redo copy: 1 0.01 SQL*Net more data from client: 151 19.95
SQL*Net more data to client: 1218 0.01 buffer busy waits: 2 0.01
control file parallel write: 1 0.51 control file sequential read: 1 0.26
cursor: pin S: 0 0.00 cursor: pin S wait on X: 0 0.00
db file parallel read: 0 0.00 db file parallel write: 0 0.00
db file scattered read: 0 0.00 db file sequential read: 2040 3.43
direct path read: 269 0.71 direct path read temp: 0 0.00
direct path write: 23 0.26 direct path write temp: 0 0.00
enq: CF - contention: 0 0.00 enq: HW - contention: 7 9.00
enq: SQ - contention: 0 0.00 enq: TX - allocate ITL entry: 0 0.00
enq: TX - index contention: 0 0.00 enq: TX - row lock contention: 0 0.00
latch free: 0 0.00 latch: cache buffers chains: 0 0.00
latch: library cache: 0 0.00 latch: redo writing: 0 0.00
latch: session allocation: 0 0.00 library cache lock: 0 0.00
log buffer space: 0 0.00 log file parallel write: 145 0.60
log file sequential read: 145 0.53 log file switch completion: 0 0.00
log file sync: 147 0.78 os thread startup: 0 0.00
read by other session: 0 0.00 row cache lock: 0 0.00
undo segment extension: 0 0.00
如果输入的name是精确匹配到只有一条统计信息的,会在后面打印出间隔时间内排名前10的sid的值。利用此功能,可以很方便的抓到造成某些统计信息异常的会话和SQL语句,会话和SQL信息是通过关联v$session来获取的。因此需要注意,如果统计信息对应的事件持续时间很短,从v$session里抓取到的sql可能并不是造成统计信息升高的罪魁祸首,但是sid一般来说还是准确的,因为应用采用的大多是连接池来连接数据库的,因此还是可以更具sid和machine信息来看看造成异常的是哪个具体的应用。
例如,全表扫描一般会导致physical reads cache prefetch等待事件,因此可以通过查看该事件对应的top sid来获得具体的语句,当然,不是所有的physical reads cache prefetch都是全表扫描导致的,因此对于获得的结果,还需要DBA根据具体情况做进一步分析:
$tbstat 1 0 'physical reads cache prefetch'
-------------------------------------------------------------------------------
-- tbstat v0.3.3 --- a tool for oracle system statistics and event.
-- Powered by NinGoo.net
-------------------------------------------------------------------------------
physical reads cache prefetch: 526
sid value % machine sql_id
---------- ----------- ----- ------------------- --------------
2928 302 69.7 test11 79db58a3dg921
4902 67 15.5 test71 79db58a3dg921
4821 64 14.8 test33 3afdq50xt03ch
4544 0 0.0 test54 3afdq50xt03ch
1801 0 0.0 test06 79db58a3dg921
2830 0 0.0 test12 79db58a3dg921
898 0 0.0 test09 4n7675hwwcndc
1031 0 0.0 test16 79db58a3dg921
463 0 0.0 test04 3afdq50xt03ch
1364 0 0.0 test08 cq749u66x06uj
1408 0 0.0 test27 39rbqj3ck76w3
722 0 0.0 test37 26hdkf07336uf
当然,tbstat只是一个用于抽取统计状态的小工具而已,如果要用于故障诊断,则还是要求DBA对于v$systat和v$system_event中各种统计和事件非常的熟悉。tbstat使用了DBD::Oracle以sysdba身份来连接数据库,因此需要为Perl安装DBI和DBD::Oracle模块,并且在数据库服务器本机上执行。如果你对于这个工具有兴趣,可以在这里下载源代码,使用过程中,如果有什么建议和需求,欢迎告诉我。
使用jpgraph绘制数据库监控图形
对于数据库的监控,可以分成两种类型,一种是实时的错误告警,需要尽快将一些错误信息发送给相关责任人,这更多的属于救火的性质。另外一种就是关键指标历史趋势的展示和分析,可以帮助DBA更加直观的发现数据库的指标的异常波动,提前发现问题。
市面上有不少商品的数据库监控产品,数据库厂商们也在不遗余力的推广自己的解决方案,其中不乏优秀的东西,不过能做到多产品兼容、可扩展伸缩和高度可定制的产品就凤毛麟角了。所以很多公司会自己开发一些数据库监控产品,不求大而全,只要能满足自己的业务需求就足矣。
对于自己开发的轻量级监控产品,使用LAMP等开源产品是比较合适的。数据的抽取和告警的发送,可以使用shell或者perl,几个简单的脚本就可以实现,放在crontab里定期跑跑就行,监控数据库使用MySQL存放,如果需要实现高可用的监控,考虑一下冗余,MySQL可以使用Master-Master Replication。而展示可以使用php等搭建一个简单的web网站,成本不高,效率很高。
对于历史趋势的展示,图形绘制是必须的,一图胜千言。如果使用的是PHP,jpgraph或者是pChart都是不错的选择。相对而言,jpgraph的文档和开发都还在不断的丰富,最新版本3.0.6发布于2009-10-10,而pChart的最新版本则是2008-10-06发布的1.27d,因此建议使用jpgraph。如果使用java来架构监控网站,则anysql的DataReport是值得推荐的一款产品,简单易上手,功能很强大很邪恶。
扯的有点远了,回到这篇文章的标题。jpgraph只是一个图形绘制的库,如果需要比较方便的用于数据库监控中,最好在上面再封装一层,以实现根据SQL语句查询的结果集自动绘制图形,这样可以更方便的做到批量化的增加关键指标的图形展示。另外,jpgraph对于中文的支持,因为使用了truetype字体的关系,有一点点复杂,需要从windows复制c:\windows\fonts\simsun.ttc和c:\windows\fonts\simhei.ttc到linux的/usr/share/fonts/truetype目录。jpgraph默认会将所有的中文转化成UTF8字符,如果数据库和web使用的是gb2312,则这个转化会导致乱码,解决办法是修改jpgraph_ttf.inc.php,注释掉转化部分的代码:
/* elseif( $aFF === FF_SIMSUN ) {
// Do Chinese conversion
if( $this->g2312 == null ) {
include_once 'jpgraph_gb2312.php' ;
$this->g2312 = new GB2312toUTF8();
}
return $this->g2312->gb2utf8($aTxt);
}*/
绘制图形时,在需要使用中文的地方,显式的调用字体设置函数,将字体设置为simsun,即可正确的显示中文:
$graph->title->SetFont(FF_SIMSUN,FS_BOLD);
$graph->title->Set("中文测试");
最后,贴两张用jpgraph绘制的Oracle数据库监控效果图:


使用Oracle正则表达式监控应用到数据库的连接情况
Oracle从10g开始支持正则表达式,在一些特殊的应用场景下,可以发挥超乎想象的便利。
通过v$session,可以监控应用服务器到数据库的连接的情况。假设应用服务器的名字都是有规律的,典型的如字母+数字+.+后缀的格式,例如app123.idc1表示位于idc1机房的app应用的123机器。当然,机器名的规则要根据具体的场景来分析得出,本文以上述规则来演示如何利用正则表达式来得到每组不同的应用服务器到数据库的连接情况。
对于数据库来说,可能有多组不同的应用服务器需要连接。典型的监控指标可以包括:每组应用服务器的机器数,每组应用服务器当前总的连接数,每组应用服务器中单台最大的连接数,每组应用服务器中单台最少的连接数。通过如下的sql语句,使用正则表达式,可以轻松获取上述四个指标:
select b.machine,
count(*) machine_nums,
b.cnt total_sessions,
max(a.cnt) max_sessions,
min(a.cnt) min_sessions
from
(select machine,count(*) cnt
from v$session
group by machine) a,
(select regexp_replace(regexp_replace(machine,'[0-9]','#'),'#+','#') machine,
count(*) cnt
from v$session
group by regexp_replace(regexp_replace(machine,'[0-9]','#'),'#+','#')
) b
where regexp_replace(regexp_replace(a.machine,'[0-9]','#'),'#+','#')=b.machine
group by b.machine,b.cnt
MACHINE MACHINE_NUMS TOTAL_SESSIONS MAX_SESSIONS MIN_SESSIONS --------------- ----------- -------------- ------------ ------------ db#.idc# 1 22 22 22 test#.idc# 2 10 5 5 appa#.idc# 30 166 10 5 appb#.idc# 17 18 2 1
上面的sql中,使用了正则表达式函数REGEXP_REPLACE将数字替换成#,以方便对同组应用的机器进行分组统计。只要根据相应的规则进行修改,就可以适用到不同的场景。然后利用该sql固定时间如五分钟来采集数据,就可以得到趋势展示,绘成图形,直观的分析应用服务器到数据库的连接情况。