![如何防止“tar extract”更改当前目录的权限?](https://linux22.com/image/195731/%E5%A6%82%E4%BD%95%E9%98%B2%E6%AD%A2%E2%80%9Ctar%20extract%E2%80%9D%E6%9B%B4%E6%94%B9%E5%BD%93%E5%89%8D%E7%9B%AE%E5%BD%95%E7%9A%84%E6%9D%83%E9%99%90%EF%BC%9F.png)
在尝试使我的 tarball 可复制时,我遵循本指南。
作为副作用,我注意到我可以轻松创建一个 tar 文件,解压后将更改当前工作目录(我将文件提取到的位置)。
就像这样:
$ rm -rf /tmp/user
$ mkdir -p /tmp/user/test
$ touch /tmp/user/test/README.txt
$ ls -lhan /tmp/user/ /tmp/user/test/README.txt
-rw-r--r-- 1 11002 11002 0 Sep 15 10:31 /tmp/user/test/README.txt
/tmp/user/:
total 32K
drwxr-xr-x 3 11002 11002 4.0K Sep 15 10:31 .
drwxrwxrwt 23 0 0 20K Sep 15 10:31 ..
drwxr-xr-x 2 11002 11002 4.0K Sep 15 10:31 test
$ cd /tmp/user/test
$ tar --numeric-owner --owner=0 --group=0 --mode="go-rwx,u-w" --transform 's|\./|foobar/|' \
-czf ../foobar.tgz .
$ tar tvf ../foobar.tgz
dr-x------ 0/0 0 2021-09-15 10:25 ./
-r-------- 0/0 0 2021-09-15 10:25 foobar/README.txt
$ cd /tmp/user/
$ tar xvf foobar.tgz
$ ls -lhan
total 40K
dr-x------ 4 11002 11002 4.0K Sep 15 10:31 .
drwxrwxrwt 23 0 0 20K Sep 15 10:31 ..
drwxr-xr-x 2 11002 11002 4.0K Sep 15 10:33 foobar
-rw-r--r-- 1 11002 11002 143 Sep 15 10:32 foobar.tgz
drwxr-xr-x 2 11002 11002 4.0K Sep 15 10:31 test
$ rm foobar.tgz
rm: cannot remove 'foobar.tgz': Permission denied
$
那么发生的事情是:
- tar 文件包含一个
./
具有权限的条目0500
(又名r-x------
) - 提取 tar 文件时,它还会提取
./
目录(恰好是当前目录)并将其权限设置为存档中找到的权限 - 操作后,用户无法再从该目录中删除文件,其他人也无法再对其执行任何操作。
这是一个很大的惊喜。它可能会使系统对用户“无法使用”(例如,chmod a-rwx
在用户主目录上有效运行)。
当然,恢复权限很容易 - 如果您chmod
以前听说过(典型的 Ubuntu 用户可能没有听说过)和你记得之前的权限(我不能为自己说出这一点以及我将在其中提取 tarball 的任意目录)
所以我的问题是双重的:
- 我怎样才能防止
tar --extract
更改当前工作目录的权限,同时仍然保留其他档案中的文件? - 我怎样才能防止
tar --create
实际创建这样的存档(以便它也适用于不知道第一个问题答案的人),同时仍然预先考虑已知的路径组件)?
编辑
我可能已经找到了第二个问题的部分答案。
将路径修改更改为--transform 's|^\.|foobar|'
will还mangle 的./
条目foobar/
,然后将获得存档中声明的权限(并保留我当前的工作目录)。我想知道为什么--transform 's|\./|foobar/|'
会不是mangle ./
(看起来这与\./
正则表达式匹配得很好。
答案1
据我所知,.
在提取 tarball 时防止更改 的元数据的唯一方法是跳过现有文件,使用选项--skip-old-files
在 GNU 中可用tar
。这涵盖了以上内容.
并将导致任何现有文件按原样保留,而不是被 tarball 中的版本覆盖。
我不确定你为什么--transform
失败。提取时添加路径的推荐方法是将起始锚点“替换”为所需的目录,例如 tar --transform 's,^,foobar/,' ...
。为了避免弄乱符号链接,可以添加后缀,例如 tar --transform 's,^,foobar/,S'
这将不是将转换应用于符号链接目标。