Bladeren bron

unlinking symlinked directories and trailing slashes

Filesystem::removeDirectory() didn't detect all symlinked directories
properly due to not resolving pathnames with trailing slashes first.

this commit fixes that issue by resolving pathnames with trailing slashes
by removing those in case they are representing a symlinked directory.

#3144

Reference:

 A.4.12 Pathname Resolution - The Open Group Base Specifications Issue 7
 IEEE Std 1003.1, 2013 Edition Section
 <http://pubs.opengroup.org/onlinepubs/9699919799/xrat/V4_xbd_chap04.html>
hakre 10 jaren geleden
bovenliggende
commit
3e727850ff
1 gewijzigde bestanden met toevoegingen van 47 en 2 verwijderingen
  1. 47 2
      src/Composer/Util/Filesystem.php

+ 47 - 2
src/Composer/Util/Filesystem.php

@@ -95,8 +95,8 @@ class Filesystem
      */
     public function removeDirectory($directory)
     {
-        if (file_exists($directory) && is_link($directory)) {
-            return $this->unlink($directory);
+        if ($this->isSymlinkedDirectory($directory)) {
+            return $this->unlinkSymlinkedDirectory($directory);
         }
 
         if (!file_exists($directory) || !is_dir($directory)) {
@@ -491,4 +491,49 @@ class Filesystem
 
         return unlink($path);
     }
+
+    private function isSymlinkedDirectory($directory)
+    {
+        if (!is_dir($directory)) {
+            return false;
+        }
+
+        $resolved = $this->resolveSymlinkedDirectorySymlink($directory);
+
+        return is_link($resolved);
+    }
+
+    /**
+     * @param string $directory
+     *
+     * @return bool
+     */
+    private function unlinkSymlinkedDirectory($directory)
+    {
+        $resolved = $this->resolveSymlinkedDirectorySymlink($directory);
+
+        return $this->unlink($resolved);
+    }
+
+    /**
+     * resolve pathname to symbolic link of a directory
+     *
+     * @param string $pathname directory path to resolve
+     *
+     * @return string resolved path to symbolic link or original pathname (unresolved)
+     */
+    private function resolveSymlinkedDirectorySymlink($pathname)
+    {
+        if (!is_dir($pathname)) {
+            return $pathname;
+        }
+
+        $resolved = rtrim($pathname, '/');
+
+        if (!strlen($resolved)) {
+            return $pathname;
+        }
+
+        return $resolved;
+    }
 }