Browse Source

Updates to path repository and path downloader, refs #4365

Jordi Boggiano 9 years ago
parent
commit
89c6a68a76

+ 8 - 10
src/Composer/Downloader/PathDownloader.php

@@ -30,21 +30,19 @@ class PathDownloader extends FileDownloader
     public function download(PackageInterface $package, $path)
     {
         $fileSystem = new Filesystem();
-        if ($fileSystem->exists($path)) {
-            $fileSystem->remove($path);
-        }
-
-        try {
-            $fileSystem->symlink($package->getDistUrl(), $path);
-        } catch (IOException $e) {
-            $fileSystem->mirror($package->getDistUrl(), $path);
-        }
+        $this->filesystem->removeDirectory($path);
 
         $this->io->writeError(sprintf(
-            '    Downloaded <info>%s</info> (<comment>%s</comment>) from %s',
+            '  - Installing <info>%s</info> (<comment>%s</comment>) from %s',
             $package->getName(),
             $package->getFullPrettyVersion(),
             $package->getDistUrl()
         ));
+
+        try {
+            $fileSystem->symlink($package->getDistUrl(), $path);
+        } catch (IOException $e) {
+            $fileSystem->mirror($package->getDistUrl(), $path);
+        }
     }
 }

+ 1 - 1
src/Composer/Factory.php

@@ -265,7 +265,7 @@ class Factory
 
         // load package
         $parser = new VersionParser;
-        $guesser = new VersionGuesser(new ProcessExecutor($io), $parser);
+        $guesser = new VersionGuesser($config, new ProcessExecutor($io), $parser);
         $loader  = new Package\Loader\RootPackageLoader($rm, $config, $parser, $guesser);
         $package = $loader->load($localConfig);
         $composer->setPackage($package);

+ 2 - 2
src/Composer/Package/Loader/RootPackageLoader.php

@@ -51,7 +51,7 @@ class RootPackageLoader extends ArrayLoader
 
         $this->manager = $manager;
         $this->config = $config;
-        $this->versionGuesser = $versionGuesser ?: new VersionGuesser(new ProcessExecutor(), $this->versionParser);
+        $this->versionGuesser = $versionGuesser ?: new VersionGuesser($config, new ProcessExecutor(), $this->versionParser);
     }
 
     public function load(array $config, $class = 'Composer\Package\RootPackage')
