InstallerTest.php 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429
  1. <?php
  2. namespace Composer\Installers\Test;
  3. use Composer\Installers\Installer;
  4. use Composer\Util\Filesystem;
  5. use Composer\Package\Package;
  6. use Composer\Package\RootPackage;
  7. use Composer\Composer;
  8. use Composer\Config;
  9. class InstallerTest extends TestCase
  10. {
  11. private $composer;
  12. private $config;
  13. private $vendorDir;
  14. private $binDir;
  15. private $dm;
  16. private $repository;
  17. private $io;
  18. private $fs;
  19. /**
  20. * setUp
  21. *
  22. * @return void
  23. */
  24. public function setUp()
  25. {
  26. $this->fs = new Filesystem;
  27. $this->composer = new Composer();
  28. $this->config = new Config();
  29. $this->composer->setConfig($this->config);
  30. $this->vendorDir = realpath(sys_get_temp_dir()) . DIRECTORY_SEPARATOR . 'baton-test-vendor';
  31. $this->ensureDirectoryExistsAndClear($this->vendorDir);
  32. $this->binDir = realpath(sys_get_temp_dir()) . DIRECTORY_SEPARATOR . 'baton-test-bin';
  33. $this->ensureDirectoryExistsAndClear($this->binDir);
  34. $this->config->merge(array(
  35. 'config' => array(
  36. 'vendor-dir' => $this->vendorDir,
  37. 'bin-dir' => $this->binDir,
  38. ),
  39. ));
  40. $this->dm = $this->getMockBuilder('Composer\Downloader\DownloadManager')
  41. ->disableOriginalConstructor()
  42. ->getMock();
  43. $this->composer->setDownloadManager($this->dm);
  44. $this->repository = $this->getMock('Composer\Repository\InstalledRepositoryInterface');
  45. $this->io = $this->getMock('Composer\IO\IOInterface');
  46. }
  47. /**
  48. * tearDown
  49. *
  50. * @return void
  51. */
  52. public function tearDown()
  53. {
  54. $this->fs->removeDirectory($this->vendorDir);
  55. $this->fs->removeDirectory($this->binDir);
  56. }
  57. /**
  58. * testSupports
  59. *
  60. * @return void
  61. *
  62. * @dataProvider dataForTestSupport
  63. */
  64. public function testSupports($type, $expected)
  65. {
  66. $installer = new Installer($this->io, $this->composer);
  67. $this->assertSame($expected, $installer->supports($type), sprintf('Failed to show support for %s', $type));
  68. }
  69. /**
  70. * dataForTestSupport
  71. */
  72. public function dataForTestSupport()
  73. {
  74. return array(
  75. array('agl-module', true),
  76. array('aimeos-extension', true),
  77. array('annotatecms-module', true),
  78. array('annotatecms-component', true),
  79. array('annotatecms-service', true),
  80. array('bitrix-module', true),
  81. array('bitrix-component', true),
  82. array('bitrix-theme', true),
  83. array('bonefish-package', true),
  84. array('cakephp', false),
  85. array('cakephp-', false),
  86. array('cakephp-app', false),
  87. array('cakephp-plugin', true),
  88. array('chef-cookbook', true),
  89. array('chef-role', true),
  90. array('codeigniter-app', false),
  91. array('codeigniter-library', true),
  92. array('codeigniter-third-party', true),
  93. array('codeigniter-module', true),
  94. array('concrete5-block', true),
  95. array('concrete5-package', true),
  96. array('concrete5-theme', true),
  97. array('concrete5-update', true),
  98. array('craft-plugin', true),
  99. array('croogo-plugin', true),
  100. array('croogo-theme', true),
  101. array('dokuwiki-plugin', true),
  102. array('dokuwiki-template', true),
  103. array('drupal-module', true),
  104. array('dolibarr-module', true),
  105. array('elgg-plugin', true),
  106. array('fuel-module', true),
  107. array('fuel-package', true),
  108. array('fuel-theme', true),
  109. array('fuelphp-component', true),
  110. array('hurad-plugin', true),
  111. array('hurad-theme', true),
  112. array('joomla-library', true),
  113. array('kirby-plugin', true),
  114. array('kohana-module', true),
  115. array('laravel-library', true),
  116. array('lithium-library', true),
  117. array('magento-library', true),
  118. array('mako-package', true),
  119. array('modxevo-snippet', true),
  120. array('modxevo-plugin', true),
  121. array('modxevo-module', true),
  122. array('modxevo-template', true),
  123. array('modxevo-lib', true),
  124. array('mediawiki-extension', true),
  125. array('mediawiki-skin', true),
  126. array('microweber-module', true),
  127. array('modulework-module', true),
  128. array('moodle-mod', true),
  129. array('october-module', true),
  130. array('october-plugin', true),
  131. array('piwik-plugin', true),
  132. array('phpbb-extension', true),
  133. array('pimcore-plugin', true),
  134. array('ppi-module', true),
  135. array('prestashop-module', true),
  136. array('prestashop-theme', true),
  137. array('puppet-module', true),
  138. array('redaxo-addon', true),
  139. array('redaxo-bestyle-plugin', true),
  140. array('roundcube-plugin', true),
  141. array('shopware-backend-plugin', true),
  142. array('shopware-core-plugin', true),
  143. array('shopware-frontend-plugin', true),
  144. array('shopware-theme', true),
  145. array('silverstripe-module', true),
  146. array('silverstripe-theme', true),
  147. array('smf-module', true),
  148. array('smf-theme', true),
  149. array('symfony1-plugin', true),
  150. array('thelia-module', true),
  151. array('thelia-frontoffice-template', true),
  152. array('thelia-backoffice-template', true),
  153. array('thelia-email-template', true),
  154. array('tusk-task', true),
  155. array('tusk-asset', true),
  156. array('typo3-flow-plugin', true),
  157. array('typo3-cms-extension', true),
  158. array('whmcs-gateway', true),
  159. array('wolfcms-plugin', true),
  160. array('wordpress-plugin', true),
  161. array('wordpress-core', false),
  162. array('zend-library', true),
  163. array('zikula-module', true),
  164. array('zikula-theme', true),
  165. array('kodicms-plugin', true),
  166. array('kodicms-media', true),
  167. );
  168. }
  169. /**
  170. * testInstallPath
  171. *
  172. * @dataProvider dataForTestInstallPath
  173. */
  174. public function testInstallPath($type, $path, $name, $version = '1.0.0')
  175. {
  176. $installer = new Installer($this->io, $this->composer);
  177. $package = new Package($name, $version, $version);
  178. $package->setType($type);
  179. $result = $installer->getInstallPath($package);
  180. $this->assertEquals($path, $result);
  181. }
  182. /**
  183. * dataFormTestInstallPath
  184. */
  185. public function dataForTestInstallPath()
  186. {
  187. return array(
  188. array('agl-module', 'More/MyTestPackage/', 'agl/my_test-package'),
  189. array('aimeos-extension', 'ext/ai-test/', 'author/ai-test'),
  190. array('annotatecms-module', 'addons/modules/my_module/', 'vysinsky/my_module'),
  191. array('annotatecms-component', 'addons/components/my_component/', 'vysinsky/my_component'),
  192. array('annotatecms-service', 'addons/services/my_service/', 'vysinsky/my_service'),
  193. array('bitrix-module', 'bitrix/modules/my_module/', 'author/my_module'),
  194. array('bitrix-component', 'bitrix/components/my_component/', 'author/my_component'),
  195. array('bitrix-theme', 'bitrix/templates/my_theme/', 'author/my_theme'),
  196. array('bonefish-package', 'Packages/bonefish/package/', 'bonefish/package'),
  197. array('cakephp-plugin', 'Plugin/Ftp/', 'shama/ftp'),
  198. array('chef-cookbook', 'Chef/mre/my_cookbook/', 'mre/my_cookbook'),
  199. array('chef-role', 'Chef/roles/my_role/', 'mre/my_role'),
  200. array('codeigniter-library', 'application/libraries/my_package/', 'shama/my_package'),
  201. array('codeigniter-module', 'application/modules/my_package/', 'shama/my_package'),
  202. array('concrete5-block', 'blocks/concrete5_block/', 'remo/concrete5_block'),
  203. array('concrete5-package', 'packages/concrete5_package/', 'remo/concrete5_package'),
  204. array('concrete5-theme', 'themes/concrete5_theme/', 'remo/concrete5_theme'),
  205. array('concrete5-update', 'updates/concrete5/', 'concrete5/concrete5'),
  206. array('craft-plugin', 'craft/plugins/my_plugin/', 'mdcpepper/my_plugin'),
  207. array('croogo-plugin', 'Plugin/Sitemaps/', 'fahad19/sitemaps'),
  208. array('croogo-theme', 'View/Themed/Readable/', 'rchavik/readable'),
  209. array('dokuwiki-plugin', 'lib/plugins/someplugin/', 'author/someplugin'),
  210. array('dokuwiki-template', 'lib/tpl/sometemplate/', 'author/sometemplate'),
  211. array('dolibarr-module', 'htdocs/custom/my_module/', 'shama/my_module'),
  212. array('drupal-module', 'modules/my_module/', 'shama/my_module'),
  213. array('drupal-theme', 'themes/my_module/', 'shama/my_module'),
  214. array('drupal-profile', 'profiles/my_module/', 'shama/my_module'),
  215. array('drupal-drush', 'drush/my_module/', 'shama/my_module'),
  216. array('elgg-plugin', 'mod/sample_plugin/', 'test/sample_plugin'),
  217. array('fuel-module', 'fuel/app/modules/module/', 'fuel/module'),
  218. array('fuel-package', 'fuel/packages/orm/', 'fuel/orm'),
  219. array('fuel-theme', 'fuel/app/themes/theme/', 'fuel/theme'),
  220. array('fuelphp-component', 'components/demo/', 'fuelphp/demo'),
  221. array('hurad-plugin', 'plugins/Akismet/', 'atkrad/akismet'),
  222. array('hurad-theme', 'plugins/Hurad2013/', 'atkrad/Hurad2013'),
  223. array('joomla-plugin', 'plugins/my_plugin/', 'shama/my_plugin'),
  224. array('kirby-plugin', 'site/plugins/my_plugin/', 'shama/my_plugin'),
  225. array('kohana-module', 'modules/my_package/', 'shama/my_package'),
  226. array('laravel-library', 'libraries/my_package/', 'shama/my_package'),
  227. array('lithium-library', 'libraries/li3_test/', 'user/li3_test'),
  228. array('magento-library', 'lib/foo/', 'test/foo'),
  229. array('modxevo-snippet', 'assets/snippets/my_snippet/', 'shama/my_snippet'),
  230. array('modxevo-plugin', 'assets/plugins/my_plugin/', 'shama/my_plugin'),
  231. array('modxevo-module', 'assets/modules/my_module/', 'shama/my_module'),
  232. array('modxevo-template', 'assets/templates/my_template/', 'shama/my_template'),
  233. array('modxevo-lib', 'assets/lib/my_lib/', 'shama/my_lib'),
  234. array('mako-package', 'app/packages/my_package/', 'shama/my_package'),
  235. array('mediawiki-extension', 'extensions/APC/', 'author/APC'),
  236. array('mediawiki-extension', 'extensions/APC/', 'author/APC-extension'),
  237. array('mediawiki-extension', 'extensions/UploadWizard/', 'author/upload-wizard'),
  238. array('mediawiki-extension', 'extensions/SyntaxHighlight_GeSHi/', 'author/syntax-highlight_GeSHi'),
  239. array('mediawiki-skin', 'skins/someskin/', 'author/someskin-skin'),
  240. array('mediawiki-skin', 'skins/someskin/', 'author/someskin'),
  241. array('microweber-module', 'userfiles/modules/my-thing/', 'author/my-thing-module'),
  242. array('modulework-module', 'modules/my_package/', 'shama/my_package'),
  243. array('moodle-mod', 'mod/my_package/', 'shama/my_package'),
  244. array('october-module', 'modules/my_plugin/', 'shama/my_plugin'),
  245. array('october-plugin', 'plugins/shama/my_plugin/', 'shama/my_plugin'),
  246. array('october-theme', 'themes/my_theme/', 'shama/my_theme'),
  247. array('piwik-plugin', 'plugins/VisitSummary/', 'shama/visit-summary'),
  248. array('prestashop-module', 'modules/a-module/', 'vendor/a-module'),
  249. array('prestashop-theme', 'themes/a-theme/', 'vendor/a-theme'),
  250. array('phpbb-extension', 'ext/test/foo/', 'test/foo'),
  251. array('phpbb-style', 'styles/foo/', 'test/foo'),
  252. array('phpbb-language', 'language/foo/', 'test/foo'),
  253. array('pimcore-plugin', 'plugins/MyPlugin/', 'ubikz/my_plugin'),
  254. array('ppi-module', 'modules/foo/', 'test/foo'),
  255. array('puppet-module', 'modules/puppet-name/', 'puppet/puppet-name'),
  256. array('redaxo-addon', 'redaxo/include/addons/my_plugin/', 'shama/my_plugin'),
  257. array('redaxo-bestyle-plugin', 'redaxo/include/addons/be_style/plugins/my_plugin/', 'shama/my_plugin'),
  258. array('roundcube-plugin', 'plugins/base/', 'test/base'),
  259. array('roundcube-plugin', 'plugins/replace_dash/', 'test/replace-dash'),
  260. array('shopware-backend-plugin', 'engine/Shopware/Plugins/Local/Backend/ShamaMyBackendPlugin/', 'shama/my-backend-plugin'),
  261. array('shopware-core-plugin', 'engine/Shopware/Plugins/Local/Core/ShamaMyCorePlugin/', 'shama/my-core-plugin'),
  262. array('shopware-frontend-plugin', 'engine/Shopware/Plugins/Local/Frontend/ShamaMyFrontendPlugin/', 'shama/my-frontend-plugin'),
  263. array('shopware-theme', 'templates/my_theme/', 'shama/my-theme'),
  264. array('silverstripe-module', 'my_module/', 'shama/my_module'),
  265. array('silverstripe-module', 'sapphire/', 'silverstripe/framework', '2.4.0'),
  266. array('silverstripe-module', 'framework/', 'silverstripe/framework', '3.0.0'),
  267. array('silverstripe-module', 'framework/', 'silverstripe/framework', '3.0.0-rc1'),
  268. array('silverstripe-module', 'framework/', 'silverstripe/framework', 'my/branch'),
  269. array('silverstripe-theme', 'themes/my_theme/', 'shama/my_theme'),
  270. array('smf-module', 'Sources/my_module/', 'shama/my_module'),
  271. array('smf-theme', 'Themes/my_theme/', 'shama/my_theme'),
  272. array('symfony1-plugin', 'plugins/sfShamaPlugin/', 'shama/sfShamaPlugin'),
  273. array('symfony1-plugin', 'plugins/sfShamaPlugin/', 'shama/sf-shama-plugin'),
  274. array('thelia-module', 'local/modules/my_module/', 'shama/my_module'),
  275. array('thelia-frontoffice-template', 'templates/frontOffice/my_template_fo/', 'shama/my_template_fo'),
  276. array('thelia-backoffice-template', 'templates/backOffice/my_template_bo/', 'shama/my_template_bo'),
  277. array('thelia-email-template', 'templates/email/my_template_email/', 'shama/my_template_email'),
  278. array('tusk-task', '.tusk/tasks/my_task/', 'shama/my_task'),
  279. array('typo3-flow-package', 'Packages/Application/my_package/', 'shama/my_package'),
  280. array('typo3-flow-build', 'Build/my_package/', 'shama/my_package'),
  281. array('typo3-cms-extension', 'typo3conf/ext/my_extension/', 'shama/my_extension'),
  282. array('whmcs-gateway', 'modules/gateways/gateway_name/', 'vendor/gateway_name'),
  283. array('wolfcms-plugin', 'wolf/plugins/my_plugin/', 'shama/my_plugin'),
  284. array('wordpress-plugin', 'wp-content/plugins/my_plugin/', 'shama/my_plugin'),
  285. array('wordpress-muplugin', 'wp-content/mu-plugins/my_plugin/', 'shama/my_plugin'),
  286. array('zend-extra', 'extras/library/zend_test/', 'shama/zend_test'),
  287. array('zikula-module', 'modules/my-test_module/', 'my/test_module'),
  288. array('zikula-theme', 'themes/my-test_theme/', 'my/test_theme'),
  289. array('kodicms-media', 'cms/media/vendor/my_media/', 'shama/my_media'),
  290. array('kodicms-plugin', 'cms/plugins/my_plugin/', 'shama/my_plugin'),
  291. );
  292. }
  293. /**
  294. * testGetCakePHPInstallPathException
  295. *
  296. * @return void
  297. *
  298. * @expectedException \InvalidArgumentException
  299. */
  300. public function testGetCakePHPInstallPathException()
  301. {
  302. $installer = new Installer($this->io, $this->composer);
  303. $package = new Package('shama/ftp', '1.0.0', '1.0.0');
  304. $package->setType('cakephp-whoops');
  305. $result = $installer->getInstallPath($package);
  306. }
  307. /**
  308. * testCustomInstallPath
  309. */
  310. public function testCustomInstallPath()
  311. {
  312. $installer = new Installer($this->io, $this->composer);
  313. $package = new Package('shama/ftp', '1.0.0', '1.0.0');
  314. $package->setType('cakephp-plugin');
  315. $consumerPackage = new RootPackage('foo/bar', '1.0.0', '1.0.0');
  316. $this->composer->setPackage($consumerPackage);
  317. $consumerPackage->setExtra(array(
  318. 'installer-paths' => array(
  319. 'my/custom/path/{$name}/' => array(
  320. 'shama/ftp',
  321. 'foo/bar',
  322. ),
  323. ),
  324. ));
  325. $result = $installer->getInstallPath($package);
  326. $this->assertEquals('my/custom/path/Ftp/', $result);
  327. }
  328. /**
  329. * testCustomInstallerName
  330. */
  331. public function testCustomInstallerName()
  332. {
  333. $installer = new Installer($this->io, $this->composer);
  334. $package = new Package('shama/cakephp-ftp-plugin', '1.0.0', '1.0.0');
  335. $package->setType('cakephp-plugin');
  336. $package->setExtra(array(
  337. 'installer-name' => 'FTP',
  338. ));
  339. $result = $installer->getInstallPath($package);
  340. $this->assertEquals('Plugin/FTP/', $result);
  341. }
  342. /**
  343. * testCustomTypePath
  344. */
  345. public function testCustomTypePath()
  346. {
  347. $installer = new Installer($this->io, $this->composer);
  348. $package = new Package('slbmeh/my_plugin', '1.0.0', '1.0.0');
  349. $package->setType('wordpress-plugin');
  350. $consumerPackage = new RootPackage('foo/bar', '1.0.0', '1.0.0');
  351. $this->composer->setPackage($consumerPackage);
  352. $consumerPackage->setExtra(array(
  353. 'installer-paths' => array(
  354. 'my/custom/path/{$name}/' => array(
  355. 'type:wordpress-plugin'
  356. ),
  357. ),
  358. ));
  359. $result = $installer->getInstallPath($package);
  360. $this->assertEquals('my/custom/path/my_plugin/', $result);
  361. }
  362. /**
  363. * testNoVendorName
  364. */
  365. public function testNoVendorName()
  366. {
  367. $installer = new Installer($this->io, $this->composer);
  368. $package = new Package('sfPhpunitPlugin', '1.0.0', '1.0.0');
  369. $package->setType('symfony1-plugin');
  370. $result = $installer->getInstallPath($package);
  371. $this->assertEquals('plugins/sfPhpunitPlugin/', $result);
  372. }
  373. /**
  374. * testTypo3Inflection
  375. */
  376. public function testTypo3Inflection()
  377. {
  378. $installer = new Installer($this->io, $this->composer);
  379. $package = new Package('typo3/fluid', '1.0.0', '1.0.0');
  380. $package->setAutoload(array(
  381. 'psr-0' => array(
  382. 'TYPO3\\Fluid' => 'Classes',
  383. ),
  384. ));
  385. $package->setType('typo3-flow-package');
  386. $result = $installer->getInstallPath($package);
  387. $this->assertEquals('Packages/Application/TYPO3.Fluid/', $result);
  388. }
  389. public function testUninstallAndDeletePackageFromLocalRepo()
  390. {
  391. $package = new Package('foo', '1.0.0', '1.0.0');
  392. $installer = $this->getMock('Composer\Installers\Installer', array('getInstallPath'), array($this->io, $this->composer));
  393. $installer->expects($this->once())->method('getInstallPath')->with($package)->will($this->returnValue(sys_get_temp_dir().'/foo'));
  394. $repo = $this->getMock('Composer\Repository\InstalledRepositoryInterface');
  395. $repo->expects($this->once())->method('hasPackage')->with($package)->will($this->returnValue(true));
  396. $repo->expects($this->once())->method('removePackage')->with($package);
  397. $installer->uninstall($repo, $package);
  398. }
  399. }