inotify

Linux内核从2.6.13开始,引入了inotify机制。

通过intofity机制,能够对文件系统的变化进行监控,如对文件进行创建、删除、修改等操作,可以及时通知应用程序进行相关事件的处理。

这种响应处理机制,避免了频繁的文件轮询任务,提高了任务的处理效率。

 
 
一、检查安装
检查系统内核版本


# uname -a  


检查系统是否支持inotify


复制代码
# ls -lsart /proc/sys/fs/inotify  
total 0  
0 dr-xr-xr-x 0 root root 0 Sep 19 09:38 ..  
0 -rw-r--r-- 1 root root 0 Jan  1 13:51 max_user_watches  
0 -rw-r--r-- 1 root root 0 Jan  1 13:51 max_user_instances  
0 -rw-r--r-- 1 root root 0 Jan  1 13:51 max_queued_events  
0 dr-xr-xr-x 0 root root 0 Jan  1 13:51 .  

如果出现上面结果说明系统支持inotify
 
notify是一个API,需要通过开发应用程序进行调用,对于大多数用户来讲这有着许多不便,inotify-tools的出现弥补了这一不足。
inotify-tools是一套组件,它包括一个C库和几个命令行工具,这些命令行工具可用于通过命令行或脚本对某文件系统的事件进行监控。
 
下载安装
#wget http://github.com/downloads/rvoicilas/inotify-tools/inotify-tools-3.14.tar.gz  
  
# tar -zvxf inotify-tools-3.14.tar.gz  
# cd inotify-tools-3.14  
  
[root@ inotify-tools-3.14]
# ./configure --prefix=/usr/local/inotify  
[root@ inotify-tools-3.14]
# make  
[root@ inotify-tools-3.14]
# make install  

  
或者使用yum
yum install inotify-tools



其它的一些notify工具(参考)
inotify 的实现有几款软件
1)inotify-tools,
2)sersync(金山周洋)
3)lsyncd
 
二、命令讲解
inotify-tools提供的两个命令行工具:
inotifywait:通过inotify API等待被监控文件上的相应事件并返回监控结果
                   默认情况下,正常的结果返回至标准输出,
                   诊断类的信息则返回至标准错误输出。
                   它可以在监控到对应监控对象上指定的事件后退出,也可以进行持续性的监控。
inotifywatch:通过inotify API收集被监控文件或目录的相关事件并输出统计信息。


1.inotifywait:
常用参数: 
-m  --monitor     始终保持监听状态;默认触发事件即退出。
-r    --recursive  递归查询目录 

-q|--quiet Print less (only print events). 只打印出监控事件
-qq Print nothing (not even events).  静默输出

-o|--outfile <file>   Print events to <file> rather than stdout. 输出文件
-s|--syslog            Send errors to syslog rather than stderr. 输出错误日志



–-format       指定输出格式。
%w 表示发生事件的目录
%f 表示发生事件的文件
%e 表示发生的事件
%Xe 事件以“X”分隔,输出事件逗号分割会变为X分隔,使用*作为各项目字段的分割符
–-timefmt     指定时间格式,用于–format选项中的%T格式。%y年 %m月 %d日 %H小时 %M分钟 
%T 使用由–timefmt定义的时间格式


 

-e --event     定义监控的事件,省略此选项项即监控所有事件
可用参数:

Events:
access          file or directory contents were read         文件或目录读取
modify           file or directory contents were written     文件或目录更改
attrib              file or directory attributes changed          文件或目录属性更改
close_write    file or directory closed, after being opened in                 以只读模式打开的文件或目录被关闭
                      writeable mode
close_nowrite    file or directory closed, after being opened in             以只读模式打开的文件或目录被关闭
                          read-only mode
close             file or directory closed, regardless of read/write mode      文件或目录被关闭,不管它是如何打开的
open              file or directory opened                                                      文件或目录被打开  
moved_to       file or directory moved to watched directory       文件或目录被移入监听目录 即使是在同一目录内移动,此事件也触发
moved_from   file or directory moved from watched directory   移除监听目录中的文件或目录 即使是在同一目录内移动,此事件也触发
move             file or directory moved to or from watched directory   文件或目录发生移动 包括moved_to和 moved_from
create           file or directory created within watched directory        文件或目录被创建 
delete           file or directory deleted within watched directory         文件或目录被删除
delete_self    file or directory was deleted                                      文件或目录移除,之后不再监听此文件或目录
unmount       file system containing file or directory unmounted     文件或目录被卸载
 

监控信息汇总 

 

 

 

 

 

 

 

 

 


做个小实验,监控一个目录 
# inotifywait -rm ./test

在另一个终端对目录进行操作
# touch /root/test/abc
# rm /root/test/abc  

第一个终端显示的 状态改变
# inotifywait -rm ./test
Setting up watches.  Beware: since -r was given, this may take a 
while
!
Watches established.
.
/test/
 
CREATE abc
.
/test/
 
OPEN abc
.
/test/
 
ATTRIB abc
.
/test/
 
CLOSE_WRITE,CLOSE abc
.
/test/
 
OPEN,ISDIR
.
/test/
 
CLOSE_NOWRITE,CLOSE,ISDIR
.
/test/
 
OPEN,ISDIR
.
/test/
 
CLOSE_NOWRITE,CLOSE,ISDIR
.
/test/
 
DELETE abc


  
 2.inotifywatch:
inotifywatch [-hvzrqf] [-e ] [-t ] [-a ] [-d ] [ ... ]


