PluginProbe ʕ •ᴥ•ʔ
WP STAGING – WordPress Backup, Restore, Migration & Clone / 4.4.0
WP STAGING – WordPress Backup, Restore, Migration & Clone v4.4.0
4.9.1 4.9.0 4.8.1 trunk 3.0.0 3.0.1 3.0.2 3.0.3 3.0.4 3.0.5 3.0.6 3.1.0 3.1.1 3.1.2 3.1.3 3.1.4 3.10.0 3.2.0 3.3.1 3.3.2 3.3.3 3.4.1 3.4.3 3.5.0 3.6.0 3.7.1 3.8.0 3.8.1 3.8.2 3.8.3 3.8.4 3.8.5 3.8.6 3.8.7 3.9.0 3.9.1 3.9.2 3.9.3 3.9.4 4.0.0 4.1.0 4.1.1 4.1.2 4.1.3 4.1.4 4.2.0 4.2.1 4.3.0 4.3.1 4.3.2 4.4.0 4.5.0 4.6.0 4.7.0 4.7.1 4.7.2 4.7.3 4.8.0
wp-staging / runtimeRequirements.php
wp-staging Last commit date
Backend 6 months ago Backup 6 months ago Basic 6 months ago Component 6 months ago Core 6 months ago Framework 6 months ago Frontend 8 months ago Notifications 8 months ago Staging 6 months ago assets 6 months ago languages 1 year ago resources 1 year ago vendor_wpstg 6 months ago views 6 months ago CONTRIBUTING.md 1 year ago Deactivate.php 8 months ago README.md 9 months ago SECURITY.md 2 years ago autoloader.php 6 months ago bootstrap.php 9 months ago constantsFree.php 6 months ago freeBootstrap.php 1 year ago install.php 1 year ago opcacheBootstrap.php 6 months ago readme.txt 6 months ago runtimeRequirements.php 9 months ago uninstall.php 11 months ago wp-staging-error-handler.php 6 months ago wp-staging.php 6 months ago
runtimeRequirements.php
407 lines
1 <?php
2
3 /**
4 * @var string $pluginFilePath The absolute path to the main file of this plugin.
5 *
6 */
7 $pluginFilePath = $pluginFilePath ?? '';
8 // TODO: refactor this and implement our own methods to get rid of hard loading wp core functions which is not recommended by WP.
9 require_once(trailingslashit(ABSPATH) . 'wp-admin/includes/plugin.php');
10
11 if (!defined('WPSTGPRO_MINIMUM_FREE_VERSION')) {
12 /** Expected version number of the free plugin in order to activate it at the same time with pro */
13 define('WPSTGPRO_MINIMUM_FREE_VERSION', '3.8.0');
14 }
15
16 if (!defined('WPSTG_FREE_VERSION_PLUGIN_FILE')) {
17 define('WPSTG_FREE_VERSION_PLUGIN_FILE', 'wp-staging.php');
18 }
19
20 if (!defined('WPSTG_PRO_VERSION_PLUGIN_FILE')) {
21 define('WPSTG_PRO_VERSION_PLUGIN_FILE', 'wp-staging-pro.php');
22 }
23
24 if (!function_exists('wpstgIsProPluginActive')) {
25 /**
26 * @return bool
27 */
28 function wpstgIsProPluginActive(): bool
29 {
30 return wpstgIsPluginActivated(WPSTG_PRO_VERSION_PLUGIN_FILE);
31 }
32 }
33
34 if (!function_exists('wpstgIsProPluginActiveInNetwork')) {
35 /**
36 * @return bool
37 */
38 function wpstgIsProPluginActiveInNetwork(): bool
39 {
40 return wpstgIsPluginActiveInNetwork(WPSTG_PRO_VERSION_PLUGIN_FILE);
41 }
42 }
43
44 if (!function_exists('wpstgIsFreeVersionRequiredForPro')) {
45 /**
46 * @return bool
47 */
48 function wpstgIsFreeVersionRequiredForPro(): bool
49 {
50 return apply_filters('wpstg.free_required_by_pro', true);
51 }
52 }
53
54 if (!function_exists('wpstgIsProActiveInNetworkOrInCurrentSite')) {
55 /**
56 * @return bool
57 */
58 function wpstgIsProActiveInNetworkOrInCurrentSite(): bool
59 {
60 return wpstgIsProPluginActiveInNetwork() || wpstgIsProPluginActive();
61 }
62 }
63
64 if (!function_exists('wpstgIsFreeVersionActive')) {
65 /**
66 * @return bool
67 */
68 function wpstgIsFreeVersionActive(): bool
69 {
70 return wpstgIsPluginActivated(WPSTG_FREE_VERSION_PLUGIN_FILE);
71 }
72 }
73
74 if (!function_exists('wpstgIsFreeVersionActiveInNetwork')) {
75 /**
76 * @return bool
77 */
78 function wpstgIsFreeVersionActiveInNetwork(): bool
79 {
80 return wpstgIsPluginActiveInNetwork(WPSTG_FREE_VERSION_PLUGIN_FILE);
81 }
82 }
83
84 if (!function_exists('wpstgIsFreeActiveInNetworkOrCurrentSite')) {
85 /**
86 * @return bool
87 */
88 function wpstgIsFreeActiveInNetworkOrCurrentSite(): bool
89 {
90 return wpstgIsFreeVersionActiveInNetwork() || wpstgIsFreeVersionActive();
91 }
92 }
93
94 if (!function_exists('wpstgGetPluginSlug')) {
95 /**
96 * @param string $pluginFileName
97 *
98 * @return bool|string false if plugin is not installed otherwise return the plugin slug/basename.
99 */
100 function wpstgGetPluginSlug(string $pluginFileName)
101 {
102 $allPlugins = get_plugins();
103 foreach ($allPlugins as $key => $value) {
104 if (strpos($key, $pluginFileName) !== false) {
105 return $key;
106 }
107 }
108
109 return false;
110 }
111 }
112
113 if (!function_exists('wpstgGetPluginData')) {
114 /**
115 * @param string $pluginFileName
116 *
117 * @return array
118 */
119 function wpstgGetPluginData(string $pluginFileName): array
120 {
121 $allPlugins = get_plugins();
122 foreach ($allPlugins as $key => $value) {
123 if (strpos($key, $pluginFileName) !== false) {
124 return $value;
125 }
126 }
127
128 return [];
129 }
130 }
131
132 if (!function_exists('wpstgGetFreeVersionNumberIfInstalled')) {
133 /**
134 * @return string returns empty string if free is not installed.
135 */
136 function wpstgGetFreeVersionNumberIfInstalled(): string
137 {
138 $freeData = wpstgGetPluginData(WPSTG_FREE_VERSION_PLUGIN_FILE);
139 $installedFreeVersionNumber = isset($freeData['Version']) ? $freeData['Version'] : '';
140
141 return $installedFreeVersionNumber;
142 }
143 }
144
145 if (!function_exists('wpstgGetProVersionNumberIfInstalled')) {
146 /**
147 * @return string returns empty string if pro is not installed.
148 */
149 function wpstgGetProVersionNumberIfInstalled(): string
150 {
151 $freeData = wpstgGetPluginData(WPSTG_PRO_VERSION_PLUGIN_FILE);
152 $installedFreeVersionNumber = isset($freeData['Version']) ? $freeData['Version'] : '';
153
154 return $installedFreeVersionNumber;
155 }
156 }
157
158 if (!function_exists('wpstgIsFreeVersionCompatible')) {
159 /**
160 * @return bool
161 */
162 function wpstgIsFreeVersionCompatible(): bool
163 {
164 return defined('WPSTGPRO_MINIMUM_FREE_VERSION') && version_compare(wpstgGetFreeVersionNumberIfInstalled(), WPSTGPRO_MINIMUM_FREE_VERSION, '>=');
165 }
166 }
167
168 if (!function_exists('wpstgIsFreeActiveButOutdated')) {
169 /**
170 * @return bool
171 */
172 function wpstgIsFreeActiveButOutdated(): bool
173 {
174 if (wpstgIsFreeActiveInNetworkOrCurrentSite() && !wpstgIsFreeVersionCompatible()) {
175 return true;
176 }
177
178 return false;
179 }
180 }
181
182 if (!function_exists('wpstgDeactivatePlugin')) {
183 /**
184 * @param mixed $pluginFilePath
185 * @return void
186 */
187 function wpstgDeactivatePlugin($pluginFilePath)
188 {
189 if (is_network_admin()) {
190 deactivate_plugins($pluginFilePath, false, true);
191 } else {
192 deactivate_plugins($pluginFilePath);
193 }
194 }
195 }
196
197 if (!function_exists('wpstgCanShowAnotherInstanceRunningNotice')) {
198 /**
199 * @param string $pluginFilePath
200 * @return bool
201 */
202 function wpstgCanShowAnotherInstanceRunningNotice(string $pluginFilePath): bool
203 {
204 if (!current_user_can('activate_plugins')) {
205 return false;
206 }
207
208 if (strpos($pluginFilePath, 'wp-staging-pro.php') !== false && wpstgIsProActiveInNetworkOrInCurrentSite() && !wpstgIsFreeActiveInNetworkOrCurrentSite()) {
209 return true;
210 }
211
212 if (strpos($pluginFilePath, 'wp-staging.php') !== false && !wpstgIsProActiveInNetworkOrInCurrentSite() && wpstgIsFreeActiveInNetworkOrCurrentSite()) {
213 return true;
214 }
215
216 return false;
217 }
218 }
219
220 if (!function_exists('wpstgCanThrowAnotherInstanceLoadedException')) {
221 /**
222 * @param string $pluginFilePath
223 * @return bool
224 */
225 function wpstgCanThrowAnotherInstanceLoadedException(string $pluginFilePath = ''): bool
226 {
227 if (defined('WPSTG_VERSION') && version_compare(WPSTG_VERSION, WPSTGPRO_MINIMUM_FREE_VERSION, '<')) {
228 return true;
229 }
230
231 if (defined('WPSTGPRO_VERSION') && version_compare(WPSTGPRO_VERSION, '5.1.0', '<')) {
232 return true;
233 }
234
235 if (!wpstgIsProActiveInNetworkOrInCurrentSite() && strpos($pluginFilePath, 'wp-staging-pro.php') === false) {
236 return true;
237 }
238
239 return false;
240 }
241 }
242
243 if (!function_exists('wpstgIsPluginActivated')) {
244 /**
245 * This function checks if a plugin is activated on single site.
246 *
247 * @param string $pluginFileName
248 *
249 * @return bool
250 */
251 function wpstgIsPluginActivated(string $pluginFileName): bool
252 {
253 $activePlugins = wp_get_active_and_valid_plugins();
254 foreach ($activePlugins as $sitewidePlugin) {
255 if (strpos($sitewidePlugin, $pluginFileName) !== false) {
256 return true;
257 }
258 }
259
260 return false;
261 }
262 }
263
264 if (!function_exists('wpstgIsPluginActiveInNetwork')) {
265 /**
266 * @param string $pluginFileName
267 *
268 * @return bool
269 */
270 function wpstgIsPluginActiveInNetwork(string $pluginFileName): bool
271 {
272 if (!is_multisite()) {
273 return false;
274 }
275
276 $activePlugins = wp_get_active_network_plugins();
277 foreach ($activePlugins as $sitewidePlugin) {
278 if (strpos($sitewidePlugin, $pluginFileName) !== false) {
279 return true;
280 }
281 }
282
283 return false;
284 }
285 }
286
287 if (!function_exists('wpstgDoLoadPluginAutoLoad')) {
288 /**
289 * @param string $pluginFilePath
290 * @return void
291 */
292 function wpstgDoLoadPluginAutoLoad(string $pluginFilePath): bool
293 {
294 if (class_exists('\WPStaging\Core\WPStaging')) {
295 return false;
296 }
297
298 if (strpos($pluginFilePath, 'wp-staging.php') === false) {
299 return true;
300 }
301
302 if (strpos($pluginFilePath, 'wp-staging.php') !== false && (!is_network_admin() && !wpstgIsProPluginActive())) {
303 return true;
304 }
305
306 if (strpos($pluginFilePath, 'wp-staging.php') !== false && (is_network_admin() && !wpstgIsProPluginActiveInNetwork())) {
307 return true;
308 }
309
310 return false;
311 }
312 }
313
314 /**
315 * Early bail: Deactivate outdated free version.
316 */
317 if (strpos($pluginFilePath, 'wp-staging-pro.php') !== false && wpstgIsFreeActiveButOutdated()) {
318 // Deactivate free plugin.
319 $pluginSlug = wpstgGetPluginSlug(WPSTG_FREE_VERSION_PLUGIN_FILE);
320 wpstgDeactivatePlugin($pluginSlug);
321 }
322
323 /**
324 * Early bail: Activating another WPSTAGING Plugin.
325 * This is the only scenario where the plugin would be included after "plugins_loaded",
326 * therefore we need to detect earlier, from the context of the request, whether this is going to happen,
327 * to disable this plugin early and bail the bootstrap process to not conflict with the one being activated.
328 *
329 * Covers both clicking on the "Activate" button and selecting the "Activate" bulk-action.
330 */
331 if (isset($_REQUEST['action'])) {
332 switch ($_REQUEST['action']) :
333 case 'activate':
334 case 'error_scrape':
335 if (isset($_REQUEST['plugin'])) {
336 $plugin = (string)wp_unslash(sanitize_text_field($_REQUEST['plugin']));
337
338 $isActivatingWpStaging = strpos($plugin, 'wp-staging.php') || strpos($plugin, 'wp-staging-pro.php');
339 $isActivatingAnotherWpStaging = plugin_basename($plugin) !== plugin_basename($pluginFilePath);
340
341 if ($isActivatingWpStaging && $isActivatingAnotherWpStaging && wpstgCanThrowAnotherInstanceLoadedException($plugin) && current_user_can('deactivate_plugin', plugin_basename($pluginFilePath))) {
342 throw new Exception("Activating another WPSTAGING Plugin. Plugin that bailed bootstrapping: $pluginFilePath");
343 }
344 }
345
346 break;
347 case 'activate-selected':
348 case 'activate-multi':
349 if (isset($_REQUEST['checked'])) {
350 $plugins = array_map('sanitize_text_field', (array)wp_unslash($_REQUEST['checked']));
351
352 foreach ($plugins as $i => $plugin) {
353 $isActivatingWpStaging = strpos($plugin, 'wp-staging.php') || strpos($plugin, 'wp-staging-pro.php');
354 $isActivatingAnotherWpStaging = plugin_basename($plugin) !== plugin_basename($pluginFilePath);
355
356 if ($isActivatingWpStaging && $isActivatingAnotherWpStaging && wpstgCanThrowAnotherInstanceLoadedException($plugin) && current_user_can('deactivate_plugin', plugin_basename($pluginFilePath))) {
357 throw new Exception("Activating another WPSTAGING Plugin. Plugin that bailed bootstrapping: $pluginFilePath");
358 }
359 }
360 }
361
362 break;
363 endswitch;
364 }
365
366 /**
367 * Early bail: Another instance of WPSTAGING active.
368 */
369 if (
370 // WPSTAGING <= 2.7.5
371 class_exists('\WPStaging\WPStaging') ||
372 // WPSTAGING >= 2.7.6
373 class_exists('\WPStaging\Core\WPStaging')
374 ) {
375 if (wpstgCanShowAnotherInstanceRunningNotice($pluginFilePath)) {
376 add_action(is_network_admin() ? 'network_admin_notices' : 'admin_notices', function () { // phpcs:ignore WPStaging.Security.FirstArgNotAString, WPStaging.Security.AuthorizationChecked
377 echo '<div class="notice-warning notice is-dismissible another-wpstaging-active">';
378 echo '<p style="font-weight: bold;">' . esc_html__('WP STAGING Already Active', 'wp-staging') . '</p>';
379 echo '<p>' . esc_html__('Another WP STAGING is already activated, please leave only one instance of the WP STAGING plugin active at the same time.', 'wp-staging') . '</p>';
380 echo '</div>';
381 });
382 }
383
384 if (!wpstgCanThrowAnotherInstanceLoadedException($pluginFilePath)) {
385 return;
386 }
387
388 throw new Exception("Another instance of WPSTAGING active. Plugin that bailed bootstrapping: $pluginFilePath");
389 }
390
391 /**
392 * Early bail: Unsupported WordPress version.
393 * We check on runtime instead of activation so we can display the notice.
394 */
395 if (!version_compare($currentWordPressVersion = (string)get_bloginfo('version'), $minimumWordPressVersion = '4.4', '>=')) {
396 if (current_user_can('activate_plugins')) {
397 add_action(is_network_admin() ? 'network_admin_notices' : 'admin_notices', function () use ($currentWordPressVersion, $minimumWordPressVersion) { // phpcs:ignore WPStaging.Security.FirstArgNotAString, WPStaging.Security.AuthorizationChecked
398 echo '<div class="notice-warning notice is-dismissible">';
399 echo '<p style="font-weight: bold;">' . esc_html__('WP STAGING', 'wp-staging') . '</p>';
400 echo '<p>' . sprintf(esc_html__('WP STAGING requires at least WordPress %s to run. You have WordPress %s.', 'wp-staging'), esc_html($minimumWordPressVersion), esc_html($currentWordPressVersion)) . '</p>';
401 echo '</div>';
402 });
403 }
404
405 throw new Exception("Unsupported WordPress version. Plugin that bailed bootstrapping: $pluginFilePath");
406 }
407