Merge pull request #19284 from eileenmcnaughton/mem_r
[civicrm-core.git] / tools / scripts / phpunit
1 #!/usr/bin/env php
2 <?php
3
4 /**
5 * In the past, Civi bundled a hacked copy of PHPUnit used like:
6 *
7 * cd tools
8 * ./scripts/phpunit Some_Class_NameTest
9 *
10 * This script is an adapter for backwards compatibility.
11 */
12
13 $argFilters = [];
14
15 if (PHP_SAPI !== 'cli') {
16 die("phpunit can only be run from command line.");
17 }
18 if (version_compare(PHP_VERSION, '7.1', '>=')) {
19 $phpunit = findCommand('phpunit7');
20 $argFilters[] = function ($argv) {
21 $pos = array_search('--tap', $argv);
22 if ($pos !== FALSE) {
23 array_splice($argv, $pos, 1, ['--printer', '\Civi\Test\TAP']);
24 }
25 return $argv;
26 };
27 }
28 elseif (version_compare(PHP_VERSION, '7.0', '>=')) {
29 $phpunit = findCommand('phpunit6');
30 $argFilters[] = function ($argv) {
31 $pos = array_search('--tap', $argv);
32 if ($pos !== FALSE) {
33 array_splice($argv, $pos, 1, ['--printer', '\Civi\Test\TAP']);
34 }
35 return $argv;
36 };
37 }
38 elseif (version_compare(PHP_VERSION, '5.6', '>=')) {
39 $phpunit = findCommand('phpunit5');
40 }
41 else {
42 $phpunit = findCommand('phpunit4');
43 }
44 if (!$phpunit) {
45 $phpunit = findCommand('phpunit');
46 }
47 if (!$phpunit) {
48 echo "Plesae ensure that:\n";
49 echo " * PHPUnit is installed.\n";
50 echo " * The extensions for dbunit and selenium are installed.\n" ;
51 echo " * The command \"phpunit\" is in the PATH.\n";
52 echo "See also: https://github.com/civicrm/civicrm-buildkit/\n";
53 exit(127);
54 }
55
56 chdir(dirname(dirname(__DIR__))); // civicrm-core root dir
57
58 array_shift($argv);
59
60 // Convert class names to file names
61 $CIVICRM_UF = 'UnitTests';
62 foreach ($argv as $k => $v) {
63 if (preg_match('/^(CRM_|api_v3_|api_v4_|EnvTest|WebTest_|E2E_)/', $v)) {
64 $argv[$k] = 'tests/phpunit/' . strtr($v, '_', '/') . '.php';
65 }
66 elseif (preg_match('/^Civi\\\\/', $v)) {
67 $argv[$k] = 'tests/phpunit/' . strtr($v, '\\', '/') . '.php';
68 }
69
70 if (preg_match('/^(WebTest|E2E)/', $v)) {
71 $CIVICRM_UF='';
72 }
73 }
74 putenv("CIVICRM_UF=$CIVICRM_UF");
75
76 // Transition: Make sure we use phpunit code from PATH, not
77 // civicrm-packages. This will be unnecessary once civicrm-packages is
78 // updated.
79 if (is_dir('packages/PHPUnit/')) {
80 if (!rename('packages/PHPUnit', 'packages/PHPUnit.bak')) {
81 echo "Failed to move aside stale copy of PHPUnit.\n";
82 exit(1);
83 }
84 }
85
86 foreach ($argFilters as $filter) {
87 $argv = $filter($argv);
88 }
89
90 $cmd =
91 findPhp() // In case this system has multiple copies of PHP, use the active/preferred one.
92 // . ' -ddisplay_errors=1'
93 . ' '
94 . escapeshellarg($phpunit)
95 . ' '
96 . implode(' ', array_map('escapeshellarg', $argv));
97 passthru($cmd);
98
99 function findPhp() {
100 // The autodetect behavior here is a potential point of contention. These two cases are hard to reconcile:
101 // 1. `php` is actually a wrapper script which delegates to another PHP binary and
102 // passes options (such as INI's and PECL extensions). Subprocesses should use the wrapper script.
103 // Examples: bitnami, bknix
104 // 2. There are multiple PHP binaries (eg `php55`, `php70`). Subprocesses should use
105 // the final executable (regardless of its name).
106 // Example: using MAMP and adding 'ln -s /Application/MAMP/.../php7.1.2/bin/php ~/bin/php71`
107 // Since the test infra uses a wrapper script like (1), we use autodetect logic that works there.
108 // If you're in situation (2), then set an env-var or just skip on using `tools/scripts/phpunit`.
109 if (getenv('PHP')) {
110 return getenv('PHP');
111 }
112 else {
113 return 'php';
114 }
115 }
116
117 function findCommand($name) {
118 $paths = explode(PATH_SEPARATOR, getenv('PATH'));
119 foreach ($paths as $path) {
120 if (file_exists("$path/$name")) {
121 return "$path/$name";
122 }
123 }
124 return NULL;
125 }