collectd,一把网管界的瑞士军刀,小巧玲珑又功能强大,主要用来搜集主机的相关信息,用C来编写,可运行在多种操作系统之下,跟graphite的结合更是如虎添翼,是居家旅行、杀人越货的必备神器。

1. 安装

1.1 openbsd

root@openbsd-1/var/ossec/etc: # pkg_add -vr collectd
Update candidates: quirks-1.32 -> quirks-1.32 (ok)
collectd-4.10.2:libxml-2.7.8p1: ok
collectd-4.10.2:libstatgrab-0.15p1: ok
collectd-4.10.2:libltdl-1.5.26p0: ok
collectd-4.10.2:libgpg-error-1.9: ok
collectd-4.10.2:libgcrypt-1.4.6: ok
collectd-4.10.2: ok
--- +collectd-4.10.2 -------------------
First, configure collectd in /etc/collectd.conf,
Then use the following to start the daemon:
 
        sudo -u _collectd /usr/local/sbin/collectd

1.2 debian squeeze

collectd 5.1已经进入squeeze backports中,因此

$ sudo aptitude -t squeeze-backports install collectd-core
 
backports中的collectd-core,其依赖关系漏了libsnmp15包(提供libnetsnmp.so.15库文件)。然而snmp插件的正常需要该文件,否则会出错:

1.2.1 snmp:

$ sudo ldd /usr/lib/collectd/snmp.so      
        linux-gate.so.1 =>  (0xb770e000)
        libnetsnmp.so.15 => not found
        libpthread.so.0 => /lib/i686/cmov/libpthread.so.0 (0xb76e7000)
        libiptc.so.0 => /lib/libiptc.so.0 (0xb76e5000)
        libdl.so.2 => /lib/ i686/cmov/libdl.so.2 (0xb76e0000)
        libc.so.6 => /lib/i686/cmov/libc.so.6 (0xb7599000)
        /lib/ld-linux.so.2 (0xb770f000)
        libip4tc.so.0 => /lib/libip4tc.so.0 (0xb7593000)
        libip6tc.so.0 => /lib/libip6tc.so.0 (0xb758d000)
 
解决办法:
$ sudo aptitude install libsnmp15
$ sudo aptitude install snmp snmp-mibs-downloader

>说明:snmp-mibs-downloader是non-free软件包,所以source.list的条目中要加上non-free这个关键字。

1.2.2 ping:

错误:依赖liboping0

解决办法:

$ sudo aptitude install liboping0

关于依赖包明细,请参考https://github.com/collectd/collectd

$ sudo collectd -T
ERROR: lt_dlopen ("/usr/lib/collectd/snmp.so") failed: file not found. The most common cause for this problem are missing dependencies. Use ldd(1) to check the dependencies of the plugin / shared object.
Unable to load plugin snmp.
0

1.3 centos

centos 6.5的源中自带的collectd版本比较老,是4.10.9

$ sudo yum -y install collectd collectd-ping collectd-rrdtool collectd-snmp

2. 基本配置

 
$ sudo vim /etc/collectd.conf
--------8<-----------
FQDNLookup false
 
LoadPlugin syslog
LoadPlugin cpu
LoadPlugin csv
 
<Plugin "csv">
       DataDir "/var/lib/collectd/csv"
       StoreRates true
</Plugin>
--------8<-----------
 
== 3. 运行
  • 测试插件正常

    $ sudo collectd -T
  • 测试配置是否正常

    $ sudo collectd -t
  • 强制前台运行

    在标准输出设备(显示屏)打印运行日志

    $ sudo collectd -f

    当然,假如启用了syslog 插件,也可以通过/var/log/message/var/log/syslog查看collectd的运行日志

    $ sudo tail -f /var/log/syslog | grep collectd
    --------8<-----------
    Nov 28 07:10:52 deb6-collectd collectd[8145]: Exiting normally.
    Nov 28 07:10:52 deb6-collectd collectd[8145]: collectd: Stopping 5 read threads.
    Nov 28 07:10:52 deb6-collectd collectdmon[8143]: Info: collectd terminated with exit status 0
    Nov 28 07:10:52 deb6-collectd collectdmon[8143]: Info: shutting down collectdmon
    Nov 28 07:10:54 deb6-collectd collectd[9736]: Initialization complete, entering read-loop.
    -------->8-----------

前面几项都测试成功之后,就可以看是否将cpu的信息写入到csv文件中:

$ sudo tail -f /var/lib/collectd/csv/<hostname>/cpu-0/cpu-interrupt-yyyy-mm-dd
--------8<-----------
1354086456.105,198.700561
1354086466.105,199.100324
1354086476.105,199.501158
1354086486.105,199.399259
1354086496.105,199.599833
1354086506.105,199.799262
1354086516.105,198.799251
1354086526.105,199.000930
1354086536.105,199.401715
-------->8-----------

留意观察的话就会发现,每10秒就更新一次数据

4. 高级应用

4.1 snmp

