From e9c7b176379195f5d1729cac2aa9491334ebbb8b Mon Sep 17 00:00:00 2001 From: Ievgen Shakhsuvarov Date: Thu, 1 Sep 2016 12:30:42 +0300 Subject: [PATCH] MAGETWO-57905: [Backport] Compiler performance optimization for 2.1 --- .../Magento/Framework/Module/Dir/Reader.php | 40 ++++++++++--- .../Console/Command/DiCompileCommand.php | 60 +++++++++++++++---- 2 files changed, 83 insertions(+), 17 deletions(-) diff --git a/lib/internal/Magento/Framework/Module/Dir/Reader.php b/lib/internal/Magento/Framework/Module/Dir/Reader.php index 7a8b1f11ef184..353f7e51c5906 100644 --- a/lib/internal/Magento/Framework/Module/Dir/Reader.php +++ b/lib/internal/Magento/Framework/Module/Dir/Reader.php @@ -46,6 +46,13 @@ class Reader */ protected $readFactory; + /** + * Found configuration files grouped by configuration types (filename). + * + * @var array + */ + private $fileIterators = []; + /** * @param Dir $moduleDirs * @param ModuleListInterface $moduleList @@ -65,24 +72,42 @@ public function __construct( } /** - * Go through all modules and find configuration files of active modules + * Go through all modules and find configuration files of active modules. * * @param string $filename * @return FileIterator */ public function getConfigurationFiles($filename) { - return $this->fileIteratorFactory->create($this->getFiles($filename, Dir::MODULE_ETC_DIR)); + return $this->getFilesIterator($filename, Dir::MODULE_ETC_DIR); } /** - * Go through all modules and find composer.json files of active modules + * Go through all modules and find composer.json files of active modules. * * @return FileIterator */ public function getComposerJsonFiles() { - return $this->fileIteratorFactory->create($this->getFiles('composer.json')); + return $this->getFilesIterator('composer.json'); + } + + /** + * Retrieve iterator for files with $filename from components located in component $subDir. + * + * @param string $filename + * @param string $subDir + * + * @return FileIterator + */ + private function getFilesIterator($filename, $subDir = '') + { + if (!isset($this->fileIterators[$subDir][$filename])) { + $this->fileIterators[$subDir][$filename] = $this->fileIteratorFactory->create( + $this->getFiles($filename, $subDir) + ); + } + return $this->fileIterators[$subDir][$filename]; } /** @@ -96,9 +121,9 @@ private function getFiles($filename, $subDir = '') { $result = []; foreach ($this->modulesList->getNames() as $moduleName) { - $moduleEtcDir = $this->getModuleDir($subDir, $moduleName); - $file = $moduleEtcDir . '/' . $filename; - $directoryRead = $this->readFactory->create($moduleEtcDir); + $moduleSubDir = $this->getModuleDir($subDir, $moduleName); + $file = $moduleSubDir . '/' . $filename; + $directoryRead = $this->readFactory->create($moduleSubDir); $path = $directoryRead->getRelativePath($file); if ($directoryRead->isExist($path)) { $result[] = $file; @@ -159,5 +184,6 @@ public function getModuleDir($type, $moduleName) public function setModuleDir($moduleName, $type, $path) { $this->customModuleDirs[$moduleName][$type] = $path; + $this->fileIterators = []; } } diff --git a/setup/src/Magento/Setup/Console/Command/DiCompileCommand.php b/setup/src/Magento/Setup/Console/Command/DiCompileCommand.php index 870a3c7694390..e94fcbf471a94 100644 --- a/setup/src/Magento/Setup/Console/Command/DiCompileCommand.php +++ b/setup/src/Magento/Setup/Console/Command/DiCompileCommand.php @@ -140,17 +140,9 @@ protected function execute(InputInterface $input, OutputInterface $output) 'library' => $libraryPaths, 'generated_helpers' => $generationPath ]; - $excludedModulePaths = []; - foreach ($modulePaths as $appCodePath) { - $excludedModulePaths[] = '#^' . $appCodePath . '/Test#'; - } - $excludedLibraryPaths = []; - foreach ($libraryPaths as $libraryPath) { - $excludedLibraryPaths[] = '#^' . $libraryPath . '/([\\w]+/)?Test#'; - } $this->excludedPathsList = [ - 'application' => $excludedModulePaths, - 'framework' => $excludedLibraryPaths + 'application' => $this->getExcludedModulePaths($modulePaths), + 'framework' => $this->getExcludedLibraryPaths($libraryPaths), ]; $this->configureObjectManager($output); @@ -205,6 +197,54 @@ function (OperationInterface $operation) use ($progressBar) { } } + /** + * Build list of module path regexps which should be excluded from compilation + * + * @param string[] $modulePaths + * @return string[] + */ + private function getExcludedModulePaths(array $modulePaths) + { + $modulesByBasePath = []; + foreach ($modulePaths as $modulePath) { + $moduleDir = basename($modulePath); + $vendorPath = dirname($modulePath); + $vendorDir = basename($vendorPath); + $basePath = dirname($vendorPath); + $modulesByBasePath[$basePath][$vendorDir][] = $moduleDir; + } + + $basePathsRegExps = []; + foreach ($modulesByBasePath as $basePath => $vendorPaths) { + $vendorPathsRegExps = []; + foreach ($vendorPaths as $vendorDir => $vendorModules) { + $vendorPathsRegExps[] = $vendorDir + . '/(?:' . join('|', $vendorModules) . ')'; + } + $basePathsRegExps[] = $basePath + . '/(?:' . join('|', $vendorPathsRegExps) . ')'; + } + + $excludedModulePaths = [ + '#^(?:' . join('|', $basePathsRegExps) . ')/Test#', + ]; + return $excludedModulePaths; + } + + /** + * Build list of library path regexps which should be excluded from compilation + * + * @param string[] $libraryPaths + * @return string[] + */ + private function getExcludedLibraryPaths(array $libraryPaths) + { + $excludedLibraryPaths = [ + '#^(?:' . join('|', $libraryPaths) . ')/([\\w]+/)?Test#', + ]; + return $excludedLibraryPaths; + } + /** * Delete directories by their code from "var" directory *