@@ -65,7 +65,7 @@ class RootPackageLoader extends ArrayLoader
             if (getenv('COMPOSER_ROOT_VERSION')) {
                 $version = getenv('COMPOSER_ROOT_VERSION');
             } else {
-                $version = $this->versionGuesser->guessVersion($this->config, $config);
+                $version = $this->versionGuesser->guessVersion($config, getcwd());
             }
 
             if (!$version) {

+ 35 - 32
src/Composer/Package/Version/VersionGuesser.php

@@ -27,6 +27,11 @@ use Composer\Util\Svn as SvnUtil;
  */
 class VersionGuesser
 {
+    /**
+     * @var Config
+     */
+    private $config;
+
     /**
      * @var ProcessExecutor
      */
@@ -38,45 +43,44 @@ class VersionGuesser
     private $versionParser;
 
     /**
-     * @var null|string
-     */
-    private $cwd;
-
-    /**
+     * @param Config          $config
      * @param ProcessExecutor $process
      * @param VersionParser   $versionParser
-     * @param string          $cwd
      */
-    public function __construct(ProcessExecutor $process, VersionParser $versionParser, $cwd = null)
+    public function __construct(Config $config, ProcessExecutor $process, VersionParser $versionParser)
     {
+        $this->config = $config;
         $this->process = $process;
         $this->versionParser = $versionParser;
-        $this->cwd = $cwd ?: getcwd();
     }
 
-    public function guessVersion(Config $config, array $packageConfig)
+    /**
+     * @param array  $packageConfig
+     * @param string $path Path to guess into
+     */
+    public function guessVersion(array $packageConfig, $path)
     {
         if (function_exists('proc_open')) {
-            $version = $this->guessGitVersion($packageConfig);
+            $version = $this->guessGitVersion($packageConfig, $path);
             if (null !== $version) {
                 return $version;
             }
 
-            $version = $this->guessHgVersion($config, $packageConfig);
+            $version = $this->guessHgVersion($packageConfig, $path);
             if (null !== $version) {
                 return $version;
             }
 
-            return $this->guessSvnVersion($packageConfig);
+            return $this->guessSvnVersion($packageConfig, $path);
         }
     }
 
-    private function guessGitVersion(array $config)
+    private function guessGitVersion(array $packageConfig, $path)
     {
         GitUtil::cleanEnv();
 
         // try to fetch current version from git tags
-        if (0 === $this->process->execute('git describe --exact-match --tags', $output, $this->cwd)) {
+        if (0 === $this->process->execute('git describe --exact-match --tags', $output, $path)) {
             try {
                 return $this->versionParser->normalize(trim($output));
             } catch (\Exception $e) {
@@ -84,7 +88,7 @@ class VersionGuesser
         }
 
         // try to fetch current version from git branch
-        if (0 === $this->process->execute('git branch --no-color --no-abbrev -v', $output, $this->cwd)) {
+        if (0 === $this->process->execute('git branch --no-color --no-abbrev -v', $output, $path)) {
             $branches = array();
             $isFeatureBranch = false;
             $version = null;
@@ -116,16 +120,16 @@ class VersionGuesser
             }
 
             // try to find the best (nearest) version branch to assume this feature's version
-            $version = $this->guessFeatureVersion($config, $version, $branches, 'git rev-list %candidate%..%branch%');
+            $version = $this->guessFeatureVersion($packageConfig, $version, $branches, 'git rev-list %candidate%..%branch%', $path);
 
             return $version;
         }
     }
 
-    private function guessHgVersion(Config $config, array $packageConfig)
+    private function guessHgVersion(array $packageConfig, $path)
     {
         // try to fetch current version from hg branch
-        if (0 === $this->process->execute('hg branch', $output, $this->cwd)) {
+        if (0 === $this->process->execute('hg branch', $output, $path)) {
             $branch = trim($output);
             $version = $this->versionParser->normalizeBranch($branch);
             $isFeatureBranch = 0 === strpos($version, 'dev-');
@@ -139,30 +143,29 @@ class VersionGuesser
             }
 
             // re-use the HgDriver to fetch branches (this properly includes bookmarks)
-            $packageConfig = array('url' => $this->cwd);
-            $driver = new HgDriver($packageConfig, new NullIO(), $config, $this->process);
+            $driver = new HgDriver(array('url' => $path), new NullIO(), $this->config, $this->process);
             $branches = array_keys($driver->getBranches());
 
             // try to find the best (nearest) version branch to assume this feature's version
-            $version = $this->guessFeatureVersion($config, $version, $branches, 'hg log -r "not ancestors(\'%candidate%\') and ancestors(\'%branch%\')" --template "{node}\\n"');
+            $version = $this->guessFeatureVersion($packageConfig, $version, $branches, 'hg log -r "not ancestors(\'%candidate%\') and ancestors(\'%branch%\')" --template "{node}\\n"', $path);
 
             return $version;
         }
     }
 
-    private function guessFeatureVersion(array $config, $version, array $branches, $scmCmdline)
+    private function guessFeatureVersion(array $packageConfig, $version, array $branches, $scmCmdline, $path)
     {
         // ignore feature branches if they have no branch-alias or self.version is used
         // and find the branch they came from to use as a version instead
-        if ((isset($config['extra']['branch-alias']) && !isset($config['extra']['branch-alias'][$version]))
-            || strpos(json_encode($config), '"self.version"')
+        if ((isset($packageConfig['extra']['branch-alias']) && !isset($packageConfig['extra']['branch-alias'][$version]))
+            || strpos(json_encode($packageConfig), '"self.version"')
         ) {
             $branch = preg_replace('{^dev-}', '', $version);
             $length = PHP_INT_MAX;
 
             $nonFeatureBranches = '';
-            if (!empty($config['non-feature-branches'])) {
-                $nonFeatureBranches = implode('|', $config['non-feature-branches']);
+            if (!empty($packageConfig['non-feature-branches'])) {
+                $nonFeatureBranches = implode('|', $packageConfig['non-feature-branches']);
             }
 
             foreach ($branches as $candidate) {
@@ -177,7 +180,7 @@ class VersionGuesser
                 }
 
                 $cmdLine = str_replace(array('%candidate%', '%branch%'), array($candidate, $branch), $scmCmdline);
-                if (0 !== $this->process->execute($cmdLine, $output, $this->cwd)) {
+                if (0 !== $this->process->execute($cmdLine, $output, $path)) {
                     continue;
                 }
 
@@ -194,15 +197,15 @@ class VersionGuesser
         return $version;
     }
 
-    private function guessSvnVersion(array $config)
+    private function guessSvnVersion(array $packageConfig, $path)
     {
         SvnUtil::cleanEnv();
 
         // try to fetch current version from svn
-        if (0 === $this->process->execute('svn info --xml', $output, $this->cwd)) {
-            $trunkPath = isset($config['trunk-path']) ? preg_quote($config['trunk-path'], '#') : 'trunk';
-            $branchesPath = isset($config['branches-path']) ? preg_quote($config['branches-path'], '#') : 'branches';
-            $tagsPath = isset($config['tags-path']) ? preg_quote($config['tags-path'], '#') : 'tags';
+        if (0 === $this->process->execute('svn info --xml', $output, $path)) {
+            $trunkPath = isset($packageConfig['trunk-path']) ? preg_quote($packageConfig['trunk-path'], '#') : 'trunk';
+            $branchesPath = isset($packageConfig['branches-path']) ? preg_quote($packageConfig['branches-path'], '#') : 'branches';
+            $tagsPath = isset($packageConfig['tags-path']) ? preg_quote($packageConfig['tags-path'], '#') : 'tags';
 
             $urlPattern = '#<url>.*/('.$trunkPath.'|('.$branchesPath.'|'. $tagsPath .')/(.*))</url>#';
 

+ 19 - 30
src/Composer/Repository/PathRepository.php

@@ -20,7 +20,6 @@ use Composer\Package\Loader\LoaderInterface;
 use Composer\Package\Version\VersionGuesser;
 use Composer\Package\Version\VersionParser;
 use Composer\Util\ProcessExecutor;
-use Symfony\Component\Filesystem\Filesystem;
 
 /**
  * This repository allows installing local packages that are not necessarily under their own VCS.
@@ -48,16 +47,6 @@ use Symfony\Component\Filesystem\Filesystem;
  */
 class PathRepository extends ArrayRepository
 {
-    /**
-     * @var Config
-     */
-    private $config;
-
-    /**
-     * @var Filesystem
-     */
-    private $fileSystem;
-
     /**
      * @var ArrayLoader
      */
@@ -69,51 +58,47 @@ class PathRepository extends ArrayRepository
     private $versionGuesser;
 
     /**
-     * @var array
+     * @var string
      */
-    private $packageConfig;
+    private $path;
 
     /**
-     * @var string
+     * @var ProcessExecutor
      */
-    private $path;
+    private $process;
 
     /**
      * Initializes path repository.
      *
-     * @param array $packageConfig
+     * @param array $repoConfig
      * @param IOInterface $io
      * @param Config $config
-     * @param LoaderInterface $loader
-     * @param Filesystem $filesystem
-     * @param VersionGuesser $versionGuesser
      */
-    public function __construct(array $packageConfig, IOInterface $io, Config $config, LoaderInterface $loader = null, Filesystem $filesystem = null, VersionGuesser $versionGuesser = null)
+    public function __construct(array $repoConfig, IOInterface $io, Config $config)
     {
-        if (!isset($packageConfig['url'])) {
+        if (!isset($repoConfig['url'])) {
             throw new \RuntimeException('You must specify the `url` configuration for the path repository');
         }
 
-        $this->fileSystem = $filesystem ?: new Filesystem();
-        $this->loader = $loader ?: new ArrayLoader();
-        $this->config = $config;
-        $this->packageConfig = $packageConfig;
-        $this->path = realpath(rtrim($packageConfig['url'], '/')) . '/';
-        $this->versionGuesser = $versionGuesser ?: new VersionGuesser(new ProcessExecutor($io), new VersionParser(), $this->path);
+        $this->loader = new ArrayLoader();
+        $this->path = realpath(rtrim($repoConfig['url'], '/')) . '/';
+        $this->process = new ProcessExecutor($io);
+        $this->versionGuesser = new VersionGuesser($config, $this->process, new VersionParser());
+
+        parent::__construct();
     }
 
     /**
      * Initializes path repository.
      *
      * This method will basically read the folder and add the found package.
-     *
      */
     protected function initialize()
     {
         parent::initialize();
 
         $composerFilePath = $this->path.'composer.json';
-        if (!$this->fileSystem->exists($composerFilePath)) {
+        if (!file_exists($composerFilePath)) {
             throw new \RuntimeException(sprintf('No `composer.json` file found in path repository "%s"', $this->path));
         }
 
@@ -122,10 +107,14 @@ class PathRepository extends ArrayRepository
         $package['dist'] = array(
             'type' => 'path',
             'url' => $this->path,
+            'reference' => '',
         );
 
         if (!isset($package['version'])) {
-            $package['version'] = $this->versionGuesser->guessVersion($this->config, $this->packageConfig) ?: 'dev-master';
+            $package['version'] = $this->versionGuesser->guessVersion($package, $this->path) ?: 'dev-master';
+        }
+        if (is_dir($this->path.'/.git') && 0 === $this->process->execute('git log -n1 --pretty=%H', $output, $this->path)) {
+            $package['dist']['reference'] = trim($output);
         }
 
         $package = $this->loader->load($package);

+ 3 - 3
tests/Composer/Test/Package/Loader/RootPackageLoaderTest.php

@@ -76,7 +76,7 @@ class RootPackageLoaderTest extends \PHPUnit_Framework_TestCase
 
         $config = new Config;
         $config->merge(array('repositories' => array('packagist' => false)));
-        $loader = new RootPackageLoader($manager, $config, null, new VersionGuesser($executor, new VersionParser()));
+        $loader = new RootPackageLoader($manager, $config, null, new VersionGuesser($config, $executor, new VersionParser()));
         $package = $loader->load(array());
 
         $this->assertEquals("1.0.0.0", $package->getVersion());
@@ -139,7 +139,7 @@ class RootPackageLoaderTest extends \PHPUnit_Framework_TestCase
 
         $config = new Config;
         $config->merge(array('repositories' => array('packagist' => false)));
-        $loader = new RootPackageLoader($manager, $config, null, new VersionGuesser($executor, new VersionParser()));
+        $loader = new RootPackageLoader($manager, $config, null, new VersionGuesser($config, $executor, new VersionParser()));
         $package = $loader->load(array('require' => array('foo/bar' => 'self.version')));
 
         $this->assertEquals("dev-master", $package->getPrettyVersion());
@@ -188,7 +188,7 @@ class RootPackageLoaderTest extends \PHPUnit_Framework_TestCase
 
         $config = new Config;
         $config->merge(array('repositories' => array('packagist' => false)));
-        $loader = new RootPackageLoader($manager, $config, null, new VersionGuesser($executor, new VersionParser()));
+        $loader = new RootPackageLoader($manager, $config, null, new VersionGuesser($config, $executor, new VersionParser()));
         $package = $loader->load(array('require' => array('foo/bar' => 'self.version'), "non-feature-branches" => array("latest-.*")));
 
         $this->assertEquals("dev-latest-production", $package->getPrettyVersion());

+ 6 - 6
tests/Composer/Test/Package/Version/VersionGuesserTest.php

@@ -58,8 +58,8 @@ class VersionGuesserTest extends \PHPUnit_Framework_TestCase
 
         $config = new Config;
         $config->merge(array('repositories' => array('packagist' => false)));
-        $guesser = new VersionGuesser($executor, new VersionParser());
-        $version = $guesser->guessVersion($config, array());
+        $guesser = new VersionGuesser($config, $executor, new VersionParser());
+        $version = $guesser->guessVersion(array(), 'dummy/path');
 
         $this->assertEquals("dev-$commitHash", $version);
     }
@@ -88,8 +88,8 @@ class VersionGuesserTest extends \PHPUnit_Framework_TestCase
 
         $config = new Config;
         $config->merge(array('repositories' => array('packagist' => false)));
-        $guesser = new VersionGuesser($executor, new VersionParser());
-        $version = $guesser->guessVersion($config, array());
+        $guesser = new VersionGuesser($config, $executor, new VersionParser());
+        $version = $guesser->guessVersion(array(), 'dummy/path');
 
         $this->assertEquals("2.0.5.0-alpha2", $version);
     }
@@ -129,8 +129,8 @@ class VersionGuesserTest extends \PHPUnit_Framework_TestCase
 
         $config = new Config;
         $config->merge(array('repositories' => array('packagist' => false)));
-        $guesser = new VersionGuesser($executor, new VersionParser());
-        $version = $guesser->guessVersion($config, array());
+        $guesser = new VersionGuesser($config, $executor, new VersionParser());
+        $version = $guesser->guessVersion(array(), 'dummy/path');
 
         $this->assertEquals("dev-foo", $version);
     }