Browse Source

Add RepositoryInterface::filterPackages to stream ops on lists

This cuts down on memory usage and also speeds up the search command to a third of its previous time
Jordi Boggiano 12 years ago
parent
commit
e3b6bd781c

+ 14 - 0
src/Composer/Repository/ArrayRepository.php

@@ -112,6 +112,20 @@ class ArrayRepository implements RepositoryInterface
         }
     }
 
+    /**
+     * {@inheritDoc}
+     */
+    public function filterPackages($callback, $class = 'Composer\Package\Package')
+    {
+        foreach ($this->getPackages() as $package) {
+            if (false === $callback($package)) {
+                return false;
+            }
+        }
+
+        return true;
+    }
+
     protected function createAliasPackage(PackageInterface $package, $alias = null, $prettyAlias = null)
     {
         return new AliasPackage($package, $alias ?: $package->getAlias(), $prettyAlias ?: $package->getPrettyAlias());

+ 22 - 1
src/Composer/Repository/ComposerRepository.php

@@ -122,6 +122,27 @@ class ComposerRepository extends ArrayRepository implements NotifiableRepository
         return $this->minimalPackages;
     }
 
+    /**
+     * {@inheritDoc}
+     */
+    public function filterPackages($callback, $class = 'Composer\Package\Package')
+    {
+        $repoData = $this->loadDataFromServer();
+
+        foreach ($repoData as $package) {
+            if (false === $callback($package = $this->loader->load($package, $class))) {
+                return false;
+            }
+            if ($package->getAlias()) {
+                if (false === $callback($this->createAliasPackage($package))) {
+                    return false;
+                }
+            }
+        }
+
+        return true;
+    }
+
     /**
      * {@inheritDoc}
      */
@@ -154,7 +175,7 @@ class ComposerRepository extends ArrayRepository implements NotifiableRepository
         $repoData = $this->loadDataFromServer();
 
         foreach ($repoData as $package) {
-            $this->addPackage($this->loader->load($package, 'Composer\Package\Package'));
+            $this->addPackage($this->loader->load($package, 'Composer\Package\CompletePackage'));
         }
     }
 

+ 14 - 0
src/Composer/Repository/CompositeRepository.php

@@ -91,6 +91,20 @@ class CompositeRepository implements RepositoryInterface
         return call_user_func_array('array_merge', $packages);
     }
 
+    /**
+     * {@inheritDoc}
+     */
+    public function filterPackages($callback, $class = 'Composer\Package\Package')
+    {
+        foreach ($this->repositories as $repository) {
+            if (false === $repository->filterPackages($callback, $class)) {
+                return false;
+            }
+        }
+
+        return true;
+    }
+
     /**
      * {@inheritdoc}
      */

+ 14 - 0
src/Composer/Repository/RepositoryInterface.php

@@ -51,6 +51,20 @@ interface RepositoryInterface extends \Countable
      */
     public function findPackages($name, $version = null);
 
+    /**
+     * Filters all the packages throuhg a callback
+     *
+     * The packages are not guaranteed to be instances in the repository
+     * and this can only be used for streaming through a list of packages.
+     *
+     * If the callback returns false, the process stops
+     *
+     * @param callable $callback
+     * @param string   $class
+     * @return bool false if the process was interrupted, true otherwise
+     */
+    public function filterPackages($callback, $class = 'Composer\Package\Package');
+
     /**
      * Returns list of registered packages.
      *