教学之友,学习之友。

站长教学网

当前位置: 站长教学网 > 电脑教学 > 软件 >

rsync参数filter过滤规则详解

时间:2013-12-24 14:41来源:未知 作者:ken 点击:

关于rsync参数filter的过滤规则:
译者注:这部分其实是man page中关于client的过滤规则的条目!不过,我把daemon中的过滤规则也集合到了里,两部分对比着进行理解。
关于pattern和rule,个人理解是:pattern是用来匹配文件或目录的正则,而rule则是前缀+pattern,也即整条规则。如:
+ foo/
+ foo/bar.c
- *
这是三条规则(rule),规则开头的”+”或”-“是前缀,foo/等前缀后面的东西即pattern(模式)。

下面是正文:
首先,来看rsyncd.conf官方文档在filter部分的描述(daemon上的过滤规则):
daemon拥有自己的过滤链,来决定哪些文件允许被client访问。这个过滤链不会被发送到client,并且独立于client中已经指定的过滤规则。
当client拉文件时,那些被daemon过滤链排除的文件会被视为不存在;而当client往server推送文件时,会跳过那些被daemon过滤链排除的文件,并且server会返回client一个错误消息;(当同步文件时)被daemon过滤链排除的文件永远不会从模块中删除。
daemon过滤链由”filter”、”include from”、”include”、”exclude from”、”exclude”参数组成,并以此为先后(生效)顺序。
(译者注:关于规则的生效顺序,应该是最先匹配。rsyncd.conf文档明确指出include规则可以覆盖掉exclude规则,照此理解,如果发生冲突,后面的规则应该不会覆盖掉前面的规则。下面filter rules部分也提到,最先匹配的模式会生效,但是在include/exclude pattern rules部分也提到一个特殊例子,在排除父目录,特别是使用*号匹配来排除父目录时,有些地方需要特别留意。
条目中还有一句话:Anchored patterns are anchored at the root of the module.大意似乎是:锚点模式标记的是模块根目录。下面还会有提到Anchored pattern。)

