Correct Aphlict websocket URI construction after PHP8 compatibility changes
[phabricator.git] / src / applications / config / check / PhabricatorPathSetupCheck.php
blob8a98c5ba9f55c35031fb82e4c2f11d9897264a1e
1 <?php
3 final class PhabricatorPathSetupCheck extends PhabricatorSetupCheck {
5 public function getDefaultGroup() {
6 return self::GROUP_OTHER;
9 protected function executeChecks() {
10 // NOTE: We've already appended `environment.append-paths`, so we don't
11 // need to explicitly check for it.
12 $path = getenv('PATH');
14 if (!$path) {
15 $summary = pht(
16 'The environmental variable %s is empty. This server will not '.
17 'be able to execute some commands.',
18 '$PATH');
20 $message = pht(
21 "The environmental variable %s is empty. This server needs to execute ".
22 "some system commands, like `%s`, `%s`, `%s`, and `%s`. To execute ".
23 "these commands, the binaries must be available in the webserver's ".
24 "%s. You can set additional paths in configuration.",
25 '$PATH',
26 'svn',
27 'git',
28 'hg',
29 'diff',
30 '$PATH');
32 $this
33 ->newIssue('config.environment.append-paths')
34 ->setName(pht('%s Not Set', '$PATH'))
35 ->setSummary($summary)
36 ->setMessage($message)
37 ->addPhabricatorConfig('environment.append-paths');
39 // Bail on checks below.
40 return;
43 // Users are remarkably industrious at misconfiguring software. Try to
44 // catch mistaken configuration of PATH.
46 $path_parts = explode(PATH_SEPARATOR, $path);
47 $bad_paths = array();
48 foreach ($path_parts as $path_part) {
49 if (!strlen($path_part)) {
50 continue;
53 $message = null;
54 $not_exists = false;
55 foreach (Filesystem::walkToRoot($path_part) as $part) {
56 if (!Filesystem::pathExists($part)) {
57 $not_exists = $part;
58 // Walk up so we can tell if this is a readability issue or not.
59 continue;
60 } else if (!is_dir(Filesystem::resolvePath($part))) {
61 $message = pht(
62 "The PATH component '%s' (which resolves as the absolute path ".
63 "'%s') is not usable because '%s' is not a directory.",
64 $path_part,
65 Filesystem::resolvePath($path_part),
66 $part);
67 } else if (!is_readable($part)) {
68 $message = pht(
69 "The PATH component '%s' (which resolves as the absolute path ".
70 "'%s') is not usable because '%s' is not readable.",
71 $path_part,
72 Filesystem::resolvePath($path_part),
73 $part);
74 } else if ($not_exists) {
75 $message = pht(
76 "The PATH component '%s' (which resolves as the absolute path ".
77 "'%s') is not usable because '%s' does not exist.",
78 $path_part,
79 Filesystem::resolvePath($path_part),
80 $not_exists);
81 } else {
82 // Everything seems good.
83 break;
86 if ($message !== null) {
87 break;
91 if ($message === null) {
92 if (!phutil_is_windows() && !@file_exists($path_part.'/.')) {
93 $message = pht(
94 "The PATH component '%s' (which resolves as the absolute path ".
95 "'%s') is not usable because it is not traversable (its '%s' ".
96 "permission bit is not set).",
97 $path_part,
98 Filesystem::resolvePath($path_part),
99 '+x');
103 if ($message !== null) {
104 $bad_paths[$path_part] = $message;
108 if ($bad_paths) {
109 foreach ($bad_paths as $path_part => $message) {
110 $digest = substr(PhabricatorHash::weakDigest($path_part), 0, 8);
112 $this
113 ->newIssue('config.PATH.'.$digest)
114 ->setName(pht('%s Component Unusable', '$PATH'))
115 ->setSummary(
116 pht(
117 'A component of the configured PATH can not be used by '.
118 'the webserver: %s',
119 $path_part))
120 ->setMessage(
121 pht(
122 "The configured PATH includes a component which is not usable. ".
123 "This server will be unable to find or execute binaries located ".
124 "here:".
125 "\n\n".
126 "%s".
127 "\n\n".
128 "The user that the webserver runs as must be able to read all ".
129 "the directories in PATH in order to make use of them.",
130 $message))
131 ->addPhabricatorConfig('environment.append-paths');