由于 macOS 正在积极阻止 UF_NOUNLINK Unix 标志,因此我正在考虑使用自制的 shell 脚本来实现与 ACL 类似的功能,即防止意外删除文件或目录,同时保留完全权限和访问权限,否则,读取、写入、执行、更改属性、更改 XA、更改所有者/组/权限等。我对 ACE 使用的命令如下:
chmod -h +a# 0 "group:$access_group deny delete" "$filepath"
我已经创建了一个特殊组($access_group
)dscl
,我只想将其用于这种访问控制,并且已将我的用户(501)添加到该组。
现在,基本功能可以正常工作:与uunlnk
Unix 标志不同,deny delete
ACE 阻止我移动或重命名文件 - 为什么?因为 ACL 不与 inode 绑定?- 但好消息是,我的 501 用户无法删除,因为它属于 所涵盖的特殊组的一部分deny delete
。
然而,问题是 ACL 现在也禁止文件修改,例如在 TextEdit 等中编辑文件:macOS 告诉我该文件据称被“锁定”,但事实并非如此,因为我可以在命令行上正常编辑该文件,例如使用echo "foo" >> bar
。
旁注:当我将命令修改为
chmod -h +a#0 "user:$(id -un) deny delete" "$filepath"
因此,我使用特殊组这一事实不会导致问题。但这种奇怪行为的原因可能是什么?这与 macOS 在 GUI 中保存文件的方式有关吗?还是必须以不同的方式创建 ACL?
答案1
TextEdit 和许多其他 macOS 程序使用原子写入来编辑文件。也就是说,它们将新文件内容写入临时文件,然后将临时文件重命名为原始文件(副作用是取消链接)。这样做是为了如果程序在写入新内容时崩溃,您不会留下损坏的半写文件。
这确实会产生一些奇怪的效果:编辑文件需要删除/取消链接权限(以及对文件所在目录的写入权限)。编辑后,文件将具有不同的 inode 编号(因为它是不同的文件,只是名称相同)。此外,新文件将归编辑它的用户所有,即使原始文件归其他人所有。
当 TextEdit 说文件“已锁定”时,这实际上只是意味着它无法编辑它。该文件可能已设置“已锁定”标志(又名 uchg),或者您可能没有对它的写权限(不是严格要求,但 TextEdit 很“礼貌”,会拒绝编辑无写权限的文件),或者没有对其目录的写权限,或者其他原因。
顺便问一下,你所说的 UF_NOUNLINK“被 macOS 主动阻止”是什么意思?文件系统在支持的属性方面各不相同,HFS+ 和 APFS 都不支持该标志。并非所有文件系统都支持。