参数:
-h,–help          # 输出帮助信息
-v,–verbose    # 输出详细信息
@                      # 排除不需要监视的文件,可以是相对路径,也可以是绝对路径。
–fromfile            # 从文件读取需要监视的文件或排除的文件,一个文件一行,排除的文件以@开头。
-z,–zero          # 输出表格的行和列,即使元素为空
–exclude            # 正则匹配需要排除的文件,大小写敏感。
–excludei           # 正则匹配需要排除的文件,忽略大小写。
-r,–recursive    # 监视一个目录下的所有子目录。
-t,–timeout        # 设置超时时间
-e,–event          # 只监听指定的事件。  监听事件同上
-a,–ascending     # 以指定事件升序排列。
-d,–descending       # 以指定事件降序排列


同样做个实验,统计 /home 目录发生事件的次数
# inotifywatch -v -e create -e modify -e delete -t 30 -r /home 

在新打开的终端上,创建了4个文件,修改了3个文件内容,删除了一个文件。
等监控的30秒时间到了之后,他就会显示出上面的事件次数报告!
# inotifywatch -v -e create -e modify -e delete -t 30 -r /home
Establishing watches...
Setting up 
watch
(es) on 
/home
OK, 
/home
 
is now being watched.
Total of 3 watches.
Finished establishing watches, now collecting statistics.
Will listen 
for
 
events 
for
 
60 seconds.
total  modify  create  delete  filename
8       3        4       1     
/home/


  
 
三、实际操作
以下为生产环境 使用脚本:
监控源目标文件,发生变化立刻同步


#!/bin/sh
SRC=/var/www/channel/
DST=/var/www/webroot/channel/
INWT=/usr/local/bin/inotifywait
RSYNC=/usr/bin/rsync
$INWT -mrq -e create,move,delete,modify $SRC | while  read  D E F;
do
  rsync  -aHqzt $SRC $DST
done


  inotifywait 产生的数据
# inotifywait -mrq -e create,move,delete,modify ./test/
./test/ DELETE abc
目录    事件 文件名    
分别写进 D E F变量里,一旦有变量写入立即执行 同步操作 

 




一个复杂的脚本
按照事件类型 分格式写入日志


复制代码
#!/bin/bash
inotifywait -mrq --timefmt '%y/%m/%d %H:%M' --format  '%T %w%f %e' --event delete,modify,create,attrib  /data/web | while read  date time file event
  do
      case $event in
          MODIFY|CREATE|MOVE|MODIFY,ISDIR|CREATE,ISDIR|MODIFY,ISDIR)
                  echo $event'-'$file'-'$date'-'$time >> /var/log/web_watch.log
              ;;
   
          MOVED_FROM|MOVED_FROM,ISDIR|DELETE|DELETE,ISDIR)
                  echo $event'-'$file'-'$date'-'$time /var/log/web_watch.log
              ;;
      esac
  done




inotifywait 产生的数据
# inotifywait -mrq --timefmt '%y/%m/%d %H:%M' --format '%T %w%f %e' --event delete,modify,create,attrib ./test/
17/10/10 17:31 ./test/abc CREATE
17/10/10 17:31 ./test/abc ATTRIB

 



四、inotify 系统参数 优化

在/proc/sys/fs/inotify目录下有三个文件,对inotify机制有一定的限制,
可以增加数值以提高性能


max_queued_events    :设置inotify实例事件(event)队列可容纳的事件数量。
                                               如果值太小,会出现"** Event Queue Overflow **"错误,导致监控文件不准确

max_user_instances   :设置每个用户可以运行的inotifywait或inotifywatch命令的进程数
max_user_watches     :设置inotify命令可以监视的目录数量(单进程)
                                     如果报错  upper limit on inotify watches reached! 即是这个原因
                                     可以用:find /xxx -type d | wc -l 统计,必须保证max_user_watches值大于统计结果


查看参数值:

[root@test01 inotify]# ls
max_queued_events  max_user_instances  max_user_watches
[root@test01 inotify]# cat * 
16384    128       8192 

也可用以下命令查看结果:
# sysctl -a | grep max_queued_events 


修改方法:

1.直接使用vi 修改数值报错  E667: Fsync failed  无法保存!!
缓存的原因?? 网上也没有明确答案……

网上解决办法  echo 32767 > ./max_queued_events      

 

  2.

若第一种方法不生效,参考以下命令
 
sysctl -w fs.inotify.max_queued_events="32767"
 
sysctl -w fs.inotify.max_user_watches="32767"
 
sysctl -w fs.inotify.max_user_instances="81900"
 

3.若还不生效,最终修改方法
 
vi /etc/sysctl.conf   #添加以下代码
 
fs.inotify.max_queued_events=32767
 
fs.inotify.max_user_watches=32767
 
fs.inotify.max_user_instances=65535
 
wq!   #保存退出

 



五、inotify+rsync
Rsync(remote sync)远程同步工具,通过rsync可以实现对远程服务器数据的增量备份同步,但rsync自身也有瓶颈,同步数据时,rsync采用核心算法对远程服务器的目标文件进行比对,只进行差异同步。
我们可以想象一下,如果服务器的文件数量达到了百万甚至千万量级,那么文件对比将是非常耗时的。而且发生变化的往往是其中很少的一部分,这是非常低效的方式。
inotify的出现,可以缓解rsync不足之处,取长补短
 
 


 
 
 


 

posted @ 2017-10-11 09:49  乌托邦眺望  阅读(2802)  评论(0编辑  收藏  举报