/** * @param string $identifier * * @return array|bool */ protected function convertPackageXml($identifier) { $packageXmlNames = ['package.xml', 'package2.xml']; $found = false; foreach ($packageXmlNames as $path) { try { $contents = $this->client->api('repo')->contents()->download($this->gitHubVendorName, $this->gitHubRepositoryName, $path, $identifier); } catch (\RuntimeException $e) { if ($e->getCode() == 404) { $this->log->write('github driver: no ' . $path . ' found for ' . $identifier); continue; } } $found = true; break; } if (!$found || !isset($contents)) { return false; } $packagexmlPath = $this->cacheDir . DIRECTORY_SEPARATOR . 'package.xml'; file_put_contents($packagexmlPath, $contents); $loader = new \Pickle\Package\XML\Loader(new Package\Loader()); $package = $loader->load($packagexmlPath); $package->setRootDir($this->cacheDir); $dumper = new \Pickle\Package\Dumper(); $xml = simplexml_load_file($packagexmlPath); $date = $xml->date; $time = $xml->time; $info = $dumper->dump($package); $info['name'] = $this->name; $info['type'] = 'extension'; $info['time'] = date('Y-m-d H:i', strtotime($date . ' ' . $time)); unlink($packagexmlPath); return $info; }
public function test_it_receives_event() { $this->composer->getPluginManager()->addPlugin(new ChangelogsPlugin()); $initialPackage = new Package('foo/bar', '1.0.0.0', 'v1.0.0'); $initialPackage->setSourceUrl('https://github.com/foo/bar.git'); $targetPackage = new Package('foo/bar', '1.0.1.0', 'v1.0.1'); $targetPackage->setSourceUrl('https://github.com/foo/bar.git'); $operation = new UpdateOperation($initialPackage, $targetPackage); $this->composer->getEventDispatcher()->dispatchPackageEvent(PackageEvents::POST_PACKAGE_UPDATE, false, new DefaultPolicy(false, false), new Pool(), new CompositeRepository([]), new Request(new Pool()), [$operation], $operation); $this->composer->getEventDispatcher()->dispatchScript(ScriptEvents::POST_UPDATE_CMD); $expectedOutput = <<<OUTPUT Changelogs summary: - foo/bar updated from v1.0.0 to v1.0.1 See changes: https://github.com/foo/bar/compare/v1.0.0...v1.0.1 Release notes: https://github.com/foo/bar/releases/tag/v1.0.1 OUTPUT; $this->assertSame($expectedOutput, $this->io->getOutput()); }
public function test_it_commits_with_always_option() { $this->config->merge(['config' => ['home' => realpath(__DIR__ . '/fixtures/home')]]); $plugin = new ChangelogsPlugin(); $plugin->activate($this->composer, $this->io); $operation = $this->getUpdateOperation(); $packageEvent = new PackageEvent(PackageEvents::POST_PACKAGE_UPDATE, $this->composer, $this->io, false, new DefaultPolicy(false, false), new Pool(), new CompositeRepository([]), new Request(new Pool()), [$operation], $operation); $plugin->postPackageOperation($packageEvent); $postUpdateEvent = new Event(ScriptEvents::POST_UPDATE_CMD, $this->composer, $this->io); $plugin->postUpdate($postUpdateEvent); $this->assertStringMatchesFormat('%aExecuting following command: %s/tests/fixtures/bin/fake.sh \'%s\' \'%s/composer-changelogs-%s\'', $this->io->getOutput()); }
/** * @ApiDoc( * section="Bundle/Package Manager", * description="Installs a composer package and (optional) activates its containing bundle" * ) * * @Rest\QueryParam(name="name", requirements=".+", strict=true, description="The composer package name") * @Rest\QueryParam(name="version", requirements=".+", strict=true, description="The version") * @Rest\QueryParam(name="withBundles", requirements=".+", default="false", description="If the containing bundle should be activated") * * @Rest\Post("/admin/system/bundle/manager/composer/install") * * @param ParamFetcher $paramFetcher * * @return string * @throws FileNotWritableException * @throws PackageNotFoundException */ public function installComposerAction(ParamFetcher $paramFetcher) { $name = $paramFetcher->get('name'); $version = $paramFetcher->get('version'); $withBundles = filter_var($paramFetcher->get('withBundles'), FILTER_VALIDATE_BOOLEAN); if (!is_writeable($vendorDir = $this->getComposerVendorDir())) { throw new FileNotWritableException(sprintf('Directory `%s` is not writable.', $vendorDir)); } $composer = $this->getComposer(); //check if bundle exist $this->versionParser = new VersionParser(); $platformRepo = new PlatformRepository(); $localRepo = $composer->getRepositoryManager()->getLocalRepository(); $installedRepo = new CompositeRepository(array($localRepo, $platformRepo)); $repos = new CompositeRepository(array_merge(array($installedRepo), $composer->getRepositoryManager()->getRepositories())); list($package, ) = $this->getPackage($installedRepo, $repos, $name, $version); if (!$package) { throw new PackageNotFoundException(sprintf('Can not find package `%s` with version `%s`.', $name, $version)); } $fs = $this->localFilesystem; if ($fs->has('composer.json') && is_string($name)) { $composerJson = $fs->read('composer.json'); if ($composerJson) { $composerJson = json_decode($composerJson, true); if (is_array($composerJson)) { $found = false; foreach ($composerJson['require'] as $key => $value) { if (strtolower($key) == strtolower($name)) { unset($composerJson['require'][$key]); $found = $key; } } if (!$found) { $composerJson['require'][$name] = $version; $fs->write('composer.json', json_encode($composerJson, JSON_PRETTY_PRINT)); } else { $name = $found; } } } } $install = Installer::create($this->composerIO, $composer); $install->setVerbose(true)->setPreferDist(true)->setDevMode(true)->setUpdate(true)->setUpdateWhitelist([$name]); if (filter_var($withBundles, FILTER_VALIDATE_BOOLEAN)) { $this->searchAndInstallBundles($this->getComposerVendorDir() . $name); } $this->updateAutoloader(); return $this->composerIO->getOutput(); }
/** * @param string $packageName * @throws VerboseException */ public function update($packageName) { $this->logger->info(sprintf('%s updating begin', $packageName)); $this->maintenance->activate(); $previousInstalled = $this->getInstalled(); $currentPackage = $this->findInstalledPackage($packageName); $this->updateComposerJsonFile($currentPackage, '*'); $this->scriptRunner->removeApplicationCache(); if ($this->doInstall($packageName)) { $currentlyInstalled = $this->getInstalled(); $changeSetBuilder = new ChangeSetBuilder(); list($installedPackages, $updatedPackages, $uninstalledPackages) = $changeSetBuilder->build($previousInstalled, $currentlyInstalled); array_map(function (PackageInterface $p) { $this->scriptRunner->runInstallScripts($p); }, $installedPackages); $fetchPreviousInstalledPackageVersion = function ($packageName) use($previousInstalled) { foreach ($previousInstalled as $p) { if ($p->getName() == $packageName) { return $p->getVersion(); } } return ''; }; array_map(function (PackageInterface $p) use($fetchPreviousInstalledPackageVersion) { $previousInstalledPackageVersion = $fetchPreviousInstalledPackageVersion($p->getName()); $this->scriptRunner->runUpdateScripts($p, $previousInstalledPackageVersion); }, $updatedPackages); array_map(function (PackageInterface $p) { $this->scriptRunner->runUninstallScripts($p); }, $uninstalledPackages); $this->scriptRunner->clearApplicationCache(); $this->scriptRunner->runPlatformUpdate(); $this->scriptRunner->clearDistApplicationCache(); $justInstalledPackage = $this->findInstalledPackage($packageName); $this->updateComposerJsonFile($justInstalledPackage, $justInstalledPackage->getPrettyVersion()); } else { $this->updateComposerJsonFile($currentPackage, $currentPackage->getPrettyVersion()); $errorMessage = sprintf('%s can\'t be updated!', $packageName); $this->logger->error($errorMessage); $this->logger->error($this->composerIO->getOutput()); throw new VerboseException($errorMessage, $this->composerIO->getOutput()); } $this->logger->info(sprintf('%s updated', $packageName)); }
public function testDispatcherCanExecuteComposerScriptGroups() { $process = $this->getMock('Composer\\Util\\ProcessExecutor'); $dispatcher = $this->getMockBuilder('Composer\\EventDispatcher\\EventDispatcher')->setConstructorArgs(array($composer = $this->createComposerInstance(), $io = new BufferIO('', OutputInterface::VERBOSITY_VERBOSE), $process))->setMethods(array('getListeners'))->getMock(); $process->expects($this->exactly(3))->method('execute')->will($this->returnValue(0)); $dispatcher->expects($this->atLeastOnce())->method('getListeners')->will($this->returnCallback(function (Event $event) { if ($event->getName() === 'root') { return array('@group'); } elseif ($event->getName() === 'group') { return array('echo -n foo', '@subgroup', 'echo -n bar'); } elseif ($event->getName() === 'subgroup') { return array('echo -n baz'); } return array(); })); $dispatcher->dispatch('root', new CommandEvent('root', $composer, $io)); $expected = '> root: @group' . PHP_EOL . '> group: echo -n foo' . PHP_EOL . '> group: @subgroup' . PHP_EOL . '> subgroup: echo -n baz' . PHP_EOL . '> group: echo -n bar' . PHP_EOL; $this->assertEquals($expected, $io->getOutput()); }
/** * {@inheritdoc} */ protected function execute(InputInterface $input, OutputInterface $output) { $verbose = $input->getOption('verbose'); $force = $input->getOption('force'); $package = $input->getArgument('package'); $doctrine = $this->getContainer()->get('doctrine'); $router = $this->getContainer()->get('router'); $flags = 0; if ($package) { $packages = array(array('id' => $doctrine->getRepository('PackagistWebBundle:Package')->findOneByName($package)->getId())); $flags = $force ? Updater::UPDATE_EQUAL_REFS : 0; } elseif ($force) { $packages = $doctrine->getManager()->getConnection()->fetchAll('SELECT id FROM package ORDER BY id ASC'); $flags = Updater::UPDATE_EQUAL_REFS; } else { $packages = $doctrine->getRepository('PackagistWebBundle:Package')->getStalePackages(); } $ids = array(); foreach ($packages as $package) { $ids[] = $package['id']; } if ($input->getOption('delete-before')) { $flags = Updater::DELETE_BEFORE; } elseif ($input->getOption('update-equal-refs')) { $flags = Updater::UPDATE_EQUAL_REFS; } $updater = $this->getContainer()->get('packagist.package_updater'); $start = new \DateTime(); if ($verbose && $input->getOption('notify-failures')) { throw new \LogicException('Failures can not be notified in verbose mode since the output is piped to the CLI'); } $input->setInteractive(false); $config = Factory::createConfig(); $io = $verbose ? new ConsoleIO($input, $output, $this->getApplication()->getHelperSet()) : new BufferIO(''); $io->loadConfiguration($config); $loader = new ValidatingArrayLoader(new ArrayLoader()); while ($ids) { $packages = $doctrine->getRepository('PackagistWebBundle:Package')->getPackagesWithVersions(array_splice($ids, 0, 50)); foreach ($packages as $package) { if ($verbose) { $output->writeln('Importing ' . $package->getRepository()); } try { if (null === $io || $io instanceof BufferIO) { $io = new BufferIO(''); $io->loadConfiguration($config); } $repository = new VcsRepository(array('url' => $package->getRepository()), $io, $config); $repository->setLoader($loader); $updater->update($io, $config, $package, $repository, $flags, $start); } catch (InvalidRepositoryException $e) { $output->writeln('<error>Broken repository in ' . $router->generate('view_package', array('name' => $package->getName()), true) . ': ' . $e->getMessage() . '</error>'); if ($input->getOption('notify-failures')) { if (!$this->getContainer()->get('packagist.package_manager')->notifyUpdateFailure($package, $e, $io->getOutput())) { $output->writeln('<error>Failed to notify maintainers</error>'); } } } catch (\Exception $e) { $output->writeln('<error>Error updating ' . $router->generate('view_package', array('name' => $package->getName()), true) . ' [' . get_class($e) . ']: ' . $e->getMessage() . ' at ' . $e->getFile() . ':' . $e->getLine() . '</error>'); } } $doctrine->getManager()->clear(); unset($packages); } }
public function thenTheOutputShouldContain($string) { $this->spec->assertContains($string, $this->file->makeRooted($this->io->getOutput())); }
/** * Perform the package update * * @param Request $request the current request * @param string $url the repository's URL (deducted from the request) * @param string $urlRegex the regex used to split the user packages into domain and path * @return Response */ protected function receivePost(Request $request, $url, $urlRegex) { // try to parse the URL first to avoid the DB lookup on malformed requests if (!preg_match($urlRegex, $url)) { return new Response(json_encode(array('status' => 'error', 'message' => 'Could not parse payload repository URL')), 406); } // find the user $user = $this->findUser($request); if (!$user) { return new Response(json_encode(array('status' => 'error', 'message' => 'Invalid credentials')), 403); } // try to find the user package $packages = $this->findPackagesByUrl($user, $url, $urlRegex); if (!$packages) { return new Response(json_encode(array('status' => 'error', 'message' => 'Could not find a package that matches this request (does user maintain the package?)')), 404); } // don't die if this takes a while set_time_limit(3600); // put both updating the database and scanning the repository in a transaction $em = $this->get('doctrine.orm.entity_manager'); $updater = $this->get('packagist.package_updater'); $config = Factory::createConfig(); $io = new BufferIO('', OutputInterface::VERBOSITY_VERBOSE, new HtmlOutputFormatter(Factory::createAdditionalStyles())); $io->loadConfiguration($config); try { foreach ($packages as $package) { $em->transactional(function ($em) use($package, $updater, $io, $config) { // prepare dependencies $loader = new ValidatingArrayLoader(new ArrayLoader()); // prepare repository $repository = new VcsRepository(array('url' => $package->getRepository()), $io, $config); $repository->setLoader($loader); // perform the actual update (fetch and re-scan the repository's source) $updater->update($io, $config, $package, $repository); // update the package entity $package->setAutoUpdated(true); $em->flush(); }); } } catch (\Exception $e) { if ($e instanceof InvalidRepositoryException) { $this->get('packagist.package_manager')->notifyUpdateFailure($package, $e, $io->getOutput()); } return new Response(json_encode(array('status' => 'error', 'message' => '[' . get_class($e) . '] ' . $e->getMessage(), 'details' => '<pre>' . $io->getOutput() . '</pre>')), 400); } return new JsonResponse(array('status' => 'success'), 202); }
public function testHidePasswords() { $process = new ProcessExecutor($buffer = new BufferIO('', StreamOutput::VERBOSITY_DEBUG)); $process->execute('echo https://foo:bar@example.org/ && echo http://foo@example.org && echo http://abcdef1234567890234578:x-oauth-token@github.com/', $output); $this->assertEquals('Executing command (CWD): echo https://foo:***@example.org/ && echo http://foo@example.org && echo http://***:***@github.com/', trim($buffer->getOutput())); }
/** * @Template() * @Route("/packages/{name}", name="update_package", requirements={"name"="[A-Za-z0-9_.-]+/[A-Za-z0-9_.-]+"}, defaults={"_format" = "json"}) * @Method({"PUT"}) */ public function updatePackageAction(Request $req, $name) { $doctrine = $this->getDoctrine(); try { /** @var Package $package */ $package = $doctrine->getRepository('PackagistWebBundle:Package')->getPackageByName($name); } catch (NoResultException $e) { return new Response(json_encode(array('status' => 'error', 'message' => 'Package not found')), 404); } $username = $req->request->has('username') ? $req->request->get('username') : $req->query->get('username'); $apiToken = $req->request->has('apiToken') ? $req->request->get('apiToken') : $req->query->get('apiToken'); $update = $req->request->get('update', $req->query->get('update')); $autoUpdated = $req->request->get('autoUpdated', $req->query->get('autoUpdated')); $updateEqualRefs = $req->request->get('updateAll', $req->query->get('updateAll')); $user = $this->getUser() ?: $doctrine->getRepository('PackagistWebBundle:User')->findOneBy(array('username' => $username, 'apiToken' => $apiToken)); if (!$user) { return new Response(json_encode(array('status' => 'error', 'message' => 'Invalid credentials')), 403); } if ($package->getMaintainers()->contains($user) || $this->isGranted('ROLE_UPDATE_PACKAGES')) { $req->getSession()->save(); if (null !== $autoUpdated) { $package->setAutoUpdated((bool) $autoUpdated); $doctrine->getManager()->flush(); } if ($update) { set_time_limit(3600); $updater = $this->get('packagist.package_updater'); $io = new BufferIO('', OutputInterface::VERBOSITY_VERY_VERBOSE, new HtmlOutputFormatter(Factory::createAdditionalStyles())); $config = Factory::createConfig(); $io->loadConfiguration($config); $repository = new VcsRepository(array('url' => $package->getRepository()), $io, $config); $loader = new ValidatingArrayLoader(new ArrayLoader()); $repository->setLoader($loader); try { $updater->update($io, $config, $package, $repository, $updateEqualRefs ? Updater::UPDATE_EQUAL_REFS : 0); } catch (\Exception $e) { return new Response(json_encode(array('status' => 'error', 'message' => '[' . get_class($e) . '] ' . $e->getMessage(), 'details' => '<pre>' . $io->getOutput() . '</pre>')), 400); } } return new Response('{"status": "success"}', 202); } return new JsonResponse(array('status' => 'error', 'message' => 'Could not find a package that matches this request (does user maintain the package?)'), 404); }
public function testDoesntHidePorts() { $process = new ProcessExecutor($buffer = new BufferIO('', StreamOutput::VERBOSITY_DEBUG)); $process->execute('echo https://localhost:1234/', $output); $this->assertEquals('Executing command (CWD): echo https://localhost:1234/', trim($buffer->getOutput())); }
/** * Return the output from the last IO. * * @return string */ public function getOutput() { return $this->io->getOutput(); }
/** * Run the dependency analysis. * * @return void */ public function run() { $this->setUp(); $this->progress->start(); try { $this->search(); $this->progress->finish(); } catch (\Exception $e) { $this->progress->finish(); $this->application->renderException($e, $this->output); if ($this->output->getVerbosity() > OutputInterface::VERBOSITY_NORMAL) { $this->formatter->formatBlock($this->io->getOutput(), 'error'); } } }