├── .gitignore ├── config-examples ├── .campaign-config.example └── .env.example ├── bin └── banner-toolkit ├── phpunit.xml.dist ├── src ├── PageUpload │ ├── PageUploadRequest.php │ ├── PageUploadResponse.php │ └── PageUploadUseCase.php ├── FileToPageNameTranslator.php ├── CliConfiguration.php └── Commands │ └── UploadCommand.php ├── composer.json ├── tests ├── FileToPageNameTranslatorTest.php ├── CliConfigurationTest.php └── PageUploadUseCaseTest.php ├── README.md ├── phpcs.xml └── composer.lock /.gitignore: -------------------------------------------------------------------------------- 1 | /vendor/ 2 | -------------------------------------------------------------------------------- /config-examples/.campaign-config.example: -------------------------------------------------------------------------------- 1 | API_URL = "https://meta.wikimedia.org/w/api.php" 2 | 3 | PAGE_PREFIX = "MediaWiki:Centralnotice-template-" 4 | 5 | CAMPAIGN_NAME = "B16WMDE_" 6 | -------------------------------------------------------------------------------- /config-examples/.env.example: -------------------------------------------------------------------------------- 1 | # Example dotenv file 2 | # DO NOT commit the non-example version of this file to version control!!! 3 | 4 | USER="Banner Administrator" 5 | PASSWORD="1ns3cure" 6 | -------------------------------------------------------------------------------- /bin/banner-toolkit: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env php 2 | add( new UploadCommand() ); 12 | 13 | $application->run(); -------------------------------------------------------------------------------- /phpunit.xml.dist: -------------------------------------------------------------------------------- 1 | 15 | 16 | 17 | tests 18 | 19 | 20 | -------------------------------------------------------------------------------- /src/PageUpload/PageUploadRequest.php: -------------------------------------------------------------------------------- 1 | pageName = $pageName; 16 | $this->lastChange = $lastChange; 17 | $this->newContent = $newContent; 18 | $this->editMessage = $editMessage; 19 | } 20 | 21 | public function getPageName() : string { 22 | return $this->pageName; 23 | } 24 | 25 | public function getLastChange() : \DateTime { 26 | 27 | return $this->lastChange; 28 | } 29 | 30 | public function getNewContent() : string { 31 | return $this->newContent; 32 | } 33 | 34 | public function getEditMessage(): string { 35 | return $this->editMessage; 36 | } 37 | 38 | } 39 | -------------------------------------------------------------------------------- /src/PageUpload/PageUploadResponse.php: -------------------------------------------------------------------------------- 1 | message = $message; 15 | $this->hasError = $hasError; 16 | $this->contentChanged = $contentChanged; 17 | } 18 | 19 | public static function newSuccessResponse( $message ): self { 20 | return new self( $message, false, true ); 21 | } 22 | 23 | public static function newFailureResponse( $message ): self { 24 | return new self( $message, true, false ); 25 | } 26 | 27 | public static function newNoOpResponse( $message ): self { 28 | return new self( $message, false, false ); 29 | } 30 | 31 | public function contentHasChanged(): bool { 32 | return $this->contentChanged; 33 | } 34 | 35 | public function isSuccess(): bool { 36 | return !$this->hasError; 37 | } 38 | 39 | public function getMessage(): string { 40 | return $this->message; 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "wmde/banner-toolkit", 3 | "description": "Command line tool for editing banner code locally", 4 | "license": "MIT", 5 | "authors": [ 6 | { 7 | "name": "Gabriel Birke", 8 | "email": "gabriel.birke@wikimedia.de" 9 | } 10 | ], 11 | "bin": [ "bin/banner-toolkit" ], 12 | "autoload": { 13 | "psr-4": { 14 | "WMDE\\Fundraising\\BannerToolkit\\": "src/" 15 | } 16 | }, 17 | "require": { 18 | "php":"~7.0", 19 | "addwiki/mediawiki-api": "~0.5.0", 20 | "symfony/console": "^3.1", 21 | "symfony/config": "^3.1", 22 | "m1/env": "^2.1" 23 | }, 24 | "require-dev": { 25 | "phpunit/phpunit": "^5.6", 26 | "mediawiki/mediawiki-codesniffer": "^0.7.2" 27 | }, 28 | "scripts": { 29 | "test": "vendor/bin/phpunit", 30 | "fix": "vendor/bin/phpcbf", 31 | "ci": [ 32 | "@test", 33 | "@cs" 34 | ], 35 | "cs": "vendor/bin/phpcs src/ tests/ --standard=phpcs.xml --extensions=php -sp" 36 | }, 37 | "extra": { 38 | "branch-alias": { 39 | "dev-master": "1.0.x-dev" 40 | } 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /src/FileToPageNameTranslator.php: -------------------------------------------------------------------------------- 1 | filePartRx = $filePartRx; 15 | $this->pageNameTemplate = $pageNameTemplate; 16 | $this->context = $context; 17 | } 18 | 19 | public function getPageName( string $fileName ): string 20 | { 21 | preg_match( $this->filePartRx, $fileName, $matches ); 22 | $values = array_replace( $this->getEmptyValuesForTemplate(), $this->context, $matches ); 23 | return strtr( $this->pageNameTemplate, $this->getPlaceholders( $values ) ); 24 | } 25 | 26 | private function getPlaceholders( $values ): array { 27 | $placeholders = []; 28 | foreach ( $values as $k => $v ) { 29 | $placeholders['{{' . $k . '}}'] = $v; 30 | } 31 | return $placeholders; 32 | } 33 | 34 | private function getEmptyValuesForTemplate(): array { 35 | preg_match_all( '/\{\{(\w+)\}\}/', $this->pageNameTemplate, $matches ); 36 | $emptyValues = []; 37 | foreach ( $matches[1] as $placeholder ) { 38 | $emptyValues[(string) $placeholder] = ''; 39 | } 40 | return $emptyValues; 41 | } 42 | 43 | } -------------------------------------------------------------------------------- /src/CliConfiguration.php: -------------------------------------------------------------------------------- 1 | root( 'cli' ); 15 | $rootNode->children() 16 | ->scalarNode( 'api_url' ) 17 | ->info( 'Mediawiki API URL' ) 18 | ->isRequired() 19 | ->cannotBeEmpty() 20 | ->defaultValue( 'https://meta.wikimedia.org/w/api.php' ) 21 | ->end() 22 | ->scalarNode( 'user' ) 23 | ->info( 'User Name for API usage' ) 24 | ->isRequired() 25 | ->cannotBeEmpty() 26 | ->end() 27 | ->scalarNode( 'password' ) 28 | ->info( 'Password for API usage' ) 29 | ->isRequired() 30 | ->cannotBeEmpty() 31 | ->end() 32 | ->scalarNode( 'page_prefix' ) 33 | ->info( 'Namespace and page prefix on wiki' ) 34 | ->defaultValue( '' ) 35 | ->end() 36 | ->scalarNode( 'campaign_name' ) 37 | ->info( 'Campaign prefix for each Banner, e.g. B16WMDE_, B16WMDE_mob_, B16WMDE_EN_, etc' ) 38 | ->defaultValue( '' ) 39 | ->end() 40 | ->end(); 41 | return $treeBuilder; 42 | } 43 | } -------------------------------------------------------------------------------- /tests/FileToPageNameTranslatorTest.php: -------------------------------------------------------------------------------- 1 | assertSame( 'B16WMDE_test', $translator->getPageName( 'Banner_test.html' ) ); 13 | } 14 | 15 | public function testFilePartsCanContainNamedPlaceholders() { 16 | $translator = new FileToPageNameTranslator( '/^Banner(?P.*)\.html$/', 'B16WMDE{{variant}}' ); 17 | $this->assertSame( 'B16WMDE_test', $translator->getPageName( 'Banner_test.html' ) ); 18 | } 19 | 20 | public function testMissingPlaceholdersAreRemoved() { 21 | $translator = new FileToPageNameTranslator( '/^Banner(.*)\.html$/', 'B16WMDE{{1}}{{2}}{{foo}}' ); 22 | $this->assertSame( 'B16WMDE_test', $translator->getPageName( 'Banner_test.html' ) ); 23 | } 24 | 25 | public function testAdditionalContextValuesAreInsertedIntoPlaceholders() { 26 | $context = [ 27 | 'campaign' => 'B16WMDE_mobile', 28 | 'name' => '_01' 29 | ]; 30 | $translator = new FileToPageNameTranslator( '/^Banner(.*)\.html$/', '{{campaign}}{{1}}{{2}}{{name}}', $context ); 31 | $this->assertSame( 'B16WMDE_mobile_test_01', $translator->getPageName( 'Banner_test.html' ) ); 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/PageUpload/PageUploadUseCase.php: -------------------------------------------------------------------------------- 1 | pageGetter = $pageGetter; 22 | $this->revisionSaver = $revisionSaver; 23 | } 24 | 25 | public function uploadIfChanged( PageUploadRequest $request ) : PageUploadResponse { 26 | $page = $this->pageGetter->getFromTitle( $request->getPageName() ); 27 | 28 | if ( empty ( $page->getPageIdentifier()->getId() ) ) { 29 | return PageUploadResponse::newFailureResponse( sprintf( 'Page \'%s\' does not exist', $request->getPageName() ) ); 30 | } 31 | 32 | $revision = $page->getRevisions()->getLatest(); 33 | $lastModified = ( new \DateTime( $revision->getTimestamp() ) ); 34 | if ( $lastModified >= $request->getLastChange() ) { 35 | return PageUploadResponse::newNoOpResponse( 'File is older than page' ); 36 | } 37 | 38 | $content = new Content( $request->getNewContent() ); 39 | $newRevision = new Revision( $content, $page->getPageIdentifier() ); 40 | 41 | if ( $this->revisionSaver->save( $newRevision, $this->getEditInfo( $request ) ) ) { 42 | return PageUploadResponse::newSuccessResponse( sprintf( "Content was uploaded to '%s'", $request->getPageName() ) ); 43 | } 44 | return PageUploadResponse::newFailureResponse( 'Content upload failed' ); 45 | } 46 | 47 | /** 48 | * @param PageUploadRequest $request 49 | * @return EditInfo|null 50 | */ 51 | private function getEditInfo( PageUploadRequest $request ) { 52 | if ( $request->getEditMessage() ) { 53 | return new EditInfo( $request->getEditMessage() ); 54 | } 55 | return null; 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # WMDE Banner Toolkit 2 | 3 | This command line tool is managing fundraising campaign banners on a wiki. 4 | 5 | ## Installation 6 | 7 | Install the command line tool as a global command 8 | 9 | composer install -g wmde/banner-toolkit 10 | 11 | ## Usage 12 | 13 | ### Concepts and conventions 14 | 15 | Banner names in the wiki should follow the Schema `__`. 16 | Example name: `C16WMDE_01_161224_ctrl` 17 | 18 | * `` is the general campaign prefix, common to all banners of a campaign. 19 | Example: `C16WMDE` `C15WMDE_mobile_`, etc 20 | * `` is the test number and the approximate date (in YYMMDD format) the test was created/went live. 21 | Example: `01_161112`, `10_16123024` 22 | * `` are the different variants of a banner, usually `ctrl` and `var` 23 | 24 | ### Create credentials and campaign configuration 25 | Copy the files from the `config-examples` directory to the files `.env` and `.campaign_config`. Put the files in the directory where you will edit and upload the banners. 26 | 27 | ### Uploading banners 28 | 29 | **Attention:** If you're using CentralNotice, you must first create one or more banners in CentralNotice. This will create the banner text as wiki pages in the `MediaWiki` namespace. *It does not work the other way around!* 30 | 31 | Create banner HTML files named after variants, e.g. `Banner_ctrl.html` and `Banner_var.html`. 32 | 33 | Call the command like this (changing the placeholders): 34 | 35 | banner-toolkit upload 36 | 37 | The command will then look for HTML files matching the `Banner_.html` pattern and copy the file contents to the corresponding page. The command figures out the page name by combining the page prefix and campaign name from the configuration, the test name and the variant parts in the file names. 38 | 39 | If you want to have an edit comment for the banners, use the `-m` Parameter: 40 | 41 | banner-toolkit upload -m "banner redesign" 42 | 43 | ### Automatic upload 44 | 45 | **TODO:** Describe how to integrate with Git commit hooks or automatic upload on saving in the editor, with [Watchman](https://facebook.github.io/watchman/). 46 | 47 | ## Why use this tool instead of CentralNotice editor? 48 | 49 | On CentralNotice you only have a textarea for entering banner code. That means you lose focus when you save, have no line numbers and syntax highlighting, no indentation tools except your spacebar. 50 | 51 | Furthermore, this tool will probably expanded with cool stuff to further modularize the banner code and re-assemble it before uploading. 52 | -------------------------------------------------------------------------------- /tests/CliConfigurationTest.php: -------------------------------------------------------------------------------- 1 | 's33cr3t', 17 | 'user' => 'nemo' 18 | ]; 19 | $settings = [ 20 | 'api_url' => 'http://localhost/w/api.php', 21 | 'page_prefix' => 'Web:Banner/', 22 | 'campaign_name' => 'B16WMDE' 23 | ]; 24 | $config = $processor->processConfiguration( 25 | $configuration, 26 | [ $credentials, $settings ] 27 | ); 28 | $expectedConfig = [ 29 | 'password' => 's33cr3t', 30 | 'user' => 'nemo', 31 | 'api_url' => 'http://localhost/w/api.php', 32 | 'page_prefix' => 'Web:Banner/', 33 | 'campaign_name' => 'B16WMDE' 34 | ]; 35 | $this->assertEquals( $expectedConfig, $config ); 36 | } 37 | 38 | public function testApiUrlIsRequired() { 39 | $processor = new Processor(); 40 | $configuration = new CliConfiguration(); 41 | try { 42 | $processor->processConfiguration( 43 | $configuration, 44 | [ [ 45 | 'api_url' => '', 46 | 'password' => 's33cr3t', 47 | 'user' => 'nemo' 48 | ] ] 49 | ); 50 | $this->fail( 'Missing API URL should throw an exception' ); 51 | } catch ( InvalidConfigurationException $e ) { 52 | $this->assertContains( 'cli.api_url', $e->getMessage() ); 53 | } 54 | } 55 | 56 | public function testUsernameIsRequired() { 57 | $processor = new Processor(); 58 | $configuration = new CliConfiguration(); 59 | try { 60 | $processor->processConfiguration( 61 | $configuration, 62 | [ [ 63 | 'api_url' => 'http://localhost/w/api.php', 64 | 'password' => 's33cr3t', 65 | 'user' => '' 66 | ] ] 67 | ); 68 | $this->fail( 'Missing user name should throw an exception' ); 69 | } catch ( InvalidConfigurationException $e ) { 70 | $this->assertContains( 'cli.user', $e->getMessage() ); 71 | } 72 | } 73 | 74 | public function testPasswordIsRequired() { 75 | $processor = new Processor(); 76 | $configuration = new CliConfiguration(); 77 | try { 78 | $processor->processConfiguration( 79 | $configuration, 80 | [ [ 81 | 'api_url' => 'http://localhost/w/api.php', 82 | 'password' => '', 83 | 'user' => 'nemo' 84 | ] ] 85 | ); 86 | $this->fail( 'Missing password should throw an exception' ); 87 | } catch ( InvalidConfigurationException $e ) { 88 | $this->assertContains( 'cli.password', $e->getMessage() ); 89 | } 90 | } 91 | } 92 | -------------------------------------------------------------------------------- /phpcs.xml: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 0 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 0 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 0 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 0 107 | 108 | 109 | 110 | -------------------------------------------------------------------------------- /src/Commands/UploadCommand.php: -------------------------------------------------------------------------------- 1 | .*).html$/'; 26 | const FILE_GLOB = 'Banner_*.html'; 27 | 28 | protected function configure() 29 | { 30 | $this->setName( 'upload' ) 31 | ->setDescription( 'Upload banner files to wiki' ) 32 | ->addOption( 'api_url', null, InputOption::VALUE_REQUIRED, 'API url, e.g. https://meta.wikimedia.org/w/api.php' ) 33 | ->addOption( 'user', 'u', InputOption::VALUE_REQUIRED, 'User name' ) 34 | ->addOption( 'password', 'p', InputOption::VALUE_REQUIRED, 'Password' ) 35 | ->addOption( 'page_prefix', 'w', InputOption::VALUE_REQUIRED, 'Namespace and page prefix on wiki' ) 36 | ->addOption( 'campaign_name', 'c', InputOption::VALUE_REQUIRED, 'Campaign prefix, e.g. B16WMDE_' ) 37 | ->addOption( 'config_file', null, InputOption::VALUE_REQUIRED, 'Config file for all options', '.campaign_config' ) 38 | ->addOption( 'message', 'm', InputOption::VALUE_REQUIRED, 'Edit message for the wiki' ) 39 | ->addArgument( 'test_name', InputArgument::REQUIRED, 'Test name (without campaign prefix), e.g. 20_161224' ); 40 | } 41 | 42 | protected function execute( InputInterface $input, OutputInterface $output ) 43 | { 44 | try { 45 | $config = $this->getConfigFromInputAndFiles( $input ); 46 | } catch ( InvalidConfigurationException $ex ) { 47 | $output->writeln( '' .$ex->getMessage() . '' ); 48 | return; 49 | } 50 | 51 | $fileToPageMapper = $this->createFileToPageMapper( $config, $input->getArgument( 'test_name' ) ); 52 | $useCase = $this->newUseCase( $config ); 53 | foreach ( glob( self::FILE_GLOB ) as $file ) { 54 | $this->outputResponse( 55 | $useCase->uploadIfChanged( $this->getRequestFromFilename( $file, $fileToPageMapper, $input->getOption( 'message' ) ?? '' ) ), 56 | $output 57 | ); 58 | } 59 | } 60 | 61 | private function newMediawikiServices( string $apiUrl, string $user, string $password ): MediawikiFactory 62 | { 63 | $api = new MediawikiApi( $apiUrl ); 64 | $api->login( new ApiUser( $user, $password ) ); 65 | return new MediawikiFactory( $api ); 66 | } 67 | 68 | private function createFileToPageMapper( array $config, string $testName ): FileToPageNameTranslator 69 | { 70 | $context = [ 71 | 'page_prefix' => $config['page_prefix'], 72 | 'campaign_name' => $config['campaign_name'], 73 | 'test_name' => $testName 74 | ]; 75 | return new FileToPageNameTranslator( self::FILE_PATTERN_REGEX, self::BANNER_PAGE_NAME_TEMPLATE, $context ); 76 | } 77 | 78 | private function getRequestFromFilename( string $file, FileToPageNameTranslator $fileToPageMapper, 79 | string $editMessage ): PageUploadRequest 80 | { 81 | return new PageUploadRequest( 82 | $fileToPageMapper->getPageName( $file ), 83 | new \DateTime( '@' . filemtime( $file ) ), 84 | file_get_contents( $file ), 85 | $editMessage 86 | ); 87 | } 88 | 89 | private function newUseCase( array $config ): PageUploadUseCase 90 | { 91 | $services = $this->newMediawikiServices( 92 | $config['api_url'], 93 | $config['user'], 94 | $config['password'] 95 | ); 96 | return new PageUploadUseCase( $services->newPageGetter(), $services->newRevisionSaver() ); 97 | } 98 | 99 | private function outputResponse( PageUploadResponse $response, OutputInterface $output ) 100 | { 101 | if ( !$response->isSuccess() ) { 102 | $output->writeln( '' . $response->getMessage() . '' ); 103 | return; 104 | } 105 | if ( $response->contentHasChanged() ) { 106 | $output->writeln( '' . $response->getMessage() . '' ); 107 | return; 108 | } 109 | $output->writeln( '' . $response->getMessage() . '' ); 110 | } 111 | 112 | private function getConfigFromInputAndFiles( InputInterface $input ): array 113 | { 114 | $processor = new Processor(); 115 | array_filter( $configs = [ 116 | $this->loadConfigValues( $input->getOption( 'config_file' ) ), 117 | $this->loadConfigValues( '.env' ), 118 | array_filter( [ 119 | 'api_url' => $input->getOption( 'api_url' ), 120 | 'user' => $input->getOption( 'user' ), 121 | 'password' => $input->getOption( 'password' ), 122 | 'page_prefix' => $input->getOption( 'page_prefix' ), 123 | 'campaign_name' => $input->getOption( 'campaign_name' ) 124 | ] ) 125 | ] ); 126 | 127 | return $processor->processConfiguration( new CliConfiguration(), $configs ); 128 | } 129 | 130 | private function loadConfigValues( $name ): array { 131 | if ( !file_exists( $name ) ) { 132 | return []; 133 | } 134 | $values = []; 135 | foreach ( Parser::parse( file_get_contents( $name ) ) as $k => $v ) { 136 | $values[strtolower( $k )] = $v; 137 | } 138 | return $values; 139 | } 140 | 141 | } -------------------------------------------------------------------------------- /tests/PageUploadUseCaseTest.php: -------------------------------------------------------------------------------- 1 | getMockBuilder( PageGetter::class )->disableOriginalConstructor()->getMock(); 26 | $saver = $this->getMockBuilder( RevisionSaver::class )->disableOriginalConstructor()->getMock(); 27 | $useCase = new PageUploadUseCase( $getter, $saver ); 28 | $getter->method( 'getFromTitle' ) 29 | ->willReturn( $this->newNonexistingPage() ); 30 | 31 | $this->assertFalse( $useCase->uploadIfChanged( $this->newRequest() )->isSuccess() ); 32 | } 33 | 34 | private function newNonexistingPage(): Page { 35 | return new Page( new PageIdentifier( null, 0 ) ); 36 | } 37 | 38 | private function newRequest(): PageUploadRequest { 39 | return new PageUploadRequest( self::BANNER_NAME, new \DateTime( self::LAST_CHANGE_TIMESTAMP ), 'New Banner' ); 40 | } 41 | 42 | public function testGivenUnchangedPage_noOpResponseIsCreated() { 43 | $getter = $this->getMockBuilder( PageGetter::class )->disableOriginalConstructor()->getMock(); 44 | $saver = $this->getMockBuilder( RevisionSaver::class )->disableOriginalConstructor()->getMock(); 45 | $useCase = new PageUploadUseCase( $getter, $saver ); 46 | $getter->method( 'getFromTitle' ) 47 | ->willReturn( $this->createPageWithDate( new \DateTime( self::LAST_CHANGE_TIMESTAMP ) ) ); 48 | 49 | $this->assertFalse( $useCase->uploadIfChanged( $this->newRequest() )->contentHasChanged() ); 50 | } 51 | 52 | public function testGivenChangeTimestampDifferenceIsTooLowDueToTimezone_noOpResponseIsCreated() { 53 | $getter = $this->getMockBuilder( PageGetter::class )->disableOriginalConstructor()->getMock(); 54 | $saver = $this->getMockBuilder( RevisionSaver::class )->disableOriginalConstructor()->getMock(); 55 | $useCase = new PageUploadUseCase( $getter, $saver ); 56 | $getter->method( 'getFromTitle' ) 57 | ->willReturn( $this->createPageWithDate( new \DateTime( self::LAST_CHANGE_TIMESTAMP ) ) ); 58 | 59 | $lastChange = new \DateTime( self::LAST_CHANGE_TIMESTAMP, new \DateTimeZone( 'Europe/Berlin' ) ); 60 | $lastChange->modify( '+ 10 minutes' ); 61 | $request = new PageUploadRequest( self::BANNER_NAME, $lastChange, 'New Banner' ); 62 | $this->assertFalse( $useCase->uploadIfChanged( $request )->contentHasChanged() ); 63 | } 64 | 65 | private function createPageWithDate( \DateTime $lastChangeTimestamp ): Page { 66 | $identifier = new PageIdentifier( new Title( self::BANNER_NAME ), self::BANNER_PAGE_ID ); 67 | $page = new Page( $identifier ); 68 | $content = new Content( 'Old Banner' ); 69 | $page->getRevisions()->addRevision( new Revision( $content, $identifier, null, null, null, $lastChangeTimestamp->format( 'Y-m-d\TH:i:s\Z' ) ) ); 70 | return $page; 71 | } 72 | 73 | public function testGivenChangedPage_successReponseIsCreated() { 74 | $getter = $this->getMockBuilder( PageGetter::class )->disableOriginalConstructor()->getMock(); 75 | $saver = $this->getMockBuilder( RevisionSaver::class )->disableOriginalConstructor()->getMock(); 76 | $saver->method( 'save' )->willReturn( true ); 77 | $useCase = new PageUploadUseCase( $getter, $saver ); 78 | $getter->method( 'getFromTitle' ) 79 | ->willReturn( $this->createPageWithDate( ( new \DateTime( self::LAST_CHANGE_TIMESTAMP ) )->modify( '-10 minutes' ) ) ); 80 | 81 | $this->assertTrue( $useCase->uploadIfChanged( $this->newRequest() )->contentHasChanged() ); 82 | } 83 | 84 | public function testFailingUpload_successResponseIsCreated() { 85 | $getter = $this->getMockBuilder( PageGetter::class )->disableOriginalConstructor()->getMock(); 86 | $saver = $this->getMockBuilder( RevisionSaver::class )->disableOriginalConstructor()->getMock(); 87 | $saver->method( 'save' )->willReturn( false ); 88 | $useCase = new PageUploadUseCase( $getter, $saver ); 89 | $getter->method( 'getFromTitle' ) 90 | ->willReturn( $this->createPageWithDate( ( new \DateTime( self::LAST_CHANGE_TIMESTAMP ) )->modify( '-10 minutes' ) ) ); 91 | 92 | $this->assertFalse( $useCase->uploadIfChanged( $this->newRequest() )->contentHasChanged() ); 93 | $this->assertFalse( $useCase->uploadIfChanged( $this->newRequest() )->isSuccess() ); 94 | } 95 | 96 | public function testGivenRequestWithEditMessage_editMessageIsUsed() { 97 | $getter = $this->getMockBuilder( PageGetter::class )->disableOriginalConstructor()->getMock(); 98 | $saver = $this->getMockBuilder( RevisionSaver::class )->disableOriginalConstructor()->getMock(); 99 | $expectedEditInfo = new EditInfo( 'Some changes' ); 100 | $saver->expects( $this->once() ) 101 | ->method( 'save' ) 102 | ->with( $this->anything(), $expectedEditInfo ) 103 | ->willReturn( true ); 104 | $useCase = new PageUploadUseCase( $getter, $saver ); 105 | $getter->method( 'getFromTitle' ) 106 | ->willReturn( $this->createPageWithDate( ( new \DateTime( self::LAST_CHANGE_TIMESTAMP ) )->modify( '-10 minutes' ) ) ); 107 | 108 | $request = new PageUploadRequest( 109 | self::BANNER_NAME, 110 | new \DateTime( self::LAST_CHANGE_TIMESTAMP ), 111 | 'New Banner', 112 | 'Some changes' 113 | ); 114 | $this->assertTrue( $useCase->uploadIfChanged( $request )->contentHasChanged() ); 115 | } 116 | 117 | } 118 | -------------------------------------------------------------------------------- /composer.lock: -------------------------------------------------------------------------------- 1 | { 2 | "_readme": [ 3 | "This file locks the dependencies of your project to a known state", 4 | "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file", 5 | "This file is @generated automatically" 6 | ], 7 | "hash": "78df26b8ee1819b485ecc1136ab388e6", 8 | "content-hash": "753741c93dac1045c53fdf68a9b646c2", 9 | "packages": [ 10 | { 11 | "name": "addwiki/mediawiki-api", 12 | "version": "0.5.1", 13 | "source": { 14 | "type": "git", 15 | "url": "https://github.com/addwiki/mediawiki-api.git", 16 | "reference": "6e966d299430c65356cf50126581710e30313fd4" 17 | }, 18 | "dist": { 19 | "type": "zip", 20 | "url": "https://api.github.com/repos/addwiki/mediawiki-api/zipball/6e966d299430c65356cf50126581710e30313fd4", 21 | "reference": "6e966d299430c65356cf50126581710e30313fd4", 22 | "shasum": "" 23 | }, 24 | "require": { 25 | "addwiki/mediawiki-api-base": "~1.0", 26 | "addwiki/mediawiki-datamodel": "~0.6.0" 27 | }, 28 | "type": "library", 29 | "extra": { 30 | "branch-alias": { 31 | "dev-master": "0.5.x-dev" 32 | } 33 | }, 34 | "autoload": { 35 | "psr-4": { 36 | "Mediawiki\\Api\\": "src/" 37 | } 38 | }, 39 | "notification-url": "https://packagist.org/downloads/", 40 | "license": [ 41 | "GPL-2.0+" 42 | ], 43 | "authors": [ 44 | { 45 | "name": "Addshore" 46 | } 47 | ], 48 | "description": "A Mediawiki api lib", 49 | "keywords": [ 50 | "mediawiki" 51 | ], 52 | "time": "2015-09-07 14:31:18" 53 | }, 54 | { 55 | "name": "addwiki/mediawiki-api-base", 56 | "version": "1.1.1", 57 | "source": { 58 | "type": "git", 59 | "url": "https://github.com/addwiki/mediawiki-api-base.git", 60 | "reference": "abe560ccef154ef6f9142b1498c3bc19fc41baa7" 61 | }, 62 | "dist": { 63 | "type": "zip", 64 | "url": "https://api.github.com/repos/addwiki/mediawiki-api-base/zipball/abe560ccef154ef6f9142b1498c3bc19fc41baa7", 65 | "reference": "abe560ccef154ef6f9142b1498c3bc19fc41baa7", 66 | "shasum": "" 67 | }, 68 | "require": { 69 | "guzzlehttp/guzzle": "~5.0", 70 | "guzzlehttp/retry-subscriber": "~2.0", 71 | "psr/log": "~1.0" 72 | }, 73 | "type": "library", 74 | "autoload": { 75 | "psr-4": { 76 | "Mediawiki\\Api\\": "src/" 77 | } 78 | }, 79 | "notification-url": "https://packagist.org/downloads/", 80 | "license": [ 81 | "GPL-2.0+" 82 | ], 83 | "authors": [ 84 | { 85 | "name": "Addshore" 86 | } 87 | ], 88 | "description": "A basic Mediawiki api base lib", 89 | "keywords": [ 90 | "mediawiki" 91 | ], 92 | "time": "2016-07-20 08:49:18" 93 | }, 94 | { 95 | "name": "addwiki/mediawiki-datamodel", 96 | "version": "0.6", 97 | "source": { 98 | "type": "git", 99 | "url": "https://github.com/addwiki/mediawiki-datamodel.git", 100 | "reference": "bbc2603db84c87e098907039de060c75d971b5f4" 101 | }, 102 | "dist": { 103 | "type": "zip", 104 | "url": "https://api.github.com/repos/addwiki/mediawiki-datamodel/zipball/bbc2603db84c87e098907039de060c75d971b5f4", 105 | "reference": "bbc2603db84c87e098907039de060c75d971b5f4", 106 | "shasum": "" 107 | }, 108 | "type": "library", 109 | "extra": { 110 | "branch-alias": { 111 | "dev-master": "0.6.x-dev" 112 | } 113 | }, 114 | "autoload": { 115 | "psr-4": { 116 | "Mediawiki\\DataModel\\": "src/" 117 | } 118 | }, 119 | "notification-url": "https://packagist.org/downloads/", 120 | "license": [ 121 | "GPL-2.0+" 122 | ], 123 | "authors": [ 124 | { 125 | "name": "Addshore" 126 | } 127 | ], 128 | "description": "A Mediawiki datamodel", 129 | "keywords": [ 130 | "mediawiki" 131 | ], 132 | "time": "2015-09-04 12:48:13" 133 | }, 134 | { 135 | "name": "guzzlehttp/guzzle", 136 | "version": "5.3.1", 137 | "source": { 138 | "type": "git", 139 | "url": "https://github.com/guzzle/guzzle.git", 140 | "reference": "70f1fa53b71c4647bf2762c09068a95f77e12fb8" 141 | }, 142 | "dist": { 143 | "type": "zip", 144 | "url": "https://api.github.com/repos/guzzle/guzzle/zipball/70f1fa53b71c4647bf2762c09068a95f77e12fb8", 145 | "reference": "70f1fa53b71c4647bf2762c09068a95f77e12fb8", 146 | "shasum": "" 147 | }, 148 | "require": { 149 | "guzzlehttp/ringphp": "^1.1", 150 | "php": ">=5.4.0" 151 | }, 152 | "require-dev": { 153 | "ext-curl": "*", 154 | "phpunit/phpunit": "^4.0" 155 | }, 156 | "type": "library", 157 | "autoload": { 158 | "psr-4": { 159 | "GuzzleHttp\\": "src/" 160 | } 161 | }, 162 | "notification-url": "https://packagist.org/downloads/", 163 | "license": [ 164 | "MIT" 165 | ], 166 | "authors": [ 167 | { 168 | "name": "Michael Dowling", 169 | "email": "mtdowling@gmail.com", 170 | "homepage": "https://github.com/mtdowling" 171 | } 172 | ], 173 | "description": "Guzzle is a PHP HTTP client library and framework for building RESTful web service clients", 174 | "homepage": "http://guzzlephp.org/", 175 | "keywords": [ 176 | "client", 177 | "curl", 178 | "framework", 179 | "http", 180 | "http client", 181 | "rest", 182 | "web service" 183 | ], 184 | "time": "2016-07-15 19:28:39" 185 | }, 186 | { 187 | "name": "guzzlehttp/retry-subscriber", 188 | "version": "2.0.2", 189 | "source": { 190 | "type": "git", 191 | "url": "https://github.com/guzzle/retry-subscriber.git", 192 | "reference": "f13a4c640b823e9eaf06975d8e8981f9551250e8" 193 | }, 194 | "dist": { 195 | "type": "zip", 196 | "url": "https://api.github.com/repos/guzzle/retry-subscriber/zipball/f13a4c640b823e9eaf06975d8e8981f9551250e8", 197 | "reference": "f13a4c640b823e9eaf06975d8e8981f9551250e8", 198 | "shasum": "" 199 | }, 200 | "require": { 201 | "guzzlehttp/guzzle": "~5.1", 202 | "php": ">=5.4.0" 203 | }, 204 | "require-dev": { 205 | "guzzlehttp/log-subscriber": "~1.0", 206 | "phpunit/phpunit": "~4.0" 207 | }, 208 | "type": "library", 209 | "extra": { 210 | "branch-alias": { 211 | "dev-master": "1.0-dev" 212 | } 213 | }, 214 | "autoload": { 215 | "psr-4": { 216 | "GuzzleHttp\\Subscriber\\Retry\\": "src/" 217 | } 218 | }, 219 | "notification-url": "https://packagist.org/downloads/", 220 | "license": [ 221 | "MIT" 222 | ], 223 | "authors": [ 224 | { 225 | "name": "Michael Dowling", 226 | "email": "mtdowling@gmail.com", 227 | "homepage": "https://github.com/mtdowling" 228 | } 229 | ], 230 | "description": "Retries failed HTTP requests using customizable retry strategies (Guzzle 4+)", 231 | "homepage": "http://guzzlephp.org/", 232 | "keywords": [ 233 | "Guzzle", 234 | "http", 235 | "retry" 236 | ], 237 | "time": "2014-12-19 20:42:37" 238 | }, 239 | { 240 | "name": "guzzlehttp/ringphp", 241 | "version": "1.1.0", 242 | "source": { 243 | "type": "git", 244 | "url": "https://github.com/guzzle/RingPHP.git", 245 | "reference": "dbbb91d7f6c191e5e405e900e3102ac7f261bc0b" 246 | }, 247 | "dist": { 248 | "type": "zip", 249 | "url": "https://api.github.com/repos/guzzle/RingPHP/zipball/dbbb91d7f6c191e5e405e900e3102ac7f261bc0b", 250 | "reference": "dbbb91d7f6c191e5e405e900e3102ac7f261bc0b", 251 | "shasum": "" 252 | }, 253 | "require": { 254 | "guzzlehttp/streams": "~3.0", 255 | "php": ">=5.4.0", 256 | "react/promise": "~2.0" 257 | }, 258 | "require-dev": { 259 | "ext-curl": "*", 260 | "phpunit/phpunit": "~4.0" 261 | }, 262 | "suggest": { 263 | "ext-curl": "Guzzle will use specific adapters if cURL is present" 264 | }, 265 | "type": "library", 266 | "extra": { 267 | "branch-alias": { 268 | "dev-master": "1.1-dev" 269 | } 270 | }, 271 | "autoload": { 272 | "psr-4": { 273 | "GuzzleHttp\\Ring\\": "src/" 274 | } 275 | }, 276 | "notification-url": "https://packagist.org/downloads/", 277 | "license": [ 278 | "MIT" 279 | ], 280 | "authors": [ 281 | { 282 | "name": "Michael Dowling", 283 | "email": "mtdowling@gmail.com", 284 | "homepage": "https://github.com/mtdowling" 285 | } 286 | ], 287 | "description": "Provides a simple API and specification that abstracts away the details of HTTP into a single PHP function.", 288 | "time": "2015-05-20 03:37:09" 289 | }, 290 | { 291 | "name": "guzzlehttp/streams", 292 | "version": "3.0.0", 293 | "source": { 294 | "type": "git", 295 | "url": "https://github.com/guzzle/streams.git", 296 | "reference": "47aaa48e27dae43d39fc1cea0ccf0d84ac1a2ba5" 297 | }, 298 | "dist": { 299 | "type": "zip", 300 | "url": "https://api.github.com/repos/guzzle/streams/zipball/47aaa48e27dae43d39fc1cea0ccf0d84ac1a2ba5", 301 | "reference": "47aaa48e27dae43d39fc1cea0ccf0d84ac1a2ba5", 302 | "shasum": "" 303 | }, 304 | "require": { 305 | "php": ">=5.4.0" 306 | }, 307 | "require-dev": { 308 | "phpunit/phpunit": "~4.0" 309 | }, 310 | "type": "library", 311 | "extra": { 312 | "branch-alias": { 313 | "dev-master": "3.0-dev" 314 | } 315 | }, 316 | "autoload": { 317 | "psr-4": { 318 | "GuzzleHttp\\Stream\\": "src/" 319 | } 320 | }, 321 | "notification-url": "https://packagist.org/downloads/", 322 | "license": [ 323 | "MIT" 324 | ], 325 | "authors": [ 326 | { 327 | "name": "Michael Dowling", 328 | "email": "mtdowling@gmail.com", 329 | "homepage": "https://github.com/mtdowling" 330 | } 331 | ], 332 | "description": "Provides a simple abstraction over streams of data", 333 | "homepage": "http://guzzlephp.org/", 334 | "keywords": [ 335 | "Guzzle", 336 | "stream" 337 | ], 338 | "time": "2014-10-12 19:18:40" 339 | }, 340 | { 341 | "name": "m1/env", 342 | "version": "2.1.0", 343 | "source": { 344 | "type": "git", 345 | "url": "https://github.com/m1/Env.git", 346 | "reference": "d87eddd031f2aa5450fa04bb1325de8a489b3cd0" 347 | }, 348 | "dist": { 349 | "type": "zip", 350 | "url": "https://api.github.com/repos/m1/Env/zipball/d87eddd031f2aa5450fa04bb1325de8a489b3cd0", 351 | "reference": "d87eddd031f2aa5450fa04bb1325de8a489b3cd0", 352 | "shasum": "" 353 | }, 354 | "require": { 355 | "php": ">=5.3.0" 356 | }, 357 | "require-dev": { 358 | "phpunit/phpunit": "4.*", 359 | "scrutinizer/ocular": "~1.1", 360 | "squizlabs/php_codesniffer": "^2.3" 361 | }, 362 | "suggest": { 363 | "josegonzalez/dotenv": "For loading of .env", 364 | "m1/vars": "For loading of configs" 365 | }, 366 | "type": "library", 367 | "autoload": { 368 | "psr-4": { 369 | "M1\\Env\\": "src" 370 | } 371 | }, 372 | "notification-url": "https://packagist.org/downloads/", 373 | "license": [ 374 | "MIT" 375 | ], 376 | "authors": [ 377 | { 378 | "name": "Miles Croxford", 379 | "email": "hello@milescroxford.com", 380 | "homepage": "http://milescroxford.com", 381 | "role": "Developer" 382 | } 383 | ], 384 | "description": "Env is a lightweight library bringing .env file parser compatibility to PHP. In short - it enables you to read .env files with PHP.", 385 | "homepage": "https://github.com/m1/Env", 386 | "keywords": [ 387 | ".env", 388 | "config", 389 | "dotenv", 390 | "env", 391 | "loader", 392 | "m1", 393 | "parser", 394 | "support" 395 | ], 396 | "time": "2016-10-06 19:31:28" 397 | }, 398 | { 399 | "name": "psr/log", 400 | "version": "1.0.2", 401 | "source": { 402 | "type": "git", 403 | "url": "https://github.com/php-fig/log.git", 404 | "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d" 405 | }, 406 | "dist": { 407 | "type": "zip", 408 | "url": "https://api.github.com/repos/php-fig/log/zipball/4ebe3a8bf773a19edfe0a84b6585ba3d401b724d", 409 | "reference": "4ebe3a8bf773a19edfe0a84b6585ba3d401b724d", 410 | "shasum": "" 411 | }, 412 | "require": { 413 | "php": ">=5.3.0" 414 | }, 415 | "type": "library", 416 | "extra": { 417 | "branch-alias": { 418 | "dev-master": "1.0.x-dev" 419 | } 420 | }, 421 | "autoload": { 422 | "psr-4": { 423 | "Psr\\Log\\": "Psr/Log/" 424 | } 425 | }, 426 | "notification-url": "https://packagist.org/downloads/", 427 | "license": [ 428 | "MIT" 429 | ], 430 | "authors": [ 431 | { 432 | "name": "PHP-FIG", 433 | "homepage": "http://www.php-fig.org/" 434 | } 435 | ], 436 | "description": "Common interface for logging libraries", 437 | "homepage": "https://github.com/php-fig/log", 438 | "keywords": [ 439 | "log", 440 | "psr", 441 | "psr-3" 442 | ], 443 | "time": "2016-10-10 12:19:37" 444 | }, 445 | { 446 | "name": "react/promise", 447 | "version": "v2.4.1", 448 | "source": { 449 | "type": "git", 450 | "url": "https://github.com/reactphp/promise.git", 451 | "reference": "8025426794f1944de806618671d4fa476dc7626f" 452 | }, 453 | "dist": { 454 | "type": "zip", 455 | "url": "https://api.github.com/repos/reactphp/promise/zipball/8025426794f1944de806618671d4fa476dc7626f", 456 | "reference": "8025426794f1944de806618671d4fa476dc7626f", 457 | "shasum": "" 458 | }, 459 | "require": { 460 | "php": ">=5.4.0" 461 | }, 462 | "type": "library", 463 | "extra": { 464 | "branch-alias": { 465 | "dev-master": "2.0-dev" 466 | } 467 | }, 468 | "autoload": { 469 | "psr-4": { 470 | "React\\Promise\\": "src/" 471 | }, 472 | "files": [ 473 | "src/functions_include.php" 474 | ] 475 | }, 476 | "notification-url": "https://packagist.org/downloads/", 477 | "license": [ 478 | "MIT" 479 | ], 480 | "authors": [ 481 | { 482 | "name": "Jan Sorgalla", 483 | "email": "jsorgalla@gmail.com" 484 | } 485 | ], 486 | "description": "A lightweight implementation of CommonJS Promises/A for PHP", 487 | "time": "2016-05-03 17:50:52" 488 | }, 489 | { 490 | "name": "symfony/config", 491 | "version": "v3.1.6", 492 | "source": { 493 | "type": "git", 494 | "url": "https://github.com/symfony/config.git", 495 | "reference": "949e7e846743a7f9e46dc50eb639d5fde1f53341" 496 | }, 497 | "dist": { 498 | "type": "zip", 499 | "url": "https://api.github.com/repos/symfony/config/zipball/949e7e846743a7f9e46dc50eb639d5fde1f53341", 500 | "reference": "949e7e846743a7f9e46dc50eb639d5fde1f53341", 501 | "shasum": "" 502 | }, 503 | "require": { 504 | "php": ">=5.5.9", 505 | "symfony/filesystem": "~2.8|~3.0" 506 | }, 507 | "suggest": { 508 | "symfony/yaml": "To use the yaml reference dumper" 509 | }, 510 | "type": "library", 511 | "extra": { 512 | "branch-alias": { 513 | "dev-master": "3.1-dev" 514 | } 515 | }, 516 | "autoload": { 517 | "psr-4": { 518 | "Symfony\\Component\\Config\\": "" 519 | }, 520 | "exclude-from-classmap": [ 521 | "/Tests/" 522 | ] 523 | }, 524 | "notification-url": "https://packagist.org/downloads/", 525 | "license": [ 526 | "MIT" 527 | ], 528 | "authors": [ 529 | { 530 | "name": "Fabien Potencier", 531 | "email": "fabien@symfony.com" 532 | }, 533 | { 534 | "name": "Symfony Community", 535 | "homepage": "https://symfony.com/contributors" 536 | } 537 | ], 538 | "description": "Symfony Config Component", 539 | "homepage": "https://symfony.com", 540 | "time": "2016-09-25 08:27:07" 541 | }, 542 | { 543 | "name": "symfony/console", 544 | "version": "v3.1.6", 545 | "source": { 546 | "type": "git", 547 | "url": "https://github.com/symfony/console.git", 548 | "reference": "c99da1119ae61e15de0e4829196b9fba6f73d065" 549 | }, 550 | "dist": { 551 | "type": "zip", 552 | "url": "https://api.github.com/repos/symfony/console/zipball/c99da1119ae61e15de0e4829196b9fba6f73d065", 553 | "reference": "c99da1119ae61e15de0e4829196b9fba6f73d065", 554 | "shasum": "" 555 | }, 556 | "require": { 557 | "php": ">=5.5.9", 558 | "symfony/debug": "~2.8|~3.0", 559 | "symfony/polyfill-mbstring": "~1.0" 560 | }, 561 | "require-dev": { 562 | "psr/log": "~1.0", 563 | "symfony/event-dispatcher": "~2.8|~3.0", 564 | "symfony/process": "~2.8|~3.0" 565 | }, 566 | "suggest": { 567 | "psr/log": "For using the console logger", 568 | "symfony/event-dispatcher": "", 569 | "symfony/process": "" 570 | }, 571 | "type": "library", 572 | "extra": { 573 | "branch-alias": { 574 | "dev-master": "3.1-dev" 575 | } 576 | }, 577 | "autoload": { 578 | "psr-4": { 579 | "Symfony\\Component\\Console\\": "" 580 | }, 581 | "exclude-from-classmap": [ 582 | "/Tests/" 583 | ] 584 | }, 585 | "notification-url": "https://packagist.org/downloads/", 586 | "license": [ 587 | "MIT" 588 | ], 589 | "authors": [ 590 | { 591 | "name": "Fabien Potencier", 592 | "email": "fabien@symfony.com" 593 | }, 594 | { 595 | "name": "Symfony Community", 596 | "homepage": "https://symfony.com/contributors" 597 | } 598 | ], 599 | "description": "Symfony Console Component", 600 | "homepage": "https://symfony.com", 601 | "time": "2016-10-06 01:44:51" 602 | }, 603 | { 604 | "name": "symfony/debug", 605 | "version": "v3.1.6", 606 | "source": { 607 | "type": "git", 608 | "url": "https://github.com/symfony/debug.git", 609 | "reference": "e2b3f74a67fc928adc3c1b9027f73e1bc01190a8" 610 | }, 611 | "dist": { 612 | "type": "zip", 613 | "url": "https://api.github.com/repos/symfony/debug/zipball/e2b3f74a67fc928adc3c1b9027f73e1bc01190a8", 614 | "reference": "e2b3f74a67fc928adc3c1b9027f73e1bc01190a8", 615 | "shasum": "" 616 | }, 617 | "require": { 618 | "php": ">=5.5.9", 619 | "psr/log": "~1.0" 620 | }, 621 | "conflict": { 622 | "symfony/http-kernel": ">=2.3,<2.3.24|~2.4.0|>=2.5,<2.5.9|>=2.6,<2.6.2" 623 | }, 624 | "require-dev": { 625 | "symfony/class-loader": "~2.8|~3.0", 626 | "symfony/http-kernel": "~2.8|~3.0" 627 | }, 628 | "type": "library", 629 | "extra": { 630 | "branch-alias": { 631 | "dev-master": "3.1-dev" 632 | } 633 | }, 634 | "autoload": { 635 | "psr-4": { 636 | "Symfony\\Component\\Debug\\": "" 637 | }, 638 | "exclude-from-classmap": [ 639 | "/Tests/" 640 | ] 641 | }, 642 | "notification-url": "https://packagist.org/downloads/", 643 | "license": [ 644 | "MIT" 645 | ], 646 | "authors": [ 647 | { 648 | "name": "Fabien Potencier", 649 | "email": "fabien@symfony.com" 650 | }, 651 | { 652 | "name": "Symfony Community", 653 | "homepage": "https://symfony.com/contributors" 654 | } 655 | ], 656 | "description": "Symfony Debug Component", 657 | "homepage": "https://symfony.com", 658 | "time": "2016-09-06 11:02:40" 659 | }, 660 | { 661 | "name": "symfony/filesystem", 662 | "version": "v3.1.6", 663 | "source": { 664 | "type": "git", 665 | "url": "https://github.com/symfony/filesystem.git", 666 | "reference": "0565b61bf098cb4dc09f4f103f033138ae4f42c6" 667 | }, 668 | "dist": { 669 | "type": "zip", 670 | "url": "https://api.github.com/repos/symfony/filesystem/zipball/0565b61bf098cb4dc09f4f103f033138ae4f42c6", 671 | "reference": "0565b61bf098cb4dc09f4f103f033138ae4f42c6", 672 | "shasum": "" 673 | }, 674 | "require": { 675 | "php": ">=5.5.9" 676 | }, 677 | "type": "library", 678 | "extra": { 679 | "branch-alias": { 680 | "dev-master": "3.1-dev" 681 | } 682 | }, 683 | "autoload": { 684 | "psr-4": { 685 | "Symfony\\Component\\Filesystem\\": "" 686 | }, 687 | "exclude-from-classmap": [ 688 | "/Tests/" 689 | ] 690 | }, 691 | "notification-url": "https://packagist.org/downloads/", 692 | "license": [ 693 | "MIT" 694 | ], 695 | "authors": [ 696 | { 697 | "name": "Fabien Potencier", 698 | "email": "fabien@symfony.com" 699 | }, 700 | { 701 | "name": "Symfony Community", 702 | "homepage": "https://symfony.com/contributors" 703 | } 704 | ], 705 | "description": "Symfony Filesystem Component", 706 | "homepage": "https://symfony.com", 707 | "time": "2016-10-18 04:30:12" 708 | }, 709 | { 710 | "name": "symfony/polyfill-mbstring", 711 | "version": "v1.3.0", 712 | "source": { 713 | "type": "git", 714 | "url": "https://github.com/symfony/polyfill-mbstring.git", 715 | "reference": "e79d363049d1c2128f133a2667e4f4190904f7f4" 716 | }, 717 | "dist": { 718 | "type": "zip", 719 | "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/e79d363049d1c2128f133a2667e4f4190904f7f4", 720 | "reference": "e79d363049d1c2128f133a2667e4f4190904f7f4", 721 | "shasum": "" 722 | }, 723 | "require": { 724 | "php": ">=5.3.3" 725 | }, 726 | "suggest": { 727 | "ext-mbstring": "For best performance" 728 | }, 729 | "type": "library", 730 | "extra": { 731 | "branch-alias": { 732 | "dev-master": "1.3-dev" 733 | } 734 | }, 735 | "autoload": { 736 | "psr-4": { 737 | "Symfony\\Polyfill\\Mbstring\\": "" 738 | }, 739 | "files": [ 740 | "bootstrap.php" 741 | ] 742 | }, 743 | "notification-url": "https://packagist.org/downloads/", 744 | "license": [ 745 | "MIT" 746 | ], 747 | "authors": [ 748 | { 749 | "name": "Nicolas Grekas", 750 | "email": "p@tchwork.com" 751 | }, 752 | { 753 | "name": "Symfony Community", 754 | "homepage": "https://symfony.com/contributors" 755 | } 756 | ], 757 | "description": "Symfony polyfill for the Mbstring extension", 758 | "homepage": "https://symfony.com", 759 | "keywords": [ 760 | "compatibility", 761 | "mbstring", 762 | "polyfill", 763 | "portable", 764 | "shim" 765 | ], 766 | "time": "2016-11-14 01:06:16" 767 | } 768 | ], 769 | "packages-dev": [ 770 | { 771 | "name": "doctrine/instantiator", 772 | "version": "1.0.5", 773 | "source": { 774 | "type": "git", 775 | "url": "https://github.com/doctrine/instantiator.git", 776 | "reference": "8e884e78f9f0eb1329e445619e04456e64d8051d" 777 | }, 778 | "dist": { 779 | "type": "zip", 780 | "url": "https://api.github.com/repos/doctrine/instantiator/zipball/8e884e78f9f0eb1329e445619e04456e64d8051d", 781 | "reference": "8e884e78f9f0eb1329e445619e04456e64d8051d", 782 | "shasum": "" 783 | }, 784 | "require": { 785 | "php": ">=5.3,<8.0-DEV" 786 | }, 787 | "require-dev": { 788 | "athletic/athletic": "~0.1.8", 789 | "ext-pdo": "*", 790 | "ext-phar": "*", 791 | "phpunit/phpunit": "~4.0", 792 | "squizlabs/php_codesniffer": "~2.0" 793 | }, 794 | "type": "library", 795 | "extra": { 796 | "branch-alias": { 797 | "dev-master": "1.0.x-dev" 798 | } 799 | }, 800 | "autoload": { 801 | "psr-4": { 802 | "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/" 803 | } 804 | }, 805 | "notification-url": "https://packagist.org/downloads/", 806 | "license": [ 807 | "MIT" 808 | ], 809 | "authors": [ 810 | { 811 | "name": "Marco Pivetta", 812 | "email": "ocramius@gmail.com", 813 | "homepage": "http://ocramius.github.com/" 814 | } 815 | ], 816 | "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors", 817 | "homepage": "https://github.com/doctrine/instantiator", 818 | "keywords": [ 819 | "constructor", 820 | "instantiate" 821 | ], 822 | "time": "2015-06-14 21:17:01" 823 | }, 824 | { 825 | "name": "mediawiki/mediawiki-codesniffer", 826 | "version": "v0.7.2", 827 | "source": { 828 | "type": "git", 829 | "url": "https://github.com/wikimedia/mediawiki-tools-codesniffer.git", 830 | "reference": "6b713bcbb9c20a3bdad76f9477458c9b4ae0773b" 831 | }, 832 | "dist": { 833 | "type": "zip", 834 | "url": "https://api.github.com/repos/wikimedia/mediawiki-tools-codesniffer/zipball/6b713bcbb9c20a3bdad76f9477458c9b4ae0773b", 835 | "reference": "6b713bcbb9c20a3bdad76f9477458c9b4ae0773b", 836 | "shasum": "" 837 | }, 838 | "require": { 839 | "php": ">= 5.5.9", 840 | "squizlabs/php_codesniffer": "2.6.0" 841 | }, 842 | "require-dev": { 843 | "jakub-onderka/php-parallel-lint": "0.9.*", 844 | "mikey179/vfsstream": "~1.6", 845 | "phpunit/phpunit": "~4.1" 846 | }, 847 | "type": "library", 848 | "notification-url": "https://packagist.org/downloads/", 849 | "license": [ 850 | "GPL-2.0+" 851 | ], 852 | "description": "MediaWiki CodeSniffer Standards", 853 | "homepage": "https://www.mediawiki.org/wiki/Manual:Coding_conventions/PHP", 854 | "keywords": [ 855 | "codesniffer", 856 | "mediawiki" 857 | ], 858 | "time": "2016-05-28 01:08:59" 859 | }, 860 | { 861 | "name": "myclabs/deep-copy", 862 | "version": "1.5.5", 863 | "source": { 864 | "type": "git", 865 | "url": "https://github.com/myclabs/DeepCopy.git", 866 | "reference": "399c1f9781e222f6eb6cc238796f5200d1b7f108" 867 | }, 868 | "dist": { 869 | "type": "zip", 870 | "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/399c1f9781e222f6eb6cc238796f5200d1b7f108", 871 | "reference": "399c1f9781e222f6eb6cc238796f5200d1b7f108", 872 | "shasum": "" 873 | }, 874 | "require": { 875 | "php": ">=5.4.0" 876 | }, 877 | "require-dev": { 878 | "doctrine/collections": "1.*", 879 | "phpunit/phpunit": "~4.1" 880 | }, 881 | "type": "library", 882 | "autoload": { 883 | "psr-4": { 884 | "DeepCopy\\": "src/DeepCopy/" 885 | } 886 | }, 887 | "notification-url": "https://packagist.org/downloads/", 888 | "license": [ 889 | "MIT" 890 | ], 891 | "description": "Create deep copies (clones) of your objects", 892 | "homepage": "https://github.com/myclabs/DeepCopy", 893 | "keywords": [ 894 | "clone", 895 | "copy", 896 | "duplicate", 897 | "object", 898 | "object graph" 899 | ], 900 | "time": "2016-10-31 17:19:45" 901 | }, 902 | { 903 | "name": "phpdocumentor/reflection-common", 904 | "version": "1.0", 905 | "source": { 906 | "type": "git", 907 | "url": "https://github.com/phpDocumentor/ReflectionCommon.git", 908 | "reference": "144c307535e82c8fdcaacbcfc1d6d8eeb896687c" 909 | }, 910 | "dist": { 911 | "type": "zip", 912 | "url": "https://api.github.com/repos/phpDocumentor/ReflectionCommon/zipball/144c307535e82c8fdcaacbcfc1d6d8eeb896687c", 913 | "reference": "144c307535e82c8fdcaacbcfc1d6d8eeb896687c", 914 | "shasum": "" 915 | }, 916 | "require": { 917 | "php": ">=5.5" 918 | }, 919 | "require-dev": { 920 | "phpunit/phpunit": "^4.6" 921 | }, 922 | "type": "library", 923 | "extra": { 924 | "branch-alias": { 925 | "dev-master": "1.0.x-dev" 926 | } 927 | }, 928 | "autoload": { 929 | "psr-4": { 930 | "phpDocumentor\\Reflection\\": [ 931 | "src" 932 | ] 933 | } 934 | }, 935 | "notification-url": "https://packagist.org/downloads/", 936 | "license": [ 937 | "MIT" 938 | ], 939 | "authors": [ 940 | { 941 | "name": "Jaap van Otterdijk", 942 | "email": "opensource@ijaap.nl" 943 | } 944 | ], 945 | "description": "Common reflection classes used by phpdocumentor to reflect the code structure", 946 | "homepage": "http://www.phpdoc.org", 947 | "keywords": [ 948 | "FQSEN", 949 | "phpDocumentor", 950 | "phpdoc", 951 | "reflection", 952 | "static analysis" 953 | ], 954 | "time": "2015-12-27 11:43:31" 955 | }, 956 | { 957 | "name": "phpdocumentor/reflection-docblock", 958 | "version": "3.1.1", 959 | "source": { 960 | "type": "git", 961 | "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git", 962 | "reference": "8331b5efe816ae05461b7ca1e721c01b46bafb3e" 963 | }, 964 | "dist": { 965 | "type": "zip", 966 | "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/8331b5efe816ae05461b7ca1e721c01b46bafb3e", 967 | "reference": "8331b5efe816ae05461b7ca1e721c01b46bafb3e", 968 | "shasum": "" 969 | }, 970 | "require": { 971 | "php": ">=5.5", 972 | "phpdocumentor/reflection-common": "^1.0@dev", 973 | "phpdocumentor/type-resolver": "^0.2.0", 974 | "webmozart/assert": "^1.0" 975 | }, 976 | "require-dev": { 977 | "mockery/mockery": "^0.9.4", 978 | "phpunit/phpunit": "^4.4" 979 | }, 980 | "type": "library", 981 | "autoload": { 982 | "psr-4": { 983 | "phpDocumentor\\Reflection\\": [ 984 | "src/" 985 | ] 986 | } 987 | }, 988 | "notification-url": "https://packagist.org/downloads/", 989 | "license": [ 990 | "MIT" 991 | ], 992 | "authors": [ 993 | { 994 | "name": "Mike van Riel", 995 | "email": "me@mikevanriel.com" 996 | } 997 | ], 998 | "description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.", 999 | "time": "2016-09-30 07:12:33" 1000 | }, 1001 | { 1002 | "name": "phpdocumentor/type-resolver", 1003 | "version": "0.2", 1004 | "source": { 1005 | "type": "git", 1006 | "url": "https://github.com/phpDocumentor/TypeResolver.git", 1007 | "reference": "b39c7a5b194f9ed7bd0dd345c751007a41862443" 1008 | }, 1009 | "dist": { 1010 | "type": "zip", 1011 | "url": "https://api.github.com/repos/phpDocumentor/TypeResolver/zipball/b39c7a5b194f9ed7bd0dd345c751007a41862443", 1012 | "reference": "b39c7a5b194f9ed7bd0dd345c751007a41862443", 1013 | "shasum": "" 1014 | }, 1015 | "require": { 1016 | "php": ">=5.5", 1017 | "phpdocumentor/reflection-common": "^1.0" 1018 | }, 1019 | "require-dev": { 1020 | "mockery/mockery": "^0.9.4", 1021 | "phpunit/phpunit": "^5.2||^4.8.24" 1022 | }, 1023 | "type": "library", 1024 | "extra": { 1025 | "branch-alias": { 1026 | "dev-master": "1.0.x-dev" 1027 | } 1028 | }, 1029 | "autoload": { 1030 | "psr-4": { 1031 | "phpDocumentor\\Reflection\\": [ 1032 | "src/" 1033 | ] 1034 | } 1035 | }, 1036 | "notification-url": "https://packagist.org/downloads/", 1037 | "license": [ 1038 | "MIT" 1039 | ], 1040 | "authors": [ 1041 | { 1042 | "name": "Mike van Riel", 1043 | "email": "me@mikevanriel.com" 1044 | } 1045 | ], 1046 | "time": "2016-06-10 07:14:17" 1047 | }, 1048 | { 1049 | "name": "phpspec/prophecy", 1050 | "version": "v1.6.1", 1051 | "source": { 1052 | "type": "git", 1053 | "url": "https://github.com/phpspec/prophecy.git", 1054 | "reference": "58a8137754bc24b25740d4281399a4a3596058e0" 1055 | }, 1056 | "dist": { 1057 | "type": "zip", 1058 | "url": "https://api.github.com/repos/phpspec/prophecy/zipball/58a8137754bc24b25740d4281399a4a3596058e0", 1059 | "reference": "58a8137754bc24b25740d4281399a4a3596058e0", 1060 | "shasum": "" 1061 | }, 1062 | "require": { 1063 | "doctrine/instantiator": "^1.0.2", 1064 | "php": "^5.3|^7.0", 1065 | "phpdocumentor/reflection-docblock": "^2.0|^3.0.2", 1066 | "sebastian/comparator": "^1.1", 1067 | "sebastian/recursion-context": "^1.0" 1068 | }, 1069 | "require-dev": { 1070 | "phpspec/phpspec": "^2.0" 1071 | }, 1072 | "type": "library", 1073 | "extra": { 1074 | "branch-alias": { 1075 | "dev-master": "1.6.x-dev" 1076 | } 1077 | }, 1078 | "autoload": { 1079 | "psr-0": { 1080 | "Prophecy\\": "src/" 1081 | } 1082 | }, 1083 | "notification-url": "https://packagist.org/downloads/", 1084 | "license": [ 1085 | "MIT" 1086 | ], 1087 | "authors": [ 1088 | { 1089 | "name": "Konstantin Kudryashov", 1090 | "email": "ever.zet@gmail.com", 1091 | "homepage": "http://everzet.com" 1092 | }, 1093 | { 1094 | "name": "Marcello Duarte", 1095 | "email": "marcello.duarte@gmail.com" 1096 | } 1097 | ], 1098 | "description": "Highly opinionated mocking framework for PHP 5.3+", 1099 | "homepage": "https://github.com/phpspec/prophecy", 1100 | "keywords": [ 1101 | "Double", 1102 | "Dummy", 1103 | "fake", 1104 | "mock", 1105 | "spy", 1106 | "stub" 1107 | ], 1108 | "time": "2016-06-07 08:13:47" 1109 | }, 1110 | { 1111 | "name": "phpunit/php-code-coverage", 1112 | "version": "4.0.2", 1113 | "source": { 1114 | "type": "git", 1115 | "url": "https://github.com/sebastianbergmann/php-code-coverage.git", 1116 | "reference": "6cba06ff75a1a63a71033e1a01b89056f3af1e8d" 1117 | }, 1118 | "dist": { 1119 | "type": "zip", 1120 | "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/6cba06ff75a1a63a71033e1a01b89056f3af1e8d", 1121 | "reference": "6cba06ff75a1a63a71033e1a01b89056f3af1e8d", 1122 | "shasum": "" 1123 | }, 1124 | "require": { 1125 | "php": "^5.6 || ^7.0", 1126 | "phpunit/php-file-iterator": "~1.3", 1127 | "phpunit/php-text-template": "~1.2", 1128 | "phpunit/php-token-stream": "^1.4.2", 1129 | "sebastian/code-unit-reverse-lookup": "~1.0", 1130 | "sebastian/environment": "^1.3.2 || ^2.0", 1131 | "sebastian/version": "~1.0|~2.0" 1132 | }, 1133 | "require-dev": { 1134 | "ext-xdebug": ">=2.1.4", 1135 | "phpunit/phpunit": "^5.4" 1136 | }, 1137 | "suggest": { 1138 | "ext-dom": "*", 1139 | "ext-xdebug": ">=2.4.0", 1140 | "ext-xmlwriter": "*" 1141 | }, 1142 | "type": "library", 1143 | "extra": { 1144 | "branch-alias": { 1145 | "dev-master": "4.0.x-dev" 1146 | } 1147 | }, 1148 | "autoload": { 1149 | "classmap": [ 1150 | "src/" 1151 | ] 1152 | }, 1153 | "notification-url": "https://packagist.org/downloads/", 1154 | "license": [ 1155 | "BSD-3-Clause" 1156 | ], 1157 | "authors": [ 1158 | { 1159 | "name": "Sebastian Bergmann", 1160 | "email": "sb@sebastian-bergmann.de", 1161 | "role": "lead" 1162 | } 1163 | ], 1164 | "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.", 1165 | "homepage": "https://github.com/sebastianbergmann/php-code-coverage", 1166 | "keywords": [ 1167 | "coverage", 1168 | "testing", 1169 | "xunit" 1170 | ], 1171 | "time": "2016-11-01 05:06:24" 1172 | }, 1173 | { 1174 | "name": "phpunit/php-file-iterator", 1175 | "version": "1.4.1", 1176 | "source": { 1177 | "type": "git", 1178 | "url": "https://github.com/sebastianbergmann/php-file-iterator.git", 1179 | "reference": "6150bf2c35d3fc379e50c7602b75caceaa39dbf0" 1180 | }, 1181 | "dist": { 1182 | "type": "zip", 1183 | "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/6150bf2c35d3fc379e50c7602b75caceaa39dbf0", 1184 | "reference": "6150bf2c35d3fc379e50c7602b75caceaa39dbf0", 1185 | "shasum": "" 1186 | }, 1187 | "require": { 1188 | "php": ">=5.3.3" 1189 | }, 1190 | "type": "library", 1191 | "extra": { 1192 | "branch-alias": { 1193 | "dev-master": "1.4.x-dev" 1194 | } 1195 | }, 1196 | "autoload": { 1197 | "classmap": [ 1198 | "src/" 1199 | ] 1200 | }, 1201 | "notification-url": "https://packagist.org/downloads/", 1202 | "license": [ 1203 | "BSD-3-Clause" 1204 | ], 1205 | "authors": [ 1206 | { 1207 | "name": "Sebastian Bergmann", 1208 | "email": "sb@sebastian-bergmann.de", 1209 | "role": "lead" 1210 | } 1211 | ], 1212 | "description": "FilterIterator implementation that filters files based on a list of suffixes.", 1213 | "homepage": "https://github.com/sebastianbergmann/php-file-iterator/", 1214 | "keywords": [ 1215 | "filesystem", 1216 | "iterator" 1217 | ], 1218 | "time": "2015-06-21 13:08:43" 1219 | }, 1220 | { 1221 | "name": "phpunit/php-text-template", 1222 | "version": "1.2.1", 1223 | "source": { 1224 | "type": "git", 1225 | "url": "https://github.com/sebastianbergmann/php-text-template.git", 1226 | "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686" 1227 | }, 1228 | "dist": { 1229 | "type": "zip", 1230 | "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/31f8b717e51d9a2afca6c9f046f5d69fc27c8686", 1231 | "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686", 1232 | "shasum": "" 1233 | }, 1234 | "require": { 1235 | "php": ">=5.3.3" 1236 | }, 1237 | "type": "library", 1238 | "autoload": { 1239 | "classmap": [ 1240 | "src/" 1241 | ] 1242 | }, 1243 | "notification-url": "https://packagist.org/downloads/", 1244 | "license": [ 1245 | "BSD-3-Clause" 1246 | ], 1247 | "authors": [ 1248 | { 1249 | "name": "Sebastian Bergmann", 1250 | "email": "sebastian@phpunit.de", 1251 | "role": "lead" 1252 | } 1253 | ], 1254 | "description": "Simple template engine.", 1255 | "homepage": "https://github.com/sebastianbergmann/php-text-template/", 1256 | "keywords": [ 1257 | "template" 1258 | ], 1259 | "time": "2015-06-21 13:50:34" 1260 | }, 1261 | { 1262 | "name": "phpunit/php-timer", 1263 | "version": "1.0.8", 1264 | "source": { 1265 | "type": "git", 1266 | "url": "https://github.com/sebastianbergmann/php-timer.git", 1267 | "reference": "38e9124049cf1a164f1e4537caf19c99bf1eb260" 1268 | }, 1269 | "dist": { 1270 | "type": "zip", 1271 | "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/38e9124049cf1a164f1e4537caf19c99bf1eb260", 1272 | "reference": "38e9124049cf1a164f1e4537caf19c99bf1eb260", 1273 | "shasum": "" 1274 | }, 1275 | "require": { 1276 | "php": ">=5.3.3" 1277 | }, 1278 | "require-dev": { 1279 | "phpunit/phpunit": "~4|~5" 1280 | }, 1281 | "type": "library", 1282 | "autoload": { 1283 | "classmap": [ 1284 | "src/" 1285 | ] 1286 | }, 1287 | "notification-url": "https://packagist.org/downloads/", 1288 | "license": [ 1289 | "BSD-3-Clause" 1290 | ], 1291 | "authors": [ 1292 | { 1293 | "name": "Sebastian Bergmann", 1294 | "email": "sb@sebastian-bergmann.de", 1295 | "role": "lead" 1296 | } 1297 | ], 1298 | "description": "Utility class for timing", 1299 | "homepage": "https://github.com/sebastianbergmann/php-timer/", 1300 | "keywords": [ 1301 | "timer" 1302 | ], 1303 | "time": "2016-05-12 18:03:57" 1304 | }, 1305 | { 1306 | "name": "phpunit/php-token-stream", 1307 | "version": "1.4.9", 1308 | "source": { 1309 | "type": "git", 1310 | "url": "https://github.com/sebastianbergmann/php-token-stream.git", 1311 | "reference": "3b402f65a4cc90abf6e1104e388b896ce209631b" 1312 | }, 1313 | "dist": { 1314 | "type": "zip", 1315 | "url": "https://api.github.com/repos/sebastianbergmann/php-token-stream/zipball/3b402f65a4cc90abf6e1104e388b896ce209631b", 1316 | "reference": "3b402f65a4cc90abf6e1104e388b896ce209631b", 1317 | "shasum": "" 1318 | }, 1319 | "require": { 1320 | "ext-tokenizer": "*", 1321 | "php": ">=5.3.3" 1322 | }, 1323 | "require-dev": { 1324 | "phpunit/phpunit": "~4.2" 1325 | }, 1326 | "type": "library", 1327 | "extra": { 1328 | "branch-alias": { 1329 | "dev-master": "1.4-dev" 1330 | } 1331 | }, 1332 | "autoload": { 1333 | "classmap": [ 1334 | "src/" 1335 | ] 1336 | }, 1337 | "notification-url": "https://packagist.org/downloads/", 1338 | "license": [ 1339 | "BSD-3-Clause" 1340 | ], 1341 | "authors": [ 1342 | { 1343 | "name": "Sebastian Bergmann", 1344 | "email": "sebastian@phpunit.de" 1345 | } 1346 | ], 1347 | "description": "Wrapper around PHP's tokenizer extension.", 1348 | "homepage": "https://github.com/sebastianbergmann/php-token-stream/", 1349 | "keywords": [ 1350 | "tokenizer" 1351 | ], 1352 | "time": "2016-11-15 14:06:22" 1353 | }, 1354 | { 1355 | "name": "phpunit/phpunit", 1356 | "version": "5.6.4", 1357 | "source": { 1358 | "type": "git", 1359 | "url": "https://github.com/sebastianbergmann/phpunit.git", 1360 | "reference": "4ddb822f1de421b4cadb47570a525fd7d9359493" 1361 | }, 1362 | "dist": { 1363 | "type": "zip", 1364 | "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/4ddb822f1de421b4cadb47570a525fd7d9359493", 1365 | "reference": "4ddb822f1de421b4cadb47570a525fd7d9359493", 1366 | "shasum": "" 1367 | }, 1368 | "require": { 1369 | "ext-dom": "*", 1370 | "ext-json": "*", 1371 | "ext-libxml": "*", 1372 | "ext-mbstring": "*", 1373 | "ext-xml": "*", 1374 | "myclabs/deep-copy": "~1.3", 1375 | "php": "^5.6 || ^7.0", 1376 | "phpspec/prophecy": "^1.3.1", 1377 | "phpunit/php-code-coverage": "^4.0.1", 1378 | "phpunit/php-file-iterator": "~1.4", 1379 | "phpunit/php-text-template": "~1.2", 1380 | "phpunit/php-timer": "^1.0.6", 1381 | "phpunit/phpunit-mock-objects": "^3.2", 1382 | "sebastian/comparator": "~1.1", 1383 | "sebastian/diff": "~1.2", 1384 | "sebastian/environment": "^1.3 || ^2.0", 1385 | "sebastian/exporter": "~1.2", 1386 | "sebastian/global-state": "~1.0", 1387 | "sebastian/object-enumerator": "~1.0", 1388 | "sebastian/resource-operations": "~1.0", 1389 | "sebastian/version": "~1.0|~2.0", 1390 | "symfony/yaml": "~2.1|~3.0" 1391 | }, 1392 | "conflict": { 1393 | "phpdocumentor/reflection-docblock": "3.0.2", 1394 | "sebastian/object-enumerator": "1.0.1", 1395 | "sebastian/recursion-context": "1.0.3 || 1.0.4" 1396 | }, 1397 | "require-dev": { 1398 | "ext-pdo": "*" 1399 | }, 1400 | "suggest": { 1401 | "ext-xdebug": "*", 1402 | "phpunit/php-invoker": "~1.1" 1403 | }, 1404 | "bin": [ 1405 | "phpunit" 1406 | ], 1407 | "type": "library", 1408 | "extra": { 1409 | "branch-alias": { 1410 | "dev-master": "5.6.x-dev" 1411 | } 1412 | }, 1413 | "autoload": { 1414 | "classmap": [ 1415 | "src/" 1416 | ] 1417 | }, 1418 | "notification-url": "https://packagist.org/downloads/", 1419 | "license": [ 1420 | "BSD-3-Clause" 1421 | ], 1422 | "authors": [ 1423 | { 1424 | "name": "Sebastian Bergmann", 1425 | "email": "sebastian@phpunit.de", 1426 | "role": "lead" 1427 | } 1428 | ], 1429 | "description": "The PHP Unit Testing framework.", 1430 | "homepage": "https://phpunit.de/", 1431 | "keywords": [ 1432 | "phpunit", 1433 | "testing", 1434 | "xunit" 1435 | ], 1436 | "time": "2016-11-18 09:50:51" 1437 | }, 1438 | { 1439 | "name": "phpunit/phpunit-mock-objects", 1440 | "version": "3.4.1", 1441 | "source": { 1442 | "type": "git", 1443 | "url": "https://github.com/sebastianbergmann/phpunit-mock-objects.git", 1444 | "reference": "45026c8383187ad1dcb14fbfec77dced265b9cfc" 1445 | }, 1446 | "dist": { 1447 | "type": "zip", 1448 | "url": "https://api.github.com/repos/sebastianbergmann/phpunit-mock-objects/zipball/45026c8383187ad1dcb14fbfec77dced265b9cfc", 1449 | "reference": "45026c8383187ad1dcb14fbfec77dced265b9cfc", 1450 | "shasum": "" 1451 | }, 1452 | "require": { 1453 | "doctrine/instantiator": "^1.0.2", 1454 | "php": "^5.6 || ^7.0", 1455 | "phpunit/php-text-template": "^1.2", 1456 | "sebastian/exporter": "^1.2 || ^2.0" 1457 | }, 1458 | "conflict": { 1459 | "phpunit/phpunit": "<5.4.0" 1460 | }, 1461 | "require-dev": { 1462 | "phpunit/phpunit": "^5.4" 1463 | }, 1464 | "suggest": { 1465 | "ext-soap": "*" 1466 | }, 1467 | "type": "library", 1468 | "extra": { 1469 | "branch-alias": { 1470 | "dev-master": "3.2.x-dev" 1471 | } 1472 | }, 1473 | "autoload": { 1474 | "classmap": [ 1475 | "src/" 1476 | ] 1477 | }, 1478 | "notification-url": "https://packagist.org/downloads/", 1479 | "license": [ 1480 | "BSD-3-Clause" 1481 | ], 1482 | "authors": [ 1483 | { 1484 | "name": "Sebastian Bergmann", 1485 | "email": "sb@sebastian-bergmann.de", 1486 | "role": "lead" 1487 | } 1488 | ], 1489 | "description": "Mock Object library for PHPUnit", 1490 | "homepage": "https://github.com/sebastianbergmann/phpunit-mock-objects/", 1491 | "keywords": [ 1492 | "mock", 1493 | "xunit" 1494 | ], 1495 | "time": "2016-11-19 09:07:46" 1496 | }, 1497 | { 1498 | "name": "sebastian/code-unit-reverse-lookup", 1499 | "version": "1.0.0", 1500 | "source": { 1501 | "type": "git", 1502 | "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git", 1503 | "reference": "c36f5e7cfce482fde5bf8d10d41a53591e0198fe" 1504 | }, 1505 | "dist": { 1506 | "type": "zip", 1507 | "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/c36f5e7cfce482fde5bf8d10d41a53591e0198fe", 1508 | "reference": "c36f5e7cfce482fde5bf8d10d41a53591e0198fe", 1509 | "shasum": "" 1510 | }, 1511 | "require": { 1512 | "php": ">=5.6" 1513 | }, 1514 | "require-dev": { 1515 | "phpunit/phpunit": "~5" 1516 | }, 1517 | "type": "library", 1518 | "extra": { 1519 | "branch-alias": { 1520 | "dev-master": "1.0.x-dev" 1521 | } 1522 | }, 1523 | "autoload": { 1524 | "classmap": [ 1525 | "src/" 1526 | ] 1527 | }, 1528 | "notification-url": "https://packagist.org/downloads/", 1529 | "license": [ 1530 | "BSD-3-Clause" 1531 | ], 1532 | "authors": [ 1533 | { 1534 | "name": "Sebastian Bergmann", 1535 | "email": "sebastian@phpunit.de" 1536 | } 1537 | ], 1538 | "description": "Looks up which function or method a line of code belongs to", 1539 | "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/", 1540 | "time": "2016-02-13 06:45:14" 1541 | }, 1542 | { 1543 | "name": "sebastian/comparator", 1544 | "version": "1.2.2", 1545 | "source": { 1546 | "type": "git", 1547 | "url": "https://github.com/sebastianbergmann/comparator.git", 1548 | "reference": "6a1ed12e8b2409076ab22e3897126211ff8b1f7f" 1549 | }, 1550 | "dist": { 1551 | "type": "zip", 1552 | "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/6a1ed12e8b2409076ab22e3897126211ff8b1f7f", 1553 | "reference": "6a1ed12e8b2409076ab22e3897126211ff8b1f7f", 1554 | "shasum": "" 1555 | }, 1556 | "require": { 1557 | "php": ">=5.3.3", 1558 | "sebastian/diff": "~1.2", 1559 | "sebastian/exporter": "~1.2 || ~2.0" 1560 | }, 1561 | "require-dev": { 1562 | "phpunit/phpunit": "~4.4" 1563 | }, 1564 | "type": "library", 1565 | "extra": { 1566 | "branch-alias": { 1567 | "dev-master": "1.2.x-dev" 1568 | } 1569 | }, 1570 | "autoload": { 1571 | "classmap": [ 1572 | "src/" 1573 | ] 1574 | }, 1575 | "notification-url": "https://packagist.org/downloads/", 1576 | "license": [ 1577 | "BSD-3-Clause" 1578 | ], 1579 | "authors": [ 1580 | { 1581 | "name": "Jeff Welch", 1582 | "email": "whatthejeff@gmail.com" 1583 | }, 1584 | { 1585 | "name": "Volker Dusch", 1586 | "email": "github@wallbash.com" 1587 | }, 1588 | { 1589 | "name": "Bernhard Schussek", 1590 | "email": "bschussek@2bepublished.at" 1591 | }, 1592 | { 1593 | "name": "Sebastian Bergmann", 1594 | "email": "sebastian@phpunit.de" 1595 | } 1596 | ], 1597 | "description": "Provides the functionality to compare PHP values for equality", 1598 | "homepage": "http://www.github.com/sebastianbergmann/comparator", 1599 | "keywords": [ 1600 | "comparator", 1601 | "compare", 1602 | "equality" 1603 | ], 1604 | "time": "2016-11-19 09:18:40" 1605 | }, 1606 | { 1607 | "name": "sebastian/diff", 1608 | "version": "1.4.1", 1609 | "source": { 1610 | "type": "git", 1611 | "url": "https://github.com/sebastianbergmann/diff.git", 1612 | "reference": "13edfd8706462032c2f52b4b862974dd46b71c9e" 1613 | }, 1614 | "dist": { 1615 | "type": "zip", 1616 | "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/13edfd8706462032c2f52b4b862974dd46b71c9e", 1617 | "reference": "13edfd8706462032c2f52b4b862974dd46b71c9e", 1618 | "shasum": "" 1619 | }, 1620 | "require": { 1621 | "php": ">=5.3.3" 1622 | }, 1623 | "require-dev": { 1624 | "phpunit/phpunit": "~4.8" 1625 | }, 1626 | "type": "library", 1627 | "extra": { 1628 | "branch-alias": { 1629 | "dev-master": "1.4-dev" 1630 | } 1631 | }, 1632 | "autoload": { 1633 | "classmap": [ 1634 | "src/" 1635 | ] 1636 | }, 1637 | "notification-url": "https://packagist.org/downloads/", 1638 | "license": [ 1639 | "BSD-3-Clause" 1640 | ], 1641 | "authors": [ 1642 | { 1643 | "name": "Kore Nordmann", 1644 | "email": "mail@kore-nordmann.de" 1645 | }, 1646 | { 1647 | "name": "Sebastian Bergmann", 1648 | "email": "sebastian@phpunit.de" 1649 | } 1650 | ], 1651 | "description": "Diff implementation", 1652 | "homepage": "https://github.com/sebastianbergmann/diff", 1653 | "keywords": [ 1654 | "diff" 1655 | ], 1656 | "time": "2015-12-08 07:14:41" 1657 | }, 1658 | { 1659 | "name": "sebastian/environment", 1660 | "version": "1.3.8", 1661 | "source": { 1662 | "type": "git", 1663 | "url": "https://github.com/sebastianbergmann/environment.git", 1664 | "reference": "be2c607e43ce4c89ecd60e75c6a85c126e754aea" 1665 | }, 1666 | "dist": { 1667 | "type": "zip", 1668 | "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/be2c607e43ce4c89ecd60e75c6a85c126e754aea", 1669 | "reference": "be2c607e43ce4c89ecd60e75c6a85c126e754aea", 1670 | "shasum": "" 1671 | }, 1672 | "require": { 1673 | "php": "^5.3.3 || ^7.0" 1674 | }, 1675 | "require-dev": { 1676 | "phpunit/phpunit": "^4.8 || ^5.0" 1677 | }, 1678 | "type": "library", 1679 | "extra": { 1680 | "branch-alias": { 1681 | "dev-master": "1.3.x-dev" 1682 | } 1683 | }, 1684 | "autoload": { 1685 | "classmap": [ 1686 | "src/" 1687 | ] 1688 | }, 1689 | "notification-url": "https://packagist.org/downloads/", 1690 | "license": [ 1691 | "BSD-3-Clause" 1692 | ], 1693 | "authors": [ 1694 | { 1695 | "name": "Sebastian Bergmann", 1696 | "email": "sebastian@phpunit.de" 1697 | } 1698 | ], 1699 | "description": "Provides functionality to handle HHVM/PHP environments", 1700 | "homepage": "http://www.github.com/sebastianbergmann/environment", 1701 | "keywords": [ 1702 | "Xdebug", 1703 | "environment", 1704 | "hhvm" 1705 | ], 1706 | "time": "2016-08-18 05:49:44" 1707 | }, 1708 | { 1709 | "name": "sebastian/exporter", 1710 | "version": "1.2.2", 1711 | "source": { 1712 | "type": "git", 1713 | "url": "https://github.com/sebastianbergmann/exporter.git", 1714 | "reference": "42c4c2eec485ee3e159ec9884f95b431287edde4" 1715 | }, 1716 | "dist": { 1717 | "type": "zip", 1718 | "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/42c4c2eec485ee3e159ec9884f95b431287edde4", 1719 | "reference": "42c4c2eec485ee3e159ec9884f95b431287edde4", 1720 | "shasum": "" 1721 | }, 1722 | "require": { 1723 | "php": ">=5.3.3", 1724 | "sebastian/recursion-context": "~1.0" 1725 | }, 1726 | "require-dev": { 1727 | "ext-mbstring": "*", 1728 | "phpunit/phpunit": "~4.4" 1729 | }, 1730 | "type": "library", 1731 | "extra": { 1732 | "branch-alias": { 1733 | "dev-master": "1.3.x-dev" 1734 | } 1735 | }, 1736 | "autoload": { 1737 | "classmap": [ 1738 | "src/" 1739 | ] 1740 | }, 1741 | "notification-url": "https://packagist.org/downloads/", 1742 | "license": [ 1743 | "BSD-3-Clause" 1744 | ], 1745 | "authors": [ 1746 | { 1747 | "name": "Jeff Welch", 1748 | "email": "whatthejeff@gmail.com" 1749 | }, 1750 | { 1751 | "name": "Volker Dusch", 1752 | "email": "github@wallbash.com" 1753 | }, 1754 | { 1755 | "name": "Bernhard Schussek", 1756 | "email": "bschussek@2bepublished.at" 1757 | }, 1758 | { 1759 | "name": "Sebastian Bergmann", 1760 | "email": "sebastian@phpunit.de" 1761 | }, 1762 | { 1763 | "name": "Adam Harvey", 1764 | "email": "aharvey@php.net" 1765 | } 1766 | ], 1767 | "description": "Provides the functionality to export PHP variables for visualization", 1768 | "homepage": "http://www.github.com/sebastianbergmann/exporter", 1769 | "keywords": [ 1770 | "export", 1771 | "exporter" 1772 | ], 1773 | "time": "2016-06-17 09:04:28" 1774 | }, 1775 | { 1776 | "name": "sebastian/global-state", 1777 | "version": "1.1.1", 1778 | "source": { 1779 | "type": "git", 1780 | "url": "https://github.com/sebastianbergmann/global-state.git", 1781 | "reference": "bc37d50fea7d017d3d340f230811c9f1d7280af4" 1782 | }, 1783 | "dist": { 1784 | "type": "zip", 1785 | "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/bc37d50fea7d017d3d340f230811c9f1d7280af4", 1786 | "reference": "bc37d50fea7d017d3d340f230811c9f1d7280af4", 1787 | "shasum": "" 1788 | }, 1789 | "require": { 1790 | "php": ">=5.3.3" 1791 | }, 1792 | "require-dev": { 1793 | "phpunit/phpunit": "~4.2" 1794 | }, 1795 | "suggest": { 1796 | "ext-uopz": "*" 1797 | }, 1798 | "type": "library", 1799 | "extra": { 1800 | "branch-alias": { 1801 | "dev-master": "1.0-dev" 1802 | } 1803 | }, 1804 | "autoload": { 1805 | "classmap": [ 1806 | "src/" 1807 | ] 1808 | }, 1809 | "notification-url": "https://packagist.org/downloads/", 1810 | "license": [ 1811 | "BSD-3-Clause" 1812 | ], 1813 | "authors": [ 1814 | { 1815 | "name": "Sebastian Bergmann", 1816 | "email": "sebastian@phpunit.de" 1817 | } 1818 | ], 1819 | "description": "Snapshotting of global state", 1820 | "homepage": "http://www.github.com/sebastianbergmann/global-state", 1821 | "keywords": [ 1822 | "global state" 1823 | ], 1824 | "time": "2015-10-12 03:26:01" 1825 | }, 1826 | { 1827 | "name": "sebastian/object-enumerator", 1828 | "version": "1.0.0", 1829 | "source": { 1830 | "type": "git", 1831 | "url": "https://github.com/sebastianbergmann/object-enumerator.git", 1832 | "reference": "d4ca2fb70344987502567bc50081c03e6192fb26" 1833 | }, 1834 | "dist": { 1835 | "type": "zip", 1836 | "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/d4ca2fb70344987502567bc50081c03e6192fb26", 1837 | "reference": "d4ca2fb70344987502567bc50081c03e6192fb26", 1838 | "shasum": "" 1839 | }, 1840 | "require": { 1841 | "php": ">=5.6", 1842 | "sebastian/recursion-context": "~1.0" 1843 | }, 1844 | "require-dev": { 1845 | "phpunit/phpunit": "~5" 1846 | }, 1847 | "type": "library", 1848 | "extra": { 1849 | "branch-alias": { 1850 | "dev-master": "1.0.x-dev" 1851 | } 1852 | }, 1853 | "autoload": { 1854 | "classmap": [ 1855 | "src/" 1856 | ] 1857 | }, 1858 | "notification-url": "https://packagist.org/downloads/", 1859 | "license": [ 1860 | "BSD-3-Clause" 1861 | ], 1862 | "authors": [ 1863 | { 1864 | "name": "Sebastian Bergmann", 1865 | "email": "sebastian@phpunit.de" 1866 | } 1867 | ], 1868 | "description": "Traverses array structures and object graphs to enumerate all referenced objects", 1869 | "homepage": "https://github.com/sebastianbergmann/object-enumerator/", 1870 | "time": "2016-01-28 13:25:10" 1871 | }, 1872 | { 1873 | "name": "sebastian/recursion-context", 1874 | "version": "1.0.2", 1875 | "source": { 1876 | "type": "git", 1877 | "url": "https://github.com/sebastianbergmann/recursion-context.git", 1878 | "reference": "913401df809e99e4f47b27cdd781f4a258d58791" 1879 | }, 1880 | "dist": { 1881 | "type": "zip", 1882 | "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/913401df809e99e4f47b27cdd781f4a258d58791", 1883 | "reference": "913401df809e99e4f47b27cdd781f4a258d58791", 1884 | "shasum": "" 1885 | }, 1886 | "require": { 1887 | "php": ">=5.3.3" 1888 | }, 1889 | "require-dev": { 1890 | "phpunit/phpunit": "~4.4" 1891 | }, 1892 | "type": "library", 1893 | "extra": { 1894 | "branch-alias": { 1895 | "dev-master": "1.0.x-dev" 1896 | } 1897 | }, 1898 | "autoload": { 1899 | "classmap": [ 1900 | "src/" 1901 | ] 1902 | }, 1903 | "notification-url": "https://packagist.org/downloads/", 1904 | "license": [ 1905 | "BSD-3-Clause" 1906 | ], 1907 | "authors": [ 1908 | { 1909 | "name": "Jeff Welch", 1910 | "email": "whatthejeff@gmail.com" 1911 | }, 1912 | { 1913 | "name": "Sebastian Bergmann", 1914 | "email": "sebastian@phpunit.de" 1915 | }, 1916 | { 1917 | "name": "Adam Harvey", 1918 | "email": "aharvey@php.net" 1919 | } 1920 | ], 1921 | "description": "Provides functionality to recursively process PHP variables", 1922 | "homepage": "http://www.github.com/sebastianbergmann/recursion-context", 1923 | "time": "2015-11-11 19:50:13" 1924 | }, 1925 | { 1926 | "name": "sebastian/resource-operations", 1927 | "version": "1.0.0", 1928 | "source": { 1929 | "type": "git", 1930 | "url": "https://github.com/sebastianbergmann/resource-operations.git", 1931 | "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52" 1932 | }, 1933 | "dist": { 1934 | "type": "zip", 1935 | "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/ce990bb21759f94aeafd30209e8cfcdfa8bc3f52", 1936 | "reference": "ce990bb21759f94aeafd30209e8cfcdfa8bc3f52", 1937 | "shasum": "" 1938 | }, 1939 | "require": { 1940 | "php": ">=5.6.0" 1941 | }, 1942 | "type": "library", 1943 | "extra": { 1944 | "branch-alias": { 1945 | "dev-master": "1.0.x-dev" 1946 | } 1947 | }, 1948 | "autoload": { 1949 | "classmap": [ 1950 | "src/" 1951 | ] 1952 | }, 1953 | "notification-url": "https://packagist.org/downloads/", 1954 | "license": [ 1955 | "BSD-3-Clause" 1956 | ], 1957 | "authors": [ 1958 | { 1959 | "name": "Sebastian Bergmann", 1960 | "email": "sebastian@phpunit.de" 1961 | } 1962 | ], 1963 | "description": "Provides a list of PHP built-in functions that operate on resources", 1964 | "homepage": "https://www.github.com/sebastianbergmann/resource-operations", 1965 | "time": "2015-07-28 20:34:47" 1966 | }, 1967 | { 1968 | "name": "sebastian/version", 1969 | "version": "2.0.0", 1970 | "source": { 1971 | "type": "git", 1972 | "url": "https://github.com/sebastianbergmann/version.git", 1973 | "reference": "c829badbd8fdf16a0bad8aa7fa7971c029f1b9c5" 1974 | }, 1975 | "dist": { 1976 | "type": "zip", 1977 | "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/c829badbd8fdf16a0bad8aa7fa7971c029f1b9c5", 1978 | "reference": "c829badbd8fdf16a0bad8aa7fa7971c029f1b9c5", 1979 | "shasum": "" 1980 | }, 1981 | "require": { 1982 | "php": ">=5.6" 1983 | }, 1984 | "type": "library", 1985 | "extra": { 1986 | "branch-alias": { 1987 | "dev-master": "2.0.x-dev" 1988 | } 1989 | }, 1990 | "autoload": { 1991 | "classmap": [ 1992 | "src/" 1993 | ] 1994 | }, 1995 | "notification-url": "https://packagist.org/downloads/", 1996 | "license": [ 1997 | "BSD-3-Clause" 1998 | ], 1999 | "authors": [ 2000 | { 2001 | "name": "Sebastian Bergmann", 2002 | "email": "sebastian@phpunit.de", 2003 | "role": "lead" 2004 | } 2005 | ], 2006 | "description": "Library that helps with managing the version number of Git-hosted PHP projects", 2007 | "homepage": "https://github.com/sebastianbergmann/version", 2008 | "time": "2016-02-04 12:56:52" 2009 | }, 2010 | { 2011 | "name": "squizlabs/php_codesniffer", 2012 | "version": "2.6.0", 2013 | "source": { 2014 | "type": "git", 2015 | "url": "https://github.com/squizlabs/PHP_CodeSniffer.git", 2016 | "reference": "1bcdf03b068a530ac1962ce671dead356eeba43b" 2017 | }, 2018 | "dist": { 2019 | "type": "zip", 2020 | "url": "https://api.github.com/repos/squizlabs/PHP_CodeSniffer/zipball/1bcdf03b068a530ac1962ce671dead356eeba43b", 2021 | "reference": "1bcdf03b068a530ac1962ce671dead356eeba43b", 2022 | "shasum": "" 2023 | }, 2024 | "require": { 2025 | "ext-simplexml": "*", 2026 | "ext-tokenizer": "*", 2027 | "ext-xmlwriter": "*", 2028 | "php": ">=5.1.2" 2029 | }, 2030 | "require-dev": { 2031 | "phpunit/phpunit": "~4.0" 2032 | }, 2033 | "bin": [ 2034 | "scripts/phpcs", 2035 | "scripts/phpcbf" 2036 | ], 2037 | "type": "library", 2038 | "extra": { 2039 | "branch-alias": { 2040 | "dev-master": "2.x-dev" 2041 | } 2042 | }, 2043 | "autoload": { 2044 | "classmap": [ 2045 | "CodeSniffer.php", 2046 | "CodeSniffer/CLI.php", 2047 | "CodeSniffer/Exception.php", 2048 | "CodeSniffer/File.php", 2049 | "CodeSniffer/Fixer.php", 2050 | "CodeSniffer/Report.php", 2051 | "CodeSniffer/Reporting.php", 2052 | "CodeSniffer/Sniff.php", 2053 | "CodeSniffer/Tokens.php", 2054 | "CodeSniffer/Reports/", 2055 | "CodeSniffer/Tokenizers/", 2056 | "CodeSniffer/DocGenerators/", 2057 | "CodeSniffer/Standards/AbstractPatternSniff.php", 2058 | "CodeSniffer/Standards/AbstractScopeSniff.php", 2059 | "CodeSniffer/Standards/AbstractVariableSniff.php", 2060 | "CodeSniffer/Standards/IncorrectPatternException.php", 2061 | "CodeSniffer/Standards/Generic/Sniffs/", 2062 | "CodeSniffer/Standards/MySource/Sniffs/", 2063 | "CodeSniffer/Standards/PEAR/Sniffs/", 2064 | "CodeSniffer/Standards/PSR1/Sniffs/", 2065 | "CodeSniffer/Standards/PSR2/Sniffs/", 2066 | "CodeSniffer/Standards/Squiz/Sniffs/", 2067 | "CodeSniffer/Standards/Zend/Sniffs/" 2068 | ] 2069 | }, 2070 | "notification-url": "https://packagist.org/downloads/", 2071 | "license": [ 2072 | "BSD-3-Clause" 2073 | ], 2074 | "authors": [ 2075 | { 2076 | "name": "Greg Sherwood", 2077 | "role": "lead" 2078 | } 2079 | ], 2080 | "description": "PHP_CodeSniffer tokenizes PHP, JavaScript and CSS files and detects violations of a defined set of coding standards.", 2081 | "homepage": "http://www.squizlabs.com/php-codesniffer", 2082 | "keywords": [ 2083 | "phpcs", 2084 | "standards" 2085 | ], 2086 | "time": "2016-04-03 22:58:34" 2087 | }, 2088 | { 2089 | "name": "symfony/yaml", 2090 | "version": "v3.1.6", 2091 | "source": { 2092 | "type": "git", 2093 | "url": "https://github.com/symfony/yaml.git", 2094 | "reference": "7ff51b06c6c3d5cc6686df69004a42c69df09e27" 2095 | }, 2096 | "dist": { 2097 | "type": "zip", 2098 | "url": "https://api.github.com/repos/symfony/yaml/zipball/7ff51b06c6c3d5cc6686df69004a42c69df09e27", 2099 | "reference": "7ff51b06c6c3d5cc6686df69004a42c69df09e27", 2100 | "shasum": "" 2101 | }, 2102 | "require": { 2103 | "php": ">=5.5.9" 2104 | }, 2105 | "type": "library", 2106 | "extra": { 2107 | "branch-alias": { 2108 | "dev-master": "3.1-dev" 2109 | } 2110 | }, 2111 | "autoload": { 2112 | "psr-4": { 2113 | "Symfony\\Component\\Yaml\\": "" 2114 | }, 2115 | "exclude-from-classmap": [ 2116 | "/Tests/" 2117 | ] 2118 | }, 2119 | "notification-url": "https://packagist.org/downloads/", 2120 | "license": [ 2121 | "MIT" 2122 | ], 2123 | "authors": [ 2124 | { 2125 | "name": "Fabien Potencier", 2126 | "email": "fabien@symfony.com" 2127 | }, 2128 | { 2129 | "name": "Symfony Community", 2130 | "homepage": "https://symfony.com/contributors" 2131 | } 2132 | ], 2133 | "description": "Symfony Yaml Component", 2134 | "homepage": "https://symfony.com", 2135 | "time": "2016-10-24 18:41:13" 2136 | }, 2137 | { 2138 | "name": "webmozart/assert", 2139 | "version": "1.1.0", 2140 | "source": { 2141 | "type": "git", 2142 | "url": "https://github.com/webmozart/assert.git", 2143 | "reference": "bb2d123231c095735130cc8f6d31385a44c7b308" 2144 | }, 2145 | "dist": { 2146 | "type": "zip", 2147 | "url": "https://api.github.com/repos/webmozart/assert/zipball/bb2d123231c095735130cc8f6d31385a44c7b308", 2148 | "reference": "bb2d123231c095735130cc8f6d31385a44c7b308", 2149 | "shasum": "" 2150 | }, 2151 | "require": { 2152 | "php": "^5.3.3|^7.0" 2153 | }, 2154 | "require-dev": { 2155 | "phpunit/phpunit": "^4.6", 2156 | "sebastian/version": "^1.0.1" 2157 | }, 2158 | "type": "library", 2159 | "extra": { 2160 | "branch-alias": { 2161 | "dev-master": "1.2-dev" 2162 | } 2163 | }, 2164 | "autoload": { 2165 | "psr-4": { 2166 | "Webmozart\\Assert\\": "src/" 2167 | } 2168 | }, 2169 | "notification-url": "https://packagist.org/downloads/", 2170 | "license": [ 2171 | "MIT" 2172 | ], 2173 | "authors": [ 2174 | { 2175 | "name": "Bernhard Schussek", 2176 | "email": "bschussek@gmail.com" 2177 | } 2178 | ], 2179 | "description": "Assertions to validate method input/output with nice error messages.", 2180 | "keywords": [ 2181 | "assert", 2182 | "check", 2183 | "validate" 2184 | ], 2185 | "time": "2016-08-09 15:02:57" 2186 | } 2187 | ], 2188 | "aliases": [], 2189 | "minimum-stability": "stable", 2190 | "stability-flags": [], 2191 | "prefer-stable": false, 2192 | "prefer-lowest": false, 2193 | "platform": [], 2194 | "platform-dev": [] 2195 | } 2196 | --------------------------------------------------------------------------------