<Plugin snmp>
   <Data "std_traffic">
       Type "if_octets"
       Table true
       Instance "IF-MIB::ifName"
       #Values "IF-MIB::ifHCInOctets" "IF-MIB::ifHCOutOctets"
       Values "IF-MIB::ifInOctets" "IF-MIB::ifOutOctets"
   </Data>
 
   <Data "sysUpTime">
       Type "uptime"
       Table false
       Instance ""
       Scale 0.0000001157
       Values "iso.3.6.1.2.1.1.3.0"
   </Data>

通过snmpget iso.3.6.1.2.1.1.3.0获得的数据类型是timeticks,单位是1/100秒,所以需要转换成易读的值。1天=24小时*60分*60秒,uptime = sysUpTime/24*60*60*100 = sysUpTime* 0.0000001157 天。snmp plugin中提供了两个配置参数,用于对原始值进行数学计算,其中Scale表示乘除,所以此处的Scale值应为0.0000001157,另外还有一个配置参数是shift,表示加/减,本处没用上。

实际上,可以通过match_regex和target scale统一将if_octet的值进行乘积运算,避免重复工作,详见下文   Type "uptime",该值必须从/usr/share/collectd/types.db挑选,不能随便填,对于sysUpTime,其值类型为gauge。   华为交换机的sysUpTime oid为.1.3.6.1.2.1.1.3.0,也可表示为iso.3.6.1.2.1.1.3.0

$ sudo snmpget -c public -v 2c 192.168.33.254 iso.3.6.1.2.1.1.3.0
iso.3.6.1.2.1.1.3.0 = Timeticks: (3422757479) 396 days, 3:39:34.79
 
   <Host "SW5328-3.dataSrv.4f">
       Address "192.168.33.254"
       Version 2
       Community "public"
       Collect "std_traffic"
       Collect "sysUpTime"
       Interval 60
   </Host>
   <Host "SW5328-4.dataSrv.4f">
       Address "192.168.55.254"
       Version 2
       Community "public"
       Collect "std_traffic"
       Collect "sysUpTime"
       Interval 60
   </Host>
   <Host "SW5328-1.dslab.2f">
       Address "192.168.66.254"
       Version 2
       Community "public"
       Collect "std_traffic"
       Collect "sysUpTime"
       Interval 60
   </Host>
   <Host "SW5328-2.dslab.2f">
       Address "192.168.88.254"
       Version 2
       Community "public"
       Collect "std_traffic"
       Collect "sysUpTime"
       Interval 60
   </Host>
</Plugin>

4.2 ping

默认情况下,collectd的interval是10s,所以在ping plugins中,interval必须小于10s,否则出不了图。

<Plugin ping>
        Host "192.168.8.99"
        Interval 5.0
        Timeout 0.9
        TTL 255
        SourceAddress "192.168.8.254"
        Device "eth4"
        MaxMissed -1
</Plugin>

4.3 libvirt

<Plugin libvirt>
       Connection "qemu:///system"
       RefreshInterval 60
       Domain "d6-64-unifi-ac"
#       BlockDevice "name:device"
#       InterfaceDevice "name:device"
       IgnoreSelected false
#       HostnameFormat name
</Plugin>

可以通过libvirt查看某个或多个domain,但是在visage-app中,domain的所有metric全部都显示在一张图中,很不方便,而且libvirt这个插件稳定性似乎不行,运行一段时间后会导致进程消失(崩溃?未能确认),通过ps aux | grep collectd找不到。

4.4 interface

LoadPlugin ping
<Plugin interface>
        Interface "eth0"   # oa outboud
        Interface "eth4"   # unifi ap
        Interface "br3"     # internet connection
        IgnoreSelected false
</Plugin>

4.5 chains

借用了iptables的概念,还没有深入研究,总之以下的配置可以将interface中的if_octets转换成bit,在两台主机之间,使用iperf来生成背景流量,然后通过visage-app观察,发现与iperf的结果一致。

LoadPlugin match_regex
LoadPlugin target_scale
<Chain "PreCache">
  <Rule "8timesForBits">
    <Match "regex">
      Plugin "interface"
      Type "if_octets"
    </Match>
    <Target "scale">
      Factor 8
    </Target>
  </Rule>
</Chain>

证明上面的配置是生效的,说明在centos6.5 + collectd 4.10中,match_regex和target_scale可正常工作。

5. web UI

5.1 visage

$ sudo yum -y install ruby rubygems ruby-devel rrdtool-ruby
$ sudo gem install visage-app

在启用visage之前,需要确保collectd正常工作,正常输出rrd,然后启动:

# RRDDIR=/usr/var/lib/collectd/rrd visage-app start

RRDDIR路径要完整,否则在create profile的时候无法显示host visage-app的问题是collectd plugin输出的rrd文件,需要显示在同一张图片中,使用起来很不方便。不过对付一两台服务器足以。

6. 排错

  1. no such file to load — RRD (LoadError)

    这是因为有安装rrdtool-ruby,我尝试了安装rrd-ffi,但是要求ruby1.9.3,费事装ruby,所以直接安装了rrdtool-ruby组件。

  2. 让图X轴的时间以local time显示

    # cd $(dirname $(gem which visage-app))/visage-app/public/javascripts
    # vi highcharts.js