Version Description
- Enhancement: Removed the requirement for the user to select "Yes" from the drop down in order to initiate an update. This new version does not change the appearance of the upload form. Instead, it automatically creates a backup and performs an upgrade if the supplied plugin or theme already exists.
- Enhancement: If a zip backup file cannot be created, the old directory is renamed to a new name in order to still keep a backup.
- Enhancement: Updated the code to use a better way of integrating the upgrade logic. This approach should greatly reduce the potential for conflicts with other code or site configurations.
- Enhancement: The backup details now are found in the same format as the rest of the upgrade messages.
Download this release
Release Info
Developer | chrisjean |
Plugin | Easy Theme and Plugin Upgrades |
Version | 2.0.0 |
Comparing to | |
See all releases |
Code changes from version 1.0.6 to 2.0.0
- admin.php +85 -0
- custom-plugin-upgrader.php +225 -0
- custom-theme-upgrader.php +206 -0
- history.txt +5 -0
- index.php +2 -0
- init.php +4 -5
- maintenance-page.html +0 -46
- modify-installer.php +0 -274
- readme.txt +32 -9
- show-maintenance-message.php +0 -23
admin.php
ADDED
@@ -0,0 +1,85 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
|
4 |
+
final class CAJ_ETPU_Admin {
|
5 |
+
public static function init() {
|
6 |
+
add_action( 'load-update.php', array( __CLASS__, 'set_hooks' ) );
|
7 |
+
}
|
8 |
+
|
9 |
+
public static function set_hooks() {
|
10 |
+
include_once( ABSPATH . 'wp-admin/includes/class-wp-upgrader.php' );
|
11 |
+
|
12 |
+
add_action( 'admin_action_upload-theme', array( __CLASS__, 'update_theme' ) );
|
13 |
+
add_action( 'admin_action_upload-plugin', array( __CLASS__, 'update_plugin' ) );
|
14 |
+
}
|
15 |
+
|
16 |
+
public static function update_theme() {
|
17 |
+
if ( ! current_user_can( 'upload_themes' ) ) {
|
18 |
+
wp_die( esc_html__( 'Sorry, you are not allowed to install themes on this site.' ) );
|
19 |
+
}
|
20 |
+
|
21 |
+
check_admin_referer( 'theme-upload' );
|
22 |
+
|
23 |
+
$file_upload = new File_Upload_Upgrader( 'themezip', 'package' );
|
24 |
+
|
25 |
+
wp_enqueue_script( 'customize-loader' );
|
26 |
+
|
27 |
+
$title = __( 'Upload Theme' );
|
28 |
+
$parent_file = 'themes.php';
|
29 |
+
$submenu_file = 'theme-install.php';
|
30 |
+
|
31 |
+
require_once( ABSPATH . 'wp-admin/admin-header.php' );
|
32 |
+
|
33 |
+
$title = sprintf( __( 'Installing Theme from uploaded file: %s' ), esc_html( basename( $file_upload->filename ) ) );
|
34 |
+
$nonce = 'theme-upload';
|
35 |
+
$url = add_query_arg( array( 'package' => $file_upload->id ), 'update.php?action=upload-theme' );
|
36 |
+
$type = 'upload'; // Install plugin type, From Web or an Upload.
|
37 |
+
|
38 |
+
require_once( dirname( __FILE__ ) . '/custom-theme-upgrader.php' );
|
39 |
+
|
40 |
+
$upgrader = new CAJ_ETPU_Theme_Upgrader( new Theme_Installer_Skin( compact( 'type', 'title', 'nonce', 'url' ) ) );
|
41 |
+
$result = $upgrader->install( $file_upload->package );
|
42 |
+
|
43 |
+
if ( $result || is_wp_error( $result ) ) {
|
44 |
+
$file_upload->cleanup();
|
45 |
+
}
|
46 |
+
|
47 |
+
include( ABSPATH . 'wp-admin/admin-footer.php' );
|
48 |
+
|
49 |
+
exit();
|
50 |
+
}
|
51 |
+
|
52 |
+
public static function update_plugin() {
|
53 |
+
if ( ! current_user_can( 'upload_plugins' ) ) {
|
54 |
+
wp_die( esc_html__( 'Sorry, you are not allowed to install plugins on this site.' ) );
|
55 |
+
}
|
56 |
+
|
57 |
+
check_admin_referer( 'plugin-upload' );
|
58 |
+
|
59 |
+
$file_upload = new File_Upload_Upgrader( 'pluginzip', 'package' );
|
60 |
+
|
61 |
+
$title = __( 'Upload Plugin' );
|
62 |
+
$parent_file = 'plugins.php';
|
63 |
+
$submenu_file = 'plugin-install.php';
|
64 |
+
require_once( ABSPATH . 'wp-admin/admin-header.php' );
|
65 |
+
|
66 |
+
$title = sprintf( __( 'Installing Plugin from uploaded file: %s' ), esc_html( basename( $file_upload->filename ) ) );
|
67 |
+
$nonce = 'plugin-upload';
|
68 |
+
$url = add_query_arg( array( 'package' => $file_upload->id ), 'update.php?action=upload-plugin' );
|
69 |
+
$type = 'upload'; // Install plugin type, From Web or an Upload.
|
70 |
+
|
71 |
+
require_once( dirname( __FILE__ ) . '/custom-plugin-upgrader.php' );
|
72 |
+
|
73 |
+
$upgrader = new CAJ_ETPU_Plugin_Upgrader( new Plugin_Installer_Skin( compact( 'type', 'title', 'nonce', 'url' ) ) );
|
74 |
+
$result = $upgrader->install( $file_upload->package );
|
75 |
+
|
76 |
+
if ( $result || is_wp_error( $result ) ) {
|
77 |
+
$file_upload->cleanup();
|
78 |
+
}
|
79 |
+
|
80 |
+
include( ABSPATH . 'wp-admin/admin-footer.php' );
|
81 |
+
|
82 |
+
exit();
|
83 |
+
}
|
84 |
+
}
|
85 |
+
CAJ_ETPU_Admin::init();
|
custom-plugin-upgrader.php
ADDED
@@ -0,0 +1,225 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class CAJ_ETPU_Plugin_Upgrader extends Plugin_Upgrader {
|
4 |
+
public function install_package( $args = array() ) {
|
5 |
+
global $wp_filesystem;
|
6 |
+
|
7 |
+
error_reporting( E_ALL );
|
8 |
+
ini_set( 'display_errors', 1 );
|
9 |
+
|
10 |
+
if ( empty( $args['source'] ) || empty( $args['destination'] ) ) {
|
11 |
+
// Only run if the arguments we need are present.
|
12 |
+
return parent::install_package( $args );
|
13 |
+
}
|
14 |
+
|
15 |
+
$source_files = array_keys( $wp_filesystem->dirlist( $args['source'] ) );
|
16 |
+
$remote_destination = $wp_filesystem->find_folder( $args['destination'] );
|
17 |
+
|
18 |
+
// Locate which directory to copy to the new folder, This is based on the actual folder holding the files.
|
19 |
+
if ( 1 === count( $source_files ) && $wp_filesystem->is_dir( trailingslashit( $args['source'] ) . $source_files[0] . '/' ) ) { // Only one folder? Then we want its contents.
|
20 |
+
$destination = trailingslashit( $remote_destination ) . trailingslashit( $source_files[0] );
|
21 |
+
} elseif ( 0 === count( $source_files ) ) {
|
22 |
+
// Looks like an empty zip, we'll let the default code handle this.
|
23 |
+
return parent::install_package( $args );
|
24 |
+
} else { // It's only a single file, the upgrader will use the folder name of this file as the destination folder. Folder name is based on zip filename.
|
25 |
+
$destination = trailingslashit( $remote_destination ) . trailingslashit( basename( $args['source'] ) );
|
26 |
+
}
|
27 |
+
|
28 |
+
if ( is_dir( $destination ) ) {
|
29 |
+
// This is an upgrade, clear the destination.
|
30 |
+
$args['clear_destination'] = true;
|
31 |
+
|
32 |
+
// Switch template strings to use upgrade terminology rather than install terminology.
|
33 |
+
$this->upgrade_strings();
|
34 |
+
|
35 |
+
// Replace default remove_old string to make the messages more meaningful.
|
36 |
+
$this->strings['installing_package'] = __( 'Upgrading the plugin…', 'easy-theme-and-plugin-upgrades' );
|
37 |
+
$this->strings['remove_old'] = __( 'Backing up the old version of the plugin…', 'easy-theme-and-plugin-upgrades' );
|
38 |
+
}
|
39 |
+
|
40 |
+
return parent::install_package( $args );
|
41 |
+
}
|
42 |
+
|
43 |
+
private function caj_get_plugin_data( $directory ) {
|
44 |
+
$files = glob( $directory . '*.php' );
|
45 |
+
|
46 |
+
if ( $files ) {
|
47 |
+
foreach ( $files as $file ) {
|
48 |
+
$info = get_plugin_data( $file, false, false );
|
49 |
+
|
50 |
+
if ( ! empty( $info['Name'] ) ) {
|
51 |
+
$data = array(
|
52 |
+
'name' => $info['Name'],
|
53 |
+
'version' => $info['Version'],
|
54 |
+
);
|
55 |
+
|
56 |
+
return $data;
|
57 |
+
}
|
58 |
+
}
|
59 |
+
}
|
60 |
+
|
61 |
+
return false;
|
62 |
+
}
|
63 |
+
|
64 |
+
public function clear_destination( $destination ) {
|
65 |
+
global $wp_filesystem;
|
66 |
+
|
67 |
+
if ( ! is_dir( $destination ) ) {
|
68 |
+
// This is an installation not an upgrade.
|
69 |
+
return parent::clear_destination( $destination );
|
70 |
+
}
|
71 |
+
|
72 |
+
$data = $this->caj_get_plugin_data( $destination );
|
73 |
+
|
74 |
+
if ( false === $data ) {
|
75 |
+
// The existing directory is not a valid plugin, skip backup.
|
76 |
+
return parent::clear_destination( $destination );
|
77 |
+
}
|
78 |
+
|
79 |
+
$backup_url = $this->caj_create_backup( $destination );
|
80 |
+
|
81 |
+
if ( ! is_wp_error( $backup_url ) ) {
|
82 |
+
/* translators: 1: plugin zip URL */
|
83 |
+
$this->skin->feedback( sprintf( __( 'A backup zip file of the old plugin version can be downloaded <a href="%1$s">here</a>.', 'easy-theme-and-plugin-upgrades' ), $backup_url ) );
|
84 |
+
|
85 |
+
// Restore default strings and display the original remove_old message.
|
86 |
+
$this->upgrade_strings();
|
87 |
+
$this->skin->feedback( 'remove_old' );
|
88 |
+
|
89 |
+
return parent::clear_destination( $destination );
|
90 |
+
}
|
91 |
+
|
92 |
+
$this->skin->error( $backup_url );
|
93 |
+
$this->skin->feedback( __( 'Moving the old version of the plugin to a new directory…', 'easy-theme-and-plugin-upgrades' ) );
|
94 |
+
|
95 |
+
$new_name = basename( $destination ) . "-{$data['version']}";
|
96 |
+
$directory = dirname( $destination );
|
97 |
+
|
98 |
+
for ( $x = 0; $x < 20; $x++ ) {
|
99 |
+
$test_name = $new_name . '-' . $this->get_random_characters( 10, 20 );
|
100 |
+
|
101 |
+
if ( ! is_dir( "$directory/$test_name" ) ) {
|
102 |
+
$new_name = $test_name;
|
103 |
+
break;
|
104 |
+
}
|
105 |
+
}
|
106 |
+
|
107 |
+
if ( is_dir( "$directory/$new_name" ) ) {
|
108 |
+
// We gave it our best effort. Time to give up on the idea of having a backup.
|
109 |
+
$this->skin->error( __( 'Unable to find a new directory name to move the old version of the plugin to. No backup will be created.', 'easy-theme-and-plugin-upgrades' ) );
|
110 |
+
} else {
|
111 |
+
$result = $wp_filesystem->move( $destination, "$directory/$new_name" );
|
112 |
+
|
113 |
+
if ( $result ) {
|
114 |
+
/* translators: 1: new plugin directory name */
|
115 |
+
$this->skin->feedback( sprintf( __( 'Moved the old version of the plugin to a new plugin directory named %1$s. This directory should be backed up and removed from the site.', 'easy-theme-and-plugin-upgrades' ), "<code>$new_name</code>" ) );
|
116 |
+
} else {
|
117 |
+
$this->skin->error( __( 'Unable to move the old version of the plugin to a new directory. No backup will be created.', 'easy-theme-and-plugin-upgrades' ) );
|
118 |
+
}
|
119 |
+
}
|
120 |
+
|
121 |
+
// Restore default strings and display the original remove_old message.
|
122 |
+
$this->upgrade_strings();
|
123 |
+
$this->skin->feedback( 'remove_old' );
|
124 |
+
|
125 |
+
return parent::clear_destination( $destination );
|
126 |
+
}
|
127 |
+
|
128 |
+
private function caj_create_backup( $directory ) {
|
129 |
+
require_once( ABSPATH . 'wp-admin/includes/file.php' );
|
130 |
+
|
131 |
+
$wp_upload_dir = wp_upload_dir();
|
132 |
+
|
133 |
+
$zip_path = $wp_upload_dir['path'];
|
134 |
+
$zip_url = $wp_upload_dir['url'];
|
135 |
+
|
136 |
+
if ( ! is_dir( $zip_path ) ) {
|
137 |
+
return new WP_Error( 'caj-etpu-cannot-backup-no-destination-path', __( 'A plugin backup can not be created since a destination path for the backup file could not be found.', 'easy-theme-and-plugin-upgrades' ) );
|
138 |
+
}
|
139 |
+
|
140 |
+
$data = $this->caj_get_plugin_data( $directory );
|
141 |
+
|
142 |
+
$rand_string = $this->get_random_characters( 10, 20 );
|
143 |
+
$zip_file = basename( $directory ) . "-{$data['version']}-$rand_string.zip";
|
144 |
+
|
145 |
+
// Reduce the chance that a timeout will occur while creating the zip file.
|
146 |
+
@set_time_limit( 600 );
|
147 |
+
|
148 |
+
// Attempt to increase memory limits.
|
149 |
+
$this->set_minimum_memory_limit( '256M' );
|
150 |
+
|
151 |
+
$zip_path .= "/$zip_file";
|
152 |
+
$zip_url .= "/$zip_file";
|
153 |
+
|
154 |
+
require_once( ABSPATH . 'wp-admin/includes/class-pclzip.php' );
|
155 |
+
|
156 |
+
$archive = new PclZip( $zip_path );
|
157 |
+
|
158 |
+
$zip_result = $archive->create( $directory, PCLZIP_OPT_REMOVE_PATH, dirname( $directory ) );
|
159 |
+
|
160 |
+
if ( 0 === $zip_result ) {
|
161 |
+
/* translators: 1: zip error details */
|
162 |
+
return new WP_Error( 'caj-etpu-cannot-backup-zip-failed', sprintf( __( 'A plugin backup can not be created as creation of the zip file failed with the following error: %1$s', 'easy-theme-and-plugin-upgrades' ), $archive->errorInfo( true ) ) );
|
163 |
+
}
|
164 |
+
|
165 |
+
$attachment = array(
|
166 |
+
'post_mime_type' => 'application/zip',
|
167 |
+
'guid' => $zip_url,
|
168 |
+
/* translators: 1: plugin name, 2: plugin version */
|
169 |
+
'post_title' => sprintf( __( 'Plugin Backup - %1$s - %2$s', 'easy-theme-and-plugin-upgrades' ), $data['name'], $data['version'] ),
|
170 |
+
'post_content' => '',
|
171 |
+
);
|
172 |
+
|
173 |
+
$id = wp_insert_attachment( $attachment, $zip_path );
|
174 |
+
|
175 |
+
if ( ! is_wp_error( $id ) ) {
|
176 |
+
wp_update_attachment_metadata( $id, wp_generate_attachment_metadata( $id, $zip_path ) );
|
177 |
+
}
|
178 |
+
|
179 |
+
return $zip_url;
|
180 |
+
}
|
181 |
+
|
182 |
+
private function get_random_characters( $min_length, $max_length ) {
|
183 |
+
$characters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
|
184 |
+
$rand_string = '';
|
185 |
+
$length = rand( $min_length, $max_length );
|
186 |
+
|
187 |
+
for ( $count = 0; $count < $length; $count++ ) {
|
188 |
+
$rand_string .= $characters[ rand( 0, strlen( $characters ) - 1 ) ];
|
189 |
+
}
|
190 |
+
|
191 |
+
return $rand_string;
|
192 |
+
}
|
193 |
+
|
194 |
+
function set_minimum_memory_limit( $new_memory_limit ) {
|
195 |
+
$memory_limit = @ini_get( 'memory_limit' );
|
196 |
+
|
197 |
+
if ( $memory_limit > -1 ) {
|
198 |
+
$unit = strtolower( substr( $memory_limit, -1 ) );
|
199 |
+
$new_unit = strtolower( substr( $new_memory_limit, -1 ) );
|
200 |
+
|
201 |
+
$memory_limit = intval( $memory_limit );
|
202 |
+
$new_memory_limit = intval( $new_memory_limit );
|
203 |
+
|
204 |
+
if ( 'm' == $unit ) {
|
205 |
+
$memory_limit *= 1048576;
|
206 |
+
} elseif ( 'g' == $unit ) {
|
207 |
+
$memory_limit *= 1073741824;
|
208 |
+
} elseif ( 'k' == $unit ) {
|
209 |
+
$memory_limit *= 1024;
|
210 |
+
}
|
211 |
+
|
212 |
+
if ( 'm' == $new_unit ) {
|
213 |
+
$new_memory_limit *= 1048576;
|
214 |
+
} else if ( 'g' == $new_unit ) {
|
215 |
+
$new_memory_limit *= 1073741824;
|
216 |
+
} else if ( 'k' == $new_unit ) {
|
217 |
+
$new_memory_limit *= 1024;
|
218 |
+
}
|
219 |
+
|
220 |
+
if ( (int) $memory_limit < (int) $new_memory_limit ) {
|
221 |
+
@ini_set( 'memory_limit', $new_memory_limit );
|
222 |
+
}
|
223 |
+
}
|
224 |
+
}
|
225 |
+
}
|
custom-theme-upgrader.php
ADDED
@@ -0,0 +1,206 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class CAJ_ETPU_Theme_Upgrader extends Theme_Upgrader {
|
4 |
+
public function install_package( $args = array() ) {
|
5 |
+
global $wp_filesystem;
|
6 |
+
|
7 |
+
error_reporting( E_ALL );
|
8 |
+
ini_set( 'display_errors', 1 );
|
9 |
+
|
10 |
+
if ( empty( $args['source'] ) || empty( $args['destination'] ) ) {
|
11 |
+
// Only run if the arguments we need are present.
|
12 |
+
return parent::install_package( $args );
|
13 |
+
}
|
14 |
+
|
15 |
+
$source_files = array_keys( $wp_filesystem->dirlist( $args['source'] ) );
|
16 |
+
$remote_destination = $wp_filesystem->find_folder( $args['destination'] );
|
17 |
+
|
18 |
+
// Locate which directory to copy to the new folder, This is based on the actual folder holding the files.
|
19 |
+
if ( 1 === count( $source_files ) && $wp_filesystem->is_dir( trailingslashit( $args['source'] ) . $source_files[0] . '/' ) ) { // Only one folder? Then we want its contents.
|
20 |
+
$destination = trailingslashit( $remote_destination ) . trailingslashit( $source_files[0] );
|
21 |
+
} elseif ( 0 === count( $source_files ) ) {
|
22 |
+
// Looks like an empty zip, we'll let the default code handle this.
|
23 |
+
return parent::install_package( $args );
|
24 |
+
} else { // It's only a single file, the upgrader will use the folder name of this file as the destination folder. Folder name is based on zip filename.
|
25 |
+
$destination = trailingslashit( $remote_destination ) . trailingslashit( basename( $args['source'] ) );
|
26 |
+
}
|
27 |
+
|
28 |
+
if ( is_dir( $destination ) && file_exists( "$destination/style.css" ) ) {
|
29 |
+
// This is an upgrade, clear the destination.
|
30 |
+
$args['clear_destination'] = true;
|
31 |
+
|
32 |
+
// Switch template strings to use upgrade terminology rather than install terminology.
|
33 |
+
$this->upgrade_strings();
|
34 |
+
|
35 |
+
// Replace default remove_old string to make the messages more meaningful.
|
36 |
+
$this->strings['installing_package'] = __( 'Upgrading the theme…', 'easy-theme-and-plugin-upgrades' );
|
37 |
+
$this->strings['remove_old'] = __( 'Backing up the old version of the theme…', 'easy-theme-and-plugin-upgrades' );
|
38 |
+
}
|
39 |
+
|
40 |
+
return parent::install_package( $args );
|
41 |
+
}
|
42 |
+
|
43 |
+
public function clear_destination( $destination ) {
|
44 |
+
global $wp_filesystem;
|
45 |
+
|
46 |
+
if ( ! is_dir( $destination ) || ! file_exists( "$destination/style.css" ) ) {
|
47 |
+
// This is an installation not an upgrade.
|
48 |
+
return parent::clear_destination( $destination );
|
49 |
+
}
|
50 |
+
|
51 |
+
$backup_url = $this->create_backup( $destination );
|
52 |
+
|
53 |
+
if ( ! is_wp_error( $backup_url ) ) {
|
54 |
+
/* translators: 1: theme zip URL */
|
55 |
+
$this->skin->feedback( sprintf( __( 'A backup zip file of the old theme version can be downloaded <a href="%1$s">here</a>.', 'easy-theme-and-plugin-upgrades' ), $backup_url ) );
|
56 |
+
|
57 |
+
// Restore default strings and display the original remove_old message.
|
58 |
+
$this->upgrade_strings();
|
59 |
+
$this->skin->feedback( 'remove_old' );
|
60 |
+
|
61 |
+
return parent::clear_destination( $destination );
|
62 |
+
}
|
63 |
+
|
64 |
+
$this->skin->error( $backup_url );
|
65 |
+
$this->skin->feedback( __( 'Moving the old version of the theme to a new directory…', 'easy-theme-and-plugin-upgrades' ) );
|
66 |
+
|
67 |
+
$headers = array(
|
68 |
+
'version' => 'Version',
|
69 |
+
);
|
70 |
+
$data = get_file_data( "$destination/style.css", $headers );
|
71 |
+
|
72 |
+
$new_name = basename( $destination ) . "-{$data['version']}";
|
73 |
+
$directory = dirname( $destination );
|
74 |
+
|
75 |
+
for ( $x = 0; $x < 20; $x++ ) {
|
76 |
+
$test_name = $new_name . '-' . $this->get_random_characters( 10, 20 );
|
77 |
+
|
78 |
+
if ( ! is_dir( "$directory/$test_name" ) ) {
|
79 |
+
$new_name = $test_name;
|
80 |
+
break;
|
81 |
+
}
|
82 |
+
}
|
83 |
+
|
84 |
+
if ( is_dir( "$directory/$new_name" ) ) {
|
85 |
+
// We gave it our best effort. Time to give up on the idea of having a backup.
|
86 |
+
$this->skin->error( __( 'Unable to find a new directory name to move the old version of the theme to. No backup will be created.', 'easy-theme-and-plugin-upgrades' ) );
|
87 |
+
} else {
|
88 |
+
$result = $wp_filesystem->move( $destination, "$directory/$new_name" );
|
89 |
+
|
90 |
+
if ( $result ) {
|
91 |
+
/* translators: 1: new theme directory name */
|
92 |
+
$this->skin->feedback( sprintf( __( 'Moved the old version of the theme to a new theme directory named %1$s. This directory should be backed up and removed from the site.', 'easy-theme-and-plugin-upgrades' ), "<code>$new_name</code>" ) );
|
93 |
+
} else {
|
94 |
+
$this->skin->error( __( 'Unable to move the old version of the theme to a new directory. No backup will be created.', 'easy-theme-and-plugin-upgrades' ) );
|
95 |
+
}
|
96 |
+
}
|
97 |
+
|
98 |
+
// Restore default strings and display the original remove_old message.
|
99 |
+
$this->upgrade_strings();
|
100 |
+
$this->skin->feedback( 'remove_old' );
|
101 |
+
|
102 |
+
return parent::clear_destination( $destination );
|
103 |
+
}
|
104 |
+
|
105 |
+
private function create_backup( $directory ) {
|
106 |
+
require_once( ABSPATH . 'wp-admin/includes/file.php' );
|
107 |
+
|
108 |
+
$wp_upload_dir = wp_upload_dir();
|
109 |
+
|
110 |
+
$zip_path = $wp_upload_dir['path'];
|
111 |
+
$zip_url = $wp_upload_dir['url'];
|
112 |
+
|
113 |
+
if ( ! is_dir( $zip_path ) ) {
|
114 |
+
return new WP_Error( 'caj-etpu-cannot-backup-no-destination-path', __( 'A theme backup can not be created since a destination path for the backup file could not be found.', 'easy-theme-and-plugin-upgrades' ) );
|
115 |
+
}
|
116 |
+
|
117 |
+
$headers = array(
|
118 |
+
'name' => 'Theme Name',
|
119 |
+
'version' => 'Version',
|
120 |
+
);
|
121 |
+
$data = get_file_data( "$directory/style.css", $headers );
|
122 |
+
|
123 |
+
$rand_string = $this->get_random_characters( 10, 20 );
|
124 |
+
$zip_file = basename( $directory ) . "-{$data['version']}-$rand_string.zip";
|
125 |
+
|
126 |
+
// Reduce the chance that a timeout will occur while creating the zip file.
|
127 |
+
@set_time_limit( 600 );
|
128 |
+
|
129 |
+
// Attempt to increase memory limits.
|
130 |
+
$this->set_minimum_memory_limit( '256M' );
|
131 |
+
|
132 |
+
$zip_path .= "/$zip_file";
|
133 |
+
$zip_url .= "/$zip_file";
|
134 |
+
|
135 |
+
require_once( ABSPATH . 'wp-admin/includes/class-pclzip.php' );
|
136 |
+
|
137 |
+
$archive = new PclZip( $zip_path );
|
138 |
+
|
139 |
+
$zip_result = $archive->create( $directory, PCLZIP_OPT_REMOVE_PATH, dirname( $directory ) );
|
140 |
+
|
141 |
+
if ( 0 === $zip_result ) {
|
142 |
+
/* translators: 1: zip error details */
|
143 |
+
return new WP_Error( 'caj-etpu-cannot-backup-zip-failed', sprintf( __( 'A theme backup can not be created as creation of the zip file failed with the following error: %1$s', 'easy-theme-and-plugin-upgrades' ), $archive->errorInfo( true ) ) );
|
144 |
+
}
|
145 |
+
|
146 |
+
$attachment = array(
|
147 |
+
'post_mime_type' => 'application/zip',
|
148 |
+
'guid' => $zip_url,
|
149 |
+
/* translators: 1: theme name, 2: theme version */
|
150 |
+
'post_title' => sprintf( __( 'Theme Backup - %1$s - %2$s', 'easy-theme-and-plugin-upgrades' ), $data['name'], $data['version'] ),
|
151 |
+
'post_content' => '',
|
152 |
+
);
|
153 |
+
|
154 |
+
$id = wp_insert_attachment( $attachment, $zip_path );
|
155 |
+
|
156 |
+
if ( ! is_wp_error( $id ) ) {
|
157 |
+
wp_update_attachment_metadata( $id, wp_generate_attachment_metadata( $id, $zip_path ) );
|
158 |
+
}
|
159 |
+
|
160 |
+
return $zip_url;
|
161 |
+
}
|
162 |
+
|
163 |
+
private function get_random_characters( $min_length, $max_length ) {
|
164 |
+
$characters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
|
165 |
+
$rand_string = '';
|
166 |
+
$length = rand( $min_length, $max_length );
|
167 |
+
|
168 |
+
for ( $count = 0; $count < $length; $count++ ) {
|
169 |
+
$rand_string .= $characters[ rand( 0, strlen( $characters ) - 1 ) ];
|
170 |
+
}
|
171 |
+
|
172 |
+
return $rand_string;
|
173 |
+
}
|
174 |
+
|
175 |
+
function set_minimum_memory_limit( $new_memory_limit ) {
|
176 |
+
$memory_limit = @ini_get( 'memory_limit' );
|
177 |
+
|
178 |
+
if ( $memory_limit > -1 ) {
|
179 |
+
$unit = strtolower( substr( $memory_limit, -1 ) );
|
180 |
+
$new_unit = strtolower( substr( $new_memory_limit, -1 ) );
|
181 |
+
|
182 |
+
$memory_limit = intval( $memory_limit );
|
183 |
+
$new_memory_limit = intval( $new_memory_limit );
|
184 |
+
|
185 |
+
if ( 'm' == $unit ) {
|
186 |
+
$memory_limit *= 1048576;
|
187 |
+
} elseif ( 'g' == $unit ) {
|
188 |
+
$memory_limit *= 1073741824;
|
189 |
+
} elseif ( 'k' == $unit ) {
|
190 |
+
$memory_limit *= 1024;
|
191 |
+
}
|
192 |
+
|
193 |
+
if ( 'm' == $new_unit ) {
|
194 |
+
$new_memory_limit *= 1048576;
|
195 |
+
} else if ( 'g' == $new_unit ) {
|
196 |
+
$new_memory_limit *= 1073741824;
|
197 |
+
} else if ( 'k' == $new_unit ) {
|
198 |
+
$new_memory_limit *= 1024;
|
199 |
+
}
|
200 |
+
|
201 |
+
if ( (int) $memory_limit < (int) $new_memory_limit ) {
|
202 |
+
@ini_set( 'memory_limit', $new_memory_limit );
|
203 |
+
}
|
204 |
+
}
|
205 |
+
}
|
206 |
+
}
|
history.txt
CHANGED
@@ -12,3 +12,8 @@
|
|
12 |
Compatibility Fix: Added support for PHP 7+.
|
13 |
1.0.6 - 2016-07-19 - Chris Jean
|
14 |
Bug Fix: Fixed incorrect handling of some zip file formats. Thanks to the team at https://kairaweb.com/ for helping solve this issue.
|
|
|
|
|
|
|
|
|
|
12 |
Compatibility Fix: Added support for PHP 7+.
|
13 |
1.0.6 - 2016-07-19 - Chris Jean
|
14 |
Bug Fix: Fixed incorrect handling of some zip file formats. Thanks to the team at https://kairaweb.com/ for helping solve this issue.
|
15 |
+
2.0.0 - 2016-08-15 - Chris Jean
|
16 |
+
Enhancement: Removed the requirement for the user to select "Yes" from the drop down in order to initiate an update. This new version does not change the appearance of the upload form. Instead, it automatically creates a backup and performs an upgrade if the supplied plugin or theme already exists.
|
17 |
+
Enhancement: If a zip backup file cannot be created, the old directory is renamed to a new name in order to still keep a backup.
|
18 |
+
Enhancement: Updated the code to use a better way of integrating the upgrade logic. This approach should greatly reduce the potential for conflicts with other code or site configurations.
|
19 |
+
Enhancement: The backup details now are found in the same format as the rest of the upgrade messages.
|
index.php
ADDED
@@ -0,0 +1,2 @@
|
|
|
|
|
1 |
+
<?php
|
2 |
+
// Silence is golden.
|
init.php
CHANGED
@@ -6,7 +6,7 @@ Plugin URI: http://wordpress.org/extend/plugins/easy-theme-and-plugin-upgrades/
|
|
6 |
Description: Upgrade themes and plugins using a zip file without having to remove them first.
|
7 |
Author: Chris Jean
|
8 |
Author URI: https://chrisjean.com/
|
9 |
-
Version:
|
10 |
License: GPLv2 or later
|
11 |
License URI: https://www.gnu.org/licenses/gpl-2.0.html
|
12 |
Text Domain: easy-theme-and-plugin-upgrades
|
@@ -27,7 +27,6 @@ https://www.gnu.org/licenses/gpl-2.0.html.
|
|
27 |
*/
|
28 |
|
29 |
|
30 |
-
if ( is_admin() )
|
31 |
-
|
32 |
-
|
33 |
-
require_once( dirname( __FILE__ ) . '/show-maintenance-message.php' );
|
6 |
Description: Upgrade themes and plugins using a zip file without having to remove them first.
|
7 |
Author: Chris Jean
|
8 |
Author URI: https://chrisjean.com/
|
9 |
+
Version: 2.0.0
|
10 |
License: GPLv2 or later
|
11 |
License URI: https://www.gnu.org/licenses/gpl-2.0.html
|
12 |
Text Domain: easy-theme-and-plugin-upgrades
|
27 |
*/
|
28 |
|
29 |
|
30 |
+
if ( is_admin() ) {
|
31 |
+
require( dirname( __FILE__ ) . '/admin.php' );
|
32 |
+
}
|
|
maintenance-page.html
DELETED
@@ -1,46 +0,0 @@
|
|
1 |
-
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
2 |
-
<html xmlns="http://www.w3.org/1999/xhtml">
|
3 |
-
|
4 |
-
<head profile="http://gmpg.org/xfn/11">
|
5 |
-
<style>
|
6 |
-
* {
|
7 |
-
padding: 0;
|
8 |
-
margin: 0;
|
9 |
-
}
|
10 |
-
html, body {
|
11 |
-
height: 100%;
|
12 |
-
}
|
13 |
-
body {
|
14 |
-
font-size: 1.5em;
|
15 |
-
background-color: #C0C0C0;
|
16 |
-
}
|
17 |
-
.pusher {
|
18 |
-
width: 1px;
|
19 |
-
height: 50%;
|
20 |
-
margin-bottom: -2.7em;
|
21 |
-
float: left;
|
22 |
-
}
|
23 |
-
.content {
|
24 |
-
height: 3.8em;
|
25 |
-
width: 16em;
|
26 |
-
clear: left;
|
27 |
-
margin: 0 auto;
|
28 |
-
position: relative;
|
29 |
-
border: 0.2em solid #369;
|
30 |
-
background-color: #FFF;
|
31 |
-
padding: 1.2em 1em 0 1em;
|
32 |
-
-moz-border-radius: 1em;
|
33 |
-
-webkit-border-radius: 1em;
|
34 |
-
text-align: center;
|
35 |
-
}
|
36 |
-
</style>
|
37 |
-
</head>
|
38 |
-
|
39 |
-
<body>
|
40 |
-
<div class="pusher"><!-- centers next div --></div>
|
41 |
-
<div class="content">
|
42 |
-
The site is being updated and will be back in a few minutes.
|
43 |
-
</div>
|
44 |
-
</body>
|
45 |
-
|
46 |
-
</html>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
modify-installer.php
DELETED
@@ -1,274 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
|
4 |
-
if ( ! class_exists( 'ETUModifyInstaller' ) ) {
|
5 |
-
class ETUModifyInstaller {
|
6 |
-
var $_errors = array();
|
7 |
-
var $_type = '';
|
8 |
-
|
9 |
-
|
10 |
-
function __construct() {
|
11 |
-
if ( preg_match( '/update\.php/', $_SERVER['REQUEST_URI'] ) && isset( $_REQUEST['action'] ) ) {
|
12 |
-
if ( 'upload-theme' === $_REQUEST['action'] ) {
|
13 |
-
$this->_type = 'theme';
|
14 |
-
} else if ( 'upload-plugin' === $_REQUEST['action'] ) {
|
15 |
-
$this->_type = 'plugin';
|
16 |
-
}
|
17 |
-
|
18 |
-
if ( ! empty( $this->_type ) ) {
|
19 |
-
add_action( 'admin_init', array( $this, 'handle_upgrades' ), 100 );
|
20 |
-
}
|
21 |
-
}
|
22 |
-
|
23 |
-
add_action( 'load-theme-install.php', array( $this, 'start_theme_output_buffering' ) );
|
24 |
-
add_action( 'load-plugin-install.php', array( $this, 'start_plugin_output_buffering' ) );
|
25 |
-
}
|
26 |
-
|
27 |
-
function filter_output( $output ) {
|
28 |
-
$text = "<div style='max-width:600px;'>\n";
|
29 |
-
$text .= "<p><i>By default, the installer will not overwrite an existing {$this->_type}. Change the following option to \"Yes\" to allow this installer to perform upgrades as well.</i></p>";
|
30 |
-
$text .= "<p>Upgrade existing {$this->_type}? <select name='caj_etu_upgrade_existing'><option value=''>No</option><option value='yes'>Yes</option></select></p>\n";
|
31 |
-
$text .= "<p>If a {$this->_type} is upgraded, the following process will be used:</p>\n";
|
32 |
-
$text .= "<ol>\n";
|
33 |
-
$text .= "<li>A backup zip of the existing {$this->_type} will be created and added to the <a href='" . admin_url( 'upload.php' ) . "'>Media Library</a>.</li>\n";
|
34 |
-
$text .= "<li>If the selected {$this->_type} is active, the site will display a 'Site being updated' message until the upgrade has finished. This typically lasts a few seconds at most.</li>\n";
|
35 |
-
$text .= "<li>The existing {$this->_type} directory will be deleted in order for the installer to install the new version.</li>\n";
|
36 |
-
$text .= "<li>The {$this->_type} installer will install the new {$this->_type}.</li>\n";
|
37 |
-
$text .= "<li>The site update message will be removed from the site.</li>\n";
|
38 |
-
$text .= "</ol><br />\n";
|
39 |
-
$text .= "</div>\n";
|
40 |
-
|
41 |
-
$output = preg_replace( '/(<input [^>]*name="(?:theme|plugin)zip".+?\n)/', "\$1$text", $output );
|
42 |
-
|
43 |
-
return $output;
|
44 |
-
}
|
45 |
-
|
46 |
-
function start_theme_output_buffering() {
|
47 |
-
$this->_type = 'theme';
|
48 |
-
ob_start( array( $this, 'filter_output' ) );
|
49 |
-
}
|
50 |
-
|
51 |
-
function start_plugin_output_buffering() {
|
52 |
-
$this->_type = 'plugin';
|
53 |
-
ob_start( array( $this, 'filter_output' ) );
|
54 |
-
}
|
55 |
-
|
56 |
-
function _get_themes() {
|
57 |
-
global $wp_themes;
|
58 |
-
|
59 |
-
if ( isset( $wp_themes ) ) {
|
60 |
-
return $wp_themes;
|
61 |
-
}
|
62 |
-
|
63 |
-
$themes = wp_get_themes();
|
64 |
-
$wp_themes = array();
|
65 |
-
|
66 |
-
foreach ( $themes as $theme ) {
|
67 |
-
$name = $theme->get( 'Name' );
|
68 |
-
if ( isset( $wp_themes[$name] ) )
|
69 |
-
$wp_themes[$name . '/' . $theme->get_stylesheet()] = $theme;
|
70 |
-
else
|
71 |
-
$wp_themes[$name] = $theme;
|
72 |
-
}
|
73 |
-
|
74 |
-
return $wp_themes;
|
75 |
-
}
|
76 |
-
|
77 |
-
function _get_theme_data( $directory ) {
|
78 |
-
$data = array();
|
79 |
-
|
80 |
-
$themes = $this->_get_themes();
|
81 |
-
$active_theme = wp_get_theme();
|
82 |
-
$current_theme = array();
|
83 |
-
|
84 |
-
foreach ( (array) $themes as $theme_name => $theme_data ) {
|
85 |
-
if ( $directory === $theme_data['Stylesheet'] )
|
86 |
-
$current_theme = $theme_data;
|
87 |
-
}
|
88 |
-
|
89 |
-
if ( empty( $current_theme ) )
|
90 |
-
return $data;
|
91 |
-
|
92 |
-
$data['version'] = $current_theme['Version'];
|
93 |
-
$data['name'] = $current_theme['Name'];
|
94 |
-
$data['directory'] = $current_theme['Stylesheet Dir'];
|
95 |
-
|
96 |
-
$data['is_active'] = false;
|
97 |
-
if ( ( $active_theme->template_dir === $current_theme['Template Dir'] ) || ( $active_theme->template_dir === $current_theme['Template Dir'] ) )
|
98 |
-
$data['is_active'] = true;
|
99 |
-
|
100 |
-
global $wp_version;
|
101 |
-
if ( version_compare( '2.8.6', $wp_version, '>' ) )
|
102 |
-
$data['directory'] = WP_CONTENT_DIR . $current_theme['Stylesheet Dir'];
|
103 |
-
|
104 |
-
return $data;
|
105 |
-
}
|
106 |
-
|
107 |
-
function _get_plugin_data( $directory ) {
|
108 |
-
$data = array();
|
109 |
-
|
110 |
-
$plugins = get_plugins();
|
111 |
-
$active_plugins = get_option('active_plugins');
|
112 |
-
$current_plugin = array();
|
113 |
-
|
114 |
-
foreach ( (array) $plugins as $plugin_path_file => $plugin_data ) {
|
115 |
-
$path_parts = explode( '/', $plugin_path_file );
|
116 |
-
if ( $directory === reset( $path_parts ) ) {
|
117 |
-
$current_plugin = array( 'path' => $plugin_path_file, 'data' => $plugin_data );
|
118 |
-
}
|
119 |
-
}
|
120 |
-
|
121 |
-
if ( empty( $current_plugin ) ) {
|
122 |
-
return $data;
|
123 |
-
}
|
124 |
-
|
125 |
-
$data['version'] = $current_plugin['data']['Version'];
|
126 |
-
$data['name'] = $current_plugin['data']['Name'];
|
127 |
-
$data['directory'] = WP_PLUGIN_DIR . '/' . $directory;
|
128 |
-
$data['is_active'] = ( is_plugin_active( $current_plugin['path'] ) ) ? true : false;
|
129 |
-
|
130 |
-
return $data;
|
131 |
-
}
|
132 |
-
|
133 |
-
function handle_upgrades() {
|
134 |
-
if ( empty( $_POST['caj_etu_upgrade_existing'] ) ) {
|
135 |
-
$this->_errors[] = "The Easy Theme and Plugin Upgrades plugin was unable to handle requests for this upgrade. Unfortunately, this setup may be incompatible with the plugin.";
|
136 |
-
add_action( 'admin_notices', array( $this, 'show_upgrade_option_error_message' ) );
|
137 |
-
|
138 |
-
return;
|
139 |
-
}
|
140 |
-
|
141 |
-
if ( 'yes' !== $_POST['caj_etu_upgrade_existing'] ) {
|
142 |
-
if ( 'plugin' == $this->_type ) {
|
143 |
-
$link = admin_url( "plugin-install.php?tab=upload" );
|
144 |
-
} else if ( version_compare( $GLOBALS['wp_version'], '3.8.9', '>' ) ) {
|
145 |
-
$link = admin_url( "theme-install.php" );
|
146 |
-
} else {
|
147 |
-
$link = admin_url( "theme-install.php?tab=upload" );
|
148 |
-
}
|
149 |
-
|
150 |
-
$this->_errors[] = "You must select \"Yes\" from the \"Upgrade existing {$this->_type}?\" dropdown option in order to upgrade an existing {$this->_type}. <a href=\"$link\">Try again</a>.";
|
151 |
-
add_action( 'admin_notices', array( $this, 'show_upgrade_option_error_message' ) );
|
152 |
-
|
153 |
-
return;
|
154 |
-
}
|
155 |
-
|
156 |
-
remove_action( 'admin_print_styles', 'builder_add_global_admin_styles' );
|
157 |
-
|
158 |
-
|
159 |
-
include_once( ABSPATH . 'wp-admin/includes/class-wp-upgrader.php' );
|
160 |
-
require_once( ABSPATH . 'wp-admin/includes/class-pclzip.php' );
|
161 |
-
require_once( ABSPATH . 'wp-admin/includes/file.php' );
|
162 |
-
|
163 |
-
check_admin_referer( "{$this->_type}-upload" );
|
164 |
-
@set_time_limit( 300 );
|
165 |
-
|
166 |
-
$archive = new PclZip( $_FILES["{$this->_type}zip"]['tmp_name'] );
|
167 |
-
|
168 |
-
$contents = $archive->listContent();
|
169 |
-
$directories = array();
|
170 |
-
|
171 |
-
foreach ( (array) $contents as $content ) {
|
172 |
-
list( $directory ) = explode( '/', $content['filename'], 2 );
|
173 |
-
if ( isset( $directories[$directory] ) ) {
|
174 |
-
$directories[$directory]++;
|
175 |
-
} else {
|
176 |
-
$directories[$directory] = 1;
|
177 |
-
}
|
178 |
-
}
|
179 |
-
arsort( $directories );
|
180 |
-
reset( $directories );
|
181 |
-
|
182 |
-
$directory = key( $directories );
|
183 |
-
|
184 |
-
if ( 'theme' === $this->_type )
|
185 |
-
$data = $this->_get_theme_data( $directory );
|
186 |
-
else if ( 'plugin' === $this->_type )
|
187 |
-
$data = $this->_get_plugin_data( $directory );
|
188 |
-
|
189 |
-
if ( empty( $data ) )
|
190 |
-
return;
|
191 |
-
|
192 |
-
|
193 |
-
$characters = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
|
194 |
-
$rand_string = '';
|
195 |
-
$length = rand( 10, 20 );
|
196 |
-
for ( $count = 0; $count < $length; $count++ )
|
197 |
-
$rand_string .= $characters[rand( 0, strlen( $characters ) - 1 )];
|
198 |
-
|
199 |
-
$zip_file = "$directory-{$data['version']}-$rand_string.zip";
|
200 |
-
|
201 |
-
$wp_upload_dir = wp_upload_dir();
|
202 |
-
$zip_path = $wp_upload_dir['path'] . '/' . $zip_file;
|
203 |
-
$zip_url = $wp_upload_dir['url'] . '/' . $zip_file;
|
204 |
-
|
205 |
-
$archive = new PclZip( $zip_path );
|
206 |
-
|
207 |
-
$zip_result = $archive->create( $data['directory'], PCLZIP_OPT_REMOVE_PATH, dirname( $data['directory'] ) );
|
208 |
-
|
209 |
-
if ( 0 == $zip_result ) {
|
210 |
-
$this->_errors[] = "Unable to make a backup of the existing {$this->_type}. Will not proceed with the upgrade.";
|
211 |
-
add_action( 'admin_notices', array( $this, 'show_upgrade_option_error_message' ) );
|
212 |
-
|
213 |
-
return;
|
214 |
-
}
|
215 |
-
|
216 |
-
|
217 |
-
$attachment = array(
|
218 |
-
'post_mime_type' => 'application/zip',
|
219 |
-
'guid' => $zip_url,
|
220 |
-
'post_title' => ucfirst( $this->_type ) . " Backup - {$data['name']} - {$data['version']}",
|
221 |
-
'post_content' => '',
|
222 |
-
);
|
223 |
-
|
224 |
-
$id = wp_insert_attachment( $attachment, $zip_path );
|
225 |
-
if ( !is_wp_error( $id ) )
|
226 |
-
wp_update_attachment_metadata( $id, wp_generate_attachment_metadata( $id, $zip_path ) );
|
227 |
-
|
228 |
-
|
229 |
-
if ( $data['is_active'] )
|
230 |
-
set_transient( 'etu-in-maintenance-mode', '1', 300 );
|
231 |
-
|
232 |
-
|
233 |
-
global $wp_filesystem;
|
234 |
-
|
235 |
-
if ( ! WP_Filesystem() ) {
|
236 |
-
$this->_errors[] = 'Unable to initialize WP_Filesystem. Will not proceed with the upgrade.';
|
237 |
-
add_action( 'admin_notices', array( $this, 'show_upgrade_option_error_message' ) );
|
238 |
-
|
239 |
-
return;
|
240 |
-
}
|
241 |
-
|
242 |
-
if ( ! $wp_filesystem->delete( $data['directory'], true ) ) {
|
243 |
-
$this->_errors[] = "Unable to remove the existing {$this->_type} directory. Will not proceed with the upgrade.";
|
244 |
-
add_action( 'admin_notices', array( $this, 'show_upgrade_option_error_message' ) );
|
245 |
-
|
246 |
-
return;
|
247 |
-
}
|
248 |
-
|
249 |
-
|
250 |
-
$this->_zip_url = $zip_url;
|
251 |
-
|
252 |
-
add_action( 'all_admin_notices', array( $this, 'show_message' ) );
|
253 |
-
}
|
254 |
-
|
255 |
-
function show_message() {
|
256 |
-
echo "<div id=\"message\" class=\"updated fade\"><p><strong>A backup zip file of the old {$this->_type} version can be downloaded <a href='$this->_zip_url'>here</a>.</strong></p></div>\n";
|
257 |
-
|
258 |
-
delete_transient( 'etu-in-maintenance-mode' );
|
259 |
-
}
|
260 |
-
|
261 |
-
function show_upgrade_option_error_message() {
|
262 |
-
if ( ! isset( $this->_errors ) )
|
263 |
-
return;
|
264 |
-
|
265 |
-
if ( ! is_array( $this->_errors ) )
|
266 |
-
$this->_errors = array( $this->_errors );
|
267 |
-
|
268 |
-
foreach ( (array) $this->_errors as $error )
|
269 |
-
echo "<div id=\"message\" class=\"error\"><p><strong>$error</strong></p></div>\n";
|
270 |
-
}
|
271 |
-
}
|
272 |
-
|
273 |
-
new ETUModifyInstaller();
|
274 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
readme.txt
CHANGED
@@ -2,23 +2,31 @@
|
|
2 |
Contributors: chrisjean
|
3 |
Tags: plugin, theme, upgrade, update, upload
|
4 |
Requires at least: 4.4
|
5 |
-
Tested up to: 4.
|
6 |
-
Stable tag:
|
7 |
License: GPLv2 or later
|
8 |
License URI: http://www.gnu.org/licenses/gpl-2.0.html
|
9 |
|
10 |
Easily upgrade your themes and plugins using zip files without removing the theme or plugin first.
|
11 |
|
|
|
12 |
== Description ==
|
13 |
|
14 |
WordPress has a built-in feature to install themes and plugins by supplying a zip file. Unfortunately, you cannot upgrade a theme or plugin using the same process. Instead, WordPress will say "destination already exists" when trying to upgrade using a zip file and will fail to upgrade the theme or plugin.
|
15 |
|
16 |
-
Easy Theme and Plugin Upgrades fixes this limitation in WordPress
|
17 |
|
18 |
While upgrading, a backup copy of the old theme or plugin is first created. This allows you to install the old version in case of problems with the new version.
|
19 |
|
|
|
|
|
|
|
20 |
== Frequently Asked Questions ==
|
21 |
|
|
|
|
|
|
|
|
|
22 |
= How do I upgrade a theme? =
|
23 |
|
24 |
1. Download the latest zip file for your theme.
|
@@ -26,20 +34,28 @@ While upgrading, a backup copy of the old theme or plugin is first created. This
|
|
26 |
1. Go to Appearance > Themes.
|
27 |
1. Click the "Add New" button at the top of the page.
|
28 |
1. Click the "Upload Theme" button at the top of the page.
|
29 |
-
1. Click the file browse button to select your theme zip file. The button's text varies by browser. It typically says "Browse...", "Choose File", or "Choose...".
|
30 |
1. Select the zip file with the new theme version to install.
|
31 |
-
1. Select "Yes" from the "Upgrade existing theme?" option.
|
32 |
1. Click the "Install Now" button.
|
33 |
|
34 |
= How do I upgrade a plugin? =
|
35 |
|
36 |
1. Download the latest zip file for your plugin.
|
37 |
1. Log into your WordPress site.
|
38 |
-
1. Go to Plugins > Add New
|
|
|
39 |
1. Select the zip file with the new plugin version to install.
|
40 |
-
1. Select "Yes" from the "Upgrade existing plugin?" option.
|
41 |
1. Click the "Install Now" button.
|
42 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
43 |
== Installation ==
|
44 |
|
45 |
1. Download and unzip the latest release zip file
|
@@ -48,6 +64,12 @@ While upgrading, a backup copy of the old theme or plugin is first created. This
|
|
48 |
|
49 |
== Changelog ==
|
50 |
|
|
|
|
|
|
|
|
|
|
|
|
|
51 |
= 1.0.6 =
|
52 |
* Bug Fix: Fixed updates not working with some formats of zip files. Thanks to the team at [Kaira](https://kairaweb.com/) for helping solve this issue.
|
53 |
|
@@ -69,7 +91,8 @@ While upgrading, a backup copy of the old theme or plugin is first created. This
|
|
69 |
= 1.0.0 =
|
70 |
* Initial release version
|
71 |
|
|
|
72 |
== Upgrade Notice ==
|
73 |
|
74 |
-
=
|
75 |
-
Version
|
2 |
Contributors: chrisjean
|
3 |
Tags: plugin, theme, upgrade, update, upload
|
4 |
Requires at least: 4.4
|
5 |
+
Tested up to: 4.6
|
6 |
+
Stable tag: 2.0.0
|
7 |
License: GPLv2 or later
|
8 |
License URI: http://www.gnu.org/licenses/gpl-2.0.html
|
9 |
|
10 |
Easily upgrade your themes and plugins using zip files without removing the theme or plugin first.
|
11 |
|
12 |
+
|
13 |
== Description ==
|
14 |
|
15 |
WordPress has a built-in feature to install themes and plugins by supplying a zip file. Unfortunately, you cannot upgrade a theme or plugin using the same process. Instead, WordPress will say "destination already exists" when trying to upgrade using a zip file and will fail to upgrade the theme or plugin.
|
16 |
|
17 |
+
Easy Theme and Plugin Upgrades fixes this limitation in WordPress by automatically upgrading the theme or plugin if it already exists.
|
18 |
|
19 |
While upgrading, a backup copy of the old theme or plugin is first created. This allows you to install the old version in case of problems with the new version.
|
20 |
|
21 |
+
Attention: Version 2.0.0 changed the functionality of the plugin. You are no longer required to select "Yes" from a drop down before the theme or plugin can be upgraded. The need for an upgrade is now detected automatically. So, if you are used to the old functionality of the plugin, do not be concerned about the absence of upgrade details on the theme and plugin upload pages. Simply upload the theme or plugin as if you were installing it, and the plugin will automatically handle upgrading as needed.
|
22 |
+
|
23 |
+
|
24 |
== Frequently Asked Questions ==
|
25 |
|
26 |
+
= Why does the plugin no longer show the drop down to select "Yes"? Is the plugin broken? =
|
27 |
+
|
28 |
+
Version 2.0.0 no longer requires that a drop down is used to indicate that an upgrade is to be performed. The plugin now can determine if an upgrade is required automatically. This change not only streamlines the process for many users, it also fixed compatibility issues that some users experienced with older versions.
|
29 |
+
|
30 |
= How do I upgrade a theme? =
|
31 |
|
32 |
1. Download the latest zip file for your theme.
|
34 |
1. Go to Appearance > Themes.
|
35 |
1. Click the "Add New" button at the top of the page.
|
36 |
1. Click the "Upload Theme" button at the top of the page.
|
|
|
37 |
1. Select the zip file with the new theme version to install.
|
|
|
38 |
1. Click the "Install Now" button.
|
39 |
|
40 |
= How do I upgrade a plugin? =
|
41 |
|
42 |
1. Download the latest zip file for your plugin.
|
43 |
1. Log into your WordPress site.
|
44 |
+
1. Go to Plugins > Add New.
|
45 |
+
1. Click the "Upload Plugin" button at the top of the page.
|
46 |
1. Select the zip file with the new plugin version to install.
|
|
|
47 |
1. Click the "Install Now" button.
|
48 |
|
49 |
+
= How do I access the backup of an old theme or plugin? =
|
50 |
+
|
51 |
+
1. Log into your WordPress site.
|
52 |
+
1. Go to Media > Library.
|
53 |
+
1. Type "backup" into the search input and press the "Enter" key.
|
54 |
+
1. Find the desired backup from the resulting list.
|
55 |
+
1. Click the title of the desired backup.
|
56 |
+
1. The URL to the backup file is listed on the right side of the page under "File URL". You can copy and paste that URL into your browser's URL bar in order to start a download.
|
57 |
+
|
58 |
+
|
59 |
== Installation ==
|
60 |
|
61 |
1. Download and unzip the latest release zip file
|
64 |
|
65 |
== Changelog ==
|
66 |
|
67 |
+
= 2.0.0 =
|
68 |
+
* Enhancement: Removed the requirement for the user to select "Yes" from the drop down in order to initiate an update. This new version does not change the appearance of the upload form. Instead, it automatically creates a backup and performs an upgrade if the supplied plugin or theme already exists.
|
69 |
+
* Enhancement: If a zip backup file cannot be created, the old directory is renamed to a new name in order to still keep a backup.
|
70 |
+
* Enhancement: Updated the code to use a better way of integrating the upgrade logic. This approach should greatly reduce the potential for conflicts with other code or site configurations.
|
71 |
+
* Enhancement: The backup details now are found in the same format as the rest of the upgrade messages.
|
72 |
+
|
73 |
= 1.0.6 =
|
74 |
* Bug Fix: Fixed updates not working with some formats of zip files. Thanks to the team at [Kaira](https://kairaweb.com/) for helping solve this issue.
|
75 |
|
91 |
= 1.0.0 =
|
92 |
* Initial release version
|
93 |
|
94 |
+
|
95 |
== Upgrade Notice ==
|
96 |
|
97 |
+
= 2.0.0 =
|
98 |
+
Version 2.0.0 fixes many of the site and plugin compatibility issues that people have reported and removes any need to tell the plugin to perform an upgrade.
|
show-maintenance-message.php
DELETED
@@ -1,23 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
|
4 |
-
if ( ! class_exists( 'ETUShowMaintenanceMessage' ) ) {
|
5 |
-
class ETUShowMaintenanceMessage {
|
6 |
-
function __construct() {
|
7 |
-
if ( false !== get_transient( 'etu-in-maintenance-mode' ) )
|
8 |
-
add_action( 'template_redirect', array( $this, 'show_message' ) );
|
9 |
-
}
|
10 |
-
|
11 |
-
function show_message() {
|
12 |
-
$file = dirname( __FILE__ ) . '/maintenance-page.html';
|
13 |
-
if ( file_exists( dirname( __FILE__ ) . '/custom-maintenance-page.html' ) )
|
14 |
-
$file = dirname( __FILE__ ) . '/custom-maintenance-page.html';
|
15 |
-
|
16 |
-
echo file_get_contents( $file );
|
17 |
-
|
18 |
-
exit;
|
19 |
-
}
|
20 |
-
}
|
21 |
-
|
22 |
-
new ETUShowMaintenanceMessage();
|
23 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|