要阻止对整个目录的访问,必须排除该目录下的所有文件,最简单的方法是使用三个星号,如,想要阻止访问/secret,过滤规则就应该这样写:/secret/***

再来看rsync的man page对过滤规则的描述(client中的过滤规则),这部分内容很多,由FILTER RULES条目开始,包括了条目:INCLUDE/EXCLUDE PATTERN RULES、MERGE-FILE FILTER RULES、MERGE-FILE FILTER RULES、ANCHORING INCLUDE/EXCLUDE PATTERNS等。

filter rules:
filter规则允许选择传输哪些文件(include),跳过哪些文件(exclude)。filter规则既可以直接指定include/exclude模式,也可以指定一个获取include/exclude模式的途径(如从一个文件中读取)。
当建立了要传输的文件/目录列表后,rsync会依次核查它们是否符合include/exclude模式,匹配到的第一个模式会生效:如果符合exclude模式,则跳过该文件,如果符合include模式,不跳过该,如果不符合任何模式,文件也不会被跳过。
rsync按照命令行中filter规则顺序建立一个有序列表。filter规则的语法如下:
rule [pattern_or_filename]
rule,modfiers [pattern_or_filename]
可以使用完整规则名称,也可以使用简写名称,可用的规则前缀如下:
exclude, - :排除模式
include, + :包含模式
merge, . :指定一个merge-file,供多个规则读取
dir-merge, : :指定一个per-directory merge-file
hide, H :指定一个模式,符合该模式的文件将被隐藏,以防止传输
show, S :不隐藏符合该模式的文件
protect, p :指定一个模式来防止文件被删除
risk, R :符合该模式的文件不会被保护
clear, ! :清除当前的include/exclude模式列表(该选项无参数)
注:关于merge-file和per-directory,见下文。
如果使用简写形式,前面语法中rule和modefiers之间的逗号是可选的,紧跟着的pattern或filename(如果存在)之后必须有一个空格或下划线。
如果规则是从文件中读取的,那么文件中的空白行将被忽略,以#开头的行被视为注释。
注意:--include/--exclude命令行中的选项,不能完全依照上面filter规则的解释。--include/--exclude命令只允许使用指明的include/exclude模式加”!”标识(即:模式+标识)来清除(译者注:排除或许更准确)(文件或目录)列表。如果模式不以”- “(两个字符:减号和空格)或”+ “(两个字符:加号和空格)开头,那么,对于包含选项而言,规则将被解释为字符串前添加了”+”前缀;对于排除选项而言,规则将被解释为字符串前添加了”-“前缀。与之相反,--filter选项必须在规则开头包含一个简写或完整的规则名称。
另外要注意的是,每个--filter选项,--include选项,和--exclude选项只接受一个rule/pattern,如果想添加多个rule/pattern,可以在命令行中的重复这些选项,或在--filter选项中使用merge-file语法,或使用--include-from/--exclude-from选项。

include/exclude pattern ruls:
注:rsync的man page说,--include和--exclude是--filter选项的简化版。站长教学网 eduyo.com
你可以使用”+”、”-“等filter过滤规则来指定模式,用以包含和排除文件。每个include/exclude规则指定一个模式来匹配传输文件。模式可以有以下几种形式:
1)如果”/”出现在模式的开头,那么它标记了层级中的一个特殊位置(译者注:指的应该是文件系统的位置或完整路径的层次结构中的某一层次),否则,它只是匹配路径的结束。(译者注:这里又出现了anchor,计算机术语称之为锚点,它设置一个标记,然后可以在本文档或页面的其它地方创建一个指向本标记的链接:锚点,标记了一个特定位置。)因此,”/foo”将匹配”root of the transfer”中的foo(对全局规则而言),或者merge-file目录中的foo(对per-directory规则而言)。而未经限定的foo将匹配文件系统中任何位置的foo,因为算法是自上而下递归地生效,就像是路径的每个部分轮流变成文件或目录的结尾(译者注:例如foo/a/b/c,算法对该路径的解释将会是foo/a,foo/a/b,foo/a/b/c,算法依次把a、b、c作为文件或目录结尾)。实际上,非锚定的”sub/foo”将会匹配层次结构中包含子目录sub的,任何位置的foo。
2)如果”/”出现在模式的结尾,那么它只匹配目录,而不匹配常规文件、链接,或设备。
3)rsync会检查模式中是否包含下列通配符,以确定做简单的字符匹配还是通配符匹配:”*”、”?”、”[“
* :匹配路径的任何部分,遇到斜杠终止
** :匹配任何东西,包括斜杠
? :匹配任何单个字符,斜杠(“/”)除外
[ :匹配一个字符集,如[a-z],或[[:alpha:]]
4)在通配符模式中,反斜杠(“\”)对通配符进行转义,如果通配符不存在,它会被解释一个普通字符
5)如果模式包含”/”(尾部的”/”不计算在内)或”**”,它将匹配完整路径,包括前导目录(即foo/a,既匹配a,也匹配前导的foo);如果模式不包含”/”或”**”,它只匹配路径最后的部分。(注意:算法是递归地应用,所以实际上“完整路径”可能是从起始目录向下,路径的任何一个部分。)
6)以dir_name/***结尾的模式,既匹配目录(就像指定了dir_name/),又匹配目录中的所有文件(就像指定了dir_name/**)。
请注意:如果使用了-r选项(-a选项隐含了此选项),那么,自顶向下,路径的每一个部分都将被访问,所以,include/exclude模式会递归地对路径的每个组成部分生效(如,要包含/foo/bar/baz,就不能排除/foo和/foo/bar)。当rsync寻找要发送的文件时,exclude模式实际上是rsync在历遍目录时的一个短路。如果一个模式排除了特定的父目录,它就能使一个更深的include模式无法生效,因为rsync无法穿过层级中的排除部分而向下(匹配文件)。(译者注:意思应该是,如果模式排除一个指定的父目录,那么它将无法继续匹配该父目录下的子目录或文件。)这一点非常重要,尤其是使用一个以”*”结尾的规则时。如下:
+ /some/path/this-file-will-not-be-found
+ /file-is-included
- *
上述规则链将无法得到你想要的结果,因为父目录some被”*”规则排除了,所以rsync不会去访问some或some/path目录下的任何文件。要解决这个问题,可以使用一个”+ */”规则来包含层级的所有目录(把它放到”- *”前面的任意位置),或许还需要--prune-empty-dirs选项。另外一个解决途径是,添加一个include规则来包含所有需要被访问的父目录。下例的规则集就可以很好的工作:
+ /some/
+ /some/path/
+ /some/path/this-file-is-found
+ /file-also-included
- *
(译者注:
1)不知道大家是否理解了上面的官方示例。第一个例子本想包含两个文件,但结果只包含到了一个。文件this-file-will-not-be-found没有被包含的原因在于:基于最先匹配原则,文件本身被include规则所匹配,但其父目录以及爷爷目录并没有被include规则所匹配,所以它们被后面的exclude规则所匹配,而由于rsync不能穿过被exclude规则排除的父目录而匹配其中的文件,所以该文件最终将无法出现在匹配结果中。
这一过程有三个关键:一是rsync无法穿过被排除的父目录而向下匹配文件;二是*匹配路径任一部分,遇/终止匹配;三是最先匹配。
2)关于--prune-empty-dirs(简写模式为-m):这个命令行中的选项告诉rsync的接收方从文件列表中删除空目录,包括那些没有非空子目录的嵌套目录。这个选项很有用,当rsync的发送方使用include/exclude/filter规则扫描具有多层次结构的文件时,它可以避免(接收方)创建一系列无用的目录。)

