Open reversefold opened 9 years ago
Can you provide more descriptions of the problem. I am not sure I understand.
For instance, I have a package that uses a python virtualenv. Part of the setup for the virtualenv is to create symlinks to system files inside of the virtualenv directory. It is definitely not intended for glu to remove the system files linked to by these symlinks when it uninstalls the package which includes the virtualenv.
In general, I think that following symlinks when deleting files is a bug and a violation of the principal of least surprise. On unix, symlinks are generally treated as files unless you explicitly treat them like a directory. For instance, if you do this:
{/tmp} $ mkdir test
{/tmp} $ touch test_file
{/tmp} $ cd test
{test} $ ln -s ../test_file .
{test} $ ls -al
total 8
drwxr-xr-x 3 jpatrin wheel 102 Jul 14 14:42 .
drwxrwxrwt 11 root wheel 374 Jul 14 14:41 ..
lrwxr-xr-x 1 jpatrin wheel 12 Jul 14 14:42 test_file -> ../test_file
{test} $ cd ..
{/tmp} $ rm -r test
{/tmp} $ ls -al test_file
-rw-r--r-- 1 jpatrin wheel 0 Jul 14 14:41 test_file
The symlink is removed, as if it is a file in the directory, but the target file is left unchanged. I would argue that this should always be the default when recursively deleting a directory as removing the target of a symlink could affect files outside of the directory. In the case we are running into, if we were (inadvisably) running glu as an inherently privileged user (such as root, or one with a group who had write to system files) then it would have removed system files which were not installed by glu.
This is a similar case to this: http://glu.977617.n3.nabble.com/Glu-uninstall-follows-symlinks-and-delete-files-outside-of-mountPoint-td4024877.html
What is happening is that justin is installing a package that has a lot of symlinks pointing to root owned files (Python's VirtualEnv is doing it). When uninstalling our groovy script is calling shell.exec('rm -rf $mountPoint')
when calling the uninstall step which works fine.
There is a case however where if the install step failed, after unpacking the archive with the symlinks, where the console consider (correctly) that the uninstall step should not be called and then the code in RootScript.groovy is calling shell.rmdirs(args.mountPoint)
which fails since that code follows symlinks and fails on the first root owned file.
We can't change the behavior of the package since it is using Python's VirtualEnv which symlinks to OS owned files a lot. This case should be rare yet we would need to have a way to handle it.
I propose 2 ways to handle this:
uninstall
(or destroyChild
) calls in RootScript.groovy
. Can we simply add a destroyChild
in our groovy script btw?agent.uninstall.follow.symlink=false
, with true as default for preserving existing behavior and change the RootScript.groovy code to not follow symlinks based on that option.Personally I think symlinks should not be followed on deletes by default since it indeeds differs from the standard *nix behavior but I respect the fact that you might want to preserve existing behavior by default.
I understand now. It was not obvious what the problem was from the original bug. I do agree that glu should not be deleting the target of symlinks. I am not sure who would be relying on this behavior but I can imagine it would be a non backward compatible change so there should definitely be an option to turn it on/off.
Removal of the symlink is sufficient and more correct as it follows the conventions of e.g. rm -r.