/**
  * {@inheritdoc}
  *
  * @SuppressWarnings(PHPMD.LongVariable)
  */
 public function handle(\Input $input)
 {
     $packageName = $input->get('install');
     if ($packageName == 'contao/core') {
         $this->redirect('contao/main.php?do=composer');
     }
     if ($input->post('version')) {
         $version = base64_decode(rawurldecode($input->post('version')));
         // make a backup
         copy(TL_ROOT . '/' . $this->configPathname, TL_ROOT . '/' . $this->configPathname . '~');
         // update requires
         $json = new JsonFile(TL_ROOT . '/' . $this->configPathname);
         $config = $json->read();
         if (!array_key_exists('require', $config)) {
             $config['require'] = array();
         }
         $config['require'][$packageName] = $version;
         ksort($config['require']);
         $json->write($config);
         Messages::addInfo(sprintf($GLOBALS['TL_LANG']['composer_client']['added_candidate'], $packageName, $version));
         $_SESSION['COMPOSER_OUTPUT'] .= $this->io->getOutput();
         $this->redirect('contao/main.php?do=composer');
     }
     $installationCandidates = $this->searchPackage($packageName);
     if (empty($installationCandidates)) {
         Messages::addError(sprintf($GLOBALS['TL_LANG']['composer_client']['noInstallationCandidates'], $packageName));
         $_SESSION['COMPOSER_OUTPUT'] .= $this->io->getOutput();
         $this->redirect('contao/main.php?do=composer');
     }
     $template = new \BackendTemplate('be_composer_client_install');
     $template->composer = $this->composer;
     $template->packageName = $packageName;
     $template->candidates = $installationCandidates;
     return $template->parse();
 }
 /**
  * {@inheritdoc}
  */
 public function handle(\Input $input)
 {
     $configFile = new \File($this->configPathname);
     if ($input->post('save')) {
         $tempPathname = $this->configPathname . '~';
         $tempFile = new \File($tempPathname);
         $config = $input->postRaw('config');
         $config = html_entity_decode($config, ENT_QUOTES, 'UTF-8');
         $tempFile->write($config);
         $tempFile->close();
         $validator = new ConfigValidator($this->io);
         list($errors, $publishErrors, $warnings) = $validator->validate(TL_ROOT . '/' . $tempPathname);
         if (!$errors && !$publishErrors) {
             Messages::addConfirmation($GLOBALS['TL_LANG']['composer_client']['configValid']);
             $this->import('Files');
             $this->Files->rename($tempPathname, $this->configPathname);
         } else {
             $tempFile->delete();
             $_SESSION['COMPOSER_EDIT_CONFIG'] = $config;
             if ($errors) {
                 foreach ($errors as $message) {
                     Messages::addError('Error: ' . $message);
                 }
             }
             if ($publishErrors) {
                 foreach ($publishErrors as $message) {
                     Messages::addError('Publish error: ' . $message);
                 }
             }
         }
         if ($warnings) {
             foreach ($warnings as $message) {
                 Messages::addWarning('Warning: ' . $message);
             }
         }
         $this->reload();
     }
     if (isset($_SESSION['COMPOSER_EDIT_CONFIG'])) {
         $config = $_SESSION['COMPOSER_EDIT_CONFIG'];
         unset($_SESSION['COMPOSER_EDIT_CONFIG']);
     } else {
         $config = $configFile->getContent();
     }
     $template = new \BackendTemplate('be_composer_client_editor');
     $template->composer = $this->composer;
     $template->config = $config;
     return $template->parse();
 }
 /**
  * {@inheritdoc}
  */
 public function handle(\Input $input)
 {
     try {
         $packages = $input->post('packages') ?: $input->get('packages');
         $packages = explode(',', $packages);
         $packages = array_filter($packages);
         $dryRun = $input->get('dry-run') || $input->post('dry-run');
         $mode = $this->determineRuntimeMode();
         switch ($mode) {
             case 'inline':
                 $this->runInline($packages, $dryRun);
                 break;
             case 'process':
                 $this->runProcess($packages, $dryRun);
                 break;
             case 'detached':
                 $this->runDetached($packages, $dryRun);
                 break;
         }
     } catch (DuplicateContaoException $e) {
         if (isset($_SESSION['COMPOSER_DUPLICATE_CONTAO_EXCEPTION']) && $_SESSION['COMPOSER_DUPLICATE_CONTAO_EXCEPTION']) {
             unset($_SESSION['COMPOSER_DUPLICATE_CONTAO_EXCEPTION']);
             do {
                 Messages::addError(str_replace(TL_ROOT, '', $e->getMessage()));
                 $e = $e->getPrevious();
             } while ($e);
             $this->redirect('contao/main.php?do=composer');
         } else {
             $_SESSION['COMPOSER_DUPLICATE_CONTAO_EXCEPTION'] = true;
             $this->reload();
         }
     } catch (ConfigUpdateException $e) {
         do {
             Messages::addConfirmation(str_replace(TL_ROOT, '', $e->getMessage()));
             $e = $e->getPrevious();
         } while ($e);
         $this->reload();
     } catch (\RuntimeException $e) {
         do {
             Messages::addError(str_replace(TL_ROOT, '', $e->getMessage()));
             $e = $e->getPrevious();
         } while ($e);
         $this->redirect('contao/main.php?do=composer');
     }
 }
 /**
  * {@inheritdoc}
  */
 public function handle(\Input $input)
 {
     // get installed packages
     $localRepository = $this->composer->getRepositoryManager()->getLocalRepository();
     $packages = $localRepository->getPackages();
     // find contao composer plugin
     $plugins = $this->composer->getPluginManager()->getPlugins();
     $plugin = null;
     foreach ($plugins as $temp) {
         if ($temp instanceof Plugin) {
             $plugin = $temp;
         }
     }
     // plugin not found -> abort
     if (!$plugin) {
         Messages::addError($GLOBALS['TL_LANG']['composer_client']['pluginNotFound']);
         $this->redirect('contao/main.php?do=composer&tools=dialog');
     }
     // create installer
     $config = $this->composer->getConfig();
     if ($config->get('preferred-install') == 'dist') {
         $installer = new CopyInstaller($this->io, $this->composer, $plugin);
     } else {
         $installer = new SymlinkInstaller($this->io, $this->composer, $plugin);
     }
     /** @var PackageInterface[] $packages */
     /** @var Plugin $plugin */
     foreach ($packages as $package) {
         if ($package instanceof AliasPackage) {
             continue;
         }
         try {
             $this->io->write(sprintf($GLOBALS['TL_LANG']['composer_client']['resyncPackage'], $package->getName()));
             $installer->updateContaoFiles($package);
             Messages::addInfo(sprintf($GLOBALS['TL_LANG']['composer_client']['resyncedPackage'], $package->getName()));
         } catch (\RuntimeException $e) {
             Messages::addError(sprintf($GLOBALS['TL_LANG']['composer_client']['resyncFailed'], $package->getName(), $e->getMessage()));
         }
     }
     $_SESSION['COMPOSER_OUTPUT'] .= $this->io->getOutput();
     $this->redirect('contao/main.php?do=composer&update=database');
 }
 /**
  * {@inheritdoc}
  */
 public function handle(\Input $input)
 {
     $keyword = $input->get('keyword');
     $tokens = explode(' ', $keyword);
     $tokens = array_map('trim', $tokens);
     $tokens = array_filter($tokens);
     $searchName = count($tokens) == 1 && strpos($tokens[0], '/') !== false;
     if (empty($tokens)) {
         $_SESSION['COMPOSER_OUTPUT'] .= $this->io->getOutput();
         $this->redirect('contao/main.php?do=composer');
     }
     $packages = $this->searchPackages($tokens, $searchName ? RepositoryInterface::SEARCH_NAME : RepositoryInterface::SEARCH_FULLTEXT);
     if (empty($packages)) {
         Messages::addError(sprintf($GLOBALS['TL_LANG']['composer_client']['noSearchResult'], $keyword));
         $_SESSION['COMPOSER_OUTPUT'] .= $this->io->getOutput();
         $this->redirect('contao/main.php?do=composer');
     }
     $template = new \BackendTemplate('be_composer_client_search');
     $template->composer = $this->composer;
     $template->keyword = $keyword;
     $template->packages = $packages;
     return $template->parse();
 }
 /**
  * {@inheritdoc}
  *
  * @SuppressWarnings(PHPMD.LongVariable)
  */
 public function handle(\Input $input)
 {
     $packageName = $input->get('solve');
     $version = base64_decode(rawurldecode($input->get('version')));
     if ($input->post('mark') || $input->post('install')) {
         // make a backup
         copy(TL_ROOT . '/' . $this->configPathname, TL_ROOT . '/' . $this->configPathname . '~');
         // update requires
         $json = new JsonFile(TL_ROOT . '/' . $this->configPathname);
         $config = $json->read();
         if (!array_key_exists('require', $config)) {
             $config['require'] = array();
         }
         $config['require'][$packageName] = $version;
         $json->write($config);
         Messages::addInfo(sprintf($GLOBALS['TL_LANG']['composer_client']['added_candidate'], $packageName, $version));
         $_SESSION['COMPOSER_OUTPUT'] .= $this->io->getOutput();
         if ($input->post('install')) {
             $this->redirect('contao/main.php?do=composer&update=packages');
         }
         $this->redirect('contao/main.php?do=composer');
     }
     /** @var RootPackage $rootPackage */
     $rootPackage = $this->composer->getPackage();
     $installedRootPackage = clone $rootPackage;
     $installedRootPackage->setRequires(array());
     $installedRootPackage->setDevRequires(array());
     $repositoryManager = $this->getRepositoryManager();
     $localRepository = $repositoryManager->getLocalRepository();
     $platformRepo = new PlatformRepository();
     $installedRepository = new CompositeRepository(array($localRepository, new InstalledArrayRepository(array($installedRootPackage)), $platformRepo));
     $versionParser = new VersionParser();
     $constraint = $versionParser->parseConstraints($version);
     $stability = $versionParser->parseStability($version);
     $aliases = $this->getRootAliases($rootPackage);
     $this->aliasPlatformPackages($platformRepo, $aliases);
     $stabilityFlags = $rootPackage->getStabilityFlags();
     $stabilityFlags[$packageName] = BasePackage::$stabilities[$stability];
     $pool = $this->getPool($rootPackage->getMinimumStability(), $stabilityFlags);
     $pool->addRepository($installedRepository, $aliases);
     $policy = new DefaultPolicy($rootPackage->getPreferStable());
     $request = new Request($pool);
     // add root package
     $rootPackageConstraint = $this->createConstraint('=', $rootPackage->getVersion());
     $rootPackageConstraint->setPrettyString($rootPackage->getPrettyVersion());
     $request->install($rootPackage->getName(), $rootPackageConstraint);
     // add requirements
     $links = $rootPackage->getRequires();
     /** @var Link $link */
     foreach ($links as $link) {
         if ($link->getTarget() != $packageName) {
             $request->install($link->getTarget(), $link->getConstraint());
         }
     }
     /** @var PackageInterface $package */
     foreach ($installedRepository->getPackages() as $package) {
         $request->install($package->getName(), $this->createConstraint('=', $package->getVersion()));
     }
     $operations = array();
     try {
         $solver = new Solver($policy, $pool, $installedRepository);
         $beforeOperations = $solver->solve($request);
         $request->install($packageName, $constraint);
         $operations = $solver->solve($request);
         /** @var \Composer\DependencyResolver\Operation\SolverOperation $beforeOperation */
         foreach ($beforeOperations as $beforeOperation) {
             /** @var \Composer\DependencyResolver\Operation\InstallOperation $operation */
             foreach ($operations as $index => $operation) {
                 if ($operation->getPackage()->getName() != $packageName && $beforeOperation->__toString() == $operation->__toString()) {
                     unset($operations[$index]);
                 }
             }
         }
     } catch (SolverProblemsException $e) {
         Messages::addError(sprintf('<span style="white-space: pre-line">%s</span>', trim($e->getMessage())));
     }
     $template = new \BackendTemplate('be_composer_client_solve');
     $template->composer = $this->composer;
     $template->packageName = $packageName;
     $template->packageVersion = $version;
     $template->operations = $operations;
     return $template->parse();
 }
 /**
  * Load composer and the composer class loader.
  */
 protected function loadComposer()
 {
     // search for composer build version
     $composerDevWarningTime = Runtime::readComposerDevWarningTime();
     $incompatibleVersion = false === $composerDevWarningTime || mktime(11, 0, 0, 6, 5, 2014) > $composerDevWarningTime - 30 * 86400;
     // Update if allowed or composer version is incompatible.
     if ($incompatibleVersion || $GLOBALS['TL_CONFIG']['composerAutoUpdateLibrary'] && time() > $composerDevWarningTime) {
         Runtime::updateComposer();
         Messages::addConfirmation($GLOBALS['TL_LANG']['composer_client']['composerUpdated']);
     }
     if ($composerDevWarningTime && !$GLOBALS['TL_CONFIG']['composerAutoUpdateLibrary'] && $incompatibleVersion) {
         Messages::addError($GLOBALS['TL_LANG']['composer_client']['composerUpdateNecessary']);
     }
     // register composer class loader
     Runtime::registerComposerClassLoader();
     // define pathname to config file
     $this->configPathname = COMPOSER_DIR_RELATIVE . '/' . Factory::getComposerFile();
     // create io interface
     $this->io = new BufferIO('', $this->getDebugLevel(), new HtmlOutputFormatter());
     // create composer
     $this->composer = Runtime::createComposer($this->io);
 }
 /**
  * Build replacement map for installed packages.
  *
  * @param RepositoryInterface $repository
  *
  * @return array
  */
 protected function calculateLegacyReplaceMap(RepositoryInterface $repository)
 {
     $replaceMap = array();
     try {
         $abandon = Downloader::download('https://legacy-packages-via.contao-community-alliance.org/abandoned.json');
     } catch (\Exception $exception) {
         Messages::addError($exception->getMessage());
         return array();
     }
     $legacyReplaces = json_decode($abandon, true);
     /** @var \Composer\Package\PackageInterface $package */
     foreach ($repository->getPackages() as $package) {
         if (isset($legacyReplaces[$package->getName()])) {
             $replaceMap[$package->getName()] = $legacyReplaces[$package->getName()];
         }
     }
     return $replaceMap;
 }