下面是一些exclude/include匹配的示例:
- *.o:排除所有以o结尾的文件
- /foo:排除transfer-root目录中,名为foo的文件或目录
(译者注:前面也提到了transfer-root,这个概念会在ANCHORING INCLUDE/EXCLUDE PATTERNS条目中讲到,举例来说明,有一个路径/home/me/foo/bar:
rsync -a - /me/foo/bar /home/me /dest
rsync -a - /foo/bar /home/me/ /dest
上述规则要复制/home/me目录及其下所有文件到/dest,但要排除/me/foo/bar文件(或目录)。两条规则的效果是一样的,但是transfer-root不同。第一条规则中,/home目录就是transfer-root;而对于第二条规则,/home/me/才是transfer-root。也就是说,transfer-root是从路径的最末位向前追溯,遇到的第一个以"/"结尾的目录。)
- foo/:排除任何名为foo的目录
- /foo/*/bar:从transfer-root中的foo目录向下两级的位置,排除名为bar的文件。
- /foo/**/bar:从transfer-root中的foo目录向下至少两级的位置,排除名为bar的文件。
+ */c,+ *.c,和- *的组合,会包含所有目录,以及以c结尾的文件,除此之外,所有文件都排除。
+ /foo/,+ foo/bar.c,和- *的组合,将只包含foo目录,以及foo/bar.c文件。(必须明确包含foo目录,否则它将被exclude规则中的*所匹配,这会导致前面所讲到的排除特定父目录的问题,将无法如你所愿匹配到foo/bar.c文件。)

"+"或"-"接受下列修饰符:
/,指定include/exclude规则要匹配当前项目的绝对路径。例如,-/ /etc/passwd,每当从/etc目录中传输文件时,都要排除密码文件;再比如,-/ subdir/foo,当从名为subdir的目录中传输文件时,总是排除文件foo,即使该文件位于当前传输的根目录。
译者注:不要混淆匹配模式中的/和修饰符/ !
!,告诉rsync,当模式匹配失败时,include/exclude规则才生效。如,-! */,它将匹配所有非目录文件。
C,该修饰符指示,所有全局的CVS-exclude规则将插入到-C的地方。该修饰符后面无参数。(译者注:文档在介绍-C --cvs-exclude选项时说,如果在自己的--filter规则中同时使用-C,那么所有的CVS exclude规则将附加到你自己的规则的末尾,不管-C位于命令行的什么地方。)
s,指示规则作用于发送端。当规则对发送端生效时,它将阻止文件被传输。该修饰符通常用于那些在两端都生效的规则,除非指定了--delete-excluded;它将使规则默认只在发送端生效。另一种指定发送端includes/excludes的途经是使用hide(H)和show(S)。
r,通常用来指示规则应用于接收端。当规则对接收方生效时,它将防止文件被删除。另一种指定接收端includes/excludes的方法是,使用protect(P)和risk(R)规则。

(责任编辑:ken)
TAG标签: Rsync filter
顶一下
(0)
0%
踩一下
(0)
0%
------分隔线----------------------------
发表评论
请自觉遵守互联网相关的政策法规,严禁发布色情、暴力、反动的言论。
评价:
表情:
注册登录:不允许匿名留言,登录后留言无需输入验证码。
栏目列表
最新内容