diff options
author | ArthurHoaro <arthur@hoa.ro> | 2020-11-12 13:02:36 +0100 |
---|---|---|
committer | ArthurHoaro <arthur@hoa.ro> | 2020-11-12 13:02:36 +0100 |
commit | 1409f1c89a7ca01456ae2dcd6357d296e2b99f5a (patch) | |
tree | ffa30a9358e82d27be75d8fc5e57f3c8820dc6d3 /application/ApplicationUtils.php | |
parent | 054e03f37fa29da8066f1a637919f13c7e7dc5d2 (diff) | |
parent | a6935feb22df8d9634189ee87d257da9f03eedbd (diff) | |
download | Shaarli-v0.12.tar.gz Shaarli-v0.12.tar.zst Shaarli-v0.12.zip |
Diffstat (limited to 'application/ApplicationUtils.php')
-rw-r--r-- | application/ApplicationUtils.php | 249 |
1 files changed, 0 insertions, 249 deletions
diff --git a/application/ApplicationUtils.php b/application/ApplicationUtils.php deleted file mode 100644 index 3aa21829..00000000 --- a/application/ApplicationUtils.php +++ /dev/null | |||
@@ -1,249 +0,0 @@ | |||
1 | <?php | ||
2 | namespace Shaarli; | ||
3 | |||
4 | use Exception; | ||
5 | use Shaarli\Config\ConfigManager; | ||
6 | |||
7 | /** | ||
8 | * Shaarli (application) utilities | ||
9 | */ | ||
10 | class ApplicationUtils | ||
11 | { | ||
12 | /** | ||
13 | * @var string File containing the current version | ||
14 | */ | ||
15 | public static $VERSION_FILE = 'shaarli_version.php'; | ||
16 | |||
17 | private static $GIT_URL = 'https://raw.githubusercontent.com/shaarli/Shaarli'; | ||
18 | private static $GIT_BRANCHES = array('latest', 'stable'); | ||
19 | private static $VERSION_START_TAG = '<?php /* '; | ||
20 | private static $VERSION_END_TAG = ' */ ?>'; | ||
21 | |||
22 | /** | ||
23 | * Gets the latest version code from the Git repository | ||
24 | * | ||
25 | * The code is read from the raw content of the version file on the Git server. | ||
26 | * | ||
27 | * @param string $url URL to reach to get the latest version. | ||
28 | * @param int $timeout Timeout to check the URL (in seconds). | ||
29 | * | ||
30 | * @return mixed the version code from the repository if available, else 'false' | ||
31 | */ | ||
32 | public static function getLatestGitVersionCode($url, $timeout = 2) | ||
33 | { | ||
34 | list($headers, $data) = get_http_response($url, $timeout); | ||
35 | |||
36 | if (strpos($headers[0], '200 OK') === false) { | ||
37 | error_log('Failed to retrieve ' . $url); | ||
38 | return false; | ||
39 | } | ||
40 | |||
41 | return $data; | ||
42 | } | ||
43 | |||
44 | /** | ||
45 | * Retrieve the version from a remote URL or a file. | ||
46 | * | ||
47 | * @param string $remote URL or file to fetch. | ||
48 | * @param int $timeout For URLs fetching. | ||
49 | * | ||
50 | * @return bool|string The version or false if it couldn't be retrieved. | ||
51 | */ | ||
52 | public static function getVersion($remote, $timeout = 2) | ||
53 | { | ||
54 | if (startsWith($remote, 'http')) { | ||
55 | if (($data = static::getLatestGitVersionCode($remote, $timeout)) === false) { | ||
56 | return false; | ||
57 | } | ||
58 | } else { | ||
59 | if (!is_file($remote)) { | ||
60 | return false; | ||
61 | } | ||
62 | $data = file_get_contents($remote); | ||
63 | } | ||
64 | |||
65 | return str_replace( | ||
66 | array(self::$VERSION_START_TAG, self::$VERSION_END_TAG, PHP_EOL), | ||
67 | array('', '', ''), | ||
68 | $data | ||
69 | ); | ||
70 | } | ||
71 | |||
72 | /** | ||
73 | * Checks if a new Shaarli version has been published on the Git repository | ||
74 | * | ||
75 | * Updates checks are run periodically, according to the following criteria: | ||
76 | * - the update checks are enabled (install, global config); | ||
77 | * - the user is logged in (or this is an open instance); | ||
78 | * - the last check is older than a given interval; | ||
79 | * - the check is non-blocking if the HTTPS connection to Git fails; | ||
80 | * - in case of failure, the update file's modification date is updated, | ||
81 | * to avoid intempestive connection attempts. | ||
82 | * | ||
83 | * @param string $currentVersion the current version code | ||
84 | * @param string $updateFile the file where to store the latest version code | ||
85 | * @param int $checkInterval the minimum interval between update checks (in seconds | ||
86 | * @param bool $enableCheck whether to check for new versions | ||
87 | * @param bool $isLoggedIn whether the user is logged in | ||
88 | * @param string $branch check update for the given branch | ||
89 | * | ||
90 | * @throws Exception an invalid branch has been set for update checks | ||
91 | * | ||
92 | * @return mixed the new version code if available and greater, else 'false' | ||
93 | */ | ||
94 | public static function checkUpdate( | ||
95 | $currentVersion, | ||
96 | $updateFile, | ||
97 | $checkInterval, | ||
98 | $enableCheck, | ||
99 | $isLoggedIn, | ||
100 | $branch = 'stable' | ||
101 | ) { | ||
102 | // Do not check versions for visitors | ||
103 | // Do not check if the user doesn't want to | ||
104 | // Do not check with dev version | ||
105 | if (!$isLoggedIn || empty($enableCheck) || $currentVersion === 'dev') { | ||
106 | return false; | ||
107 | } | ||
108 | |||
109 | if (is_file($updateFile) && (filemtime($updateFile) > time() - $checkInterval)) { | ||
110 | // Shaarli has checked for updates recently - skip HTTP query | ||
111 | $latestKnownVersion = file_get_contents($updateFile); | ||
112 | |||
113 | if (version_compare($latestKnownVersion, $currentVersion) == 1) { | ||
114 | return $latestKnownVersion; | ||
115 | } | ||
116 | return false; | ||
117 | } | ||
118 | |||
119 | if (!in_array($branch, self::$GIT_BRANCHES)) { | ||
120 | throw new Exception( | ||
121 | 'Invalid branch selected for updates: "' . $branch . '"' | ||
122 | ); | ||
123 | } | ||
124 | |||
125 | // Late Static Binding allows overriding within tests | ||
126 | // See http://php.net/manual/en/language.oop5.late-static-bindings.php | ||
127 | $latestVersion = static::getVersion( | ||
128 | self::$GIT_URL . '/' . $branch . '/' . self::$VERSION_FILE | ||
129 | ); | ||
130 | |||
131 | if (!$latestVersion) { | ||
132 | // Only update the file's modification date | ||
133 | file_put_contents($updateFile, $currentVersion); | ||
134 | return false; | ||
135 | } | ||
136 | |||
137 | // Update the file's content and modification date | ||
138 | file_put_contents($updateFile, $latestVersion); | ||
139 | |||
140 | if (version_compare($latestVersion, $currentVersion) == 1) { | ||
141 | return $latestVersion; | ||
142 | } | ||
143 | |||
144 | return false; | ||
145 | } | ||
146 | |||
147 | /** | ||
148 | * Checks the PHP version to ensure Shaarli can run | ||
149 | * | ||
150 | * @param string $minVersion minimum PHP required version | ||
151 | * @param string $curVersion current PHP version (use PHP_VERSION) | ||
152 | * | ||
153 | * @return bool true on success | ||
154 | * | ||
155 | * @throws Exception the PHP version is not supported | ||
156 | */ | ||
157 | public static function checkPHPVersion($minVersion, $curVersion) | ||
158 | { | ||
159 | if (version_compare($curVersion, $minVersion) < 0) { | ||
160 | $msg = t( | ||
161 | 'Your PHP version is obsolete!' | ||
162 | . ' Shaarli requires at least PHP %s, and thus cannot run.' | ||
163 | . ' Your PHP version has known security vulnerabilities and should be' | ||
164 | . ' updated as soon as possible.' | ||
165 | ); | ||
166 | throw new Exception(sprintf($msg, $minVersion)); | ||
167 | } | ||
168 | return true; | ||
169 | } | ||
170 | |||
171 | /** | ||
172 | * Checks Shaarli has the proper access permissions to its resources | ||
173 | * | ||
174 | * @param ConfigManager $conf Configuration Manager instance. | ||
175 | * | ||
176 | * @return array A list of the detected configuration issues | ||
177 | */ | ||
178 | public static function checkResourcePermissions($conf) | ||
179 | { | ||
180 | $errors = array(); | ||
181 | $rainTplDir = rtrim($conf->get('resource.raintpl_tpl'), '/'); | ||
182 | |||
183 | // Check script and template directories are readable | ||
184 | foreach (array( | ||
185 | 'application', | ||
186 | 'inc', | ||
187 | 'plugins', | ||
188 | $rainTplDir, | ||
189 | $rainTplDir . '/' . $conf->get('resource.theme'), | ||
190 | ) as $path) { | ||
191 | if (!is_readable(realpath($path))) { | ||
192 | $errors[] = '"' . $path . '" ' . t('directory is not readable'); | ||
193 | } | ||
194 | } | ||
195 | |||
196 | // Check cache and data directories are readable and writable | ||
197 | foreach (array( | ||
198 | $conf->get('resource.thumbnails_cache'), | ||
199 | $conf->get('resource.data_dir'), | ||
200 | $conf->get('resource.page_cache'), | ||
201 | $conf->get('resource.raintpl_tmp'), | ||
202 | ) as $path) { | ||
203 | if (!is_readable(realpath($path))) { | ||
204 | $errors[] = '"' . $path . '" ' . t('directory is not readable'); | ||
205 | } | ||
206 | if (!is_writable(realpath($path))) { | ||
207 | $errors[] = '"' . $path . '" ' . t('directory is not writable'); | ||
208 | } | ||
209 | } | ||
210 | |||
211 | // Check configuration files are readable and writable | ||
212 | foreach (array( | ||
213 | $conf->getConfigFileExt(), | ||
214 | $conf->get('resource.datastore'), | ||
215 | $conf->get('resource.ban_file'), | ||
216 | $conf->get('resource.log'), | ||
217 | $conf->get('resource.update_check'), | ||
218 | ) as $path) { | ||
219 | if (!is_file(realpath($path))) { | ||
220 | # the file may not exist yet | ||
221 | continue; | ||
222 | } | ||
223 | |||
224 | if (!is_readable(realpath($path))) { | ||
225 | $errors[] = '"' . $path . '" ' . t('file is not readable'); | ||
226 | } | ||
227 | if (!is_writable(realpath($path))) { | ||
228 | $errors[] = '"' . $path . '" ' . t('file is not writable'); | ||
229 | } | ||
230 | } | ||
231 | |||
232 | return $errors; | ||
233 | } | ||
234 | |||
235 | /** | ||
236 | * Returns a salted hash representing the current Shaarli version. | ||
237 | * | ||
238 | * Useful for assets browser cache. | ||
239 | * | ||
240 | * @param string $currentVersion of Shaarli | ||
241 | * @param string $salt User personal salt, also used for the authentication | ||
242 | * | ||
243 | * @return string version hash | ||
244 | */ | ||
245 | public static function getVersionHash($currentVersion, $salt) | ||
246 | { | ||
247 | return hash_hmac('sha256', $currentVersion, $salt); | ||
248 | } | ||
249 | } | ||