Version Description
17/July/2018 =
FEATURE: Added UpdraftCentral's theme management module handler
FEATURE: User can mark any backup as "do not delete", and it will then not be deleted even when retention limits are hit
FEATURE: WP-CLI - add a 'restore' command
FEATURE: WP-CLI - Add an option 'delete-during-restore' in the 'restore' command
FEATURE: Add optional 'fingerprint' configuration for sftp/scp remote storage, allowing the connection to be halted if the server's fingerprint does not match what was entered
FEATURE: Added the ability to take an incremental backup via WP-CLI (note: incremental backups are still considered an experimental/work-in-progress feature)
FIX: If a user gave the wrong key to decrypt an encrypted database, the "Decryption failed" message did not display
FIX: The Migration was not changing an unsupported database table engine with the MyISAM engine automatically
FIX: Issue with the Dropbox account API call on some installs
FIX: The web server disk space refresh link of the existing backups is not working
FIX: The UpdraftPlus News couldn't print first time when the news cache was not made
FIX: Activating the "all addons" licence did not remove the corresponding 'activate on this account' link in the "Premium / Extensions" tab
FIX: When set names query character set hadnt support by the current MySQL server, the restoration process wasn't gave replace the character set
TWEAK: Updated the plugin.php handler for UpdraftCentral's new plugin management module
TWEAK: Update posts handler to fix and update pagination in UpdraftCentral
TWEAK: Refresh UpdraftCentral keys upon successful login or registration using the UpdraftCentral Cloud wizard
TWEAK: Correct admin page URL in WP-CLI 'restore' command when on multisite without multisite add-on
TWEAK: Prevent PHP notice when checking non-existent files in relation to an extraneous whitespace warning
TWEAK: Prevent PHP notices in add-ons with non-present settings
TWEAK: Add the "Migrate / Clone" tab in place of the "Migrate / Clone" dialog
TWEAK: Prevent call to the the wp_get_sites() deprecated function on WP 4.6 and newer
TWEAK: Prevent a potential PHP debugging notice when displaying the 'Connect with your UpdraftPlus.com' form
TWEAK: Do not show the confusing JetPack 'backup' notice on the 'Updates' page
TWEAK: Added clone notices and commands for when UpdraftPlus is running on a UpdraftClone
TWEAK: Move 'Log all messages to syslog (only server admins are likely to want this)' into the 'expert' settings section
TWEAK: Replace a missing class constant in the Dropbox SDK (only relevant to people upgrading from Dropbox API v1 tokens - indicates upgrading UpdraftPlus from a very old version that previously used Dropbox APIv1 but never v2)
TWEAK: It's "backup", not "back up"
TWEAK: Prevent potential PHP debugging notices in restoration step 2
TWEAK: Allow non-Super Admins to access UpdraftPlus Premium if they have 'manage_network_plugins' capability and the updraft_user_can_manage filter is used
TWEAK: Improved code in a way that prevents continuous polling in the themes page, thes plugins page and the updates page
Release Info
Developer | DavidAnderson |
Plugin | UpdraftPlus WordPress Backup Plugin |
Version | 1.14.12 |
Comparing to | |
See all releases |
Code changes from version 1.14.10 to 1.14.12
- admin.php +87 -62
- backup.php +34 -8
- central/bootstrap.php +1 -0
- central/commands.php +23 -0
- central/modules/plugin.php +394 -79
- central/modules/posts.php +71 -31
- central/modules/theme.php +503 -0
- central/modules/updates.php +49 -0
- changelog.txt +7 -7
- class-updraftplus.php +97 -16
- css/updraftplus-admin.css +8 -3
- css/updraftplus-admin.min.css +1 -1
- css/updraftplus-admin.min.css.map +1 -1
- images/icons/lock.png +0 -0
- includes/Dropbox2/OAuth/Consumer/ConsumerAbstract.php +1 -1
- includes/Dropbox2/OAuth/Consumer/Curl.php +7 -3
- includes/class-backup-history.php +19 -0
- includes/class-commands.php +58 -2
- includes/class-manipulation-functions.php +13 -1
- includes/class-remote-send.php +528 -0
- includes/class-updraft-dashboard-news.php +61 -0
- includes/class-updraftplus-encryption.php +17 -0
- includes/updraftcentral.php +5 -1
- includes/updraftplus-admin.js +154 -104
- includes/updraftplus-admin.min.js +3 -3
- includes/updraftplus-clone.php +98 -0
- includes/updraftplus-temporary-clone-commands.php +35 -0
- includes/updraftplus-temporary-clone-dash-notice.php +142 -0
- includes/updraftplus-temporary-clone-user-notice.php +115 -0
- languages/updraftplus-af.po +921 -813
- languages/updraftplus-ar.mo +0 -0
- languages/updraftplus-ar.po +921 -813
- languages/updraftplus-bg_BG.po +921 -813
- languages/updraftplus-bn_BD.po +538 -423
@@ -67,6 +67,15 @@ class UpdraftPlus_Admin {
|
|
67 |
|
68 |
}
|
69 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
70 |
public function include_template($path, $return_instead_of_echo = false, $extract_these = array()) {
|
71 |
if ($return_instead_of_echo) ob_start();
|
72 |
|
@@ -78,9 +87,7 @@ class UpdraftPlus_Admin {
|
|
78 |
}
|
79 |
}
|
80 |
|
81 |
-
if (!isset($template_file))
|
82 |
-
$template_file = UPDRAFTPLUS_DIR.'/templates/'.$path;
|
83 |
-
}
|
84 |
|
85 |
$template_file = apply_filters('updraftplus_template', $template_file, $path);
|
86 |
|
@@ -408,7 +415,7 @@ class UpdraftPlus_Admin {
|
|
408 |
* Sets up what is needed to allow an in-page backup to be run. Will enqueue scripts and output appropriate HTML (so, should be run when at a suitable place). Not intended for use on the UpdraftPlus settings page.
|
409 |
*
|
410 |
* @param string $title Text to use for the title of the modal
|
411 |
-
* @param callable $callback Callable function to output the contents of the updraft_inpage_prebackup element - i.e. what shows in the modal before a backup
|
412 |
*/
|
413 |
public function add_backup_scaffolding($title, $callback) {
|
414 |
$this->admin_enqueue_scripts();
|
@@ -545,7 +552,7 @@ class UpdraftPlus_Admin {
|
|
545 |
|
546 |
$args = array(
|
547 |
'id' => 'updraft_admin_node_status',
|
548 |
-
'title' => __('Current Status', 'updraftplus').' / '.__('Backup Now', 'updraftplus'),
|
549 |
'parent' => 'updraft_admin_node',
|
550 |
'href' => $option_location.'?page=updraftplus&tab=status'
|
551 |
);
|
@@ -671,6 +678,7 @@ class UpdraftPlus_Admin {
|
|
671 |
$mday_selector .= "\n\t<option value='" . $mday_index . "' $selected>" . $mday_index . '</option>';
|
672 |
}
|
673 |
$remote_storage_options_and_templates = $updraftplus->get_remote_storage_options_and_templates();
|
|
|
674 |
wp_localize_script('updraftplus-admin', 'updraftlion', array(
|
675 |
'sendonlyonwarnings' => __('Send a report only when there are warnings/errors', 'updraftplus'),
|
676 |
'wholebackup' => __('When the Email storage method is enabled, also send the backup', 'updraftplus'),
|
@@ -721,7 +729,8 @@ class UpdraftPlus_Admin {
|
|
721 |
'unknownresp' => __('Unknown server response:', 'updraftplus'),
|
722 |
'ukrespstatus' => __('Unknown server response status:', 'updraftplus'),
|
723 |
'uploaded' => __('The file was uploaded.', 'updraftplus'),
|
724 |
-
|
|
|
725 |
'cancel' => __('Cancel', 'updraftplus'),
|
726 |
'deletebutton' => __('Delete', 'updraftplus'),
|
727 |
'createbutton' => __('Create', 'updraftplus'),
|
@@ -818,6 +827,7 @@ class UpdraftPlus_Admin {
|
|
818 |
'data_consent_required' => __('You need to read and accept the UpdraftCentral Cloud data and privacy policies before you can proceed.', 'updraftplus'),
|
819 |
'close_wizard' => __('You can also close this wizard.', 'updraftplus'),
|
820 |
'control_udc_connections' => __('For future control of all your UpdraftCentral connections, go to the "Advanced Tools" tab.', 'updraftplus'),
|
|
|
821 |
));
|
822 |
}
|
823 |
|
@@ -992,12 +1002,13 @@ class UpdraftPlus_Admin {
|
|
992 |
}
|
993 |
|
994 |
public function show_admin_warning_unwritable() {
|
995 |
-
|
|
|
996 |
$this->show_admin_warning($unwritable_mess, "error");
|
997 |
}
|
998 |
|
999 |
public function show_admin_nosettings_warning() {
|
1000 |
-
$this->show_admin_warning('<strong>'.__('Welcome to UpdraftPlus!', 'updraftplus').'</strong> '.__('To make a backup, just press the Backup Now button.', 'updraftplus').' <a href="#" id="updraft-navtab-settings2">'.__('To change any of the default settings of what is backed up, to configure scheduled backups, to send your backups to remote storage (recommended), and more, go to the settings tab.', 'updraftplus').'</a>', 'updated notice is-dismissible');
|
1001 |
}
|
1002 |
|
1003 |
public function show_admin_warning_execution_time() {
|
@@ -1950,6 +1961,8 @@ class UpdraftPlus_Admin {
|
|
1950 |
if (!empty($request['extradata'])) {
|
1951 |
$options['extradata'] = $request['extradata'];
|
1952 |
}
|
|
|
|
|
1953 |
|
1954 |
do_action($event, apply_filters('updraft_backupnow_options', $options, $request));
|
1955 |
}
|
@@ -2530,16 +2543,8 @@ class UpdraftPlus_Admin {
|
|
2530 |
}
|
2531 |
|
2532 |
$tabflag = 'status';
|
2533 |
-
$
|
2534 |
-
|
2535 |
-
array(
|
2536 |
-
'status' => __('Current Status', 'updraftplus'),
|
2537 |
-
'backups' => __('Existing Backups', 'updraftplus').' ('.count($backup_history).')',
|
2538 |
-
'settings' => __('Settings', 'updraftplus'),
|
2539 |
-
'expert' => __('Advanced Tools', 'updraftplus'),
|
2540 |
-
'addons' => __('Premium / Extensions', 'updraftplus'),
|
2541 |
-
)
|
2542 |
-
);
|
2543 |
|
2544 |
if (isset($_REQUEST['tab'])) {
|
2545 |
$request_tab = sanitize_text_field($_REQUEST['tab']);
|
@@ -2573,6 +2578,16 @@ class UpdraftPlus_Admin {
|
|
2573 |
?>
|
2574 |
</div>
|
2575 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2576 |
<div id="updraft-navtab-settings-content" <?php if ('settings' != $tabflag) echo 'class="updraft-hidden"'; ?> style="<?php if ('settings' != $tabflag) echo 'display:none;'; ?>">
|
2577 |
<h2 class="updraft_settings_sectionheading"><?php _e('Backup Contents And Schedule', 'updraftplus');?></h2>
|
2578 |
<?php UpdraftPlus_Options::options_form_begin(); ?>
|
@@ -2663,7 +2678,32 @@ class UpdraftPlus_Admin {
|
|
2663 |
// settings_header() opens a div
|
2664 |
echo '</div>';
|
2665 |
}
|
2666 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2667 |
private function print_restore_in_progress_box_if_needed() {
|
2668 |
$restore_in_progress = get_site_option('updraft_restore_in_progress');
|
2669 |
if (!empty($restore_in_progress)) {
|
@@ -2725,7 +2765,7 @@ class UpdraftPlus_Admin {
|
|
2725 |
|
2726 |
$connect = htmlspecialchars(__('Connect', 'updraftplus'));
|
2727 |
|
2728 |
-
$enter_credentials_end = '<p style="margin-left: 258px;"><input id="ud_connectsubmit" type="submit" class="button-primary" value="'.$connect.'"
|
2729 |
|
2730 |
$enter_credentials_end .= '<p style="margin-left: 258px; font-size: 70%"><em><a href="https://updraftplus.com/faqs/tell-me-about-my-updraftplus-com-account/">'.$interested.'</a></em></p>';
|
2731 |
|
@@ -2786,7 +2826,7 @@ class UpdraftPlus_Admin {
|
|
2786 |
<th><?php _e('Password', 'updraftplus'); ?></th>
|
2787 |
<td>
|
2788 |
<label for="<?php echo $option_page; ?>'_options_password">
|
2789 |
-
<input id="<?php echo $option_page; ?>_options_password" type="password" size="36" name="<?php echo $option_page; ?>_options[password]" value="<?php echo htmlspecialchars($options['password']); ?>" />
|
2790 |
<br/>
|
2791 |
<a href="https://updraftplus.com/my-account/?action=lostpassword"><?php _e('Forgotten your details?', 'updraftplus'); ?></a>
|
2792 |
</label>
|
@@ -2811,7 +2851,8 @@ class UpdraftPlus_Admin {
|
|
2811 |
}
|
2812 |
|
2813 |
/**
|
2814 |
-
* Return widgetry for the 'backup now' modal
|
|
|
2815 |
*
|
2816 |
* @return String
|
2817 |
*/
|
@@ -2842,6 +2883,8 @@ class UpdraftPlus_Admin {
|
|
2842 |
$ret .= '<div id="backupnow_includefiles_moreoptions" class="updraft-hidden" style="display:none;"><em>'.__('Your saved settings also affect what is backed up - e.g. files excluded.', 'updraftplus').'</em><br>'.$this->files_selector_widgetry('backupnow_files_', false, 'sometimes').'</div></p>';
|
2843 |
|
2844 |
$ret .= '<span id="backupnow_remote_container">'.$this->backup_now_remote_message().'</span>';
|
|
|
|
|
2845 |
|
2846 |
$ret .= apply_filters('updraft_backupnow_modal_afteroptions', '', '');
|
2847 |
|
@@ -3754,7 +3797,15 @@ class UpdraftPlus_Admin {
|
|
3754 |
|
3755 |
}
|
3756 |
|
3757 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3758 |
|
3759 |
global $updraftplus;
|
3760 |
|
@@ -3766,16 +3817,18 @@ class UpdraftPlus_Admin {
|
|
3766 |
|
3767 |
if (!empty($backup['label'])) $rawbackup .= '<span class="raw-backup-info">'.$backup['label'].'</span>';
|
3768 |
|
3769 |
-
$rawbackup .= '<hr><p>';
|
3770 |
-
|
3771 |
-
$backupable_entities = $updraftplus->get_backupable_file_entities(true, true);
|
3772 |
-
|
3773 |
if (!empty($nonce)) {
|
3774 |
$jd = $updraftplus->jobdata_getarray($nonce);
|
3775 |
} else {
|
3776 |
$jd = array();
|
3777 |
}
|
3778 |
|
|
|
|
|
|
|
|
|
|
|
|
|
3779 |
$checksums = $updraftplus->which_checksums();
|
3780 |
|
3781 |
foreach ($backupable_entities as $type => $info) {
|
@@ -3807,9 +3860,9 @@ class UpdraftPlus_Admin {
|
|
3807 |
if ('none' == $serv || '' == $serv) {
|
3808 |
$add_none = true;
|
3809 |
} elseif (isset($updraftplus->backup_methods[$serv])) {
|
3810 |
-
$show_services .=
|
3811 |
} else {
|
3812 |
-
$show_services .=
|
3813 |
}
|
3814 |
}
|
3815 |
if ('' == $show_services && $add_none) $show_services .= __('None', 'updraftplus');
|
@@ -3820,8 +3873,6 @@ class UpdraftPlus_Admin {
|
|
3820 |
$rawbackup .= '</p><strong>'.__('Total backup size:', 'updraftplus').'</strong> '.UpdraftPlus_Manipulation_Functions::convert_numeric_size_to_text($total_size).'<p>';
|
3821 |
}
|
3822 |
|
3823 |
-
|
3824 |
-
|
3825 |
$rawbackup .= '</p><hr><p><pre>'.print_r($backup, true).'</p></pre>';
|
3826 |
|
3827 |
if (!empty($jd) && is_array($jd)) {
|
@@ -4171,34 +4222,7 @@ ENDHERE;
|
|
4171 |
if (isset($backup[$entity.'-size'])) $file_backups[$entity.'-size'] = $backup[$entity.'-size'];
|
4172 |
}
|
4173 |
|
4174 |
-
$
|
4175 |
-
|
4176 |
-
/*
|
4177 |
-
We need to tweak the database array here by setting each database entity to finished or encrypted if it's an encrypted archive.
|
4178 |
-
I also grab the backups blog name here ready to be used later, just in case this backup set is from another site.
|
4179 |
-
*/
|
4180 |
-
foreach ($db_backups as $key => $db_info) {
|
4181 |
-
$status = 'finished';
|
4182 |
-
$db_index = ('wp' == $key) ? 0 : $key;
|
4183 |
-
|
4184 |
-
if (isset($backup['db'][$db_index])) {
|
4185 |
-
$db_backup_name = $backup['db'][$db_index];
|
4186 |
-
|
4187 |
-
if (preg_match('/^backup_([\-0-9]{15})_(.*)_([0-9a-f]{12})-[\-a-z]+([0-9]+)?+(\.(zip|gz|gz\.crypt))?$/i', $db_backup_name, $matches)) {
|
4188 |
-
$blog_name = $matches[2];
|
4189 |
-
}
|
4190 |
-
|
4191 |
-
if (UpdraftPlus_Encryption::is_file_encrypted($db_backup_name)) $status = 'encrypted';
|
4192 |
-
|
4193 |
-
if (is_array($db_info) && isset($db_info['status'])) {
|
4194 |
-
$db_backups[$key]['status'] = $status;
|
4195 |
-
} else {
|
4196 |
-
$db_backups[$key] = $status;
|
4197 |
-
}
|
4198 |
-
} else {
|
4199 |
-
unset($db_backups[$key]);
|
4200 |
-
}
|
4201 |
-
}
|
4202 |
|
4203 |
// Next we need to build the services array using the remote storage destinations the user has selected to upload this backup set to
|
4204 |
$selected_services = array();
|
@@ -4213,8 +4237,8 @@ ENDHERE;
|
|
4213 |
$jobdata[] = 'backup_files_array';
|
4214 |
$jobdata[] = $file_backups;
|
4215 |
$jobdata[] = 'blog_name';
|
4216 |
-
$jobdata[] = $blog_name;
|
4217 |
-
$jobdata[$backup_database_key] = $db_backups;
|
4218 |
if (!empty($selected_services)) $jobdata[$service_key] = $selected_services;
|
4219 |
|
4220 |
|
@@ -4485,7 +4509,7 @@ ENDHERE;
|
|
4485 |
* @uses $GLOBALS['updraftplus_restorer']
|
4486 |
* @uses UpdraftPlus::log()
|
4487 |
*/
|
4488 |
-
|
4489 |
|
4490 |
global $updraftplus_restorer, $updraftplus;
|
4491 |
|
@@ -5165,6 +5189,7 @@ ENDHERE;
|
|
5165 |
}
|
5166 |
$corrupted_files = array();
|
5167 |
foreach ($files_to_check as $file) {
|
|
|
5168 |
if (false === ($fp = fopen($file, 'r'))) continue;
|
5169 |
if (false === ($file_data = fread($fp, 8192)));
|
5170 |
fclose($fp);
|
67 |
|
68 |
}
|
69 |
|
70 |
+
/**
|
71 |
+
* Output, or return, the results of running a template (from the 'templates' directory, unless a filter over-rides it). Templates are run with $updraftplus, $updraftplus_admin and $wpdb set.
|
72 |
+
*
|
73 |
+
* @param String $path - path to the template
|
74 |
+
* @param Boolean $return_instead_of_echo - by default, the template is echo-ed; set this to instead return it
|
75 |
+
* @param Array $extract_these - variables to inject into the template's run context
|
76 |
+
*
|
77 |
+
* @return Void|String
|
78 |
+
*/
|
79 |
public function include_template($path, $return_instead_of_echo = false, $extract_these = array()) {
|
80 |
if ($return_instead_of_echo) ob_start();
|
81 |
|
87 |
}
|
88 |
}
|
89 |
|
90 |
+
if (!isset($template_file)) $template_file = UPDRAFTPLUS_DIR.'/templates/'.$path;
|
|
|
|
|
91 |
|
92 |
$template_file = apply_filters('updraftplus_template', $template_file, $path);
|
93 |
|
415 |
* Sets up what is needed to allow an in-page backup to be run. Will enqueue scripts and output appropriate HTML (so, should be run when at a suitable place). Not intended for use on the UpdraftPlus settings page.
|
416 |
*
|
417 |
* @param string $title Text to use for the title of the modal
|
418 |
+
* @param callable $callback Callable function to output the contents of the updraft_inpage_prebackup element - i.e. what shows in the modal before a backup begins.
|
419 |
*/
|
420 |
public function add_backup_scaffolding($title, $callback) {
|
421 |
$this->admin_enqueue_scripts();
|
552 |
|
553 |
$args = array(
|
554 |
'id' => 'updraft_admin_node_status',
|
555 |
+
'title' => __('Current Status', 'updraftplus').' / '.str_ireplace('Back Up', 'Backup', __('Backup Now', 'updraftplus')),
|
556 |
'parent' => 'updraft_admin_node',
|
557 |
'href' => $option_location.'?page=updraftplus&tab=status'
|
558 |
);
|
678 |
$mday_selector .= "\n\t<option value='" . $mday_index . "' $selected>" . $mday_index . '</option>';
|
679 |
}
|
680 |
$remote_storage_options_and_templates = $updraftplus->get_remote_storage_options_and_templates();
|
681 |
+
$main_tabs = $this->get_main_tabs_array();
|
682 |
wp_localize_script('updraftplus-admin', 'updraftlion', array(
|
683 |
'sendonlyonwarnings' => __('Send a report only when there are warnings/errors', 'updraftplus'),
|
684 |
'wholebackup' => __('When the Email storage method is enabled, also send the backup', 'updraftplus'),
|
729 |
'unknownresp' => __('Unknown server response:', 'updraftplus'),
|
730 |
'ukrespstatus' => __('Unknown server response status:', 'updraftplus'),
|
731 |
'uploaded' => __('The file was uploaded.', 'updraftplus'),
|
732 |
+
// One of the translators has erroneously changed "Backup" into "Back up" (which means, "reverse" !)
|
733 |
+
'backupnow' => str_ireplace('Back Up', 'Backup', __('Backup Now', 'updraftplus')),
|
734 |
'cancel' => __('Cancel', 'updraftplus'),
|
735 |
'deletebutton' => __('Delete', 'updraftplus'),
|
736 |
'createbutton' => __('Create', 'updraftplus'),
|
827 |
'data_consent_required' => __('You need to read and accept the UpdraftCentral Cloud data and privacy policies before you can proceed.', 'updraftplus'),
|
828 |
'close_wizard' => __('You can also close this wizard.', 'updraftplus'),
|
829 |
'control_udc_connections' => __('For future control of all your UpdraftCentral connections, go to the "Advanced Tools" tab.', 'updraftplus'),
|
830 |
+
'main_tabs_keys' => array_keys($main_tabs),
|
831 |
));
|
832 |
}
|
833 |
|
1002 |
}
|
1003 |
|
1004 |
public function show_admin_warning_unwritable() {
|
1005 |
+
// One of the translators has erroneously changed "Backup" into "Back up" (which means, "reverse" !)
|
1006 |
+
$unwritable_mess = htmlspecialchars(str_ireplace('Back Up', 'Backup', __("The 'Backup Now' button is disabled as your backup directory is not writable (go to the 'Settings' tab and find the relevant option).", 'updraftplus')));
|
1007 |
$this->show_admin_warning($unwritable_mess, "error");
|
1008 |
}
|
1009 |
|
1010 |
public function show_admin_nosettings_warning() {
|
1011 |
+
$this->show_admin_warning('<strong>'.__('Welcome to UpdraftPlus!', 'updraftplus').'</strong> '.str_ireplace('Back Up', 'Backup', __('To make a backup, just press the Backup Now button.', 'updraftplus')).' <a href="#" id="updraft-navtab-settings2">'.__('To change any of the default settings of what is backed up, to configure scheduled backups, to send your backups to remote storage (recommended), and more, go to the settings tab.', 'updraftplus').'</a>', 'updated notice is-dismissible');
|
1012 |
}
|
1013 |
|
1014 |
public function show_admin_warning_execution_time() {
|
1961 |
if (!empty($request['extradata'])) {
|
1962 |
$options['extradata'] = $request['extradata'];
|
1963 |
}
|
1964 |
+
|
1965 |
+
$options['always_keep'] = empty($request['always_keep']) ? false : true;
|
1966 |
|
1967 |
do_action($event, apply_filters('updraft_backupnow_options', $options, $request));
|
1968 |
}
|
2543 |
}
|
2544 |
|
2545 |
$tabflag = 'status';
|
2546 |
+
$backup_count = count($backup_history);
|
2547 |
+
$main_tabs = $this->get_main_tabs_array($backup_count);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2548 |
|
2549 |
if (isset($_REQUEST['tab'])) {
|
2550 |
$request_tab = sanitize_text_field($_REQUEST['tab']);
|
2578 |
?>
|
2579 |
</div>
|
2580 |
|
2581 |
+
<div id="updraft-navtab-migrate-content"<?php if ('migrate' != $tabflag) echo ' class="updraft-hidden"'; ?> style="<?php if ('expert' != $tabflag) echo 'display:none;'; ?>">
|
2582 |
+
<?php
|
2583 |
+
if (has_action('updraftplus_migrate_tab_output')) {
|
2584 |
+
do_action('updraftplus_migrate_tab_output');
|
2585 |
+
} else {
|
2586 |
+
$this->include_template('wp-admin/settings/migrator-no-migrator.php');
|
2587 |
+
}
|
2588 |
+
?>
|
2589 |
+
</div>
|
2590 |
+
|
2591 |
<div id="updraft-navtab-settings-content" <?php if ('settings' != $tabflag) echo 'class="updraft-hidden"'; ?> style="<?php if ('settings' != $tabflag) echo 'display:none;'; ?>">
|
2592 |
<h2 class="updraft_settings_sectionheading"><?php _e('Backup Contents And Schedule', 'updraftplus');?></h2>
|
2593 |
<?php UpdraftPlus_Options::options_form_begin(); ?>
|
2678 |
// settings_header() opens a div
|
2679 |
echo '</div>';
|
2680 |
}
|
2681 |
+
|
2682 |
+
/**
|
2683 |
+
* Get main tabs array
|
2684 |
+
*
|
2685 |
+
* @param Integer|Boolean $backup_count No. of backup exist or false by default
|
2686 |
+
* @return Array Array which have key as a tab key and value as tab label
|
2687 |
+
*/
|
2688 |
+
private function get_main_tabs_array($backup_count = false) {
|
2689 |
+
if (false === $backup_count) {
|
2690 |
+
$backups_label_postfix = '';
|
2691 |
+
} else {
|
2692 |
+
$backups_label_postfix = ' ('.$backup_count.')';
|
2693 |
+
}
|
2694 |
+
return apply_filters(
|
2695 |
+
'updraftplus_main_tabs',
|
2696 |
+
array(
|
2697 |
+
'status' => __('Current Status', 'updraftplus'),
|
2698 |
+
'backups' => __('Existing Backups', 'updraftplus').$backups_label_postfix,
|
2699 |
+
'migrate' => __('Migrate / Clone', 'updraftplus'),
|
2700 |
+
'settings' => __('Settings', 'updraftplus'),
|
2701 |
+
'expert' => __('Advanced Tools', 'updraftplus'),
|
2702 |
+
'addons' => __('Premium / Extensions', 'updraftplus'),
|
2703 |
+
)
|
2704 |
+
);
|
2705 |
+
}
|
2706 |
+
|
2707 |
private function print_restore_in_progress_box_if_needed() {
|
2708 |
$restore_in_progress = get_site_option('updraft_restore_in_progress');
|
2709 |
if (!empty($restore_in_progress)) {
|
2765 |
|
2766 |
$connect = htmlspecialchars(__('Connect', 'updraftplus'));
|
2767 |
|
2768 |
+
$enter_credentials_end = '<p style="margin-left: 258px;"><input id="ud_connectsubmit" type="submit" class="button-primary" value="'.$connect.'" /><span class="updraftplus_spinner spinner">' . __('Processing', 'updraftplus') . '...</span></p>';
|
2769 |
|
2770 |
$enter_credentials_end .= '<p style="margin-left: 258px; font-size: 70%"><em><a href="https://updraftplus.com/faqs/tell-me-about-my-updraftplus-com-account/">'.$interested.'</a></em></p>';
|
2771 |
|
2826 |
<th><?php _e('Password', 'updraftplus'); ?></th>
|
2827 |
<td>
|
2828 |
<label for="<?php echo $option_page; ?>'_options_password">
|
2829 |
+
<input id="<?php echo $option_page; ?>_options_password" type="password" size="36" name="<?php echo $option_page; ?>_options[password]" value="<?php echo empty($options['password']) ? '' : htmlspecialchars($options['password']); ?>" />
|
2830 |
<br/>
|
2831 |
<a href="https://updraftplus.com/my-account/?action=lostpassword"><?php _e('Forgotten your details?', 'updraftplus'); ?></a>
|
2832 |
</label>
|
2851 |
}
|
2852 |
|
2853 |
/**
|
2854 |
+
* Return widgetry for the 'backup now' modal.
|
2855 |
+
* Don't optimise this method away; it's used by third-party plugins (e.g. EUM).
|
2856 |
*
|
2857 |
* @return String
|
2858 |
*/
|
2883 |
$ret .= '<div id="backupnow_includefiles_moreoptions" class="updraft-hidden" style="display:none;"><em>'.__('Your saved settings also affect what is backed up - e.g. files excluded.', 'updraftplus').'</em><br>'.$this->files_selector_widgetry('backupnow_files_', false, 'sometimes').'</div></p>';
|
2884 |
|
2885 |
$ret .= '<span id="backupnow_remote_container">'.$this->backup_now_remote_message().'</span>';
|
2886 |
+
|
2887 |
+
$ret .= '<p><input type="checkbox" id="always_keep"> <label for="always_keep">'.__("Only allow this backup to be deleted manually (i.e. keep it even if retention limits are hit).", 'updraftplus').'</label> ';
|
2888 |
|
2889 |
$ret .= apply_filters('updraft_backupnow_modal_afteroptions', '', '');
|
2890 |
|
3797 |
|
3798 |
}
|
3799 |
|
3800 |
+
/**
|
3801 |
+
* Get backup information in HTML format for a specific backup
|
3802 |
+
*
|
3803 |
+
* @param array $backup_history all backups history
|
3804 |
+
* @param string $key backup timestamp
|
3805 |
+
* @param string $nonce backup nonce
|
3806 |
+
* @return string HTML-formatted backup information
|
3807 |
+
*/
|
3808 |
+
public function raw_backup_info($backup_history, $key, $nonce) {
|
3809 |
|
3810 |
global $updraftplus;
|
3811 |
|
3817 |
|
3818 |
if (!empty($backup['label'])) $rawbackup .= '<span class="raw-backup-info">'.$backup['label'].'</span>';
|
3819 |
|
|
|
|
|
|
|
|
|
3820 |
if (!empty($nonce)) {
|
3821 |
$jd = $updraftplus->jobdata_getarray($nonce);
|
3822 |
} else {
|
3823 |
$jd = array();
|
3824 |
}
|
3825 |
|
3826 |
+
$rawbackup .= '<hr>';
|
3827 |
+
$rawbackup .= '<input type="checkbox" name="always_keep_this_backup" id="always_keep_this_backup" data-backup_key="'.$key.'" '.(empty($backup['always_keep']) ? '' : 'checked ').'><label for="always_keep_this_backup">'.__('Only allow this backup to be deleted manually (i.e. keep it even if retention limits are hit).', 'updraftplus').'</label>';
|
3828 |
+
$rawbackup .= '<hr><p>';
|
3829 |
+
|
3830 |
+
$backupable_entities = $updraftplus->get_backupable_file_entities(true, true);
|
3831 |
+
|
3832 |
$checksums = $updraftplus->which_checksums();
|
3833 |
|
3834 |
foreach ($backupable_entities as $type => $info) {
|
3860 |
if ('none' == $serv || '' == $serv) {
|
3861 |
$add_none = true;
|
3862 |
} elseif (isset($updraftplus->backup_methods[$serv])) {
|
3863 |
+
$show_services .= $show_services ? ', '.$updraftplus->backup_methods[$serv] : $updraftplus->backup_methods[$serv];
|
3864 |
} else {
|
3865 |
+
$show_services .= $show_services ? ', '.$serv : $serv;
|
3866 |
}
|
3867 |
}
|
3868 |
if ('' == $show_services && $add_none) $show_services .= __('None', 'updraftplus');
|
3873 |
$rawbackup .= '</p><strong>'.__('Total backup size:', 'updraftplus').'</strong> '.UpdraftPlus_Manipulation_Functions::convert_numeric_size_to_text($total_size).'<p>';
|
3874 |
}
|
3875 |
|
|
|
|
|
3876 |
$rawbackup .= '</p><hr><p><pre>'.print_r($backup, true).'</p></pre>';
|
3877 |
|
3878 |
if (!empty($jd) && is_array($jd)) {
|
4222 |
if (isset($backup[$entity.'-size'])) $file_backups[$entity.'-size'] = $backup[$entity.'-size'];
|
4223 |
}
|
4224 |
|
4225 |
+
$db_backup_info = $updraftplus->update_database_jobdata($db_backups, $backup);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
4226 |
|
4227 |
// Next we need to build the services array using the remote storage destinations the user has selected to upload this backup set to
|
4228 |
$selected_services = array();
|
4237 |
$jobdata[] = 'backup_files_array';
|
4238 |
$jobdata[] = $file_backups;
|
4239 |
$jobdata[] = 'blog_name';
|
4240 |
+
$jobdata[] = $db_backup_info['blog_name'];
|
4241 |
+
$jobdata[$backup_database_key] = $db_backup_info['db_backups'];
|
4242 |
if (!empty($selected_services)) $jobdata[$service_key] = $selected_services;
|
4243 |
|
4244 |
|
4509 |
* @uses $GLOBALS['updraftplus_restorer']
|
4510 |
* @uses UpdraftPlus::log()
|
4511 |
*/
|
4512 |
+
public function post_restore_clean_up($successful = true, $browser_context = true) {
|
4513 |
|
4514 |
global $updraftplus_restorer, $updraftplus;
|
4515 |
|
5189 |
}
|
5190 |
$corrupted_files = array();
|
5191 |
foreach ($files_to_check as $file) {
|
5192 |
+
if (!file_exists($file)) continue;
|
5193 |
if (false === ($fp = fopen($file, 'r'))) continue;
|
5194 |
if (false === ($file_data = fread($fp, 8192)));
|
5195 |
fclose($fp);
|
@@ -182,7 +182,7 @@ class UpdraftPlus_Backup {
|
|
182 |
if (!function_exists('get_mu_plugins')) include_once(ABSPATH.'wp-admin/includes/plugin.php');
|
183 |
$mu_plugins = get_mu_plugins();
|
184 |
if (count($mu_plugins) == 0) {
|
185 |
-
$updraftplus->log("There appear to be no mu-plugins to
|
186 |
$flag_error = false;
|
187 |
}
|
188 |
}
|
@@ -362,8 +362,8 @@ class UpdraftPlus_Backup {
|
|
362 |
|
363 |
// We need to make sure that the loop below actually runs
|
364 |
if (empty($services)) $services = array('none');
|
365 |
-
|
366 |
-
$storage_objects_and_ids = $updraftplus->
|
367 |
|
368 |
$total_instances_count = 0;
|
369 |
|
@@ -589,7 +589,7 @@ class UpdraftPlus_Backup {
|
|
589 |
if (!empty($ignored_because_imported)) {
|
590 |
$updraftplus->log("These backup set(s) were imported from a remote location, so will not be counted or pruned. Skipping: ".implode(', ', $ignored_because_imported));
|
591 |
}
|
592 |
-
|
593 |
$backupable_entities = $updraftplus->get_backupable_file_entities(true);
|
594 |
|
595 |
$database_backups_found = array();
|
@@ -627,10 +627,13 @@ class UpdraftPlus_Backup {
|
|
627 |
// $backup_to_examine is an array of file names, keyed on db/plugins/themes/uploads
|
628 |
// The new backup_history array is saved afterwards, so remember to unset the ones that are to be deleted
|
629 |
$this->log_with_db_occasionally(sprintf("Examining (for databases) backup set with group_id=$group_id, nonce=%s, datestamp=%s (%s)", $nonce, $backup_datestamp, gmdate('M d Y H:i:s', $backup_datestamp)));
|
630 |
-
|
|
|
|
|
|
|
631 |
// Auto-backups are only counted or deleted once we have reached the retain limit - before that, they are skipped
|
632 |
$is_autobackup = !empty($backup_to_examine['autobackup']);
|
633 |
-
|
634 |
$remote_sent = (!empty($backup_to_examine['service']) && ((is_array($backup_to_examine['service']) && in_array('remotesend', $backup_to_examine['service'])) || 'remotesend' === $backup_to_examine['service'])) ? true : false;
|
635 |
|
636 |
$any_deleted_via_filter_yet = false;
|
@@ -647,6 +650,16 @@ class UpdraftPlus_Backup {
|
|
647 |
continue;
|
648 |
}
|
649 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
650 |
if ($is_autobackup) {
|
651 |
if ($any_deleted_via_filter_yet) {
|
652 |
$this->log_with_db_occasionally("This backup set ($backup_datestamp) was an automatic backup, but we have previously deleted a backup due to a limit, so it will be pruned (but not counted towards numerical limits).");
|
@@ -761,6 +774,9 @@ class UpdraftPlus_Backup {
|
|
761 |
// The new backup_history array is saved afterwards, so remember to unset the ones that are to be deleted
|
762 |
$this->log_with_db_occasionally(sprintf("Examining (for files) backup set with nonce=%s, datestamp=%s (%s)", $nonce, $backup_datestamp, gmdate('M d Y H:i:s', $backup_datestamp)));
|
763 |
|
|
|
|
|
|
|
764 |
// Auto-backups are only counted or deleted once we have reached the retain limit - before that, they are skipped
|
765 |
$is_autobackup = !empty($backup_to_examine['autobackup']);
|
766 |
|
@@ -781,6 +797,16 @@ class UpdraftPlus_Backup {
|
|
781 |
continue;
|
782 |
}
|
783 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
784 |
if ($is_autobackup) {
|
785 |
if ($any_deleted_via_filter_yet) {
|
786 |
$this->log_with_db_occasionally("This backup set was an automatic backup, but we have previously deleted a backup due to a limit, so it will be pruned (but not counted towards numerical limits).");
|
@@ -1436,7 +1462,7 @@ class UpdraftPlus_Backup {
|
|
1436 |
// Now, store the results
|
1437 |
if (!is_string($created) && !is_array($created)) $updraftplus->log("$youwhat: create_zip returned an error");
|
1438 |
} else {
|
1439 |
-
$updraftplus->log("No backup of $youwhat: there was nothing found to
|
1440 |
}
|
1441 |
}
|
1442 |
|
@@ -1550,7 +1576,7 @@ class UpdraftPlus_Backup {
|
|
1550 |
|
1551 |
if ('wp' == $this->whichdb) {
|
1552 |
$this->wpdb_obj = $wpdb;
|
1553 |
-
// The table prefix after being filtered - i.e. what filters what we'll actually
|
1554 |
$this->table_prefix = $updraftplus->get_table_prefix(true);
|
1555 |
// The unfiltered table prefix - i.e. the real prefix that things are relative to
|
1556 |
$this->table_prefix_raw = $updraftplus->get_table_prefix(false);
|
182 |
if (!function_exists('get_mu_plugins')) include_once(ABSPATH.'wp-admin/includes/plugin.php');
|
183 |
$mu_plugins = get_mu_plugins();
|
184 |
if (count($mu_plugins) == 0) {
|
185 |
+
$updraftplus->log("There appear to be no mu-plugins to backup. Will not raise an error.");
|
186 |
$flag_error = false;
|
187 |
}
|
188 |
}
|
362 |
|
363 |
// We need to make sure that the loop below actually runs
|
364 |
if (empty($services)) $services = array('none');
|
365 |
+
|
366 |
+
$storage_objects_and_ids = $updraftplus->get_enabled_storage_objects_and_ids($services);
|
367 |
|
368 |
$total_instances_count = 0;
|
369 |
|
589 |
if (!empty($ignored_because_imported)) {
|
590 |
$updraftplus->log("These backup set(s) were imported from a remote location, so will not be counted or pruned. Skipping: ".implode(', ', $ignored_because_imported));
|
591 |
}
|
592 |
+
|
593 |
$backupable_entities = $updraftplus->get_backupable_file_entities(true);
|
594 |
|
595 |
$database_backups_found = array();
|
627 |
// $backup_to_examine is an array of file names, keyed on db/plugins/themes/uploads
|
628 |
// The new backup_history array is saved afterwards, so remember to unset the ones that are to be deleted
|
629 |
$this->log_with_db_occasionally(sprintf("Examining (for databases) backup set with group_id=$group_id, nonce=%s, datestamp=%s (%s)", $nonce, $backup_datestamp, gmdate('M d Y H:i:s', $backup_datestamp)));
|
630 |
+
|
631 |
+
// "Always Keep" Backups should be counted in the count of how many have been retained for purposes of the "how many to retain" count... but if that count is already matched, it's not a problem
|
632 |
+
$is_always_keep = !empty($backup_to_examine['always_keep']);
|
633 |
+
|
634 |
// Auto-backups are only counted or deleted once we have reached the retain limit - before that, they are skipped
|
635 |
$is_autobackup = !empty($backup_to_examine['autobackup']);
|
636 |
+
|
637 |
$remote_sent = (!empty($backup_to_examine['service']) && ((is_array($backup_to_examine['service']) && in_array('remotesend', $backup_to_examine['service'])) || 'remotesend' === $backup_to_examine['service'])) ? true : false;
|
638 |
|
639 |
$any_deleted_via_filter_yet = false;
|
650 |
continue;
|
651 |
}
|
652 |
|
653 |
+
if ($is_always_keep) {
|
654 |
+
if ($database_backups_found[$entity] < $updraft_retain) {
|
655 |
+
$this->log_with_db_occasionally("This backup set ($backup_datestamp) was an 'Always Keep' backup, and we have not yet reached any retain limits, so it should be counted in the count of how many have been retained for purposes of the 'how many to retain' count. It will not be pruned. Skipping.");
|
656 |
+
$database_backups_found[$key]++;
|
657 |
+
} else {
|
658 |
+
$this->log_with_db_occasionally("This backup set ($backup_datestamp) was an 'Always Keep' backup, so it will not be pruned. Skipping.");
|
659 |
+
}
|
660 |
+
continue;
|
661 |
+
}
|
662 |
+
|
663 |
if ($is_autobackup) {
|
664 |
if ($any_deleted_via_filter_yet) {
|
665 |
$this->log_with_db_occasionally("This backup set ($backup_datestamp) was an automatic backup, but we have previously deleted a backup due to a limit, so it will be pruned (but not counted towards numerical limits).");
|
774 |
// The new backup_history array is saved afterwards, so remember to unset the ones that are to be deleted
|
775 |
$this->log_with_db_occasionally(sprintf("Examining (for files) backup set with nonce=%s, datestamp=%s (%s)", $nonce, $backup_datestamp, gmdate('M d Y H:i:s', $backup_datestamp)));
|
776 |
|
777 |
+
// "Always Keep" Backups should be counted in the count of how many have been retained for purposes of the "how many to retain" count... but if that count is already matched, it's not a problem
|
778 |
+
$is_always_keep = !empty($backup_to_examine['always_keep']);
|
779 |
+
|
780 |
// Auto-backups are only counted or deleted once we have reached the retain limit - before that, they are skipped
|
781 |
$is_autobackup = !empty($backup_to_examine['autobackup']);
|
782 |
|
797 |
continue;
|
798 |
}
|
799 |
|
800 |
+
if ($is_always_keep) {
|
801 |
+
if ($file_entities_backups_found[$entity] < $updraft_retain) {
|
802 |
+
$this->log_with_db_occasionally("This backup set ($backup_datestamp) was an 'Always Keep' backup, and we have not yet reached any retain limits, so it should be counted in the count of how many have been retained for purposes of the 'how many to retain' count. It will not be pruned. Skipping.");
|
803 |
+
$file_entities_backups_found[$entity]++;
|
804 |
+
} else {
|
805 |
+
$this->log_with_db_occasionally("This backup set ($backup_datestamp) was an 'Always Keep' backup, so it will not be pruned. Skipping.");
|
806 |
+
}
|
807 |
+
continue;
|
808 |
+
}
|
809 |
+
|
810 |
if ($is_autobackup) {
|
811 |
if ($any_deleted_via_filter_yet) {
|
812 |
$this->log_with_db_occasionally("This backup set was an automatic backup, but we have previously deleted a backup due to a limit, so it will be pruned (but not counted towards numerical limits).");
|
1462 |
// Now, store the results
|
1463 |
if (!is_string($created) && !is_array($created)) $updraftplus->log("$youwhat: create_zip returned an error");
|
1464 |
} else {
|
1465 |
+
$updraftplus->log("No backup of $youwhat: there was nothing found to backup");
|
1466 |
}
|
1467 |
}
|
1468 |
|
1576 |
|
1577 |
if ('wp' == $this->whichdb) {
|
1578 |
$this->wpdb_obj = $wpdb;
|
1579 |
+
// The table prefix after being filtered - i.e. what filters what we'll actually backup
|
1580 |
$this->table_prefix = $updraftplus->get_table_prefix(true);
|
1581 |
// The unfiltered table prefix - i.e. the real prefix that things are relative to
|
1582 |
$this->table_prefix_raw = $updraftplus->get_table_prefix(false);
|
@@ -30,6 +30,7 @@ class UpdraftPlus_UpdraftCentral_Main {
|
|
30 |
'comments' => 'UpdraftCentral_Comments_Commands',
|
31 |
'analytics' => 'UpdraftCentral_Analytics_Commands',
|
32 |
'plugin' => 'UpdraftCentral_Plugin_Commands',
|
|
|
33 |
'posts' => 'UpdraftCentral_Posts_Commands'
|
34 |
));
|
35 |
|
30 |
'comments' => 'UpdraftCentral_Comments_Commands',
|
31 |
'analytics' => 'UpdraftCentral_Analytics_Commands',
|
32 |
'plugin' => 'UpdraftCentral_Plugin_Commands',
|
33 |
+
'theme' => 'UpdraftCentral_Theme_Commands',
|
34 |
'posts' => 'UpdraftCentral_Posts_Commands'
|
35 |
));
|
36 |
|
@@ -50,4 +50,27 @@ abstract class UpdraftCentral_Commands {
|
|
50 |
'rpcerror'
|
51 |
);
|
52 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
53 |
}
|
50 |
'rpcerror'
|
51 |
);
|
52 |
}
|
53 |
+
|
54 |
+
/**
|
55 |
+
* Checks whether a backup and a security credentials is required for the given request
|
56 |
+
*
|
57 |
+
* @param array $dir The directory location to check
|
58 |
+
* @return array
|
59 |
+
*/
|
60 |
+
final protected function _get_backup_credentials_settings($dir) {
|
61 |
+
// Do we need to ask the user for filesystem credentials? when installing and/or deleting items in the given directory
|
62 |
+
$filesystem_method = get_filesystem_method(array(), $dir);
|
63 |
+
ob_start();
|
64 |
+
$filesystem_credentials_are_stored = request_filesystem_credentials(site_url());
|
65 |
+
ob_end_clean();
|
66 |
+
$request_filesystem_credentials = ('direct' != $filesystem_method && !$filesystem_credentials_are_stored);
|
67 |
+
|
68 |
+
// Do we need to execute a backup process before installing/managing items
|
69 |
+
$automatic_backups = (class_exists('UpdraftPlus_Options') && class_exists('UpdraftPlus_Addon_Autobackup') && UpdraftPlus_Options::get_updraft_option('updraft_autobackup_default', true)) ? true : false;
|
70 |
+
|
71 |
+
return array(
|
72 |
+
'request_filesystem_credentials' => $request_filesystem_credentials,
|
73 |
+
'automatic_backups' => $automatic_backups
|
74 |
+
);
|
75 |
+
}
|
76 |
}
|
@@ -8,11 +8,46 @@ if (!defined('UPDRAFTPLUS_DIR')) die('No access.');
|
|
8 |
*/
|
9 |
class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
10 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
11 |
/**
|
12 |
* Constructor
|
13 |
*/
|
14 |
public function __construct() {
|
15 |
-
$this->_admin_include('plugin.php', 'file.php', 'template.php', 'class-wp-upgrader.php', 'plugin-install.php');
|
16 |
}
|
17 |
|
18 |
/**
|
@@ -24,13 +59,168 @@ class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
|
24 |
public function is_plugin_installed($query) {
|
25 |
|
26 |
if (!isset($query['plugin']))
|
27 |
-
return $this->
|
28 |
|
29 |
|
30 |
-
$result = $this->
|
31 |
return $this->_response($result);
|
32 |
}
|
33 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
34 |
/**
|
35 |
* Activates the plugin
|
36 |
*
|
@@ -39,24 +229,35 @@ class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
|
39 |
*/
|
40 |
public function activate_plugin($query) {
|
41 |
|
42 |
-
|
43 |
-
|
|
|
|
|
44 |
|
45 |
-
|
46 |
-
|
|
|
|
|
47 |
|
|
|
|
|
48 |
|
49 |
-
|
50 |
-
|
51 |
-
|
|
|
|
|
|
|
|
|
52 |
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
|
|
60 |
}
|
61 |
|
62 |
return $this->_response($result);
|
@@ -70,81 +271,109 @@ class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
|
70 |
*/
|
71 |
public function install_activate_plugin($query) {
|
72 |
|
73 |
-
|
74 |
-
|
|
|
|
|
75 |
|
76 |
-
|
77 |
-
return $this->_response(array('error' => true, 'message' => 'plugin_slug_required', 'values' => array()));
|
78 |
|
79 |
-
|
80 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
81 |
|
|
|
|
|
82 |
|
83 |
-
|
84 |
-
|
85 |
-
|
86 |
-
|
87 |
-
|
88 |
-
|
89 |
-
|
90 |
-
|
|
|
|
|
|
|
91 |
}
|
92 |
|
93 |
-
$
|
94 |
-
|
95 |
-
|
96 |
-
|
97 |
-
|
98 |
-
|
99 |
-
|
100 |
-
|
101 |
-
|
102 |
-
|
103 |
-
|
104 |
-
|
105 |
-
|
106 |
-
|
107 |
-
|
108 |
-
|
109 |
-
|
110 |
-
|
111 |
-
if (is_wp_error($api)) {
|
112 |
-
$result = array('error' => true, 'message' => 'generic_response_error', 'values' => array($api->get_error_message()));
|
113 |
-
} else {
|
114 |
-
$info = $this->get_plugin_info($query['plugin']);
|
115 |
-
$installed = $info['installed'];
|
116 |
|
117 |
-
|
118 |
-
|
119 |
-
|
|
|
120 |
|
121 |
-
|
122 |
-
|
123 |
|
124 |
-
|
125 |
-
|
126 |
-
}
|
127 |
|
128 |
-
if (
|
129 |
-
$result = array('
|
130 |
} else {
|
131 |
-
|
132 |
-
|
133 |
-
|
134 |
-
|
|
|
135 |
|
136 |
-
|
137 |
-
|
138 |
|
139 |
-
|
140 |
-
|
141 |
-
|
142 |
-
|
143 |
-
|
144 |
-
|
145 |
-
|
146 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
147 |
}
|
|
|
|
|
148 |
}
|
149 |
|
150 |
return $this->_response($result);
|
@@ -157,13 +386,17 @@ class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
|
157 |
* @param array $plugin The name of the plugin to pull the information from
|
158 |
* @return array Contains the plugin information
|
159 |
*/
|
160 |
-
private function
|
161 |
|
162 |
$info = array(
|
163 |
'active' => false,
|
164 |
'installed' => false
|
165 |
);
|
166 |
|
|
|
|
|
|
|
|
|
167 |
// Gets all plugins available.
|
168 |
$get_plugins = get_plugins();
|
169 |
|
@@ -181,4 +414,86 @@ class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
|
181 |
|
182 |
return $info;
|
183 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
184 |
}
|
8 |
*/
|
9 |
class UpdraftCentral_Plugin_Commands extends UpdraftCentral_Commands {
|
10 |
|
11 |
+
private $switched = false;
|
12 |
+
|
13 |
+
/**
|
14 |
+
* Function that gets called before every action
|
15 |
+
*
|
16 |
+
* @param string $command a string that corresponds to UDC command to call a certain method for this class.
|
17 |
+
* @param array $data an array of data post or get fields
|
18 |
+
* @param array $extra_info extrainfo use in the udrpc_action, e.g. user_id
|
19 |
+
*
|
20 |
+
* link to udrpc_action main function in class UpdraftPlus_UpdraftCentral_Listener
|
21 |
+
*/
|
22 |
+
public function _pre_action($command, $data, $extra_info) {
|
23 |
+
// Here we assign the current blog_id to a variable $blog_id
|
24 |
+
$blog_id = get_current_blog_id();
|
25 |
+
if (!empty($data['site_id'])) $blog_id = $data['site_id'];
|
26 |
+
|
27 |
+
if (function_exists('switch_to_blog') && is_multisite() && $blog_id) {
|
28 |
+
$this->switched = switch_to_blog($blog_id);
|
29 |
+
}
|
30 |
+
}
|
31 |
+
|
32 |
+
/**
|
33 |
+
* Function that gets called after every action
|
34 |
+
*
|
35 |
+
* @param string $command a string that corresponds to UDC command to call a certain method for this class.
|
36 |
+
* @param array $data an array of data post or get fields
|
37 |
+
* @param array $extra_info extrainfo use in the udrpc_action, e.g. user_id
|
38 |
+
*
|
39 |
+
* link to udrpc_action main function in class UpdraftPlus_UpdraftCentral_Listener
|
40 |
+
*/
|
41 |
+
public function _post_action($command, $data, $extra_info) {
|
42 |
+
// Here, we're restoring to the current (default) blog before we switched
|
43 |
+
if ($this->switched) restore_current_blog();
|
44 |
+
}
|
45 |
+
|
46 |
/**
|
47 |
* Constructor
|
48 |
*/
|
49 |
public function __construct() {
|
50 |
+
$this->_admin_include('plugin.php', 'file.php', 'template.php', 'class-wp-upgrader.php', 'plugin-install.php', 'update.php');
|
51 |
}
|
52 |
|
53 |
/**
|
59 |
public function is_plugin_installed($query) {
|
60 |
|
61 |
if (!isset($query['plugin']))
|
62 |
+
return $this->_generic_error_response('plugin_name_required');
|
63 |
|
64 |
|
65 |
+
$result = $this->_get_plugin_info($query['plugin']);
|
66 |
return $this->_response($result);
|
67 |
}
|
68 |
|
69 |
+
/**
|
70 |
+
* Applies currently requested action for plugin processing
|
71 |
+
*
|
72 |
+
* @param string $action The action to apply (e.g. activate or install)
|
73 |
+
* @param array $query Parameter array containing information for the currently requested action
|
74 |
+
*
|
75 |
+
* @return array
|
76 |
+
*/
|
77 |
+
private function _apply_plugin_action($action, $query) {
|
78 |
+
|
79 |
+
$result = array();
|
80 |
+
switch ($action) {
|
81 |
+
case 'activate':
|
82 |
+
case 'network_activate':
|
83 |
+
$info = $this->_get_plugin_info($query['plugin']);
|
84 |
+
if ($info['installed']) {
|
85 |
+
if (is_multisite() && 'network_activate' === $action) {
|
86 |
+
$activate = activate_plugin($info['plugin_path'], '', true);
|
87 |
+
} else {
|
88 |
+
$activate = activate_plugin($info['plugin_path']);
|
89 |
+
}
|
90 |
+
|
91 |
+
if (is_wp_error($activate)) {
|
92 |
+
$result = $this->_generic_error_response('generic_response_error', array($activate->get_error_message()));
|
93 |
+
} else {
|
94 |
+
$result = array('activated' => true);
|
95 |
+
}
|
96 |
+
} else {
|
97 |
+
$result = $this->_generic_error_response('plugin_not_installed', array($query['plugin']));
|
98 |
+
}
|
99 |
+
break;
|
100 |
+
case 'deactivate':
|
101 |
+
case 'network_deactivate':
|
102 |
+
$info = $this->_get_plugin_info($query['plugin']);
|
103 |
+
if ($info['active']) {
|
104 |
+
if (is_multisite() && 'network_deactivate' === $action) {
|
105 |
+
deactivate_plugins($info['plugin_path'], false, true);
|
106 |
+
} else {
|
107 |
+
deactivate_plugins($info['plugin_path']);
|
108 |
+
}
|
109 |
+
|
110 |
+
if (!is_plugin_active($info['plugin_path'])) {
|
111 |
+
$result = array('deactivated' => true);
|
112 |
+
} else {
|
113 |
+
$result = $this->_generic_error_response('deactivate_plugin_failed', array($query['plugin']));
|
114 |
+
}
|
115 |
+
} else {
|
116 |
+
$result = $this->_generic_error_response('not_active', array($query['plugin']));
|
117 |
+
}
|
118 |
+
break;
|
119 |
+
case 'install':
|
120 |
+
$api = plugins_api('plugin_information', array(
|
121 |
+
'slug' => $query['slug'],
|
122 |
+
'fields' => array(
|
123 |
+
'short_description' => false,
|
124 |
+
'sections' => false,
|
125 |
+
'requires' => false,
|
126 |
+
'rating' => false,
|
127 |
+
'ratings' => false,
|
128 |
+
'downloaded' => false,
|
129 |
+
'last_updated' => false,
|
130 |
+
'added' => false,
|
131 |
+
'tags' => false,
|
132 |
+
'compatibility' => false,
|
133 |
+
'homepage' => false,
|
134 |
+
'donate_link' => false,
|
135 |
+
)
|
136 |
+
));
|
137 |
+
|
138 |
+
if (is_wp_error($api)) {
|
139 |
+
$result = $this->_generic_error_response('generic_response_error', array($api->get_error_message()));
|
140 |
+
} else {
|
141 |
+
$info = $this->_get_plugin_info($query['plugin']);
|
142 |
+
$installed = $info['installed'];
|
143 |
+
|
144 |
+
if (!$installed) {
|
145 |
+
// WP < 3.7
|
146 |
+
if (!class_exists('Automatic_Upgrader_Skin')) include_once(UPDRAFTPLUS_DIR.'/central/classes/class-automatic-upgrader-skin.php');
|
147 |
+
|
148 |
+
$skin = new Automatic_Upgrader_Skin();
|
149 |
+
$upgrader = new Plugin_Upgrader($skin);
|
150 |
+
|
151 |
+
$download_link = $api->download_link;
|
152 |
+
$installed = $upgrader->install($download_link);
|
153 |
+
}
|
154 |
+
|
155 |
+
if (!$installed) {
|
156 |
+
$result = $this->_generic_error_response('plugin_install_failed', array($query['plugin']));
|
157 |
+
} else {
|
158 |
+
$result = array('installed' => true);
|
159 |
+
}
|
160 |
+
}
|
161 |
+
break;
|
162 |
+
}
|
163 |
+
|
164 |
+
return $result;
|
165 |
+
}
|
166 |
+
|
167 |
+
/**
|
168 |
+
* Preloads the submitted credentials to the global $_POST variable
|
169 |
+
*
|
170 |
+
* @param array $query Parameter array containing information for the currently requested action
|
171 |
+
*/
|
172 |
+
private function _preload_credentials($query) {
|
173 |
+
if (!empty($query) && isset($query['filesystem_credentials'])) {
|
174 |
+
parse_str($query['filesystem_credentials'], $filesystem_credentials);
|
175 |
+
if (is_array($filesystem_credentials)) {
|
176 |
+
foreach ($filesystem_credentials as $key => $value) {
|
177 |
+
// Put them into $_POST, which is where request_filesystem_credentials() checks for them.
|
178 |
+
$_POST[$key] = $value;
|
179 |
+
}
|
180 |
+
}
|
181 |
+
}
|
182 |
+
}
|
183 |
+
|
184 |
+
/**
|
185 |
+
* Checks whether we have the required fields submitted and the user has
|
186 |
+
* the capabilities to execute the requested action
|
187 |
+
*
|
188 |
+
* @param array $query The submitted information
|
189 |
+
* @param array $fields The required fields to check
|
190 |
+
* @param array $capabilities The capabilities to check and validate
|
191 |
+
*
|
192 |
+
* @return array|string
|
193 |
+
*/
|
194 |
+
private function _validate_fields_and_capabilities($query, $fields, $capabilities) {
|
195 |
+
|
196 |
+
$error = '';
|
197 |
+
if (!empty($fields)) {
|
198 |
+
for ($i=0; $i<count($fields); $i++) {
|
199 |
+
$field = $fields[$i];
|
200 |
+
|
201 |
+
if (!isset($query[$field])) {
|
202 |
+
if ('keyword' === $field) {
|
203 |
+
$error = $this->_generic_error_response('keyword_required');
|
204 |
+
} else {
|
205 |
+
$error = $this->_generic_error_response('plugin_'.$query[$field].'_required');
|
206 |
+
}
|
207 |
+
break;
|
208 |
+
}
|
209 |
+
}
|
210 |
+
}
|
211 |
+
|
212 |
+
if (empty($error) && !empty($capabilities)) {
|
213 |
+
for ($i=0; $i<count($capabilities); $i++) {
|
214 |
+
if (!current_user_can($capabilities[$i])) {
|
215 |
+
$error = $this->_generic_error_response('plugin_insufficient_permission');
|
216 |
+
break;
|
217 |
+
}
|
218 |
+
}
|
219 |
+
}
|
220 |
+
|
221 |
+
return $error;
|
222 |
+
}
|
223 |
+
|
224 |
/**
|
225 |
* Activates the plugin
|
226 |
*
|
229 |
*/
|
230 |
public function activate_plugin($query) {
|
231 |
|
232 |
+
$error = $this->_validate_fields_and_capabilities($query, array('plugin'), array('activate_plugins'));
|
233 |
+
if (!empty($error)) {
|
234 |
+
return $error;
|
235 |
+
}
|
236 |
|
237 |
+
$result = $this->_apply_plugin_action('activate', $query);
|
238 |
+
if (empty($result['activated'])) {
|
239 |
+
return $result;
|
240 |
+
}
|
241 |
|
242 |
+
return $this->_response($result);
|
243 |
+
}
|
244 |
|
245 |
+
/**
|
246 |
+
* Deactivates the plugin
|
247 |
+
*
|
248 |
+
* @param array $query Parameter array containing the name of the plugin to deactivate
|
249 |
+
* @return array Contains the result of the current process
|
250 |
+
*/
|
251 |
+
public function deactivate_plugin($query) {
|
252 |
|
253 |
+
$error = $this->_validate_fields_and_capabilities($query, array('plugin'), array('activate_plugins'));
|
254 |
+
if (!empty($error)) {
|
255 |
+
return $error;
|
256 |
+
}
|
257 |
+
|
258 |
+
$result = $this->_apply_plugin_action('deactivate', $query);
|
259 |
+
if (empty($result['deactivated'])) {
|
260 |
+
return $result;
|
261 |
}
|
262 |
|
263 |
return $this->_response($result);
|
271 |
*/
|
272 |
public function install_activate_plugin($query) {
|
273 |
|
274 |
+
$error = $this->_validate_fields_and_capabilities($query, array('plugin', 'slug'), array('install_plugins', 'activate_plugins'));
|
275 |
+
if (!empty($error)) {
|
276 |
+
return $error;
|
277 |
+
}
|
278 |
|
279 |
+
$this->_preload_credentials($query);
|
|
|
280 |
|
281 |
+
$result = $this->_apply_plugin_action('install', $query);
|
282 |
+
if (!empty($result['installed']) && $result['installed']) {
|
283 |
+
$result = $this->_apply_plugin_action('activate', $query);
|
284 |
+
if (empty($result['activated'])) {
|
285 |
+
return $result;
|
286 |
+
}
|
287 |
+
} else {
|
288 |
+
return $result;
|
289 |
+
}
|
290 |
|
291 |
+
return $this->_response($result);
|
292 |
+
}
|
293 |
|
294 |
+
/**
|
295 |
+
* Download, install the plugin
|
296 |
+
*
|
297 |
+
* @param array $query Parameter array containing the filesystem credentials entered by the user along with the plugin name and slug
|
298 |
+
* @return array Contains the result of the current process
|
299 |
+
*/
|
300 |
+
public function install_plugin($query) {
|
301 |
+
|
302 |
+
$error = $this->_validate_fields_and_capabilities($query, array('plugin', 'slug'), array('install_plugins'));
|
303 |
+
if (!empty($error)) {
|
304 |
+
return $error;
|
305 |
}
|
306 |
|
307 |
+
$this->_preload_credentials($query);
|
308 |
+
|
309 |
+
$result = $this->_apply_plugin_action('install', $query);
|
310 |
+
if (empty($result['installed'])) {
|
311 |
+
return $result;
|
312 |
+
}
|
313 |
+
|
314 |
+
return $this->_response($result);
|
315 |
+
}
|
316 |
+
|
317 |
+
/**
|
318 |
+
* Uninstall/delete the plugin
|
319 |
+
*
|
320 |
+
* @param array $query Parameter array containing the filesystem credentials entered by the user along with the plugin name and slug
|
321 |
+
* @return array Contains the result of the current process
|
322 |
+
*/
|
323 |
+
public function delete_plugin($query) {
|
|
|
|
|
|
|
|
|
|
|
|
|
324 |
|
325 |
+
$error = $this->_validate_fields_and_capabilities($query, array('plugin'), array('delete_plugins'));
|
326 |
+
if (!empty($error)) {
|
327 |
+
return $error;
|
328 |
+
}
|
329 |
|
330 |
+
$this->_preload_credentials($query);
|
331 |
+
$info = $this->_get_plugin_info($query['plugin']);
|
332 |
|
333 |
+
if ($info['installed']) {
|
334 |
+
$deleted = delete_plugins(array($info['plugin_path']));
|
|
|
335 |
|
336 |
+
if ($deleted) {
|
337 |
+
$result = array('deleted' => true);
|
338 |
} else {
|
339 |
+
$result = $this->_generic_error_response('delete_plugin_failed', array($query['plugin']));
|
340 |
+
}
|
341 |
+
} else {
|
342 |
+
$result = $this->_generic_error_response('plugin_not_installed', array($query['plugin']));
|
343 |
+
}
|
344 |
|
345 |
+
return $this->_response($result);
|
346 |
+
}
|
347 |
|
348 |
+
/**
|
349 |
+
* Updates/upgrade the plugin
|
350 |
+
*
|
351 |
+
* @param array $query Parameter array containing the filesystem credentials entered by the user along with the plugin name and slug
|
352 |
+
* @return array Contains the result of the current process
|
353 |
+
*/
|
354 |
+
public function update_plugin($query) {
|
355 |
+
|
356 |
+
$error = $this->_validate_fields_and_capabilities($query, array('plugin', 'slug'), array('update_plugins'));
|
357 |
+
if (!empty($error)) {
|
358 |
+
return $error;
|
359 |
+
}
|
360 |
+
|
361 |
+
$this->_preload_credentials($query);
|
362 |
+
$info = $this->_get_plugin_info($query['plugin']);
|
363 |
+
|
364 |
+
// Make sure that we still have the plugin installed before running
|
365 |
+
// the update process
|
366 |
+
if ($info['installed']) {
|
367 |
+
// Load the updates command class if not existed
|
368 |
+
if (!class_exists('UpdraftCentral_Updates_Commands')) include_once('updates.php');
|
369 |
+
$update_command = new UpdraftCentral_Updates_Commands($this->rc);
|
370 |
+
|
371 |
+
$result = $update_command->update_plugin($info['plugin_path'], $query['slug']);
|
372 |
+
if (!empty($result['error'])) {
|
373 |
+
$result['values'] = array($query['plugin']);
|
374 |
}
|
375 |
+
} else {
|
376 |
+
$result = $this->_generic_error_response('plugin_not_installed', array($query['plugin']));
|
377 |
}
|
378 |
|
379 |
return $this->_response($result);
|
386 |
* @param array $plugin The name of the plugin to pull the information from
|
387 |
* @return array Contains the plugin information
|
388 |
*/
|
389 |
+
private function _get_plugin_info($plugin) {
|
390 |
|
391 |
$info = array(
|
392 |
'active' => false,
|
393 |
'installed' => false
|
394 |
);
|
395 |
|
396 |
+
// Clear plugin cache so that newly installed/downloaded plugins
|
397 |
+
// gets reflected when calling "get_plugins"
|
398 |
+
wp_clean_plugins_cache();
|
399 |
+
|
400 |
// Gets all plugins available.
|
401 |
$get_plugins = get_plugins();
|
402 |
|
414 |
|
415 |
return $info;
|
416 |
}
|
417 |
+
|
418 |
+
/**
|
419 |
+
* Loads all available plugins with additional attributes and settings needed by UpdraftCentral
|
420 |
+
*
|
421 |
+
* @param array $query Parameter array Any available parameters needed for this action
|
422 |
+
* @return array Contains the result of the current process
|
423 |
+
*/
|
424 |
+
public function load_plugins($query) {
|
425 |
+
|
426 |
+
$error = $this->_validate_fields_and_capabilities($query, array(), array('install_plugins', 'activate_plugins'));
|
427 |
+
if (!empty($error)) {
|
428 |
+
return $error;
|
429 |
+
}
|
430 |
+
|
431 |
+
$website = get_bloginfo('name');
|
432 |
+
$results = array();
|
433 |
+
|
434 |
+
// Load the updates command class if not existed
|
435 |
+
if (!class_exists('UpdraftCentral_Updates_Commands')) include_once('updates.php');
|
436 |
+
$updates = new UpdraftCentral_Updates_Commands($this->rc);
|
437 |
+
|
438 |
+
// Get plugins for update
|
439 |
+
$plugin_updates = $updates->get_item_updates('plugins');
|
440 |
+
|
441 |
+
// Get all plugins
|
442 |
+
$plugins = get_plugins();
|
443 |
+
|
444 |
+
foreach ($plugins as $key => $value) {
|
445 |
+
$slug = basename($key, '.php');
|
446 |
+
|
447 |
+
$plugin = new stdClass();
|
448 |
+
$plugin->name = $value['Name'];
|
449 |
+
$plugin->description = $value['Description'];
|
450 |
+
$plugin->slug = $slug;
|
451 |
+
$plugin->version = $value['Version'];
|
452 |
+
$plugin->author = $value['Author'];
|
453 |
+
$plugin->status = is_plugin_active($key) ? 'active' : 'inactive';
|
454 |
+
$plugin->website = $website;
|
455 |
+
|
456 |
+
if (!empty($plugin_updates[$key])) {
|
457 |
+
$update_info = $plugin_updates[$key];
|
458 |
+
|
459 |
+
if (version_compare($update_info->Version, $update_info->update->new_version, '<')) {
|
460 |
+
if (!empty($update_info->update->new_version)) $plugin->latest_version = $update_info->update->new_version;
|
461 |
+
if (!empty($update_info->update->package)) $plugin->download_link = $update_info->update->package;
|
462 |
+
if (!empty($update_info->update->sections)) $plugin->sections = $update_info->update->sections;
|
463 |
+
}
|
464 |
+
}
|
465 |
+
|
466 |
+
if (empty($plugin->short_description) && !empty($plugin->description)) {
|
467 |
+
// Only pull the first sentence as short description, it should be enough rather than displaying
|
468 |
+
// an empty description or a full blown one which the user can access anytime if they press on
|
469 |
+
// the view details link in UpdraftCentral.
|
470 |
+
$temp = explode('.', $plugin->description);
|
471 |
+
$short_description = $temp[0];
|
472 |
+
|
473 |
+
// Adding the second sentence wouldn't hurt, in case the first sentence is too short.
|
474 |
+
if (isset($temp[1])) $short_description .= '.'.$temp[1];
|
475 |
+
|
476 |
+
$plugin->short_description = $short_description.'.';
|
477 |
+
}
|
478 |
+
|
479 |
+
$results[] = $plugin;
|
480 |
+
}
|
481 |
+
|
482 |
+
$result = array(
|
483 |
+
'plugins' => $results
|
484 |
+
);
|
485 |
+
|
486 |
+
$result = array_merge($result, $this->_get_backup_credentials_settings(WP_PLUGIN_DIR));
|
487 |
+
return $this->_response($result);
|
488 |
+
}
|
489 |
+
|
490 |
+
/**
|
491 |
+
* Gets the backup and security credentials settings for this website
|
492 |
+
*
|
493 |
+
* @param array $query Parameter array Any available parameters needed for this action
|
494 |
+
* @return array Contains the result of the current process
|
495 |
+
*/
|
496 |
+
public function get_plugin_requirements() {
|
497 |
+
return $this->_response($this->_get_backup_credentials_settings(WP_PLUGIN_DIR));
|
498 |
+
}
|
499 |
}
|
@@ -55,29 +55,51 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
55 |
*/
|
56 |
public function get_requested_posts($params) {
|
57 |
|
|
|
|
|
58 |
// check paged parameter; if empty set to 1
|
59 |
-
$paged =
|
60 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
61 |
|
62 |
// Using default function get_posts to fetch all posts object from passed parameters
|
63 |
// Count all fetch posts objects
|
64 |
// get total fetch posts and divide to number of posts for pagination
|
65 |
-
$query = new WP_Query($
|
66 |
$result = $query->posts;
|
67 |
|
68 |
-
$count_posts =
|
69 |
$page_count = 0;
|
70 |
$postdata = array();
|
71 |
|
72 |
-
if ($count_posts
|
73 |
-
|
74 |
-
$
|
|
|
|
|
75 |
}
|
76 |
|
|
|
|
|
|
|
|
|
|
|
|
|
77 |
if (empty($result)) {
|
78 |
$error_data = array(
|
79 |
'count' => $page_count,
|
80 |
-
'paged' => $paged
|
|
|
81 |
);
|
82 |
return $this->_generic_error_response('post_not_found_with_keyword', $error_data);
|
83 |
} else {
|
@@ -101,27 +123,22 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
101 |
$data->category_name = $cat_array;
|
102 |
$data->post_title = $post->post_title;
|
103 |
$data->post_status = $post->post_status;
|
|
|
104 |
$postdata[] = $data;
|
105 |
}
|
106 |
|
107 |
-
$cat_id = $params['category'][0];
|
108 |
-
if (0 != $cat_id) {
|
109 |
-
$count_category_posts = get_category($cat_id);
|
110 |
-
if (empty($params['numberposts'])) return $this->_generic_error_response('numberposts_parameter_missing', $params);
|
111 |
-
$page_count = absint($count_category_posts->category_count / $params['numberposts']);
|
112 |
-
}
|
113 |
-
|
114 |
$response = array(
|
115 |
'posts' => $postdata,
|
116 |
'count' => $page_count,
|
117 |
'paged' => $paged,
|
118 |
'categories' => $this->get_requested_categories(array('parent' => 0, 'return_object' => true)),
|
119 |
-
'message' => "found_posts_count"
|
|
|
|
|
120 |
);
|
121 |
}
|
122 |
|
123 |
return $this->_response($response);
|
124 |
-
|
125 |
}
|
126 |
|
127 |
/**
|
@@ -297,7 +314,7 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
297 |
// Check if result is false
|
298 |
if (is_wp_error($post_id)) {
|
299 |
$error_data = array(
|
300 |
-
'message' => 'Error inserting post'
|
301 |
);
|
302 |
|
303 |
return $this->_generic_error_response('post_insert_error', $error_data);
|
@@ -359,7 +376,7 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
359 |
// Check if response is false
|
360 |
if (is_wp_error($response)) {
|
361 |
$error_data = array(
|
362 |
-
'message' => 'Error updating post'
|
363 |
);
|
364 |
|
365 |
return $this->_generic_error_response('post_update_error', $error_data);
|
@@ -418,7 +435,7 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
418 |
// Check if response if false
|
419 |
if (is_wp_error($response)) {
|
420 |
$error_data = array(
|
421 |
-
'message' => 'Error deleting post'
|
422 |
);
|
423 |
return $this->_generic_error_response('post_delete_error', $error_data);
|
424 |
}
|
@@ -481,7 +498,7 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
481 |
|
482 |
if (is_wp_error($response)) {
|
483 |
$error_data = array(
|
484 |
-
'message' => 'Error inserting category'
|
485 |
);
|
486 |
return $this->_generic_error_response('category_insert_error', $error_data);
|
487 |
}
|
@@ -539,7 +556,7 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
539 |
// Check if response is false
|
540 |
if (is_wp_error($response)) {
|
541 |
$error_data = array(
|
542 |
-
'message' => 'Error updating category'
|
543 |
);
|
544 |
return $this->_generic_error_response('category_update_error', $error_data);
|
545 |
}
|
@@ -587,7 +604,7 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
587 |
|
588 |
if (is_wp_error($response)) {
|
589 |
$error_data = array(
|
590 |
-
'message' => 'Error deleting category'
|
591 |
);
|
592 |
return $this->_generic_error_response('user_no_permission_to_delete_category', $error_data);
|
593 |
}
|
@@ -612,19 +629,40 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
612 |
*/
|
613 |
public function find_post_by_title($params) {
|
614 |
|
|
|
|
|
615 |
// Check if keyword is empty or null
|
616 |
if (empty($params['s'])) {
|
617 |
return $this->_generic_error_response('search_generated_no_result', array());
|
618 |
}
|
619 |
|
620 |
// Set an array with post_type to search only post
|
621 |
-
$query_string = array(
|
|
|
|
|
|
|
|
|
|
|
622 |
$query = new WP_Query($query_string);
|
623 |
-
$published_posts = absint($query->post_count / 10);
|
624 |
$postdata = array();
|
625 |
|
626 |
-
$
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
627 |
|
|
|
628 |
if ($query->have_posts()) {
|
629 |
|
630 |
foreach ($query->posts as $post) {
|
@@ -655,14 +693,16 @@ class UpdraftCentral_Posts_Commands extends UpdraftCentral_Commands {
|
|
655 |
'categories' => $this->get_requested_categories(array('parent' => 0, 'return_object' => true)),
|
656 |
'posts' => $postdata,
|
657 |
'n' => $arr,
|
658 |
-
'count' => $
|
659 |
-
'paged' =>
|
660 |
-
'message' => "found_post"
|
|
|
661 |
);
|
662 |
} else {
|
663 |
$error_data = array(
|
664 |
-
'count' => $
|
665 |
-
'paged' =>
|
|
|
666 |
);
|
667 |
return $this->_generic_error_response('post_not_found_with_keyword', $error_data);
|
668 |
}
|
55 |
*/
|
56 |
public function get_requested_posts($params) {
|
57 |
|
58 |
+
if (empty($params['numberposts'])) return $this->_generic_error_response('numberposts_parameter_missing', $params);
|
59 |
+
|
60 |
// check paged parameter; if empty set to 1
|
61 |
+
$paged = !empty($params['paged']) ? (int) $params['paged'] : 1;
|
62 |
+
|
63 |
+
$args = array(
|
64 |
+
'posts_per_page' => $params['numberposts'],
|
65 |
+
'paged' => $paged,
|
66 |
+
'post_type' => 'post',
|
67 |
+
'post_status' => !empty($params['post_status']) ? $params['post_status'] : 'any'
|
68 |
+
);
|
69 |
+
|
70 |
+
if (!empty($params['category'][0])) {
|
71 |
+
$term_id = (int) $params['category'][0];
|
72 |
+
$args['category__in'] = array($term_id);
|
73 |
+
}
|
74 |
|
75 |
// Using default function get_posts to fetch all posts object from passed parameters
|
76 |
// Count all fetch posts objects
|
77 |
// get total fetch posts and divide to number of posts for pagination
|
78 |
+
$query = new WP_Query($args);
|
79 |
$result = $query->posts;
|
80 |
|
81 |
+
$count_posts = $query->found_posts;
|
82 |
$page_count = 0;
|
83 |
$postdata = array();
|
84 |
|
85 |
+
if ((int) $count_posts > 0) {
|
86 |
+
$page_count = absint((int) $count_posts / (int) $params['numberposts']);
|
87 |
+
$remainder = absint((int) $count_posts % (int) $params['numberposts']);
|
88 |
+
|
89 |
+
$page_count = ($remainder > 0) ? ++$page_count : $page_count;
|
90 |
}
|
91 |
|
92 |
+
$info = array(
|
93 |
+
'page' => $paged,
|
94 |
+
'pages' => $page_count,
|
95 |
+
'results' => $count_posts
|
96 |
+
);
|
97 |
+
|
98 |
if (empty($result)) {
|
99 |
$error_data = array(
|
100 |
'count' => $page_count,
|
101 |
+
'paged' => $paged,
|
102 |
+
'info' => $info
|
103 |
);
|
104 |
return $this->_generic_error_response('post_not_found_with_keyword', $error_data);
|
105 |
} else {
|
123 |
$data->category_name = $cat_array;
|
124 |
$data->post_title = $post->post_title;
|
125 |
$data->post_status = $post->post_status;
|
126 |
+
$data->ID = $post->ID;
|
127 |
$postdata[] = $data;
|
128 |
}
|
129 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
130 |
$response = array(
|
131 |
'posts' => $postdata,
|
132 |
'count' => $page_count,
|
133 |
'paged' => $paged,
|
134 |
'categories' => $this->get_requested_categories(array('parent' => 0, 'return_object' => true)),
|
135 |
+
'message' => "found_posts_count",
|
136 |
+
'params' => $params,
|
137 |
+
'info' => $info
|
138 |
);
|
139 |
}
|
140 |
|
141 |
return $this->_response($response);
|
|
|
142 |
}
|
143 |
|
144 |
/**
|
314 |
// Check if result is false
|
315 |
if (is_wp_error($post_id)) {
|
316 |
$error_data = array(
|
317 |
+
'message' => __('Error inserting post')
|
318 |
);
|
319 |
|
320 |
return $this->_generic_error_response('post_insert_error', $error_data);
|
376 |
// Check if response is false
|
377 |
if (is_wp_error($response)) {
|
378 |
$error_data = array(
|
379 |
+
'message' => __('Error updating post')
|
380 |
);
|
381 |
|
382 |
return $this->_generic_error_response('post_update_error', $error_data);
|
435 |
// Check if response if false
|
436 |
if (is_wp_error($response)) {
|
437 |
$error_data = array(
|
438 |
+
'message' => __('Error deleting post')
|
439 |
);
|
440 |
return $this->_generic_error_response('post_delete_error', $error_data);
|
441 |
}
|
498 |
|
499 |
if (is_wp_error($response)) {
|
500 |
$error_data = array(
|
501 |
+
'message' => __('Error inserting category')
|
502 |
);
|
503 |
return $this->_generic_error_response('category_insert_error', $error_data);
|
504 |
}
|
556 |
// Check if response is false
|
557 |
if (is_wp_error($response)) {
|
558 |
$error_data = array(
|
559 |
+
'message' => __('Error updating category')
|
560 |
);
|
561 |
return $this->_generic_error_response('category_update_error', $error_data);
|
562 |
}
|
604 |
|
605 |
if (is_wp_error($response)) {
|
606 |
$error_data = array(
|
607 |
+
'message' => __('Error deleting category')
|
608 |
);
|
609 |
return $this->_generic_error_response('user_no_permission_to_delete_category', $error_data);
|
610 |
}
|
629 |
*/
|
630 |
public function find_post_by_title($params) {
|
631 |
|
632 |
+
$paged = !empty($params['paged']) ? (int) $params['paged'] : 1;
|
633 |
+
|
634 |
// Check if keyword is empty or null
|
635 |
if (empty($params['s'])) {
|
636 |
return $this->_generic_error_response('search_generated_no_result', array());
|
637 |
}
|
638 |
|
639 |
// Set an array with post_type to search only post
|
640 |
+
$query_string = array(
|
641 |
+
's' => $params['s'],
|
642 |
+
'post_type' => 'post',
|
643 |
+
'posts_per_page' => $params['numberposts'],
|
644 |
+
'paged' => $paged
|
645 |
+
);
|
646 |
$query = new WP_Query($query_string);
|
|
|
647 |
$postdata = array();
|
648 |
|
649 |
+
$count_posts = $query->found_posts;
|
650 |
+
if ((int) $count_posts > 0) {
|
651 |
+
if (empty($params['numberposts'])) return $this->_generic_error_response('numberposts_parameter_missing', $params);
|
652 |
+
|
653 |
+
$page_count = absint((int) $count_posts / (int) $params['numberposts']);
|
654 |
+
$remainder = absint((int) $count_posts % (int) $params['numberposts']);
|
655 |
+
|
656 |
+
$page_count = ($remainder > 0) ? ++$page_count : $page_count;
|
657 |
+
}
|
658 |
+
|
659 |
+
$info = array(
|
660 |
+
'page' => $paged,
|
661 |
+
'pages' => $page_count,
|
662 |
+
'results' => $count_posts
|
663 |
+
);
|
664 |
|
665 |
+
$response = array();
|
666 |
if ($query->have_posts()) {
|
667 |
|
668 |
foreach ($query->posts as $post) {
|
693 |
'categories' => $this->get_requested_categories(array('parent' => 0, 'return_object' => true)),
|
694 |
'posts' => $postdata,
|
695 |
'n' => $arr,
|
696 |
+
'count' => $count_posts,
|
697 |
+
'paged' => $paged,
|
698 |
+
'message' => "found_post",
|
699 |
+
'info' => $info
|
700 |
);
|
701 |
} else {
|
702 |
$error_data = array(
|
703 |
+
'count' => $count_posts,
|
704 |
+
'paged' => $paged,
|
705 |
+
'info' => $info
|
706 |
);
|
707 |
return $this->_generic_error_response('post_not_found_with_keyword', $error_data);
|
708 |
}
|
@@ -0,0 +1,503 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|