Skip to content

Commit 7fd55b6

Browse files
committed
feature #378 Removing legacy tags significantly reduces memory and CPU usage (nicolas-grekas)
This PR was merged into the 1.0-dev branch. Discussion ---------- Removing legacy tags significantly reduces memory and CPU usage Before: > Memory usage: 272.59MB (peak: 606.6MB), time: 5.79s After: > Memory usage: 145.56MB (peak: 158.56MB), time: 1.86s Commits ------- 990b2d1 Removing legacy tags significantly reduces memory and CPU usage
2 parents 5e6b06e + 990b2d1 commit 7fd55b6

File tree

4 files changed

+92
-3
lines changed

4 files changed

+92
-3
lines changed

src/Cache.php

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <[email protected]>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Flex;
13+
14+
use Composer\Cache as BaseCache;
15+
16+
/**
17+
* @author Nicolas Grekas <[email protected]>
18+
*/
19+
class Cache extends BaseCache
20+
{
21+
private static $lowestTags = [
22+
'symfony/symfony' => 'v3.4.0',
23+
];
24+
25+
public function read($file)
26+
{
27+
$content = parent::read($file);
28+
29+
if (0 === strpos($file, 'provider-symfony$')) {
30+
$content = json_encode($this->removeLegacyTags(json_decode($content, true)));
31+
}
32+
33+
return $content;
34+
}
35+
36+
public function removeLegacyTags(array $data): array
37+
{
38+
foreach (self::$lowestTags as $package => $lowestVersion) {
39+
if (!isset($data['packages'][$package][$lowestVersion])) {
40+
continue;
41+
}
42+
foreach ($data['packages'] as $package => $versions) {
43+
foreach ($versions as $version => $composerJson) {
44+
if (version_compare($version, $lowestVersion, '<')) {
45+
unset($data['packages'][$package][$version]);
46+
}
47+
}
48+
}
49+
break;
50+
}
51+
52+
return $data;
53+
}
54+
}

src/ComposerRepository.php

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,11 @@
1111

1212
namespace Symfony\Flex;
1313

14+
use Composer\Config;
15+
use Composer\EventDispatcher\EventDispatcher;
16+
use Composer\IO\IOInterface;
1417
use Composer\Repository\ComposerRepository as BaseComposerRepository;
18+
use Composer\Util\RemoteFilesystem;
1519

1620
/**
1721
* @author Nicolas Grekas <[email protected]>
@@ -20,6 +24,13 @@ class ComposerRepository extends BaseComposerRepository
2024
{
2125
private $providerFiles;
2226

27+
public function __construct(array $repoConfig, IOInterface $io, Config $config, EventDispatcher $eventDispatcher = null, RemoteFilesystem $rfs = null)
28+
{
29+
parent::__construct($repoConfig, $io, $config, $eventDispatcher, $rfs);
30+
31+
$this->cache = new Cache($io, $config->get('cache-repo-dir').'/'.preg_replace('{[^a-z0-9.]}i', '-', $this->url), 'a-z0-9.$');
32+
}
33+
2334
protected function loadProviderListings($data)
2435
{
2536
if (null !== $this->providerFiles) {
@@ -53,6 +64,12 @@ protected function fetchFile($filename, $cacheKey = null, $sha256 = null, $store
5364
return [];
5465
}
5566

56-
return parent::fetchFile($filename, $cacheKey, $sha256, $storeLastModifiedTime);
67+
$data = parent::fetchFile($filename, $cacheKey, $sha256, $storeLastModifiedTime);
68+
69+
if (0 === strpos($filename, 'http://packagist.org/p/symfony/') || 0 === strpos($filename, 'https://packagist.org/p/symfony/')) {
70+
$data = $this->cache->removeLegacyTags($data);
71+
}
72+
73+
return $data;
5774
}
5875
}

src/Flex.php

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,8 @@
3636
use Composer\Plugin\PluginInterface;
3737
use Composer\Plugin\PreFileDownloadEvent;
3838
use Composer\Repository\ComposerRepository as BaseComposerRepository;
39+
use Composer\Repository\RepositoryFactory;
40+
use Composer\Repository\RepositoryManager;
3941
use Composer\Script\Event;
4042
use Composer\Script\ScriptEvents;
4143
use Symfony\Component\Console\Input\ArgvInput;
@@ -101,6 +103,13 @@ public function activate(Composer $composer, IOInterface $io)
101103

102104
$rfs = Factory::createRemoteFilesystem($this->io, $this->config);
103105
$this->rfs = new ParallelDownloader($this->io, $this->config, $rfs->getOptions(), $rfs->isTlsDisabled());
106+
$manager = new RepositoryManager($this->io, $this->config, $composer->getEventDispatcher(), $this->rfs);
107+
$manager->setRepositoryClass('composer', ComposerRepository::class);
108+
foreach (RepositoryFactory::defaultRepos(null, $this->config, $manager) as $repo) {
109+
$manager->addRepository($repo);
110+
}
111+
$manager->setLocalRepository($composer->getRepositoryManager()->getLocalRepository());
112+
$composer->setRepositoryManager($manager);
104113
$this->configurator = new Configurator($composer, $io, $this->options);
105114
$this->downloader = new Downloader($composer, $io, $this->rfs);
106115
$this->downloader->setFlexId($this->getFlexId());

tests/FlexTest.php

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,11 +14,14 @@
1414
use Composer\Composer;
1515
use Composer\Config;
1616
use Composer\DependencyResolver\Operation\InstallOperation;
17+
use Composer\Factory;
1718
use Composer\Installer\PackageEvent;
1819
use Composer\IO\BufferIO;
1920
use Composer\Package\Locker;
2021
use Composer\Package\Package;
2122
use Composer\Package\RootPackageInterface;
23+
use Composer\Repository\RepositoryManager;
24+
use Composer\Repository\WritableRepositoryInterface;
2225
use Composer\Script\Event;
2326
use PHPUnit\Framework\TestCase;
2427
use Symfony\Component\Console\Output\OutputInterface;
@@ -160,12 +163,18 @@ public function testPostInstall()
160163

161164
public function testActivateLoadsClasses()
162165
{
166+
$io = new BufferIO('', OutputInterface::VERBOSITY_VERBOSE);
163167
$composer = new Composer();
164-
$composer->setConfig($this->getMockBuilder(Config::class)->disableOriginalConstructor()->getMock());
168+
$composer->setConfig(Factory::createConfig($io));
165169
$package = $this->getMockBuilder(RootPackageInterface::class)->disableOriginalConstructor()->getMock();
166170
$package->method('getExtra')->will($this->returnValue(['symfony' => ['allow-contrib' => true]]));
167171
$composer->setPackage($package);
168-
$io = new BufferIO('', OutputInterface::VERBOSITY_VERBOSE);
172+
$localRepo = $this->getMockBuilder(WritableRepositoryInterface::class)->disableOriginalConstructor()->getMock();
173+
$manager = $this->getMockBuilder(RepositoryManager::class)->disableOriginalConstructor()->getMock();
174+
$manager->expects($this->once())
175+
->method('getLocalRepository')
176+
->willReturn($localRepo);
177+
$composer->setRepositoryManager($manager);
169178

170179
$flex = new Flex();
171180
$flex->activate($composer, $io);

0 commit comments

Comments
 (0)