Version Description
Download this release
Release Info
Developer | cory@lamle.org |
Plugin | Duplicator – WordPress Migration Plugin |
Version | 1.1.34 |
Comparing to | |
See all releases |
Code changes from version 1.1.32 to 1.1.34
- assets/img/paypal.png +0 -0
- assets/img/perks_bluehost.png +0 -0
- assets/img/perks_ethemes.png +0 -0
- assets/img/perks_inmotion.png +0 -0
- assets/img/perks_managewp.png +0 -0
- assets/img/perks_maxcdn.png +0 -0
- assets/img/perks_ninjaforms.png +0 -0
- assets/img/perks_optinmonster.png +0 -0
- classes/{logging.php → class.logging.php} +2 -2
- classes/{settings.php → class.settings.php} +0 -0
- classes/package.archive.php +0 -316
- classes/package.archive.zip.php +0 -181
- classes/package.database.php +0 -416
- classes/package.installer.php +0 -203
- classes/package.php +0 -547
- classes/package/class.pack.archive.filters.php +80 -0
- classes/package/class.pack.archive.php +274 -0
- classes/package/class.pack.archive.zip.php +159 -0
- classes/package/class.pack.database.php +375 -0
- classes/package/class.pack.installer.php +214 -0
- classes/package/class.pack.php +622 -0
- classes/scan.validator.php +0 -93
- classes/server.php +0 -200
- classes/ui.php +0 -92
- classes/ui/class.dialog.php +0 -165
- classes/ui/class.ui.dialog.php +200 -0
- classes/ui/class.ui.notice.php +51 -0
- classes/ui/class.ui.viewstate.php +72 -0
- classes/ui/ui.php +0 -92
- classes/utilities/class.db.php +117 -0
- classes/utilities/class.scan.check.php +146 -0
- classes/utilities/class.server.php +204 -0
- classes/utilities/class.util.php +481 -0
- classes/utility.php +0 -393
- ctrls/ctrl.base.php +2 -2
- ctrls/ctrl.package.php +27 -28
- ctrls/ctrl.tools.php +9 -6
- ctrls/ctrl.ui.php +4 -4
- debug/main.php +1 -1
- define.php +1 -1
- duplicator.php +21 -37
- installer/build/ajax.step1.php +114 -94
- installer/build/ajax.step2.php +27 -27
- installer/build/assets/inc.css.php +1 -1
- installer/build/classes/class.conf.srv.php +0 -77
- installer/build/classes/class.conf.wp.php +0 -113
- installer/build/classes/class.engine.php +441 -0
- installer/build/classes/class.logging.php +29 -10
- installer/build/classes/class.serializer.php +0 -452
- installer/build/classes/class.utils.php +0 -376
- installer/build/classes/config/class.conf.srv.php +87 -0
- installer/build/classes/config/class.conf.wp.php +122 -0
- installer/build/classes/util/class.db.php +194 -0
- installer/build/classes/util/class.utils.php +312 -0
- installer/build/main.installer.php +5 -2
- installer/build/view.step2.php +2 -2
- readme.txt +1 -1
- uninstall.php +4 -4
- views/help/about.php +1 -1
- views/help/gopro.php +1 -1
- views/help/help.php +1 -1
- views/help/perks.php +0 -183
- views/packages/controller.php +1 -1
- views/packages/details/controller.php +2 -2
- views/packages/details/detail.php +6 -4
- views/packages/main/controller.php +1 -1
- views/packages/main/new1.inc.form.php +6 -6
- views/packages/main/new1.setup.php +8 -9
- views/packages/main/new2.scan.php +12 -14
- views/packages/main/new3.build.php +1 -2
- views/packages/main/packages.php +17 -17
- views/settings/controller.php +1 -1
- views/settings/general.php +4 -4
- views/tools/cleanup.php +8 -8
- views/tools/controller.php +2 -2
- views/tools/diagnostics/inc.data.php +5 -5
- views/tools/diagnostics/inc.settings.php +16 -12
- views/tools/diagnostics/inc.validator.php +10 -10
- views/tools/diagnostics/main.php +1 -1
- views/tools/logging.php +1 -1
assets/img/paypal.png
DELETED
Binary file
|
assets/img/perks_bluehost.png
DELETED
Binary file
|
assets/img/perks_ethemes.png
DELETED
Binary file
|
assets/img/perks_inmotion.png
DELETED
Binary file
|
assets/img/perks_managewp.png
DELETED
Binary file
|
assets/img/perks_maxcdn.png
DELETED
Binary file
|
assets/img/perks_ninjaforms.png
DELETED
Binary file
|
assets/img/perks_optinmonster.png
DELETED
Binary file
|
classes/{logging.php → class.logging.php}
RENAMED
@@ -34,12 +34,12 @@ class DUP_Log {
|
|
34 |
* @param string $msg The message to log
|
35 |
*
|
36 |
* REPLACE TO DEBUG: Memory consuption as script runs
|
37 |
-
* $results = DUP_Util::
|
38 |
* @fwrite(self::$logFileHandle, "{$results} \n");
|
39 |
*/
|
40 |
static public function Info($msg) {
|
41 |
@fwrite(self::$logFileHandle, "{$msg} \n");
|
42 |
-
//$results = DUP_Util::
|
43 |
//@fwrite(self::$logFileHandle, "{$results} \n");
|
44 |
}
|
45 |
|
34 |
* @param string $msg The message to log
|
35 |
*
|
36 |
* REPLACE TO DEBUG: Memory consuption as script runs
|
37 |
+
* $results = DUP_Util::byteSize(memory_get_peak_usage(true)) . "\t" . $msg;
|
38 |
* @fwrite(self::$logFileHandle, "{$results} \n");
|
39 |
*/
|
40 |
static public function Info($msg) {
|
41 |
@fwrite(self::$logFileHandle, "{$msg} \n");
|
42 |
+
//$results = DUP_Util::byteSize(memory_get_usage(true)) . "\t" . $msg;
|
43 |
//@fwrite(self::$logFileHandle, "{$results} \n");
|
44 |
}
|
45 |
|
classes/{settings.php → class.settings.php}
RENAMED
File without changes
|
classes/package.archive.php
DELETED
@@ -1,316 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.archive.zip.php');
|
5 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'lib/forceutf8/Encoding.php');
|
6 |
-
|
7 |
-
/**
|
8 |
-
* The base class for all filter types Directories/Files/Extentions
|
9 |
-
*/
|
10 |
-
class DUP_Archive_Filter_Scope_Base
|
11 |
-
{
|
12 |
-
//All internal storage items that duplicator decides to filter
|
13 |
-
public $Core = array();
|
14 |
-
|
15 |
-
//Items when creating a package or template that a user decides to filter
|
16 |
-
public $Instance = array();
|
17 |
-
}
|
18 |
-
|
19 |
-
/**
|
20 |
-
* The filter types that belong to directories
|
21 |
-
*/
|
22 |
-
class DUP_Archive_Filter_Scope_Directory extends DUP_Archive_Filter_Scope_Base
|
23 |
-
{
|
24 |
-
//Items that are not readable
|
25 |
-
public $Warning = array();
|
26 |
-
|
27 |
-
//Items that are not readable
|
28 |
-
public $Unreadable = array();
|
29 |
-
}
|
30 |
-
|
31 |
-
/**
|
32 |
-
* The filter types that belong to files
|
33 |
-
*/
|
34 |
-
class DUP_Archive_Filter_Scope_File extends DUP_Archive_Filter_Scope_Directory
|
35 |
-
{
|
36 |
-
//Items that are too large
|
37 |
-
public $Size = array();
|
38 |
-
}
|
39 |
-
|
40 |
-
/**
|
41 |
-
* The filter information object which store all information about the filtered
|
42 |
-
* data that is gathered to the execution of a scan process
|
43 |
-
*/
|
44 |
-
class DUP_Archive_Filter_Info
|
45 |
-
{
|
46 |
-
//Contains all folder filter info
|
47 |
-
public $Dirs = array();
|
48 |
-
|
49 |
-
//Contains all file filter info
|
50 |
-
public $Files = array();
|
51 |
-
|
52 |
-
//Contains all extensions filter info
|
53 |
-
public $Exts = array();
|
54 |
-
|
55 |
-
public $UDirCount = 0;
|
56 |
-
public $UFileCount = 0;
|
57 |
-
public $UExtCount = 0;
|
58 |
-
|
59 |
-
public function __construct()
|
60 |
-
{
|
61 |
-
$this->Dirs = new DUP_Archive_Filter_Scope_Directory();
|
62 |
-
$this->Files = new DUP_Archive_Filter_Scope_File();
|
63 |
-
$this->Exts = new DUP_Archive_Filter_Scope_Base();
|
64 |
-
}
|
65 |
-
}
|
66 |
-
|
67 |
-
|
68 |
-
class DUP_Archive
|
69 |
-
{
|
70 |
-
//PUBLIC
|
71 |
-
public $FilterDirs;
|
72 |
-
public $FilterExts;
|
73 |
-
public $FilterDirsAll = array();
|
74 |
-
public $FilterExtsAll = array();
|
75 |
-
public $FilterOn;
|
76 |
-
public $File;
|
77 |
-
public $Format;
|
78 |
-
public $PackDir;
|
79 |
-
public $Size = 0;
|
80 |
-
public $Dirs = array();
|
81 |
-
public $Files = array();
|
82 |
-
public $FilterInfo;
|
83 |
-
|
84 |
-
//PROTECTED
|
85 |
-
protected $Package;
|
86 |
-
|
87 |
-
public function __construct($package)
|
88 |
-
{
|
89 |
-
$this->Package = $package;
|
90 |
-
$this->FilterOn = false;
|
91 |
-
$this->FilterInfo = new DUP_Archive_Filter_Info();
|
92 |
-
}
|
93 |
-
|
94 |
-
public function Build($package)
|
95 |
-
{
|
96 |
-
try
|
97 |
-
{
|
98 |
-
$this->Package = $package;
|
99 |
-
if (!isset($this->PackDir) && ! is_dir($this->PackDir)) throw new Exception("The 'PackDir' property must be a valid diretory.");
|
100 |
-
if (!isset($this->File)) throw new Exception("A 'File' property must be set.");
|
101 |
-
|
102 |
-
$this->Package->SetStatus(DUP_PackageStatus::ARCSTART);
|
103 |
-
switch ($this->Format)
|
104 |
-
{
|
105 |
-
case 'TAR': break;
|
106 |
-
case 'TAR-GZIP': break;
|
107 |
-
default:
|
108 |
-
if (class_exists(ZipArchive))
|
109 |
-
{
|
110 |
-
$this->Format = 'ZIP';
|
111 |
-
DUP_Zip::Create($this);
|
112 |
-
}
|
113 |
-
break;
|
114 |
-
}
|
115 |
-
|
116 |
-
$storePath = "{$this->Package->StorePath}/{$this->File}";
|
117 |
-
$this->Size = @filesize($storePath);
|
118 |
-
$this->Package->SetStatus(DUP_PackageStatus::ARCDONE);
|
119 |
-
|
120 |
-
}
|
121 |
-
catch (Exception $e)
|
122 |
-
{
|
123 |
-
echo 'Caught exception: ', $e->getMessage(), "\n";
|
124 |
-
}
|
125 |
-
}
|
126 |
-
|
127 |
-
public function GetFilterDirAsArray()
|
128 |
-
{
|
129 |
-
return array_map('DUP_Util::SafePath', explode(";", $this->FilterDirs, -1));
|
130 |
-
}
|
131 |
-
|
132 |
-
public function GetFilterExtsAsArray()
|
133 |
-
{
|
134 |
-
return explode(";", $this->FilterExts, -1);
|
135 |
-
}
|
136 |
-
|
137 |
-
/**
|
138 |
-
* Get the directory size recursively, but don't calc the snapshot directory, exclusion diretories
|
139 |
-
* @link http://msdn.microsoft.com/en-us/library/aa365247%28VS.85%29.aspx Windows filename restrictions
|
140 |
-
*/
|
141 |
-
public function Stats()
|
142 |
-
{
|
143 |
-
$this->createFilterInfo();
|
144 |
-
$this->getDirs();
|
145 |
-
$this->getFiles();
|
146 |
-
return $this;
|
147 |
-
}
|
148 |
-
|
149 |
-
//Build Filter Data
|
150 |
-
private function createFilterInfo()
|
151 |
-
{
|
152 |
-
//FILTER: INSTANCE ITEMS
|
153 |
-
//Add the items generated at create time
|
154 |
-
if ($this->FilterOn)
|
155 |
-
{
|
156 |
-
$this->FilterInfo->Dirs->Instance = array_map('DUP_Util::SafePath', explode(";", $this->FilterDirs, -1));
|
157 |
-
$this->FilterInfo->Exts->Instance = explode(";", $this->FilterExts, -1);
|
158 |
-
}
|
159 |
-
|
160 |
-
//FILTER: CORE ITMES
|
161 |
-
//Filters Duplicator free packages & All pro local directories
|
162 |
-
$this->FilterInfo->Dirs->Core[] = DUPLICATOR_SSDIR_PATH;
|
163 |
-
|
164 |
-
$this->FilterDirsAll = array_merge($this->FilterInfo->Dirs->Instance,
|
165 |
-
$this->FilterInfo->Dirs->Core);
|
166 |
-
|
167 |
-
$this->FilterExtsAll = array_merge($this->FilterInfo->Exts->Instance,
|
168 |
-
$this->FilterInfo->Exts->Core);
|
169 |
-
}
|
170 |
-
|
171 |
-
|
172 |
-
//Get All Directories then filter
|
173 |
-
private function getDirs()
|
174 |
-
{
|
175 |
-
|
176 |
-
$rootPath = DUP_Util::SafePath(rtrim(DUPLICATOR_WPROOTPATH, '//' ));
|
177 |
-
$this->Dirs = array();
|
178 |
-
|
179 |
-
//If the root directory is a filter then we will only need the root files
|
180 |
-
if (in_array($this->PackDir, $this->FilterDirsAll))
|
181 |
-
{
|
182 |
-
$this->Dirs[] = $this->PackDir;
|
183 |
-
}
|
184 |
-
else
|
185 |
-
{
|
186 |
-
$this->Dirs = $this->dirsToArray($rootPath, $this->FilterDirsAll);
|
187 |
-
$this->Dirs[] = $this->PackDir;
|
188 |
-
}
|
189 |
-
|
190 |
-
//Filter Directories
|
191 |
-
//Invalid test contains checks for: characters over 250, invlaid characters,
|
192 |
-
//empty string and directories ending with period (Windows incompatable)
|
193 |
-
foreach ($this->Dirs as $key => $val)
|
194 |
-
{
|
195 |
-
//WARNING: Find OS items that may have issues
|
196 |
-
// was commented out in pro
|
197 |
-
$name = basename($val);
|
198 |
-
|
199 |
-
$warn_test = strlen($val) > 250
|
200 |
-
|| preg_match('/(\/|\*|\?|\>|\<|\:|\\|\|)/', $name)
|
201 |
-
|| trim($name) == ""
|
202 |
-
|| (strrpos($name, '.') == strlen($name) - 1 && substr($name, -1) == '.')
|
203 |
-
|| preg_match('/[^\x20-\x7f]/', $name);
|
204 |
-
if ($warn_test)
|
205 |
-
{
|
206 |
-
$this->FilterInfo->Dirs->Warning[] = DUP_Encoding::toUTF8($val);
|
207 |
-
}
|
208 |
-
|
209 |
-
//UNREADABLE: Directory is unreadable flag it
|
210 |
-
if (! is_readable($this->Dirs[$key]))
|
211 |
-
{
|
212 |
-
unset($this->Dirs[$key]);
|
213 |
-
$this->FilterInfo->Dirs->Unreadable[] = $val;
|
214 |
-
$this->FilterDirsAll[] = $val;
|
215 |
-
}
|
216 |
-
}
|
217 |
-
}
|
218 |
-
|
219 |
-
//Get all files and filter out error prone subsets
|
220 |
-
private function getFiles()
|
221 |
-
{
|
222 |
-
foreach ($this->Dirs as $key => $val)
|
223 |
-
{
|
224 |
-
$files = DUP_Util::ListFiles($val);
|
225 |
-
foreach ($files as $filePath)
|
226 |
-
{
|
227 |
-
$fileName = basename($filePath);
|
228 |
-
if (!is_dir($filePath))
|
229 |
-
{
|
230 |
-
if (!in_array(@pathinfo($filePath, PATHINFO_EXTENSION), $this->FilterExtsAll))
|
231 |
-
{
|
232 |
-
//Unreadable
|
233 |
-
if (!is_readable($filePath))
|
234 |
-
{
|
235 |
-
$this->FilterInfo->Files->Unreadable[] = $filePath;
|
236 |
-
continue;
|
237 |
-
}
|
238 |
-
|
239 |
-
$fileSize = @filesize($filePath);
|
240 |
-
$fileSize = empty($fileSize) ? 0 : $fileSize;
|
241 |
-
$invalid_test = strlen($filePath) > 250 ||
|
242 |
-
preg_match('/(\/|\*|\?|\>|\<|\:|\\|\|)/', $fileName) ||
|
243 |
-
trim($fileName) == "";
|
244 |
-
|
245 |
-
if ($invalid_test || preg_match('/[^\x20-\x7f]/', $fileName))
|
246 |
-
{
|
247 |
-
$filePath = DUP_Encoding::toUTF8($filePath);
|
248 |
-
$this->FilterInfo->Files->Warning[] = $filePath;
|
249 |
-
}
|
250 |
-
$this->Size += $fileSize;
|
251 |
-
$this->Files[] = $filePath;
|
252 |
-
|
253 |
-
|
254 |
-
if ($fileSize > DUPLICATOR_SCAN_WARNFILESIZE)
|
255 |
-
{
|
256 |
-
$this->FilterInfo->Files->Size[] = $filePath . ' [' . DUP_Util::ByteSize($fileSize) . ']';
|
257 |
-
}
|
258 |
-
}
|
259 |
-
}
|
260 |
-
}
|
261 |
-
}
|
262 |
-
}
|
263 |
-
|
264 |
-
//Recursive function to get all Directories in a wp install
|
265 |
-
//Older PHP logic which is more stable on older version of PHP
|
266 |
-
//NOTE RecursiveIteratorIterator is problematic on some systems issues include:
|
267 |
-
// - error 'too many files open' for recursion
|
268 |
-
// - $file->getExtension() is not reliable as it silently fails at least in php 5.2.9
|
269 |
-
// - issues with when a file has a permission such as 705 and trying to get info (had to fallback to pathinfo)
|
270 |
-
// - basic conclusion wait on the SPL libs untill after php 5.4 is a requiremnt
|
271 |
-
// - since we are in a tight recursive loop lets remove the utiltiy call DUP_Util::SafePath("{$path}/{$file}") and
|
272 |
-
// squeeze out as much performance as we possible can
|
273 |
-
|
274 |
-
private function dirsToArray($path, $filterDirsAll)
|
275 |
-
{
|
276 |
-
$items = array();
|
277 |
-
$handle = @opendir($path);
|
278 |
-
if ($handle)
|
279 |
-
{
|
280 |
-
while (($file = readdir($handle)) !== false)
|
281 |
-
{
|
282 |
-
if ($file != '.' && $file != '..')
|
283 |
-
{
|
284 |
-
$fullPath = str_replace("\\", '/', "{$path}/{$file}");
|
285 |
-
|
286 |
-
if (is_dir($fullPath))
|
287 |
-
{
|
288 |
-
$addDir = true;
|
289 |
-
|
290 |
-
//Remove path filter directories
|
291 |
-
foreach ($filterDirsAll as $filterDir)
|
292 |
-
{
|
293 |
-
$trimmedFilterDir = rtrim($filterDir, '/');
|
294 |
-
|
295 |
-
if ($fullPath == $trimmedFilterDir || strstr($fullPath, $trimmedFilterDir . '/'))
|
296 |
-
{
|
297 |
-
$addDir = false;
|
298 |
-
break;
|
299 |
-
}
|
300 |
-
}
|
301 |
-
|
302 |
-
if($addDir)
|
303 |
-
{
|
304 |
-
$items = array_merge($items, $this->dirsToArray($fullPath, $filterDirsAll));
|
305 |
-
$items[] = $fullPath;
|
306 |
-
}
|
307 |
-
}
|
308 |
-
}
|
309 |
-
}
|
310 |
-
closedir($handle);
|
311 |
-
}
|
312 |
-
|
313 |
-
return $items;
|
314 |
-
}
|
315 |
-
}
|
316 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/package.archive.zip.php
DELETED
@@ -1,181 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
3 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.archive.php');
|
4 |
-
|
5 |
-
/**
|
6 |
-
* DUP_ZIP
|
7 |
-
* Creates a zip file using the built in PHP ZipArchive class
|
8 |
-
*/
|
9 |
-
class DUP_Zip extends DUP_Archive
|
10 |
-
{
|
11 |
-
//PRIVATE
|
12 |
-
private static $compressDir;
|
13 |
-
private static $countDirs = 0;
|
14 |
-
private static $countFiles = 0;
|
15 |
-
private static $sqlPath;
|
16 |
-
private static $zipPath;
|
17 |
-
private static $zipFileSize;
|
18 |
-
private static $zipArchive;
|
19 |
-
|
20 |
-
private static $limitItems = 0;
|
21 |
-
private static $networkFlush = false;
|
22 |
-
private static $scanReport;
|
23 |
-
|
24 |
-
/**
|
25 |
-
* CREATE
|
26 |
-
* Creates the zip file and adds the SQL file to the archive */
|
27 |
-
static public function Create(DUP_Archive $archive)
|
28 |
-
{
|
29 |
-
try
|
30 |
-
{
|
31 |
-
$timerAllStart = DUP_Util::GetMicrotime();
|
32 |
-
$package_zip_flush = DUP_Settings::Get('package_zip_flush');
|
33 |
-
|
34 |
-
self::$compressDir = rtrim(DUP_Util::SafePath($archive->PackDir), '/');
|
35 |
-
self::$sqlPath = DUP_Util::SafePath("{$archive->Package->StorePath}/{$archive->Package->Database->File}");
|
36 |
-
self::$zipPath = DUP_Util::SafePath("{$archive->Package->StorePath}/{$archive->File}");
|
37 |
-
self::$zipArchive = new ZipArchive();
|
38 |
-
self::$networkFlush = empty($package_zip_flush) ? false : $package_zip_flush;
|
39 |
-
|
40 |
-
$filterDirs = empty($archive->FilterDirs) ? 'not set' : $archive->FilterDirs;
|
41 |
-
$filterExts = empty($archive->FilterExts) ? 'not set' : $archive->FilterExts;
|
42 |
-
$filterOn = ($archive->FilterOn) ? 'ON' : 'OFF';
|
43 |
-
$filterDirsFormat = rtrim(str_replace(';', "\n ", $filterDirs));
|
44 |
-
$lastDirSuccess = self::$compressDir;
|
45 |
-
|
46 |
-
//LOAD SCAN REPORT
|
47 |
-
$json = file_get_contents(DUPLICATOR_SSDIR_PATH_TMP . "/{$archive->Package->NameHash}_scan.json");
|
48 |
-
self::$scanReport = json_decode($json);
|
49 |
-
|
50 |
-
DUP_Log::Info("\n********************************************************************************");
|
51 |
-
DUP_Log::Info("ARCHIVE (ZIP):");
|
52 |
-
DUP_Log::Info("********************************************************************************");
|
53 |
-
$isZipOpen = (self::$zipArchive->open(self::$zipPath, ZIPARCHIVE::CREATE) === TRUE);
|
54 |
-
if (! $isZipOpen){
|
55 |
-
DUP_Log::Error("Cannot open zip file with PHP ZipArchive.", "Path location [" . self::$zipPath . "]");
|
56 |
-
}
|
57 |
-
DUP_Log::Info("ARCHIVE DIR: " . self::$compressDir);
|
58 |
-
DUP_Log::Info("ARCHIVE FILE: " . basename(self::$zipPath));
|
59 |
-
DUP_Log::Info("FILTERS: *{$filterOn}*");
|
60 |
-
DUP_Log::Info("DIRS: {$filterDirsFormat}");
|
61 |
-
DUP_Log::Info("EXTS: {$filterExts}");
|
62 |
-
|
63 |
-
DUP_Log::Info("----------------------------------------");
|
64 |
-
DUP_Log::Info("COMPRESSING");
|
65 |
-
DUP_Log::Info("SIZE:\t" . self::$scanReport->ARC->Size);
|
66 |
-
DUP_Log::Info("STATS:\tDirs " . self::$scanReport->ARC->DirCount . " | Files " . self::$scanReport->ARC->FileCount);
|
67 |
-
|
68 |
-
//ADD SQL
|
69 |
-
$isSQLInZip = self::$zipArchive->addFile(self::$sqlPath, "database.sql");
|
70 |
-
if ($isSQLInZip) {
|
71 |
-
DUP_Log::Info("SQL ADDED: " . basename(self::$sqlPath));
|
72 |
-
} else {
|
73 |
-
DUP_Log::Error("Unable to add database.sql to archive.", "SQL File Path [" . self::$sqlath . "]");
|
74 |
-
}
|
75 |
-
self::$zipArchive->close();
|
76 |
-
self::$zipArchive->open(self::$zipPath, ZipArchive::CREATE);
|
77 |
-
|
78 |
-
//ZIP DIRECTORIES
|
79 |
-
$info = '';
|
80 |
-
foreach(self::$scanReport->ARC->Dirs as $dir)
|
81 |
-
{
|
82 |
-
if (is_readable($dir) && self::$zipArchive->addEmptyDir(ltrim(str_replace(self::$compressDir, '', $dir), '/')))
|
83 |
-
{
|
84 |
-
self::$countDirs++;
|
85 |
-
$lastDirSuccess = $dir;
|
86 |
-
}
|
87 |
-
else
|
88 |
-
{
|
89 |
-
//Don't warn when dirtory is the root path
|
90 |
-
if (strcmp($dir, rtrim(self::$compressDir, '/')) != 0) {
|
91 |
-
$dir_path = strlen($dir) ? "[{$dir}]" : "[Read Error] - last successful read was: [{$lastDirSuccess}]";
|
92 |
-
$info .= "DIR: {$dir_path}\n";
|
93 |
-
}
|
94 |
-
}
|
95 |
-
}
|
96 |
-
|
97 |
-
//LOG Unreadable DIR info
|
98 |
-
if (strlen($info))
|
99 |
-
{
|
100 |
-
DUP_Log::Info("\nWARNING: Unable to zip directories:");
|
101 |
-
DUP_Log::Info($info);
|
102 |
-
}
|
103 |
-
|
104 |
-
|
105 |
-
|
106 |
-
/* ZIP FILES: Network Flush
|
107 |
-
* This allows the process to not timeout on fcgi
|
108 |
-
* setups that need a response every X seconds */
|
109 |
-
$info = '';
|
110 |
-
if (self::$networkFlush)
|
111 |
-
{
|
112 |
-
foreach(self::$scanReport->ARC->Files as $file)
|
113 |
-
{
|
114 |
-
if (is_readable($file) && self::$zipArchive->addFile($file, ltrim(str_replace(self::$compressDir, '', $file), '/')))
|
115 |
-
{
|
116 |
-
self::$limitItems++;
|
117 |
-
self::$countFiles++;
|
118 |
-
}
|
119 |
-
else
|
120 |
-
{
|
121 |
-
$info .= "FILE: [{$file}]\n";
|
122 |
-
}
|
123 |
-
//Trigger a flush to the web server after so many files have been loaded.
|
124 |
-
if(self::$limitItems > DUPLICATOR_ZIP_FLUSH_TRIGGER)
|
125 |
-
{
|
126 |
-
$sumItems = (self::$countDirs + self::$countFiles);
|
127 |
-
self::$zipArchive->close();
|
128 |
-
self::$zipArchive->open(self::$zipPath);
|
129 |
-
self::$limitItems = 0;
|
130 |
-
DUP_Util::FcgiFlush();
|
131 |
-
DUP_Log::Info("Items archived [{$sumItems}] flushing response.");
|
132 |
-
}
|
133 |
-
}
|
134 |
-
}
|
135 |
-
//Normal
|
136 |
-
else
|
137 |
-
{
|
138 |
-
foreach(self::$scanReport->ARC->Files as $file)
|
139 |
-
{
|
140 |
-
if (is_readable($file) && self::$zipArchive->addFile($file, ltrim(str_replace(self::$compressDir, '', $file), '/'))) {
|
141 |
-
self::$countFiles++;
|
142 |
-
} else {
|
143 |
-
$info .= "FILE: [{$file}]\n";
|
144 |
-
}
|
145 |
-
}
|
146 |
-
}
|
147 |
-
|
148 |
-
//LOG Unreadable FILE info
|
149 |
-
if (strlen($info))
|
150 |
-
{
|
151 |
-
DUP_Log::Info("\nWARNING: Unable to zip files:");
|
152 |
-
DUP_Log::Info($info);
|
153 |
-
unset($info);
|
154 |
-
}
|
155 |
-
|
156 |
-
DUP_Log::Info(print_r(self::$zipArchive, true));
|
157 |
-
|
158 |
-
//--------------------------------
|
159 |
-
//LOG FINAL RESULTS
|
160 |
-
DUP_Util::FcgiFlush();
|
161 |
-
$zipCloseResult = self::$zipArchive->close();
|
162 |
-
($zipCloseResult)
|
163 |
-
? DUP_Log::Info("COMPRESSION RESULT: '{$zipCloseResult}'")
|
164 |
-
: DUP_Log::Error("ZipArchive close failure.", "This hosted server may have a disk quota limit.\nCheck to make sure this archive file can be stored.");
|
165 |
-
|
166 |
-
$timerAllEnd = DUP_Util::GetMicrotime();
|
167 |
-
$timerAllSum = DUP_Util::ElapsedTime($timerAllEnd, $timerAllStart);
|
168 |
-
|
169 |
-
|
170 |
-
self::$zipFileSize = @filesize(self::$zipPath);
|
171 |
-
DUP_Log::Info("COMPRESSED SIZE: " . DUP_Util::ByteSize(self::$zipFileSize));
|
172 |
-
DUP_Log::Info("ARCHIVE RUNTIME: {$timerAllSum}");
|
173 |
-
DUP_Log::Info("MEMORY STACK: " . DUP_Server::GetPHPMemory());
|
174 |
-
}
|
175 |
-
catch (Exception $e) {
|
176 |
-
DUP_Log::Error("Runtime error in package.archive.zip.php constructor.", "Exception: {$e}");
|
177 |
-
}
|
178 |
-
}
|
179 |
-
|
180 |
-
}
|
181 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/package.database.php
DELETED
@@ -1,416 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
class DUP_Database {
|
5 |
-
|
6 |
-
//PUBLIC
|
7 |
-
public $Type = 'MySQL';
|
8 |
-
public $Size;
|
9 |
-
public $File;
|
10 |
-
public $Path;
|
11 |
-
public $FilterTables;
|
12 |
-
public $FilterOn;
|
13 |
-
public $Name;
|
14 |
-
public $Compatible;
|
15 |
-
|
16 |
-
//PROTECTED
|
17 |
-
protected $Package;
|
18 |
-
|
19 |
-
//PRIVATE
|
20 |
-
private $dbStorePath;
|
21 |
-
private $EOFMarker;
|
22 |
-
private $networkFlush;
|
23 |
-
|
24 |
-
//CONSTRUCTOR
|
25 |
-
function __construct($package) {
|
26 |
-
$this->Package = $package;
|
27 |
-
$this->EOFMarker = "";
|
28 |
-
$package_zip_flush = DUP_Settings::Get('package_zip_flush');
|
29 |
-
$this->networkFlush = empty($package_zip_flush) ? false : $package_zip_flush;
|
30 |
-
}
|
31 |
-
|
32 |
-
public function Build($package) {
|
33 |
-
try {
|
34 |
-
|
35 |
-
$this->Package = $package;
|
36 |
-
|
37 |
-
$time_start = DUP_Util::GetMicrotime();
|
38 |
-
$this->Package->SetStatus(DUP_PackageStatus::DBSTART);
|
39 |
-
$this->dbStorePath = "{$this->Package->StorePath}/{$this->File}";
|
40 |
-
|
41 |
-
$package_mysqldump = DUP_Settings::Get('package_mysqldump');
|
42 |
-
$package_phpdump_qrylimit = DUP_Settings::Get('package_phpdump_qrylimit');
|
43 |
-
|
44 |
-
$mysqlDumpPath = self::GetMySqlDumpPath();
|
45 |
-
$mode = ($mysqlDumpPath && $package_mysqldump) ? 'MYSQLDUMP' : 'PHP';
|
46 |
-
$reserved_db_filepath = DUPLICATOR_WPROOTPATH . 'database.sql';
|
47 |
-
|
48 |
-
|
49 |
-
$log = "\n********************************************************************************\n";
|
50 |
-
$log .= "DATABASE:\n";
|
51 |
-
$log .= "********************************************************************************\n";
|
52 |
-
$log .= "BUILD MODE: {$mode}";
|
53 |
-
$log .= ($mode == 'PHP') ? "(query limit - {$package_phpdump_qrylimit})\n" : "\n";
|
54 |
-
$log .= "MYSQLTIMEOUT: " . DUPLICATOR_DB_MAX_TIME . "\n";
|
55 |
-
$log .= "MYSQLDUMP: ";
|
56 |
-
$log .= ($mysqlDumpPath) ? "Is Supported" : "Not Supported";
|
57 |
-
DUP_Log::Info($log);
|
58 |
-
$log = null;
|
59 |
-
|
60 |
-
//Reserved file found
|
61 |
-
if (file_exists($reserved_db_filepath)) {
|
62 |
-
DUP_Log::Error("Reserverd SQL file detected",
|
63 |
-
"The file database.sql was found at [{$reserved_db_filepath}].\n"
|
64 |
-
. "\tPlease remove/rename this file to continue with the package creation.");
|
65 |
-
}
|
66 |
-
|
67 |
-
switch ($mode) {
|
68 |
-
case 'MYSQLDUMP': $this->mysqlDump($mysqlDumpPath); break;
|
69 |
-
case 'PHP' : $this->phpDump(); break;
|
70 |
-
}
|
71 |
-
|
72 |
-
DUP_Log::Info("SQL CREATED: {$this->File}");
|
73 |
-
$time_end = DUP_Util::GetMicrotime();
|
74 |
-
$time_sum = DUP_Util::ElapsedTime($time_end, $time_start);
|
75 |
-
|
76 |
-
//File below 10k will be incomplete
|
77 |
-
$sql_file_size = filesize($this->dbStorePath);
|
78 |
-
DUP_Log::Info("SQL FILE SIZE: " . DUP_Util::ByteSize($sql_file_size) . " ({$sql_file_size})");
|
79 |
-
if ($sql_file_size < 10000) {
|
80 |
-
DUP_Log::Error("SQL file size too low.", "File does not look complete. Check permission on file and parent directory at [{$this->dbStorePath}]");
|
81 |
-
}
|
82 |
-
|
83 |
-
DUP_Log::Info("SQL FILE TIME: " . date("Y-m-d H:i:s"));
|
84 |
-
DUP_Log::Info("SQL RUNTIME: {$time_sum}");
|
85 |
-
|
86 |
-
$this->Size = @filesize($this->dbStorePath);
|
87 |
-
$this->Package->SetStatus(DUP_PackageStatus::DBDONE);
|
88 |
-
|
89 |
-
} catch (Exception $e) {
|
90 |
-
DUP_Log::Error("Runtime error in DUP_Database::Build","Exception: {$e}");
|
91 |
-
}
|
92 |
-
}
|
93 |
-
|
94 |
-
/**
|
95 |
-
* Get the database stats
|
96 |
-
*/
|
97 |
-
public function Stats() {
|
98 |
-
|
99 |
-
global $wpdb;
|
100 |
-
$filterTables = isset($this->FilterTables) ? explode(',', $this->FilterTables) : null;
|
101 |
-
$tblCount = 0;
|
102 |
-
|
103 |
-
$tables = $wpdb->get_results("SHOW TABLE STATUS", ARRAY_A);
|
104 |
-
$info = array();
|
105 |
-
$info['Status']['Success'] = is_null($tables) ? false : true;
|
106 |
-
//DB_Case for the database name is never checked on
|
107 |
-
$info['Status']['DB_Case'] = 'Good';
|
108 |
-
$info['Status']['DB_Rows'] = 'Good';
|
109 |
-
$info['Status']['DB_Size'] = 'Good';
|
110 |
-
$info['Status']['TBL_Case'] = 'Good';
|
111 |
-
$info['Status']['TBL_Rows'] = 'Good';
|
112 |
-
$info['Status']['TBL_Size'] = 'Good';
|
113 |
-
|
114 |
-
$info['Size'] = 0;
|
115 |
-
$info['Rows'] = 0;
|
116 |
-
$info['TableCount'] = 0;
|
117 |
-
$info['TableList'] = array();
|
118 |
-
$tblCaseFound = 0;
|
119 |
-
$tblRowsFound = 0;
|
120 |
-
$tblSizeFound = 0;
|
121 |
-
|
122 |
-
//Grab Table Stats
|
123 |
-
foreach ($tables as $table)
|
124 |
-
{
|
125 |
-
$name = $table["Name"];
|
126 |
-
if ($this->FilterOn && is_array($filterTables))
|
127 |
-
{
|
128 |
-
if (in_array($name, $filterTables)) {
|
129 |
-
continue;
|
130 |
-
}
|
131 |
-
}
|
132 |
-
|
133 |
-
$size = ($table["Data_length"] + $table["Index_length"]);
|
134 |
-
$rows = empty($table["Rows"]) ? '0' : $table["Rows"];
|
135 |
-
|
136 |
-
$info['Size'] += $size;
|
137 |
-
$info['Rows'] += ($table["Rows"]);
|
138 |
-
$info['TableList'][$name]['Case'] = preg_match('/[A-Z]/', $name) ? 1 : 0;
|
139 |
-
$info['TableList'][$name]['Rows'] = number_format($rows);
|
140 |
-
$info['TableList'][$name]['Size'] = DUP_Util::ByteSize($size);
|
141 |
-
$tblCount++;
|
142 |
-
|
143 |
-
//Table Uppercase
|
144 |
-
if ($info['TableList'][$name]['Case']) {
|
145 |
-
if (! $tblCaseFound) {
|
146 |
-
$tblCaseFound = 1;
|
147 |
-
}
|
148 |
-
}
|
149 |
-
|
150 |
-
//Table Row Count
|
151 |
-
if ($rows > DUPLICATOR_SCAN_DB_TBL_ROWS) {
|
152 |
-
if (! $tblRowsFound) {
|
153 |
-
$tblRowsFound = 1;
|
154 |
-
}
|
155 |
-
}
|
156 |
-
|
157 |
-
//Table Size
|
158 |
-
if ($size > DUPLICATOR_SCAN_DB_TBL_SIZE) {
|
159 |
-
if (! $tblSizeFound) {
|
160 |
-
$tblSizeFound = 1;
|
161 |
-
}
|
162 |
-
}
|
163 |
-
}
|
164 |
-
|
165 |
-
$info['Status']['DB_Case'] = preg_match('/[A-Z]/', $wpdb->dbname) ? 'Warn' : 'Good';
|
166 |
-
$info['Status']['DB_Rows'] = ($info['Rows'] > DUPLICATOR_SCAN_DB_ALL_ROWS) ? 'Warn' : 'Good';
|
167 |
-
$info['Status']['DB_Size'] = ($info['Size'] > DUPLICATOR_SCAN_DB_ALL_SIZE) ? 'Warn' : 'Good';
|
168 |
-
|
169 |
-
|
170 |
-
$info['Status']['TBL_Case'] = ($tblCaseFound) ? 'Warn' : 'Good';
|
171 |
-
$info['Status']['TBL_Rows'] = ($tblRowsFound) ? 'Warn' : 'Good';
|
172 |
-
$info['Status']['TBL_Size'] = ($tblSizeFound) ? 'Warn' : 'Good';
|
173 |
-
|
174 |
-
$info['Size'] = DUP_Util::ByteSize($info['Size']) or "unknown";
|
175 |
-
$info['Rows'] = number_format($info['Rows']) or "unknown";
|
176 |
-
$info['TableList'] = $info['TableList'] or "unknown";
|
177 |
-
$info['TableCount'] = $tblCount;
|
178 |
-
|
179 |
-
return $info;
|
180 |
-
}
|
181 |
-
|
182 |
-
/**
|
183 |
-
* Returns the mysqldump path if the server is enabled to execute it
|
184 |
-
* @return boolean|string
|
185 |
-
*/
|
186 |
-
public static function GetMySqlDumpPath() {
|
187 |
-
|
188 |
-
//Is shell_exec possible
|
189 |
-
if (! DUP_Util::IsShellExecAvailable()) {
|
190 |
-
return false;
|
191 |
-
}
|
192 |
-
|
193 |
-
$custom_mysqldump_path = DUP_Settings::Get('package_mysqldump_path');
|
194 |
-
$custom_mysqldump_path = (strlen($custom_mysqldump_path)) ? $custom_mysqldump_path : '';
|
195 |
-
|
196 |
-
//Common Windows Paths
|
197 |
-
if (DUP_Util::IsOSWindows()) {
|
198 |
-
$paths = array(
|
199 |
-
$custom_mysqldump_path,
|
200 |
-
'C:/xampp/mysql/bin/mysqldump.exe',
|
201 |
-
'C:/Program Files/xampp/mysql/bin/mysqldump',
|
202 |
-
'C:/Program Files/MySQL/MySQL Server 6.0/bin/mysqldump',
|
203 |
-
'C:/Program Files/MySQL/MySQL Server 5.5/bin/mysqldump',
|
204 |
-
'C:/Program Files/MySQL/MySQL Server 5.4/bin/mysqldump',
|
205 |
-
'C:/Program Files/MySQL/MySQL Server 5.1/bin/mysqldump',
|
206 |
-
'C:/Program Files/MySQL/MySQL Server 5.0/bin/mysqldump',
|
207 |
-
);
|
208 |
-
|
209 |
-
//Common Linux Paths
|
210 |
-
} else {
|
211 |
-
$path1 = '';
|
212 |
-
$path2 = '';
|
213 |
-
$mysqldump = `which mysqldump`;
|
214 |
-
if (@is_executable($mysqldump))
|
215 |
-
$path1 = (!empty($mysqldump)) ? $mysqldump : '';
|
216 |
-
|
217 |
-
$mysqldump = dirname(`which mysql`) . "/mysqldump";
|
218 |
-
if (@is_executable($mysqldump))
|
219 |
-
$path2 = (!empty($mysqldump)) ? $mysqldump : '';
|
220 |
-
|
221 |
-
$paths = array(
|
222 |
-
$custom_mysqldump_path,
|
223 |
-
$path1,
|
224 |
-
$path2,
|
225 |
-
'/usr/local/bin/mysqldump',
|
226 |
-
'/usr/local/mysql/bin/mysqldump',
|
227 |
-
'/usr/mysql/bin/mysqldump',
|
228 |
-
'/usr/bin/mysqldump',
|
229 |
-
'/opt/local/lib/mysql6/bin/mysqldump',
|
230 |
-
'/opt/local/lib/mysql5/bin/mysqldump',
|
231 |
-
'/opt/local/lib/mysql4/bin/mysqldump',
|
232 |
-
);
|
233 |
-
}
|
234 |
-
|
235 |
-
// Find the one which works
|
236 |
-
foreach ( $paths as $path ) {
|
237 |
-
if ( @is_executable($path))
|
238 |
-
return $path;
|
239 |
-
}
|
240 |
-
|
241 |
-
return false;
|
242 |
-
}
|
243 |
-
|
244 |
-
|
245 |
-
private function mysqlDump($exePath) {
|
246 |
-
|
247 |
-
global $wpdb;
|
248 |
-
|
249 |
-
$host = explode(':', DB_HOST);
|
250 |
-
$host = reset($host);
|
251 |
-
$port = strpos(DB_HOST, ':') ? end(explode( ':', DB_HOST ) ) : '';
|
252 |
-
$name = DB_NAME;
|
253 |
-
$mysqlcompat_on = isset($this->Compatible) && strlen($this->Compatible);
|
254 |
-
|
255 |
-
//Build command
|
256 |
-
$cmd = escapeshellarg($exePath);
|
257 |
-
$cmd .= ' --no-create-db';
|
258 |
-
$cmd .= ' --single-transaction';
|
259 |
-
$cmd .= ' --hex-blob';
|
260 |
-
$cmd .= ' --skip-add-drop-table';
|
261 |
-
|
262 |
-
//Compatibility mode
|
263 |
-
if ($mysqlcompat_on) {
|
264 |
-
DUP_Log::Info("COMPATIBLE: [{$this->Compatible}]");
|
265 |
-
$cmd .= " --compatible={$this->Compatible}";
|
266 |
-
}
|
267 |
-
|
268 |
-
//Filter tables
|
269 |
-
$tables = $wpdb->get_col('SHOW TABLES');
|
270 |
-
$filterTables = isset($this->FilterTables) ? explode(',', $this->FilterTables) : null;
|
271 |
-
$tblAllCount = count($tables);
|
272 |
-
$tblFilterOn = ($this->FilterOn) ? 'ON' : 'OFF';
|
273 |
-
|
274 |
-
if (is_array($filterTables) && $this->FilterOn) {
|
275 |
-
foreach ($tables as $key => $val) {
|
276 |
-
if (in_array($tables[$key], $filterTables)) {
|
277 |
-
$cmd .= " --ignore-table={$name}.{$tables[$key]} ";
|
278 |
-
unset($tables[$key]);
|
279 |
-
}
|
280 |
-
}
|
281 |
-
}
|
282 |
-
|
283 |
-
$cmd .= ' -u ' . escapeshellarg(DB_USER);
|
284 |
-
$cmd .= (DB_PASSWORD) ?
|
285 |
-
' -p' . escapeshellarg(DB_PASSWORD) : '';
|
286 |
-
$cmd .= ' -h ' . escapeshellarg($host);
|
287 |
-
$cmd .= ( ! empty($port) && is_numeric($port) ) ?
|
288 |
-
' -P ' . $port : '';
|
289 |
-
$cmd .= ' -r ' . escapeshellarg($this->dbStorePath);
|
290 |
-
$cmd .= ' ' . escapeshellarg(DB_NAME);
|
291 |
-
$cmd .= ' 2>&1';
|
292 |
-
|
293 |
-
$output = shell_exec($cmd);
|
294 |
-
|
295 |
-
// Password bug > 5.6 (@see http://bugs.mysql.com/bug.php?id=66546)
|
296 |
-
if ( trim( $output ) === 'Warning: Using a password on the command line interface can be insecure.' ) {
|
297 |
-
$output = '';
|
298 |
-
}
|
299 |
-
$output = (strlen($output)) ? $output : "Ran from {$exePath}";
|
300 |
-
|
301 |
-
$tblCreateCount = count($tables);
|
302 |
-
$tblFilterCount = $tblAllCount - $tblCreateCount;
|
303 |
-
|
304 |
-
//DEBUG
|
305 |
-
//DUP_Log::Info("COMMAND: {$cmd}");
|
306 |
-
DUP_Log::Info("FILTERED: [{$this->FilterTables}]");
|
307 |
-
DUP_Log::Info("RESPONSE: {$output}");
|
308 |
-
DUP_Log::Info("TABLES: total:{$tblAllCount} | filtered:{$tblFilterCount} | create:{$tblCreateCount}");
|
309 |
-
|
310 |
-
$sql_footer = "\n\n/* Duplicator WordPress Timestamp: " . date("Y-m-d H:i:s") . "*/\n";
|
311 |
-
$sql_footer .= "/* " . DUPLICATOR_DB_EOF_MARKER . " */\n";
|
312 |
-
file_put_contents($this->dbStorePath, $sql_footer, FILE_APPEND);
|
313 |
-
|
314 |
-
return ($output) ? false : true;
|
315 |
-
}
|
316 |
-
|
317 |
-
|
318 |
-
private function phpDump() {
|
319 |
-
|
320 |
-
global $wpdb;
|
321 |
-
|
322 |
-
$wpdb->query("SET session wait_timeout = " . DUPLICATOR_DB_MAX_TIME);
|
323 |
-
$handle = fopen($this->dbStorePath, 'w+');
|
324 |
-
$tables = $wpdb->get_col('SHOW TABLES');
|
325 |
-
|
326 |
-
$filterTables = isset($this->FilterTables) ? explode(',', $this->FilterTables) : null;
|
327 |
-
$tblAllCount = count($tables);
|
328 |
-
$tblFilterOn = ($this->FilterOn) ? 'ON' : 'OFF';
|
329 |
-
$qryLimit = DUP_Settings::Get('package_phpdump_qrylimit');
|
330 |
-
|
331 |
-
if (is_array($filterTables) && $this->FilterOn) {
|
332 |
-
foreach ($tables as $key => $val) {
|
333 |
-
if (in_array($tables[$key], $filterTables)) {
|
334 |
-
unset($tables[$key]);
|
335 |
-
}
|
336 |
-
}
|
337 |
-
}
|
338 |
-
$tblCreateCount = count($tables);
|
339 |
-
$tblFilterCount = $tblAllCount - $tblCreateCount;
|
340 |
-
|
341 |
-
DUP_Log::Info("TABLES: total:{$tblAllCount} | filtered:{$tblFilterCount} | create:{$tblCreateCount}");
|
342 |
-
DUP_Log::Info("FILTERED: [{$this->FilterTables}]");
|
343 |
-
|
344 |
-
$sql_header = "/* DUPLICATOR MYSQL SCRIPT CREATED ON : " . @date("Y-m-d H:i:s") . " */\n\n";
|
345 |
-
$sql_header .= "SET FOREIGN_KEY_CHECKS = 0;\n\n";
|
346 |
-
fwrite($handle, $sql_header);
|
347 |
-
|
348 |
-
//BUILD CREATES:
|
349 |
-
//All creates must be created before inserts do to foreign key constraints
|
350 |
-
foreach ($tables as $table) {
|
351 |
-
//$sql_del = ($GLOBALS['duplicator_opts']['dbadd_drop']) ? "DROP TABLE IF EXISTS {$table};\n\n" : "";
|
352 |
-
//@fwrite($handle, $sql_del);
|
353 |
-
$create = $wpdb->get_row("SHOW CREATE TABLE `{$table}`", ARRAY_N);
|
354 |
-
@fwrite($handle, "{$create[1]};\n\n");
|
355 |
-
}
|
356 |
-
|
357 |
-
//BUILD INSERTS:
|
358 |
-
//Create Insert in 100 row increments to better handle memory
|
359 |
-
foreach ($tables as $table) {
|
360 |
-
|
361 |
-
$row_count = $wpdb->get_var("SELECT Count(*) FROM `{$table}`");
|
362 |
-
//DUP_Log::Info("{$table} ({$row_count})");
|
363 |
-
|
364 |
-
if ($row_count > $qryLimit) {
|
365 |
-
$row_count = ceil($row_count / $qryLimit);
|
366 |
-
} else if ($row_count > 0) {
|
367 |
-
$row_count = 1;
|
368 |
-
}
|
369 |
-
|
370 |
-
if ($row_count >= 1) {
|
371 |
-
fwrite($handle, "\n/* INSERT TABLE DATA: {$table} */\n");
|
372 |
-
}
|
373 |
-
|
374 |
-
for ($i = 0; $i < $row_count; $i++) {
|
375 |
-
$sql = "";
|
376 |
-
$limit = $i * $qryLimit;
|
377 |
-
$query = "SELECT * FROM `{$table}` LIMIT {$limit}, {$qryLimit}";
|
378 |
-
$rows = $wpdb->get_results($query, ARRAY_A);
|
379 |
-
if (is_array($rows)) {
|
380 |
-
foreach ($rows as $row) {
|
381 |
-
$sql .= "INSERT INTO `{$table}` VALUES(";
|
382 |
-
$num_values = count($row);
|
383 |
-
$num_counter = 1;
|
384 |
-
foreach ($row as $value) {
|
385 |
-
if ( is_null( $value ) || ! isset( $value ) ) {
|
386 |
-
($num_values == $num_counter) ? $sql .= 'NULL' : $sql .= 'NULL, ';
|
387 |
-
} else {
|
388 |
-
($num_values == $num_counter)
|
389 |
-
? $sql .= '"' . @esc_sql($value) . '"'
|
390 |
-
: $sql .= '"' . @esc_sql($value) . '", ';
|
391 |
-
}
|
392 |
-
$num_counter++;
|
393 |
-
}
|
394 |
-
$sql .= ");\n";
|
395 |
-
}
|
396 |
-
fwrite($handle, $sql);
|
397 |
-
}
|
398 |
-
}
|
399 |
-
|
400 |
-
//Flush buffer if enabled
|
401 |
-
if ($this->networkFlush) {
|
402 |
-
DUP_Util::FcgiFlush();
|
403 |
-
}
|
404 |
-
$sql = null;
|
405 |
-
$rows = null;
|
406 |
-
}
|
407 |
-
|
408 |
-
$sql_footer = "\nSET FOREIGN_KEY_CHECKS = 1; \n\n";
|
409 |
-
$sql_footer .= "/* Duplicator WordPress Timestamp: " . date("Y-m-d H:i:s") . "*/\n";
|
410 |
-
$sql_footer .= "/* " . DUPLICATOR_DB_EOF_MARKER . " */\n";
|
411 |
-
fwrite($handle, $sql_footer);
|
412 |
-
$wpdb->flush();
|
413 |
-
fclose($handle);
|
414 |
-
}
|
415 |
-
}
|
416 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/package.installer.php
DELETED
@@ -1,203 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
4 |
-
|
5 |
-
class DUP_Installer {
|
6 |
-
|
7 |
-
//PUBLIC
|
8 |
-
public $File;
|
9 |
-
public $Size = 0;
|
10 |
-
public $OptsDBHost;
|
11 |
-
public $OptsDBPort;
|
12 |
-
public $OptsDBName;
|
13 |
-
public $OptsDBUser;
|
14 |
-
public $OptsSSLAdmin;
|
15 |
-
public $OptsSSLLogin;
|
16 |
-
public $OptsCacheWP;
|
17 |
-
public $OptsCachePath;
|
18 |
-
public $OptsURLNew;
|
19 |
-
|
20 |
-
//PROTECTED
|
21 |
-
protected $Package;
|
22 |
-
|
23 |
-
//CONSTRUCTOR
|
24 |
-
function __construct($package) {
|
25 |
-
$this->Package = $package;
|
26 |
-
}
|
27 |
-
|
28 |
-
public function Build($package) {
|
29 |
-
|
30 |
-
$this->Package = $package;
|
31 |
-
|
32 |
-
DUP_Log::Info("\n********************************************************************************");
|
33 |
-
DUP_Log::Info("MAKE INSTALLER:");
|
34 |
-
DUP_Log::Info("********************************************************************************");
|
35 |
-
DUP_Log::Info("Build Start");
|
36 |
-
|
37 |
-
$template_uniqid = uniqid('') . '_' . time();
|
38 |
-
$template_path = DUP_Util::SafePath(DUPLICATOR_SSDIR_PATH_TMP . "/installer.template_{$template_uniqid}.php");
|
39 |
-
$main_path = DUP_Util::SafePath(DUPLICATOR_PLUGIN_PATH . 'installer/build/main.installer.php');
|
40 |
-
@chmod($template_path, 0777);
|
41 |
-
@chmod($main_path, 0777);
|
42 |
-
|
43 |
-
@touch($template_path);
|
44 |
-
$main_data = file_get_contents("{$main_path}");
|
45 |
-
$template_result = file_put_contents($template_path, $main_data);
|
46 |
-
if ($main_data === false || $template_result == false) {
|
47 |
-
$err_info ="These files may have permission issues. Please validate that PHP has read/write access.\n";
|
48 |
-
$err_info .= "Main Installer: '{$main_path}' \nTemplate Installer: '$template_path'";
|
49 |
-
DUP_Log::Error("Install builder failed to generate files.", "{$err_info}");
|
50 |
-
}
|
51 |
-
|
52 |
-
$embeded_files = array(
|
53 |
-
"assets/inc.libs.css.php" => "@@INC.LIBS.CSS.PHP@@",
|
54 |
-
"assets/inc.css.php" => "@@INC.CSS.PHP@@",
|
55 |
-
"assets/inc.libs.js.php" => "@@INC.LIBS.JS.PHP@@",
|
56 |
-
"assets/inc.js.php" => "@@INC.JS.PHP@@",
|
57 |
-
"classes/class.logging.php" => "@@CLASS.LOGGING.PHP@@",
|
58 |
-
"classes/class.utils.php" => "@@CLASS.UTILS.PHP@@",
|
59 |
-
"classes/class.conf.wp.php" => "@@CLASS.CONF.WP.PHP@@",
|
60 |
-
"classes/class.conf.srv.php" => "@@CLASS.CONF.SRV.PHP@@",
|
61 |
-
"classes/class.serializer.php" => "@@CLASS.SERIALIZER.PHP@@",
|
62 |
-
"ajax.step1.php" => "@@AJAX.STEP1.PHP@@",
|
63 |
-
"ajax.step2.php" => "@@AJAX.STEP2.PHP@@",
|
64 |
-
"view.step1.php" => "@@VIEW.STEP1.PHP@@",
|
65 |
-
"view.step2.php" => "@@VIEW.STEP2.PHP@@",
|
66 |
-
"view.step3.php" => "@@VIEW.STEP3.PHP@@",
|
67 |
-
"view.help.php" => "@@VIEW.HELP.PHP@@",);
|
68 |
-
|
69 |
-
foreach ($embeded_files as $name => $token) {
|
70 |
-
$file_path = DUPLICATOR_PLUGIN_PATH . "installer/build/{$name}";
|
71 |
-
@chmod($file_path, 0777);
|
72 |
-
|
73 |
-
$search_data = @file_get_contents($template_path);
|
74 |
-
$insert_data = @file_get_contents($file_path);
|
75 |
-
file_put_contents($template_path, str_replace("${token}", "{$insert_data}", $search_data));
|
76 |
-
if ($search_data === false || $insert_data == false) {
|
77 |
-
DUP_Log::Error("Installer generation failed at {$token}.");
|
78 |
-
}
|
79 |
-
@chmod($file_path, 0644);
|
80 |
-
}
|
81 |
-
|
82 |
-
@chmod($template_path, 0644);
|
83 |
-
@chmod($main_path, 0644);
|
84 |
-
|
85 |
-
DUP_Log::Info("Build Finished");
|
86 |
-
$this->createFromTemplate($template_path);
|
87 |
-
$storePath = "{$this->Package->StorePath}/{$this->File}";
|
88 |
-
$this->Size = @filesize($storePath);
|
89 |
-
$this->addBackup();
|
90 |
-
|
91 |
-
}
|
92 |
-
|
93 |
-
|
94 |
-
/**
|
95 |
-
* createZipBackup
|
96 |
-
* Puts an installer zip file in the archive for backup purposes.
|
97 |
-
*/
|
98 |
-
private function addBackup() {
|
99 |
-
|
100 |
-
$zipPath = DUP_Util::SafePath("{$this->Package->StorePath}/{$this->Package->Archive->File}");
|
101 |
-
$installer = DUP_Util::SafePath(DUPLICATOR_SSDIR_PATH_TMP) . "/{$this->Package->NameHash}_installer.php";
|
102 |
-
|
103 |
-
$zipArchive = new ZipArchive();
|
104 |
-
if ($zipArchive->open($zipPath, ZIPARCHIVE::CREATE) === TRUE) {
|
105 |
-
if ($zipArchive->addFile($installer, "installer-backup.php")) {
|
106 |
-
DUP_Log::Info("Added to archive");
|
107 |
-
} else {
|
108 |
-
DUP_Log::Info("Unable to add installer-backup.php to archive.", "Installer File Path [{$installer}]");
|
109 |
-
}
|
110 |
-
$zipArchive->close();
|
111 |
-
}
|
112 |
-
}
|
113 |
-
|
114 |
-
/**
|
115 |
-
* createFromTemplate
|
116 |
-
* Generates the final installer file from the template file
|
117 |
-
*/
|
118 |
-
private function createFromTemplate($template) {
|
119 |
-
|
120 |
-
global $wpdb;
|
121 |
-
|
122 |
-
DUP_Log::Info("Preping for use");
|
123 |
-
$installer = DUP_Util::SafePath(DUPLICATOR_SSDIR_PATH_TMP) . "/{$this->Package->NameHash}_installer.php";
|
124 |
-
|
125 |
-
//Option values to delete at install time
|
126 |
-
$deleteOpts = $GLOBALS['DUPLICATOR_OPTS_DELETE'];
|
127 |
-
|
128 |
-
$replace_items = Array(
|
129 |
-
//COMPARE VALUES
|
130 |
-
"fwrite_created" => $this->Package->Created,
|
131 |
-
"fwrite_version_dup" => DUPLICATOR_VERSION,
|
132 |
-
"fwrite_version_wp" => $this->Package->VersionWP,
|
133 |
-
"fwrite_version_db" => $this->Package->VersionDB,
|
134 |
-
"fwrite_version_php" => $this->Package->VersionPHP,
|
135 |
-
"fwrite_version_os" => $this->Package->VersionOS,
|
136 |
-
//GENERAL
|
137 |
-
"fwrite_url_old" => get_option('siteurl'),
|
138 |
-
"fwrite_package_name" => "{$this->Package->NameHash}_archive.zip",
|
139 |
-
"fwrite_package_notes" => $this->Package->Notes,
|
140 |
-
"fwrite_secure_name" => $this->Package->NameHash,
|
141 |
-
"fwrite_url_new" => $this->Package->Installer->OptsURLNew,
|
142 |
-
"fwrite_dbhost" => $this->Package->Installer->OptsDBHost,
|
143 |
-
"fwrite_dbport" => $this->Package->Installer->OptsDBPort,
|
144 |
-
"fwrite_dbname" => $this->Package->Installer->OptsDBName,
|
145 |
-
"fwrite_dbuser" => $this->Package->Installer->OptsDBUser,
|
146 |
-
"fwrite_dbpass" => '',
|
147 |
-
"fwrite_ssl_admin" => $this->Package->Installer->OptsSSLAdmin,
|
148 |
-
"fwrite_ssl_login" => $this->Package->Installer->OptsSSLLogin,
|
149 |
-
"fwrite_cache_wp" => $this->Package->Installer->OptsCacheWP,
|
150 |
-
"fwrite_cache_path" => $this->Package->Installer->OptsCachePath,
|
151 |
-
"fwrite_wp_tableprefix" => $wpdb->prefix,
|
152 |
-
"fwrite_opts_delete" => json_encode($deleteOpts),
|
153 |
-
"fwrite_blogname" => esc_html(get_option('blogname')),
|
154 |
-
"fwrite_wproot" => DUPLICATOR_WPROOTPATH,
|
155 |
-
"fwrite_duplicator_version" => DUPLICATOR_VERSION);
|
156 |
-
|
157 |
-
if (file_exists($template) && is_readable($template)) {
|
158 |
-
$err_msg = "ERROR: Unable to read/write installer. \nERROR INFO: Check permission/owner on file and parent folder.\nInstaller File = <{$installer}>";
|
159 |
-
$install_str = $this->parseTemplate($template, $replace_items);
|
160 |
-
(empty($install_str))
|
161 |
-
? DUP_Log::Error("{$err_msg}" , "DUP_Installer::createFromTemplate => file-empty-read")
|
162 |
-
: DUP_Log::Info("Template parsed with new data");
|
163 |
-
|
164 |
-
//INSTALLER FILE
|
165 |
-
$fp = (!file_exists($installer)) ? fopen($installer, 'x+') : fopen($installer, 'w');
|
166 |
-
if (! $fp || ! fwrite($fp, $install_str, strlen($install_str))) {
|
167 |
-
DUP_Log::Error("{$err_msg}", "DUP_Installer::createFromTemplate => file-write-error");
|
168 |
-
}
|
169 |
-
|
170 |
-
@fclose($fp);
|
171 |
-
} else {
|
172 |
-
DUP_Log::Error("Installer Template missing or unreadable.", "Template [{$template}]");
|
173 |
-
}
|
174 |
-
@unlink($template);
|
175 |
-
DUP_Log::Info("Complete [{$installer}]");
|
176 |
-
}
|
177 |
-
|
178 |
-
/**
|
179 |
-
* parseTemplate
|
180 |
-
* Tokenize a file based on an array key
|
181 |
-
*
|
182 |
-
* @param string $filename The filename to tokenize
|
183 |
-
* @param array $data The array of key value items to tokenize
|
184 |
-
*/
|
185 |
-
private function parseTemplate($filename, $data) {
|
186 |
-
$q = file_get_contents($filename);
|
187 |
-
foreach ($data as $key => $value) {
|
188 |
-
//NOTE: Use var_export as it's probably best and most "thorough" way to
|
189 |
-
//make sure the values are set correctly in the template. But in the template,
|
190 |
-
//need to make things properly formatted so that when real syntax errors
|
191 |
-
//exist they are easy to spot. So the values will be surrounded by quotes
|
192 |
-
|
193 |
-
$find = array ("'%{$key}%'", "\"%{$key}%\"");
|
194 |
-
$q = str_replace($find, var_export($value, true), $q);
|
195 |
-
//now, account for places that do not surround with quotes... these
|
196 |
-
//places do NOT need to use var_export as they are not inside strings
|
197 |
-
$q = str_replace('%' . $key . '%', $value, $q);
|
198 |
-
}
|
199 |
-
return $q;
|
200 |
-
}
|
201 |
-
|
202 |
-
}
|
203 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/package.php
DELETED
@@ -1,547 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.archive.php');
|
5 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.installer.php');
|
6 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.database.php');
|
7 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/utility.php');
|
8 |
-
|
9 |
-
final class DUP_PackageStatus {
|
10 |
-
private function __construct() {}
|
11 |
-
const START = 10;
|
12 |
-
const DBSTART = 20;
|
13 |
-
const DBDONE = 30;
|
14 |
-
const ARCSTART = 40;
|
15 |
-
const ARCDONE = 50;
|
16 |
-
const COMPLETE = 100;
|
17 |
-
}
|
18 |
-
|
19 |
-
final class DUP_PackageType {
|
20 |
-
private function __construct() {}
|
21 |
-
const MANUAL = 0;
|
22 |
-
const SCHEDULED = 1;
|
23 |
-
}
|
24 |
-
|
25 |
-
/**
|
26 |
-
* Class used to store and process all Package logic
|
27 |
-
* @package Dupicator\classes
|
28 |
-
*/
|
29 |
-
class DUP_Package {
|
30 |
-
|
31 |
-
const OPT_ACTIVE = 'duplicator_package_active';
|
32 |
-
|
33 |
-
//Properties
|
34 |
-
public $Created;
|
35 |
-
public $Version;
|
36 |
-
public $VersionWP;
|
37 |
-
public $VersionDB;
|
38 |
-
public $VersionPHP;
|
39 |
-
public $VersionOS;
|
40 |
-
|
41 |
-
public $ID;
|
42 |
-
public $Name;
|
43 |
-
public $Hash;
|
44 |
-
public $NameHash;
|
45 |
-
public $Type;
|
46 |
-
public $Notes;
|
47 |
-
public $StorePath;
|
48 |
-
public $StoreURL;
|
49 |
-
public $ScanFile;
|
50 |
-
public $Runtime;
|
51 |
-
public $ExeSize;
|
52 |
-
public $ZipSize;
|
53 |
-
public $Status;
|
54 |
-
public $WPUser;
|
55 |
-
//Objects
|
56 |
-
public $Archive;
|
57 |
-
public $Installer;
|
58 |
-
public $Database;
|
59 |
-
|
60 |
-
/**
|
61 |
-
* Manages the Package Process
|
62 |
-
*/
|
63 |
-
function __construct() {
|
64 |
-
|
65 |
-
$this->ID = null;
|
66 |
-
$this->Version = DUPLICATOR_VERSION;
|
67 |
-
|
68 |
-
$this->Type = DUP_PackageType::MANUAL;
|
69 |
-
$this->Name = self::GetDefaultName();
|
70 |
-
$this->Notes = null;
|
71 |
-
$this->StoreURL = DUP_Util::SSDirURL();
|
72 |
-
$this->StorePath = DUPLICATOR_SSDIR_PATH_TMP;
|
73 |
-
$this->Database = new DUP_Database($this);
|
74 |
-
$this->Archive = new DUP_Archive($this);
|
75 |
-
$this->Installer = new DUP_Installer($this);
|
76 |
-
|
77 |
-
}
|
78 |
-
|
79 |
-
/**
|
80 |
-
* Generates a scan report
|
81 |
-
* @return array of scan results
|
82 |
-
*
|
83 |
-
* @notes: Testing = /wp-admin/admin-ajax.php?action=duplicator_package_scan
|
84 |
-
*/
|
85 |
-
public function Scan() {
|
86 |
-
|
87 |
-
$timerStart = DUP_Util::GetMicrotime();
|
88 |
-
$report = array();
|
89 |
-
$this->ScanFile = "{$this->NameHash}_scan.json";
|
90 |
-
|
91 |
-
$report['RPT']['ScanTime'] = "0";
|
92 |
-
$report['RPT']['ScanFile'] = $this->ScanFile;
|
93 |
-
|
94 |
-
//SERVER
|
95 |
-
$srv = DUP_Server::GetChecks();
|
96 |
-
$report['SRV'] = $srv['SRV'];
|
97 |
-
|
98 |
-
//FILES
|
99 |
-
$this->Archive->Stats();
|
100 |
-
$dirCount = count($this->Archive->Dirs);
|
101 |
-
$fileCount = count($this->Archive->Files);
|
102 |
-
$fullCount = $dirCount + $fileCount;
|
103 |
-
|
104 |
-
$report['ARC']['Size'] = DUP_Util::ByteSize($this->Archive->Size) or "unknown";
|
105 |
-
$report['ARC']['DirCount'] = number_format($dirCount);
|
106 |
-
$report['ARC']['FileCount'] = number_format($fileCount);
|
107 |
-
$report['ARC']['FullCount'] = number_format($fullCount);
|
108 |
-
|
109 |
-
$report['ARC']['FilterInfo']['Dirs'] = $this->Archive->FilterInfo->Dirs;
|
110 |
-
$report['ARC']['FilterInfo']['Files'] = $this->Archive->FilterInfo->Files;
|
111 |
-
$report['ARC']['FilterInfo']['Exts'] = $this->Archive->FilterInfo->Exts;
|
112 |
-
|
113 |
-
$report['ARC']['Status']['Size'] = ($this->Archive->Size > DUPLICATOR_SCAN_SITE) ? 'Warn' : 'Good';
|
114 |
-
$report['ARC']['Status']['Names'] = (count($this->Archive->FilterInfo->Files->Warning) + count($this->Archive->FilterInfo->Dirs->Warning)) ? 'Warn' : 'Good';
|
115 |
-
$report['ARC']['Status']['Big'] = count($this->Archive->FilterInfo->Files->Size) ? 'Warn' : 'Good';
|
116 |
-
|
117 |
-
$report['ARC']['Dirs'] = $this->Archive->Dirs;
|
118 |
-
$report['ARC']['Files'] = $this->Archive->Files;
|
119 |
-
|
120 |
-
//DATABASE
|
121 |
-
$db = $this->Database->Stats();
|
122 |
-
$report['DB'] = $db;
|
123 |
-
|
124 |
-
$warnings = array($report['SRV']['WEB']['ALL'],
|
125 |
-
$report['SRV']['PHP']['ALL'],
|
126 |
-
$report['SRV']['WP']['ALL'],
|
127 |
-
$report['ARC']['Status']['Size'],
|
128 |
-
$report['ARC']['Status']['Names'],
|
129 |
-
$report['ARC']['Status']['Big'],
|
130 |
-
$db['Status']['Size'],
|
131 |
-
$db['Status']['Rows'],
|
132 |
-
$db['Status']['Case']);
|
133 |
-
|
134 |
-
//array_count_values will throw a warning message if it has null values,
|
135 |
-
//so lets replace all nulls with empty string
|
136 |
-
foreach ($warnings as $i => $value) {
|
137 |
-
if (is_null($value)) {
|
138 |
-
$warnings[$i] = '';
|
139 |
-
}
|
140 |
-
}
|
141 |
-
$warn_counts = is_array($warnings) ? array_count_values($warnings) : 0;
|
142 |
-
$report['RPT']['Warnings'] = $warn_counts['Warn'];
|
143 |
-
$report['RPT']['Success'] = $warn_counts['Good'];
|
144 |
-
$report['RPT']['ScanTime'] = DUP_Util::ElapsedTime(DUP_Util::GetMicrotime(), $timerStart);
|
145 |
-
$fp = fopen(DUPLICATOR_SSDIR_PATH_TMP . "/{$this->ScanFile}", 'w');
|
146 |
-
fwrite($fp, json_encode($report));
|
147 |
-
fclose($fp);
|
148 |
-
|
149 |
-
return $report;
|
150 |
-
}
|
151 |
-
|
152 |
-
/**
|
153 |
-
* Starts the package build process
|
154 |
-
* @return DUP_Package
|
155 |
-
*/
|
156 |
-
public function Build() {
|
157 |
-
|
158 |
-
global $wp_version;
|
159 |
-
global $wpdb;
|
160 |
-
global $current_user;
|
161 |
-
|
162 |
-
$timerStart = DUP_Util::GetMicrotime();
|
163 |
-
|
164 |
-
$this->Archive->File = "{$this->NameHash}_archive.zip";
|
165 |
-
$this->Installer->File = "{$this->NameHash}_installer.php";
|
166 |
-
$this->Database->File = "{$this->NameHash}_database.sql";
|
167 |
-
$this->WPUser = isset($current_user->user_login) ? $current_user->user_login : 'unknown';
|
168 |
-
|
169 |
-
//START LOGGING
|
170 |
-
DUP_Log::Open($this->NameHash);
|
171 |
-
$php_max_time = @ini_get("max_execution_time");
|
172 |
-
$php_max_memory = @ini_set('memory_limit', DUPLICATOR_PHP_MAX_MEMORY);
|
173 |
-
$php_max_time = ($php_max_time == 0) ? "(0) no time limit imposed" : "[{$php_max_time}] not allowed";
|
174 |
-
$php_max_memory = ($php_max_memory === false) ? "Unabled to set php memory_limit" : DUPLICATOR_PHP_MAX_MEMORY . " ({$php_max_memory} default)";
|
175 |
-
|
176 |
-
$info = "********************************************************************************\n";
|
177 |
-
$info .= "DUPLICATOR-LITE PACKAGE-LOG: " . @date("Y-m-d H:i:s") . "\n";
|
178 |
-
$info .= "NOTICE: Do NOT post to public sites or forums \n";
|
179 |
-
$info .= "********************************************************************************\n";
|
180 |
-
$info .= "VERSION:\t" . DUPLICATOR_VERSION . "\n";
|
181 |
-
$info .= "WORDPRESS:\t{$wp_version}\n";
|
182 |
-
$info .= "PHP INFO:\t" . phpversion() . ' | ' . 'SAPI: ' . php_sapi_name() . "\n";
|
183 |
-
$info .= "SERVER:\t\t{$_SERVER['SERVER_SOFTWARE']} \n";
|
184 |
-
$info .= "PHP TIME LIMIT: {$php_max_time} \n";
|
185 |
-
$info .= "PHP MAX MEMORY: {$php_max_memory} \n";
|
186 |
-
$info .= "MEMORY STACK: " . DUP_Server::GetPHPMemory();
|
187 |
-
DUP_Log::Info($info);
|
188 |
-
$info = null;
|
189 |
-
|
190 |
-
//CREATE DB RECORD
|
191 |
-
$packageObj = serialize($this);
|
192 |
-
if (! $packageObj) {
|
193 |
-
DUP_Log::Error("Unable to serialize pacakge object while building record.");
|
194 |
-
}
|
195 |
-
|
196 |
-
$this->ID = $this->FindHashKey($this->Hash);
|
197 |
-
|
198 |
-
if ($this->ID != 0){
|
199 |
-
$this->SetStatus(DUP_PackageStatus::START);
|
200 |
-
} else {
|
201 |
-
$results = $wpdb->insert($wpdb->prefix . "duplicator_packages", array(
|
202 |
-
'name' => $this->Name,
|
203 |
-
'hash' => $this->Hash,
|
204 |
-
'status' => DUP_PackageStatus::START,
|
205 |
-
'created' => current_time('mysql', get_option('gmt_offset', 1)),
|
206 |
-
'owner' => isset($current_user->user_login) ? $current_user->user_login : 'unknown',
|
207 |
-
'package' => $packageObj)
|
208 |
-
);
|
209 |
-
if ($results === false) {
|
210 |
-
|
211 |
-
$wpdb->print_error();
|
212 |
-
DUP_Log::Error("Duplicator is unable to insert a package record into the database table.", "'{$wpdb->last_error}'");
|
213 |
-
}
|
214 |
-
$this->ID = $wpdb->insert_id;
|
215 |
-
}
|
216 |
-
|
217 |
-
//START BUILD
|
218 |
-
//PHPs serialze method will return the object, but the ID above is not passed
|
219 |
-
//for one reason or another so passing the object back in seems to do the trick
|
220 |
-
$this->Database->Build($this);
|
221 |
-
$this->Archive->Build($this);
|
222 |
-
$this->Installer->Build($this);
|
223 |
-
|
224 |
-
|
225 |
-
//INTEGRITY CHECKS
|
226 |
-
DUP_Log::Info("\n********************************************************************************");
|
227 |
-
DUP_Log::Info("INTEGRITY CHECKS:");
|
228 |
-
DUP_Log::Info("********************************************************************************");
|
229 |
-
$dbSizeRead = DUP_Util::ByteSize($this->Database->Size);
|
230 |
-
$zipSizeRead = DUP_Util::ByteSize($this->Archive->Size);
|
231 |
-
$exeSizeRead = DUP_Util::ByteSize($this->Installer->Size);
|
232 |
-
|
233 |
-
DUP_Log::Info("SQL File: {$dbSizeRead}");
|
234 |
-
DUP_Log::Info("Installer File: {$exeSizeRead}");
|
235 |
-
DUP_Log::Info("Archive File: {$zipSizeRead} ");
|
236 |
-
|
237 |
-
if ( !($this->Archive->Size && $this->Database->Size && $this->Installer->Size)) {
|
238 |
-
DUP_Log::Error("A required file contains zero bytes.", "Archive Size: {$zipSizeRead} | SQL Size: {$dbSizeRead} | Installer Size: {$exeSizeRead}");
|
239 |
-
}
|
240 |
-
|
241 |
-
//Validate SQL files completed
|
242 |
-
$sql_tmp_path = DUP_UTIL::SafePath(DUPLICATOR_SSDIR_PATH_TMP . '/'. $this->Database->File);
|
243 |
-
$sql_complete_txt = DUP_Util::TailFile($sql_tmp_path, 3);
|
244 |
-
if (! strstr($sql_complete_txt, 'DUPLICATOR_MYSQLDUMP_EOF')) {
|
245 |
-
DUP_Log::Error("ERROR: SQL file not complete. The end of file marker was not found. Please try to re-create the package.");
|
246 |
-
}
|
247 |
-
|
248 |
-
$timerEnd = DUP_Util::GetMicrotime();
|
249 |
-
$timerSum = DUP_Util::ElapsedTime($timerEnd, $timerStart);
|
250 |
-
|
251 |
-
$this->Runtime = $timerSum;
|
252 |
-
$this->ExeSize = $exeSizeRead;
|
253 |
-
$this->ZipSize = $zipSizeRead;
|
254 |
-
|
255 |
-
$this->buildCleanup();
|
256 |
-
|
257 |
-
//FINAL REPORT
|
258 |
-
$info = "\n********************************************************************************\n";
|
259 |
-
$info .= "RECORD ID:[{$this->ID}]\n";
|
260 |
-
$info .= "TOTAL PROCESS RUNTIME: {$timerSum}\n";
|
261 |
-
$info .= "PEAK PHP MEMORY USED: " . DUP_Server::GetPHPMemory(true) . "\n";
|
262 |
-
$info .= "DONE PROCESSING => {$this->Name} " . @date("Y-m-d H:i:s") . "\n";
|
263 |
-
|
264 |
-
DUP_Log::Info($info);
|
265 |
-
DUP_Log::Close();
|
266 |
-
|
267 |
-
$this->SetStatus(DUP_PackageStatus::COMPLETE);
|
268 |
-
return $this;
|
269 |
-
}
|
270 |
-
|
271 |
-
/**
|
272 |
-
* Saves the active options associted with the active(latest) package.
|
273 |
-
* @param $_POST $post The Post server object
|
274 |
-
* @see DUP_Package::GetActive
|
275 |
-
* @return void */
|
276 |
-
public function SaveActive($post = null)
|
277 |
-
{
|
278 |
-
global $wp_version;
|
279 |
-
|
280 |
-
if (isset($post)) {
|
281 |
-
$post = stripslashes_deep($post);
|
282 |
-
|
283 |
-
$name_chars = array(".", "-");
|
284 |
-
$name = ( isset($post['package-name']) && ! empty($post['package-name'])) ? $post['package-name'] : self::GetDefaultName();
|
285 |
-
$name = substr(sanitize_file_name($name), 0 , 40);
|
286 |
-
$name = str_replace($name_chars, '', $name);
|
287 |
-
|
288 |
-
$filter_dirs = isset($post['filter-dirs']) ? $this->parseDirectoryFilter($post['filter-dirs']) : '';
|
289 |
-
$filter_exts = isset($post['filter-exts']) ? $this->parseExtensionFilter($post['filter-exts']) : '';
|
290 |
-
$tablelist = isset($post['dbtables']) ? implode(',', $post['dbtables']) : '';
|
291 |
-
$compatlist = isset($post['dbcompat']) ? implode(',', $post['dbcompat']) : '';
|
292 |
-
$dbversion = preg_replace('/[^0-9.].*/', '', DUP_Util::MysqlVariableValue('version'));
|
293 |
-
$dbversion = is_null($dbversion) ? '- unknown -' : $dbversion;
|
294 |
-
|
295 |
-
//PACKAGE
|
296 |
-
$this->Created = date("Y-m-d H:i:s");
|
297 |
-
$this->Version = DUPLICATOR_VERSION;
|
298 |
-
$this->VersionOS = defined('PHP_OS') ? PHP_OS : 'unknown';
|
299 |
-
$this->VersionWP = $wp_version;
|
300 |
-
$this->VersionPHP = phpversion();
|
301 |
-
$this->VersionDB = $dbversion;
|
302 |
-
$this->Name = $name;
|
303 |
-
$this->Hash = $this->MakeHash();
|
304 |
-
$this->NameHash = "{$this->Name}_{$this->Hash}";;
|
305 |
-
$this->Notes = esc_html($post['package-notes']);
|
306 |
-
//ARCHIVE
|
307 |
-
$this->Archive->PackDir = rtrim(DUPLICATOR_WPROOTPATH, '/');
|
308 |
-
$this->Archive->Format = 'ZIP';
|
309 |
-
$this->Archive->FilterOn = isset($post['filter-on']) ? 1 : 0;
|
310 |
-
$this->Archive->FilterDirs = esc_html($filter_dirs);
|
311 |
-
$this->Archive->FilterExts = str_replace(array('.' ,' '), "", esc_html($filter_exts));
|
312 |
-
//INSTALLER
|
313 |
-
$this->Installer->OptsDBHost = esc_html($post['dbhost']);
|
314 |
-
$this->Installer->OptsDBPort = esc_html($post['dbport']);
|
315 |
-
$this->Installer->OptsDBName = esc_html($post['dbname']);
|
316 |
-
$this->Installer->OptsDBUser = esc_html($post['dbuser']);
|
317 |
-
$this->Installer->OptsSSLAdmin = isset($post['ssl-admin']) ? 1 : 0;
|
318 |
-
$this->Installer->OptsSSLLogin = isset($post['ssl-login']) ? 1 : 0;
|
319 |
-
$this->Installer->OptsCacheWP = isset($post['cache-wp']) ? 1 : 0;
|
320 |
-
$this->Installer->OptsCachePath = isset($post['cache-path']) ? 1 : 0;
|
321 |
-
$this->Installer->OptsURLNew = esc_html($post['url-new']);
|
322 |
-
//DATABASE
|
323 |
-
$this->Database->FilterOn = isset($post['dbfilter-on']) ? 1 : 0;
|
324 |
-
$this->Database->FilterTables = esc_html($tablelist);
|
325 |
-
$this->Database->Compatible = $compatlist;
|
326 |
-
|
327 |
-
update_option(self::OPT_ACTIVE, $this);
|
328 |
-
}
|
329 |
-
}
|
330 |
-
|
331 |
-
/**
|
332 |
-
* Save any property of this class through reflection
|
333 |
-
* @param $property A valid public property in this class
|
334 |
-
* @param $value The value for the new dynamic property
|
335 |
-
* @return void */
|
336 |
-
public function SaveActiveItem($property, $value) {
|
337 |
-
$package = self::GetActive();
|
338 |
-
|
339 |
-
$reflectionClass = new ReflectionClass($package);
|
340 |
-
$reflectionClass->getProperty($property)->setValue($package, $value);
|
341 |
-
update_option(self::OPT_ACTIVE, $package);
|
342 |
-
}
|
343 |
-
|
344 |
-
/**
|
345 |
-
* Sets the status to log the state of the build
|
346 |
-
* @param $status The status level for where the package is
|
347 |
-
* @return void */
|
348 |
-
public function SetStatus($status) {
|
349 |
-
global $wpdb;
|
350 |
-
|
351 |
-
$packageObj = serialize($this);
|
352 |
-
|
353 |
-
if (! isset($status)) {
|
354 |
-
DUP_Log::Error("Package SetStatus did not receive a proper code.");
|
355 |
-
}
|
356 |
-
|
357 |
-
if (! $packageObj) {
|
358 |
-
DUP_Log::Error("Package SetStatus was unable to serialize package object while updating record.");
|
359 |
-
}
|
360 |
-
|
361 |
-
$wpdb->flush();
|
362 |
-
$table = $wpdb->prefix . "duplicator_packages";
|
363 |
-
$sql = "UPDATE `{$table}` SET status = {$status}, package = '{$packageObj}' WHERE ID = {$this->ID}";
|
364 |
-
$wpdb->query($sql);
|
365 |
-
}
|
366 |
-
|
367 |
-
/**
|
368 |
-
* Does a hash already exisit
|
369 |
-
* @return int Returns 0 if no has is found, if found returns the table ID
|
370 |
-
*/
|
371 |
-
public function FindHashKey($hash) {
|
372 |
-
|
373 |
-
global $wpdb;
|
374 |
-
|
375 |
-
$table = $wpdb->prefix . "duplicator_packages";
|
376 |
-
$qry = $wpdb->get_row("SELECT ID, hash FROM `{$table}` WHERE hash = '{$hash}'" );
|
377 |
-
if ( strlen($qry->hash) == 0) {
|
378 |
-
return 0;
|
379 |
-
} else {
|
380 |
-
return $qry->ID;
|
381 |
-
}
|
382 |
-
|
383 |
-
}
|
384 |
-
|
385 |
-
/**
|
386 |
-
* Makes the hashkey for the package files
|
387 |
-
* @return string A unique hashkey */
|
388 |
-
public function MakeHash() {
|
389 |
-
return uniqid() . mt_rand(1000, 9999) . date("ymdHis");
|
390 |
-
}
|
391 |
-
|
392 |
-
/**
|
393 |
-
* Gets the active package. The active package is defined as the package that was lasted saved.
|
394 |
-
* Do to cache issues with the built in WP function get_option moved call to a direct DB call.
|
395 |
-
* @see DUP_Package::SaveActive
|
396 |
-
* @return DUP_Package
|
397 |
-
*/
|
398 |
-
public static function GetActive() {
|
399 |
-
|
400 |
-
global $wpdb;
|
401 |
-
$obj = new DUP_Package();
|
402 |
-
$row = $wpdb->get_row( $wpdb->prepare( "SELECT option_value FROM `{$wpdb->options}` WHERE option_name = %s LIMIT 1", self::OPT_ACTIVE ) );
|
403 |
-
if (is_object($row)) {
|
404 |
-
$obj = @unserialize($row->option_value);
|
405 |
-
}
|
406 |
-
//Incase unserilaize fails
|
407 |
-
$obj = (is_object($obj)) ? $obj : new DUP_Package();
|
408 |
-
return $obj;
|
409 |
-
}
|
410 |
-
|
411 |
-
/**
|
412 |
-
* Gets the Package by ID
|
413 |
-
* @see DUP_Package::GetByID
|
414 |
-
* @return DUP_Package
|
415 |
-
*/
|
416 |
-
public static function GetByID($id) {
|
417 |
-
|
418 |
-
global $wpdb;
|
419 |
-
$obj = new DUP_Package();
|
420 |
-
|
421 |
-
$row = $wpdb->get_row( $wpdb->prepare( "SELECT * FROM `{$wpdb->prefix}duplicator_packages` WHERE ID = %s", $id ) );
|
422 |
-
if (is_object($row)) {
|
423 |
-
$obj = @unserialize($row->package);
|
424 |
-
$obj->Status = $row->status;
|
425 |
-
}
|
426 |
-
//Incase unserilaize fails
|
427 |
-
$obj = (is_object($obj)) ? $obj : null;
|
428 |
-
return $obj;
|
429 |
-
}
|
430 |
-
|
431 |
-
/**
|
432 |
-
* Creates a default name
|
433 |
-
* @return string A default packagename
|
434 |
-
*/
|
435 |
-
public static function GetDefaultName() {
|
436 |
-
//Remove specail_chars from final result
|
437 |
-
$special_chars = array(".", "-");
|
438 |
-
$name = date('Ymd') . '_' . sanitize_title(get_bloginfo( 'name', 'display' ));
|
439 |
-
$name = substr(sanitize_file_name($name), 0 , 40);
|
440 |
-
$name = str_replace($special_chars, '', $name);
|
441 |
-
return $name;
|
442 |
-
|
443 |
-
}
|
444 |
-
|
445 |
-
/**
|
446 |
-
* Cleanup all tmp files
|
447 |
-
* @param all empty all contents
|
448 |
-
* @return void
|
449 |
-
*/
|
450 |
-
public static function TmpCleanup($all = false) {
|
451 |
-
|
452 |
-
//Delete all files now
|
453 |
-
if ($all){
|
454 |
-
$dir = DUPLICATOR_SSDIR_PATH_TMP . "/*";
|
455 |
-
foreach (glob($dir) as $file) {
|
456 |
-
unlink($file);
|
457 |
-
}
|
458 |
-
}
|
459 |
-
//Remove scan files that are 24 hours old
|
460 |
-
else {
|
461 |
-
$dir = DUPLICATOR_SSDIR_PATH_TMP . "/*_scan.json";
|
462 |
-
foreach (glob($dir) as $file) {
|
463 |
-
if (filemtime($file) <= time() - 86400) {
|
464 |
-
unlink($file);
|
465 |
-
}
|
466 |
-
}
|
467 |
-
}
|
468 |
-
}
|
469 |
-
|
470 |
-
/**
|
471 |
-
* Provides various date formats
|
472 |
-
*
|
473 |
-
* @param $date The date to format
|
474 |
-
* @param $format Various date formats to apply
|
475 |
-
*
|
476 |
-
* @return a formated date
|
477 |
-
*/
|
478 |
-
public static function FormatCreatedDate($date, $format = 1)
|
479 |
-
{
|
480 |
-
$date = new DateTime($date);
|
481 |
-
switch ($format)
|
482 |
-
{
|
483 |
-
//YEAR
|
484 |
-
case 1: return $date->format('Y-m-d H:i'); break;
|
485 |
-
case 2: return $date->format('Y-m-d H:i:s'); break;
|
486 |
-
case 3: return $date->format('y-m-d H:i'); break;
|
487 |
-
case 4: return $date->format('y-m-d H:i:s'); break;
|
488 |
-
//MONTH
|
489 |
-
case 5: return $date->format('m-d-Y H:i'); break;
|
490 |
-
case 6: return $date->format('m-d-Y H:i:s'); break;
|
491 |
-
case 7: return $date->format('m-d-y H:i'); break;
|
492 |
-
case 8: return $date->format('m-d-y H:i:s'); break;
|
493 |
-
//DAY
|
494 |
-
case 9: return $date->format('d-m-Y H:i'); break;
|
495 |
-
case 10: return $date->format('d-m-Y H:i:s'); break;
|
496 |
-
case 11: return $date->format('d-m-y H:i'); break;
|
497 |
-
case 12: return $date->format('d-m-y H:i:s'); break;
|
498 |
-
}
|
499 |
-
}
|
500 |
-
|
501 |
-
private function buildCleanup() {
|
502 |
-
|
503 |
-
$files = DUP_Util::ListFiles(DUPLICATOR_SSDIR_PATH_TMP);
|
504 |
-
$newPath = DUPLICATOR_SSDIR_PATH;
|
505 |
-
|
506 |
-
if (function_exists('rename')) {
|
507 |
-
foreach($files as $file){
|
508 |
-
$name = basename($file);
|
509 |
-
if (strstr($name, $this->NameHash)) {
|
510 |
-
rename($file,"{$newPath}/{$name}");
|
511 |
-
}
|
512 |
-
}
|
513 |
-
} else {
|
514 |
-
foreach($files as $file){
|
515 |
-
$name = basename($file);
|
516 |
-
if (strstr($name, $this->NameHash)) {
|
517 |
-
copy($file,"{$newPath}/{$name}");
|
518 |
-
unlink($file);
|
519 |
-
}
|
520 |
-
}
|
521 |
-
}
|
522 |
-
}
|
523 |
-
|
524 |
-
private function parseDirectoryFilter($dirs = "") {
|
525 |
-
$dirs = str_replace(array("\n", "\t", "\r"), '', $dirs);
|
526 |
-
$filter_dirs = "";
|
527 |
-
$dir_array = array_unique(explode(";", $dirs));
|
528 |
-
foreach ($dir_array as $val) {
|
529 |
-
if (strlen($val) >= 2) {
|
530 |
-
$filter_dirs .= DUP_Util::SafePath(trim(rtrim($val, "/\\"))) . ";";
|
531 |
-
}
|
532 |
-
}
|
533 |
-
return $filter_dirs;
|
534 |
-
}
|
535 |
-
|
536 |
-
private function parseExtensionFilter($extensions = "") {
|
537 |
-
$filter_exts = "";
|
538 |
-
if (strlen($extensions) >= 1 && $extensions != ";") {
|
539 |
-
$filter_exts = str_replace(array(' ', '.'), '', $extensions);
|
540 |
-
$filter_exts = str_replace(",", ";", $filter_exts);
|
541 |
-
$filter_exts = DUP_Util::StringAppend($extensions, ";");
|
542 |
-
}
|
543 |
-
return $filter_exts;
|
544 |
-
}
|
545 |
-
|
546 |
-
}
|
547 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/package/class.pack.archive.filters.php
ADDED
@@ -0,0 +1,80 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* The base class for all filter types Directories/Files/Extentions
|
4 |
+
*
|
5 |
+
* @package Duplicator
|
6 |
+
* @subpackage classes/package
|
7 |
+
* @since 1.1.0
|
8 |
+
*
|
9 |
+
*/
|
10 |
+
class DUP_Archive_Filter_Scope_Base
|
11 |
+
{
|
12 |
+
//All internal storage items that duplicator decides to filter
|
13 |
+
public $Core = array();
|
14 |
+
//Items when creating a package or template that a user decides to filter
|
15 |
+
public $Instance = array();
|
16 |
+
}
|
17 |
+
|
18 |
+
/**
|
19 |
+
* The filter types that belong to directories
|
20 |
+
*
|
21 |
+
* @package Duplicator
|
22 |
+
* @subpackage classes/package
|
23 |
+
* @since 1.1.0
|
24 |
+
*
|
25 |
+
*/
|
26 |
+
class DUP_Archive_Filter_Scope_Directory extends DUP_Archive_Filter_Scope_Base
|
27 |
+
{
|
28 |
+
//Items that are not readable
|
29 |
+
public $Warning = array();
|
30 |
+
//Items that are not readable
|
31 |
+
public $Unreadable = array();
|
32 |
+
}
|
33 |
+
|
34 |
+
/**
|
35 |
+
* The filter types that belong to files
|
36 |
+
*
|
37 |
+
* @package Duplicator
|
38 |
+
* @subpackage classes/package
|
39 |
+
* @since 1.1.0
|
40 |
+
*
|
41 |
+
*/
|
42 |
+
class DUP_Archive_Filter_Scope_File extends DUP_Archive_Filter_Scope_Directory
|
43 |
+
{
|
44 |
+
//Items that are too large
|
45 |
+
public $Size = array();
|
46 |
+
|
47 |
+
}
|
48 |
+
|
49 |
+
/**
|
50 |
+
* The filter information object which store all information about the filtered
|
51 |
+
* data that is gathered to the execution of a scan process
|
52 |
+
*
|
53 |
+
* @package Duplicator
|
54 |
+
* @subpackage classes/package
|
55 |
+
* @since 1.1.0
|
56 |
+
*
|
57 |
+
*/
|
58 |
+
class DUP_Archive_Filter_Info
|
59 |
+
{
|
60 |
+
//Contains all folder filter info
|
61 |
+
public $Dirs = array();
|
62 |
+
//Contains all file filter info
|
63 |
+
public $Files = array();
|
64 |
+
//Contains all extensions filter info
|
65 |
+
public $Exts = array();
|
66 |
+
public $UDirCount = 0;
|
67 |
+
public $UFileCount = 0;
|
68 |
+
public $UExtCount = 0;
|
69 |
+
|
70 |
+
/**
|
71 |
+
* Init this object
|
72 |
+
*/
|
73 |
+
public function __construct()
|
74 |
+
{
|
75 |
+
$this->Dirs = new DUP_Archive_Filter_Scope_Directory();
|
76 |
+
$this->Files = new DUP_Archive_Filter_Scope_File();
|
77 |
+
$this->Exts = new DUP_Archive_Filter_Scope_Base();
|
78 |
+
}
|
79 |
+
}
|
80 |
+
|
classes/package/class.pack.archive.php
ADDED
@@ -0,0 +1,274 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
if (!defined('DUPLICATOR_VERSION')) exit; // Exit if accessed directly
|
3 |
+
|
4 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/package/class.pack.archive.filters.php');
|
5 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/package/class.pack.archive.zip.php');
|
6 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'lib/forceutf8/Encoding.php');
|
7 |
+
|
8 |
+
/**
|
9 |
+
* Used to create the archive file
|
10 |
+
*
|
11 |
+
* @package Duplicator
|
12 |
+
* @subpackage classes/package
|
13 |
+
* @copyright (c) 2017, Snapcreek LLC
|
14 |
+
* @since 1.1.0
|
15 |
+
*
|
16 |
+
*/
|
17 |
+
class DUP_Archive
|
18 |
+
{
|
19 |
+
//PUBLIC
|
20 |
+
public $FilterDirs;
|
21 |
+
public $FilterExts;
|
22 |
+
public $FilterDirsAll = array();
|
23 |
+
public $FilterExtsAll = array();
|
24 |
+
public $FilterOn;
|
25 |
+
public $File;
|
26 |
+
public $Format;
|
27 |
+
public $PackDir;
|
28 |
+
public $Size = 0;
|
29 |
+
public $Dirs = array();
|
30 |
+
public $Files = array();
|
31 |
+
public $FilterInfo;
|
32 |
+
//PROTECTED
|
33 |
+
protected $Package;
|
34 |
+
|
35 |
+
|
36 |
+
/**
|
37 |
+
* Init this object
|
38 |
+
*/
|
39 |
+
public function __construct($package)
|
40 |
+
{
|
41 |
+
$this->Package = $package;
|
42 |
+
$this->FilterOn = false;
|
43 |
+
$this->FilterInfo = new DUP_Archive_Filter_Info();
|
44 |
+
}
|
45 |
+
|
46 |
+
/**
|
47 |
+
* Builds the archive based on the archive type
|
48 |
+
*
|
49 |
+
* @param obj $package The package object that started this process
|
50 |
+
*
|
51 |
+
* @return null
|
52 |
+
*/
|
53 |
+
public function build($package)
|
54 |
+
{
|
55 |
+
try {
|
56 |
+
$this->Package = $package;
|
57 |
+
if (!isset($this->PackDir) && !is_dir($this->PackDir)) throw new Exception("The 'PackDir' property must be a valid diretory.");
|
58 |
+
if (!isset($this->File)) throw new Exception("A 'File' property must be set.");
|
59 |
+
|
60 |
+
$this->Package->setStatus(DUP_PackageStatus::ARCSTART);
|
61 |
+
switch ($this->Format) {
|
62 |
+
case 'TAR': break;
|
63 |
+
case 'TAR-GZIP': break;
|
64 |
+
default:
|
65 |
+
if (class_exists(ZipArchive)) {
|
66 |
+
$this->Format = 'ZIP';
|
67 |
+
DUP_Zip::create($this);
|
68 |
+
}
|
69 |
+
break;
|
70 |
+
}
|
71 |
+
|
72 |
+
$storePath = "{$this->Package->StorePath}/{$this->File}";
|
73 |
+
$this->Size = @filesize($storePath);
|
74 |
+
$this->Package->setStatus(DUP_PackageStatus::ARCDONE);
|
75 |
+
} catch (Exception $e) {
|
76 |
+
echo 'Caught exception: ', $e->getMessage(), "\n";
|
77 |
+
}
|
78 |
+
}
|
79 |
+
|
80 |
+
/**
|
81 |
+
* Gets the filter directory paths as an array
|
82 |
+
*
|
83 |
+
* @return array Returns an array of filter directory paths
|
84 |
+
*/
|
85 |
+
public function getFilterDirAsArray()
|
86 |
+
{
|
87 |
+
return array_map('DUP_Util::safePath', explode(";", $this->FilterDirs, -1));
|
88 |
+
}
|
89 |
+
|
90 |
+
/**
|
91 |
+
* Gets the filter file extensions as an array
|
92 |
+
*
|
93 |
+
* @return array Returns an array of filter file extensions
|
94 |
+
*/
|
95 |
+
public function getFilterExtsAsArray()
|
96 |
+
{
|
97 |
+
return explode(";", $this->FilterExts, -1);
|
98 |
+
}
|
99 |
+
|
100 |
+
/**
|
101 |
+
* Builds a list of files and directories to be included in the archive
|
102 |
+
*
|
103 |
+
* Get the directory size recursively, but don't calc the snapshot directory, exclusion diretories
|
104 |
+
* @link http://msdn.microsoft.com/en-us/library/aa365247%28VS.85%29.aspx Windows filename restrictions
|
105 |
+
*
|
106 |
+
* @return obj Returns a DUP_Archive object
|
107 |
+
*/
|
108 |
+
public function getScanData()
|
109 |
+
{
|
110 |
+
$this->createFilterInfo();
|
111 |
+
$this->getDirs();
|
112 |
+
$this->getFiles();
|
113 |
+
return $this;
|
114 |
+
}
|
115 |
+
|
116 |
+
/**
|
117 |
+
* Creates the filter info setup data used for filtering the archive
|
118 |
+
*
|
119 |
+
* @return null
|
120 |
+
*/
|
121 |
+
private function createFilterInfo()
|
122 |
+
{
|
123 |
+
//FILTER: INSTANCE ITEMS
|
124 |
+
//Add the items generated at create time
|
125 |
+
if ($this->FilterOn) {
|
126 |
+
$this->FilterInfo->Dirs->Instance = array_map('DUP_Util::safePath', explode(";", $this->FilterDirs, -1));
|
127 |
+
$this->FilterInfo->Exts->Instance = explode(";", $this->FilterExts, -1);
|
128 |
+
}
|
129 |
+
|
130 |
+
//FILTER: CORE ITMES
|
131 |
+
//Filters Duplicator free packages & All pro local directories
|
132 |
+
$this->FilterInfo->Dirs->Core[] = DUPLICATOR_SSDIR_PATH;
|
133 |
+
|
134 |
+
$this->FilterDirsAll = array_merge($this->FilterInfo->Dirs->Instance, $this->FilterInfo->Dirs->Core);
|
135 |
+
$this->FilterExtsAll = array_merge($this->FilterInfo->Exts->Instance, $this->FilterInfo->Exts->Core);
|
136 |
+
}
|
137 |
+
|
138 |
+
/**
|
139 |
+
* Builds the directory list and directory filter lists
|
140 |
+
*
|
141 |
+
* @return null
|
142 |
+
*/
|
143 |
+
private function getDirs()
|
144 |
+
{
|
145 |
+
$rootPath = DUP_Util::safePath(rtrim(DUPLICATOR_WPROOTPATH, '//'));
|
146 |
+
$this->Dirs = array();
|
147 |
+
|
148 |
+
//If the root directory is a filter then we will only need the root files
|
149 |
+
if (in_array($this->PackDir, $this->FilterDirsAll)) {
|
150 |
+
$this->Dirs[] = $this->PackDir;
|
151 |
+
} else {
|
152 |
+
$this->Dirs = $this->dirsToArray($rootPath, $this->FilterDirsAll);
|
153 |
+
$this->Dirs[] = $this->PackDir;
|
154 |
+
}
|
155 |
+
|
156 |
+
//Filter Directories
|
157 |
+
//Invalid test contains checks for: characters over 250, invlaid characters,
|
158 |
+
//empty string and directories ending with period (Windows incompatable)
|
159 |
+
foreach ($this->Dirs as $key => $val) {
|
160 |
+
$name = basename($val);
|
161 |
+
|
162 |
+
$warn_test = strlen($val) > 250 || preg_match('/(\/|\*|\?|\>|\<|\:|\\|\|)/', $name)
|
163 |
+
|| trim($name) == "" || (strrpos($name, '.') == strlen($name) - 1 && substr($name, -1) == '.')
|
164 |
+
|| preg_match('/[^\x20-\x7f]/', $name);
|
165 |
+
if ($warn_test) {
|
166 |
+
$this->FilterInfo->Dirs->Warning[] = DUP_Encoding::toUTF8($val);
|
167 |
+
}
|
168 |
+
|
169 |
+
//UNREADABLE: Directory is unreadable flag it
|
170 |
+
if (!is_readable($this->Dirs[$key])) {
|
171 |
+
unset($this->Dirs[$key]);
|
172 |
+
$this->FilterInfo->Dirs->Unreadable[] = $val;
|
173 |
+
$this->FilterDirsAll[] = $val;
|
174 |
+
}
|
175 |
+
}
|
176 |
+
}
|
177 |
+
|
178 |
+
|
179 |
+
/**
|
180 |
+
* Get all files and filter out error prone subsets
|
181 |
+
*
|
182 |
+
* @return null
|
183 |
+
*/
|
184 |
+
private function getFiles()
|
185 |
+
{
|
186 |
+
foreach ($this->Dirs as $key => $val) {
|
187 |
+
$files = DUP_Util::listFiles($val);
|
188 |
+
foreach ($files as $filePath) {
|
189 |
+
$fileName = basename($filePath);
|
190 |
+
if (!is_dir($filePath)) {
|
191 |
+
if (!in_array(@pathinfo($filePath, PATHINFO_EXTENSION), $this->FilterExtsAll)) {
|
192 |
+
//Unreadable
|
193 |
+
if (!is_readable($filePath)) {
|
194 |
+
$this->FilterInfo->Files->Unreadable[] = $filePath;
|
195 |
+
continue;
|
196 |
+
}
|
197 |
+
|
198 |
+
$fileSize = @filesize($filePath);
|
199 |
+
$fileSize = empty($fileSize) ? 0 : $fileSize;
|
200 |
+
$invalid_test = strlen($filePath) > 250 ||
|
201 |
+
preg_match('/(\/|\*|\?|\>|\<|\:|\\|\|)/', $fileName) ||
|
202 |
+
trim($fileName) == "";
|
203 |
+
|
204 |
+
if ($invalid_test || preg_match('/[^\x20-\x7f]/', $fileName)) {
|
205 |
+
$filePath = DUP_Encoding::toUTF8($filePath);
|
206 |
+
$this->FilterInfo->Files->Warning[] = $filePath;
|
207 |
+
}
|
208 |
+
$this->Size += $fileSize;
|
209 |
+
$this->Files[] = $filePath;
|
210 |
+
|
211 |
+
|
212 |
+
if ($fileSize > DUPLICATOR_SCAN_WARNFILESIZE) {
|
213 |
+
$this->FilterInfo->Files->Size[] = $filePath.' ['.DUP_Util::byteSize($fileSize).']';
|
214 |
+
}
|
215 |
+
}
|
216 |
+
}
|
217 |
+
}
|
218 |
+
}
|
219 |
+
}
|
220 |
+
|
221 |
+
|
222 |
+
/**
|
223 |
+
* Recursive function to get all Directories in a wp install
|
224 |
+
*
|
225 |
+
* @param string $path The path of the directory to add to the array
|
226 |
+
* @param array $filterDirsAll An array of all the filtered directories
|
227 |
+
*
|
228 |
+
* NOTE: Older PHP logic which is more stable on older version of PHP
|
229 |
+
* RecursiveIteratorIterator is problematic on some systems issues include:
|
230 |
+
* - error 'too many files open' for recursion
|
231 |
+
* - $file->getExtension() is not reliable as it silently fails at least in php 5.2.9
|
232 |
+
* - issues with when a file has a permission such as 705 and trying to get info (had to fallback to pathinfo)
|
233 |
+
* - basic conclusion wait on the SPL libs untill after php 5.4 is a requiremnt
|
234 |
+
* - inside a tight recursive loop lets remove the utiltiy call DUP_Util::safePath("{$path}/{$file}") and
|
235 |
+
* squeeze out as much performance as possible
|
236 |
+
*
|
237 |
+
* @return null
|
238 |
+
*/
|
239 |
+
private function dirsToArray($path, $filterDirsAll)
|
240 |
+
{
|
241 |
+
$items = array();
|
242 |
+
$handle = @opendir($path);
|
243 |
+
if ($handle) {
|
244 |
+
while (($file = readdir($handle)) !== false) {
|
245 |
+
if ($file != '.' && $file != '..') {
|
246 |
+
$fullPath = str_replace("\\", '/', "{$path}/{$file}");
|
247 |
+
|
248 |
+
if (is_dir($fullPath)) {
|
249 |
+
$addDir = true;
|
250 |
+
|
251 |
+
//Remove path filter directories
|
252 |
+
foreach ($filterDirsAll as $filterDir) {
|
253 |
+
$trimmedFilterDir = rtrim($filterDir, '/');
|
254 |
+
|
255 |
+
if ($fullPath == $trimmedFilterDir || strstr($fullPath, $trimmedFilterDir.'/')) {
|
256 |
+
$addDir = false;
|
257 |
+
break;
|
258 |
+
}
|
259 |
+
}
|
260 |
+
|
261 |
+
if ($addDir) {
|
262 |
+
$items = array_merge($items, $this->dirsToArray($fullPath, $filterDirsAll));
|
263 |
+
$items[] = $fullPath;
|
264 |
+
}
|
265 |
+
}
|
266 |
+
}
|
267 |
+
}
|
268 |
+
closedir($handle);
|
269 |
+
}
|
270 |
+
|
271 |
+
return $items;
|
272 |
+
}
|
273 |
+
}
|
274 |
+
?>
|
classes/package/class.pack.archive.zip.php
ADDED
@@ -0,0 +1,159 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
if (!defined('DUPLICATOR_VERSION')) exit; // Exit if accessed directly
|
3 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/package/class.pack.archive.php');
|
4 |
+
|
5 |
+
/**
|
6 |
+
* Creates a zip file using the built in PHP ZipArchive class
|
7 |
+
*/
|
8 |
+
class DUP_Zip extends DUP_Archive
|
9 |
+
{
|
10 |
+
//PRIVATE
|
11 |
+
private static $compressDir;
|
12 |
+
private static $countDirs = 0;
|
13 |
+
private static $countFiles = 0;
|
14 |
+
private static $sqlPath;
|
15 |
+
private static $zipPath;
|
16 |
+
private static $zipFileSize;
|
17 |
+
private static $zipArchive;
|
18 |
+
private static $limitItems = 0;
|
19 |
+
private static $networkFlush = false;
|
20 |
+
private static $scanReport;
|
21 |
+
|
22 |
+
/**
|
23 |
+
* Creates the zip file and adds the SQL file to the archive
|
24 |
+
*/
|
25 |
+
public static function create(DUP_Archive $archive)
|
26 |
+
{
|
27 |
+
try {
|
28 |
+
$timerAllStart = DUP_Util::getMicrotime();
|
29 |
+
$package_zip_flush = DUP_Settings::Get('package_zip_flush');
|
30 |
+
|
31 |
+
self::$compressDir = rtrim(DUP_Util::safePath($archive->PackDir), '/');
|
32 |
+
self::$sqlPath = DUP_Util::safePath("{$archive->Package->StorePath}/{$archive->Package->Database->File}");
|
33 |
+
self::$zipPath = DUP_Util::safePath("{$archive->Package->StorePath}/{$archive->File}");
|
34 |
+
self::$zipArchive = new ZipArchive();
|
35 |
+
self::$networkFlush = empty($package_zip_flush) ? false : $package_zip_flush;
|
36 |
+
|
37 |
+
$filterDirs = empty($archive->FilterDirs) ? 'not set' : $archive->FilterDirs;
|
38 |
+
$filterExts = empty($archive->FilterExts) ? 'not set' : $archive->FilterExts;
|
39 |
+
$filterOn = ($archive->FilterOn) ? 'ON' : 'OFF';
|
40 |
+
$filterDirsFormat = rtrim(str_replace(';', "\n ", $filterDirs));
|
41 |
+
$lastDirSuccess = self::$compressDir;
|
42 |
+
|
43 |
+
//LOAD SCAN REPORT
|
44 |
+
$json = file_get_contents(DUPLICATOR_SSDIR_PATH_TMP."/{$archive->Package->NameHash}_scan.json");
|
45 |
+
self::$scanReport = json_decode($json);
|
46 |
+
|
47 |
+
DUP_Log::Info("\n********************************************************************************");
|
48 |
+
DUP_Log::Info("ARCHIVE (ZIP):");
|
49 |
+
DUP_Log::Info("********************************************************************************");
|
50 |
+
$isZipOpen = (self::$zipArchive->open(self::$zipPath, ZIPARCHIVE::CREATE) === TRUE);
|
51 |
+
if (!$isZipOpen) {
|
52 |
+
DUP_Log::Error("Cannot open zip file with PHP ZipArchive.", "Path location [".self::$zipPath."]");
|
53 |
+
}
|
54 |
+
DUP_Log::Info("ARCHIVE DIR: ".self::$compressDir);
|
55 |
+
DUP_Log::Info("ARCHIVE FILE: ".basename(self::$zipPath));
|
56 |
+
DUP_Log::Info("FILTERS: *{$filterOn}*");
|
57 |
+
DUP_Log::Info("DIRS: {$filterDirsFormat}");
|
58 |
+
DUP_Log::Info("EXTS: {$filterExts}");
|
59 |
+
|
60 |
+
DUP_Log::Info("----------------------------------------");
|
61 |
+
DUP_Log::Info("COMPRESSING");
|
62 |
+
DUP_Log::Info("SIZE:\t".self::$scanReport->ARC->Size);
|
63 |
+
DUP_Log::Info("STATS:\tDirs ".self::$scanReport->ARC->DirCount." | Files ".self::$scanReport->ARC->FileCount);
|
64 |
+
|
65 |
+
//ADD SQL
|
66 |
+
$isSQLInZip = self::$zipArchive->addFile(self::$sqlPath, "database.sql");
|
67 |
+
if ($isSQLInZip) {
|
68 |
+
DUP_Log::Info("SQL ADDED: ".basename(self::$sqlPath));
|
69 |
+
} else {
|
70 |
+
DUP_Log::Error("Unable to add database.sql to archive.", "SQL File Path [".self::$sqlath."]");
|
71 |
+
}
|
72 |
+
self::$zipArchive->close();
|
73 |
+
self::$zipArchive->open(self::$zipPath, ZipArchive::CREATE);
|
74 |
+
|
75 |
+
//ZIP DIRECTORIES
|
76 |
+
$info = '';
|
77 |
+
foreach (self::$scanReport->ARC->Dirs as $dir) {
|
78 |
+
if (is_readable($dir) && self::$zipArchive->addEmptyDir(ltrim(str_replace(self::$compressDir, '', $dir), '/'))) {
|
79 |
+
self::$countDirs++;
|
80 |
+
$lastDirSuccess = $dir;
|
81 |
+
} else {
|
82 |
+
//Don't warn when dirtory is the root path
|
83 |
+
if (strcmp($dir, rtrim(self::$compressDir, '/')) != 0) {
|
84 |
+
$dir_path = strlen($dir) ? "[{$dir}]" : "[Read Error] - last successful read was: [{$lastDirSuccess}]";
|
85 |
+
$info .= "DIR: {$dir_path}\n";
|
86 |
+
}
|
87 |
+
}
|
88 |
+
}
|
89 |
+
|
90 |
+
//LOG Unreadable DIR info
|
91 |
+
if (strlen($info)) {
|
92 |
+
DUP_Log::Info("\nWARNING: Unable to zip directories:");
|
93 |
+
DUP_Log::Info($info);
|
94 |
+
}
|
95 |
+
|
96 |
+
/* ZIP FILES: Network Flush
|
97 |
+
* This allows the process to not timeout on fcgi
|
98 |
+
* setups that need a response every X seconds */
|
99 |
+
$info = '';
|
100 |
+
if (self::$networkFlush) {
|
101 |
+
foreach (self::$scanReport->ARC->Files as $file) {
|
102 |
+
if (is_readable($file) && self::$zipArchive->addFile($file, ltrim(str_replace(self::$compressDir, '', $file), '/'))) {
|
103 |
+
self::$limitItems++;
|
104 |
+
self::$countFiles++;
|
105 |
+
} else {
|
106 |
+
$info .= "FILE: [{$file}]\n";
|
107 |
+
}
|
108 |
+
//Trigger a flush to the web server after so many files have been loaded.
|
109 |
+
if (self::$limitItems > DUPLICATOR_ZIP_FLUSH_TRIGGER) {
|
110 |
+
$sumItems = (self::$countDirs + self::$countFiles);
|
111 |
+
self::$zipArchive->close();
|
112 |
+
self::$zipArchive->open(self::$zipPath);
|
113 |
+
self::$limitItems = 0;
|
114 |
+
DUP_Util::fcgiFlush();
|
115 |
+
DUP_Log::Info("Items archived [{$sumItems}] flushing response.");
|
116 |
+
}
|
117 |
+
}
|
118 |
+
}
|
119 |
+
//Normal
|
120 |
+
else {
|
121 |
+
foreach (self::$scanReport->ARC->Files as $file) {
|
122 |
+
if (is_readable($file) && self::$zipArchive->addFile($file, ltrim(str_replace(self::$compressDir, '', $file), '/'))) {
|
123 |
+
self::$countFiles++;
|
124 |
+
} else {
|
125 |
+
$info .= "FILE: [{$file}]\n";
|
126 |
+
}
|
127 |
+
}
|
128 |
+
}
|
129 |
+
|
130 |
+
//LOG Unreadable FILE info
|
131 |
+
if (strlen($info)) {
|
132 |
+
DUP_Log::Info("\nWARNING: Unable to zip files:");
|
133 |
+
DUP_Log::Info($info);
|
134 |
+
unset($info);
|
135 |
+
}
|
136 |
+
|
137 |
+
DUP_Log::Info(print_r(self::$zipArchive, true));
|
138 |
+
|
139 |
+
//--------------------------------
|
140 |
+
//LOG FINAL RESULTS
|
141 |
+
DUP_Util::fcgiFlush();
|
142 |
+
$zipCloseResult = self::$zipArchive->close();
|
143 |
+
($zipCloseResult) ? DUP_Log::Info("COMPRESSION RESULT: '{$zipCloseResult}'") : DUP_Log::Error("ZipArchive close failure.",
|
144 |
+
"This hosted server may have a disk quota limit.\nCheck to make sure this archive file can be stored.");
|
145 |
+
|
146 |
+
$timerAllEnd = DUP_Util::getMicrotime();
|
147 |
+
$timerAllSum = DUP_Util::elapsedTime($timerAllEnd, $timerAllStart);
|
148 |
+
|
149 |
+
|
150 |
+
self::$zipFileSize = @filesize(self::$zipPath);
|
151 |
+
DUP_Log::Info("COMPRESSED SIZE: ".DUP_Util::byteSize(self::$zipFileSize));
|
152 |
+
DUP_Log::Info("ARCHIVE RUNTIME: {$timerAllSum}");
|
153 |
+
DUP_Log::Info("MEMORY STACK: ".DUP_Server::getPHPMemory());
|
154 |
+
} catch (Exception $e) {
|
155 |
+
DUP_Log::Error("Runtime error in class.pack.archive.zip.php constructor.", "Exception: {$e}");
|
156 |
+
}
|
157 |
+
}
|
158 |
+
}
|
159 |
+
?>
|
classes/package/class.pack.database.php
ADDED
@@ -0,0 +1,375 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
if (!defined('DUPLICATOR_VERSION')) exit; // Exit if accessed directly
|
3 |
+
|
4 |
+
class DUP_Database
|
5 |
+
{
|
6 |
+
//PUBLIC
|
7 |
+
public $Type = 'MySQL';
|
8 |
+
public $Size;
|
9 |
+
public $File;
|
10 |
+
public $Path;
|
11 |
+
public $FilterTables;
|
12 |
+
public $FilterOn;
|
13 |
+
public $Name;
|
14 |
+
public $Compatible;
|
15 |
+
public $Comments;
|
16 |
+
//PROTECTED
|
17 |
+
protected $Package;
|
18 |
+
//PRIVATE
|
19 |
+
private $dbStorePath;
|
20 |
+
private $EOFMarker;
|
21 |
+
private $networkFlush;
|
22 |
+
|
23 |
+
/**
|
24 |
+
* Init this object
|
25 |
+
*/
|
26 |
+
function __construct($package)
|
27 |
+
{
|
28 |
+
$this->Package = $package;
|
29 |
+
$this->EOFMarker = "";
|
30 |
+
$package_zip_flush = DUP_Settings::Get('package_zip_flush');
|
31 |
+
$this->networkFlush = empty($package_zip_flush) ? false : $package_zip_flush;
|
32 |
+
}
|
33 |
+
|
34 |
+
/**
|
35 |
+
* Build the database script
|
36 |
+
*
|
37 |
+
* @param obj $package A reference to the package that this database object belongs in
|
38 |
+
*
|
39 |
+
* @return null
|
40 |
+
*/
|
41 |
+
public function build($package)
|
42 |
+
{
|
43 |
+
try {
|
44 |
+
|
45 |
+
$this->Package = $package;
|
46 |
+
|
47 |
+
$time_start = DUP_Util::getMicrotime();
|
48 |
+
$this->Package->setStatus(DUP_PackageStatus::DBSTART);
|
49 |
+
$this->dbStorePath = "{$this->Package->StorePath}/{$this->File}";
|
50 |
+
|
51 |
+
$package_mysqldump = DUP_Settings::Get('package_mysqldump');
|
52 |
+
$package_phpdump_qrylimit = DUP_Settings::Get('package_phpdump_qrylimit');
|
53 |
+
|
54 |
+
$mysqlDumpPath = DUP_DB::getMySqlDumpPath();
|
55 |
+
$mode = ($mysqlDumpPath && $package_mysqldump) ? 'MYSQLDUMP' : 'PHP';
|
56 |
+
$reserved_db_filepath = DUPLICATOR_WPROOTPATH.'database.sql';
|
57 |
+
|
58 |
+
|
59 |
+
$log = "\n********************************************************************************\n";
|
60 |
+
$log .= "DATABASE:\n";
|
61 |
+
$log .= "********************************************************************************\n";
|
62 |
+
$log .= "BUILD MODE: {$mode}";
|
63 |
+
$log .= ($mode == 'PHP') ? "(query limit - {$package_phpdump_qrylimit})\n" : "\n";
|
64 |
+
$log .= "MYSQLTIMEOUT: ".DUPLICATOR_DB_MAX_TIME."\n";
|
65 |
+
$log .= "MYSQLDUMP: ";
|
66 |
+
$log .= ($mysqlDumpPath) ? "Is Supported" : "Not Supported";
|
67 |
+
DUP_Log::Info($log);
|
68 |
+
$log = null;
|
69 |
+
|
70 |
+
//Reserved file found
|
71 |
+
if (file_exists($reserved_db_filepath)) {
|
72 |
+
DUP_Log::Error("Reserverd SQL file detected",
|
73 |
+
"The file database.sql was found at [{$reserved_db_filepath}].\n"
|
74 |
+
."\tPlease remove/rename this file to continue with the package creation.");
|
75 |
+
}
|
76 |
+
|
77 |
+
switch ($mode) {
|
78 |
+
case 'MYSQLDUMP':
|
79 |
+
$this->mysqlDump($mysqlDumpPath);
|
80 |
+
break;
|
81 |
+
case 'PHP' :
|
82 |
+
$this->phpDump();
|
83 |
+
break;
|
84 |
+
}
|
85 |
+
|
86 |
+
DUP_Log::Info("SQL CREATED: {$this->File}");
|
87 |
+
$time_end = DUP_Util::getMicrotime();
|
88 |
+
$time_sum = DUP_Util::elapsedTime($time_end, $time_start);
|
89 |
+
|
90 |
+
//File below 10k will be incomplete
|
91 |
+
$sql_file_size = filesize($this->dbStorePath);
|
92 |
+
DUP_Log::Info("SQL FILE SIZE: ".DUP_Util::byteSize($sql_file_size)." ({$sql_file_size})");
|
93 |
+
if ($sql_file_size < 10000) {
|
94 |
+
DUP_Log::Error("SQL file size too low.", "File does not look complete. Check permission on file and parent directory at [{$this->dbStorePath}]");
|
95 |
+
}
|
96 |
+
|
97 |
+
DUP_Log::Info("SQL FILE TIME: ".date("Y-m-d H:i:s"));
|
98 |
+
DUP_Log::Info("SQL RUNTIME: {$time_sum}");
|
99 |
+
|
100 |
+
$this->Size = @filesize($this->dbStorePath);
|
101 |
+
$this->Package->setStatus(DUP_PackageStatus::DBDONE);
|
102 |
+
} catch (Exception $e) {
|
103 |
+
DUP_Log::Error("Runtime error in DUP_Database::Build", "Exception: {$e}");
|
104 |
+
}
|
105 |
+
}
|
106 |
+
|
107 |
+
/**
|
108 |
+
* Get the database meta-data suc as tables as all there details
|
109 |
+
*
|
110 |
+
* @return array Returns an array full of meta-data about the database
|
111 |
+
*/
|
112 |
+
public function getScanData()
|
113 |
+
{
|
114 |
+
global $wpdb;
|
115 |
+
|
116 |
+
$filterTables = isset($this->FilterTables) ? explode(',', $this->FilterTables) : null;
|
117 |
+
$tblCount = 0;
|
118 |
+
|
119 |
+
$tables = $wpdb->get_results("SHOW TABLE STATUS", ARRAY_A);
|
120 |
+
$info = array();
|
121 |
+
$info['Status']['Success'] = is_null($tables) ? false : true;
|
122 |
+
//DB_Case for the database name is never checked on
|
123 |
+
$info['Status']['DB_Case'] = 'Good';
|
124 |
+
$info['Status']['DB_Rows'] = 'Good';
|
125 |
+
$info['Status']['DB_Size'] = 'Good';
|
126 |
+
$info['Status']['TBL_Case'] = 'Good';
|
127 |
+
$info['Status']['TBL_Rows'] = 'Good';
|
128 |
+
$info['Status']['TBL_Size'] = 'Good';
|
129 |
+
|
130 |
+
$info['Size'] = 0;
|
131 |
+
$info['Rows'] = 0;
|
132 |
+
$info['TableCount'] = 0;
|
133 |
+
$info['TableList'] = array();
|
134 |
+
$tblCaseFound = 0;
|
135 |
+
$tblRowsFound = 0;
|
136 |
+
$tblSizeFound = 0;
|
137 |
+
|
138 |
+
//Grab Table Stats
|
139 |
+
foreach ($tables as $table) {
|
140 |
+
$name = $table["Name"];
|
141 |
+
if ($this->FilterOn && is_array($filterTables)) {
|
142 |
+
if (in_array($name, $filterTables)) {
|
143 |
+
continue;
|
144 |
+
}
|
145 |
+
}
|
146 |
+
|
147 |
+
$size = ($table["Data_length"] + $table["Index_length"]);
|
148 |
+
$rows = empty($table["Rows"]) ? '0' : $table["Rows"];
|
149 |
+
|
150 |
+
$info['Size'] += $size;
|
151 |
+
$info['Rows'] += ($table["Rows"]);
|
152 |
+
$info['TableList'][$name]['Case'] = preg_match('/[A-Z]/', $name) ? 1 : 0;
|
153 |
+
$info['TableList'][$name]['Rows'] = number_format($rows);
|
154 |
+
$info['TableList'][$name]['Size'] = DUP_Util::byteSize($size);
|
155 |
+
$tblCount++;
|
156 |
+
|
157 |
+
//Table Uppercase
|
158 |
+
if ($info['TableList'][$name]['Case']) {
|
159 |
+
if (!$tblCaseFound) {
|
160 |
+
$tblCaseFound = 1;
|
161 |
+
}
|
162 |
+
}
|
163 |
+
|
164 |
+
//Table Row Count
|
165 |
+
if ($rows > DUPLICATOR_SCAN_DB_TBL_ROWS) {
|
166 |
+
if (!$tblRowsFound) {
|
167 |
+
$tblRowsFound = 1;
|
168 |
+
}
|
169 |
+
}
|
170 |
+
|
171 |
+
//Table Size
|
172 |
+
if ($size > DUPLICATOR_SCAN_DB_TBL_SIZE) {
|
173 |
+
if (!$tblSizeFound) {
|
174 |
+
$tblSizeFound = 1;
|
175 |
+
}
|
176 |
+
}
|
177 |
+
}
|
178 |
+
|
179 |
+
$info['Status']['DB_Case'] = preg_match('/[A-Z]/', $wpdb->dbname) ? 'Warn' : 'Good';
|
180 |
+
$info['Status']['DB_Rows'] = ($info['Rows'] > DUPLICATOR_SCAN_DB_ALL_ROWS) ? 'Warn' : 'Good';
|
181 |
+
$info['Status']['DB_Size'] = ($info['Size'] > DUPLICATOR_SCAN_DB_ALL_SIZE) ? 'Warn' : 'Good';
|
182 |
+
|
183 |
+
|
184 |
+
$info['Status']['TBL_Case'] = ($tblCaseFound) ? 'Warn' : 'Good';
|
185 |
+
$info['Status']['TBL_Rows'] = ($tblRowsFound) ? 'Warn' : 'Good';
|
186 |
+
$info['Status']['TBL_Size'] = ($tblSizeFound) ? 'Warn' : 'Good';
|
187 |
+
|
188 |
+
$info['Size'] = DUP_Util::byteSize($info['Size']) or "unknown";
|
189 |
+
$info['Rows'] = number_format($info['Rows']) or "unknown";
|
190 |
+
$info['TableList'] = $info['TableList'] or "unknown";
|
191 |
+
$info['TableCount'] = $tblCount;
|
192 |
+
|
193 |
+
return $info;
|
194 |
+
}
|
195 |
+
|
196 |
+
/**
|
197 |
+
* Build the database script using mysqldump
|
198 |
+
*
|
199 |
+
* @return bool Returns true if the sql script was succesfully created
|
200 |
+
*/
|
201 |
+
private function mysqlDump($exePath)
|
202 |
+
{
|
203 |
+
|
204 |
+
global $wpdb;
|
205 |
+
|
206 |
+
$host = explode(':', DB_HOST);
|
207 |
+
$host = reset($host);
|
208 |
+
$port = strpos(DB_HOST, ':') ? end(explode(':', DB_HOST)) : '';
|
209 |
+
$name = DB_NAME;
|
210 |
+
$mysqlcompat_on = isset($this->Compatible) && strlen($this->Compatible);
|
211 |
+
|
212 |
+
//Build command
|
213 |
+
$cmd = escapeshellarg($exePath);
|
214 |
+
$cmd .= ' --no-create-db';
|
215 |
+
$cmd .= ' --single-transaction';
|
216 |
+
$cmd .= ' --hex-blob';
|
217 |
+
$cmd .= ' --skip-add-drop-table';
|
218 |
+
|
219 |
+
//Compatibility mode
|
220 |
+
if ($mysqlcompat_on) {
|
221 |
+
DUP_Log::Info("COMPATIBLE: [{$this->Compatible}]");
|
222 |
+
$cmd .= " --compatible={$this->Compatible}";
|
223 |
+
}
|
224 |
+
|
225 |
+
//Filter tables
|
226 |
+
$tables = $wpdb->get_col('SHOW TABLES');
|
227 |
+
$filterTables = isset($this->FilterTables) ? explode(',', $this->FilterTables) : null;
|
228 |
+
$tblAllCount = count($tables);
|
229 |
+
$tblFilterOn = ($this->FilterOn) ? 'ON' : 'OFF';
|
230 |
+
|
231 |
+
if (is_array($filterTables) && $this->FilterOn) {
|
232 |
+
foreach ($tables as $key => $val) {
|
233 |
+
if (in_array($tables[$key], $filterTables)) {
|
234 |
+
$cmd .= " --ignore-table={$name}.{$tables[$key]} ";
|
235 |
+
unset($tables[$key]);
|
236 |
+
}
|
237 |
+
}
|
238 |
+
}
|
239 |
+
|
240 |
+
$cmd .= ' -u '.escapeshellarg(DB_USER);
|
241 |
+
$cmd .= (DB_PASSWORD) ? ' -p'.escapeshellarg(DB_PASSWORD) : '';
|
242 |
+
$cmd .= ' -h '.escapeshellarg($host);
|
243 |
+
$cmd .= (!empty($port) && is_numeric($port) ) ?
|
244 |
+
' -P '.$port : '';
|
245 |
+
$cmd .= ' -r '.escapeshellarg($this->dbStorePath);
|
246 |
+
$cmd .= ' '.escapeshellarg(DB_NAME);
|
247 |
+
$cmd .= ' 2>&1';
|
248 |
+
|
249 |
+
$output = shell_exec($cmd);
|
250 |
+
|
251 |
+
// Password bug > 5.6 (@see http://bugs.mysql.com/bug.php?id=66546)
|
252 |
+
if (trim($output) === 'Warning: Using a password on the command line interface can be insecure.') {
|
253 |
+
$output = '';
|
254 |
+
}
|
255 |
+
$output = (strlen($output)) ? $output : "Ran from {$exePath}";
|
256 |
+
|
257 |
+
$tblCreateCount = count($tables);
|
258 |
+
$tblFilterCount = $tblAllCount - $tblCreateCount;
|
259 |
+
|
260 |
+
//DEBUG
|
261 |
+
//DUP_Log::Info("COMMAND: {$cmd}");
|
262 |
+
DUP_Log::Info("FILTERED: [{$this->FilterTables}]");
|
263 |
+
DUP_Log::Info("RESPONSE: {$output}");
|
264 |
+
DUP_Log::Info("TABLES: total:{$tblAllCount} | filtered:{$tblFilterCount} | create:{$tblCreateCount}");
|
265 |
+
|
266 |
+
$sql_footer = "\n\n/* Duplicator WordPress Timestamp: ".date("Y-m-d H:i:s")."*/\n";
|
267 |
+
$sql_footer .= "/* ".DUPLICATOR_DB_EOF_MARKER." */\n";
|
268 |
+
file_put_contents($this->dbStorePath, $sql_footer, FILE_APPEND);
|
269 |
+
|
270 |
+
return ($output) ? false : true;
|
271 |
+
}
|
272 |
+
|
273 |
+
/**
|
274 |
+
* Build the database script using php
|
275 |
+
*
|
276 |
+
* @return bool Returns true if the sql script was succesfully created
|
277 |
+
*/
|
278 |
+
private function phpDump()
|
279 |
+
{
|
280 |
+
|
281 |
+
global $wpdb;
|
282 |
+
|
283 |
+
$wpdb->query("SET session wait_timeout = ".DUPLICATOR_DB_MAX_TIME);
|
284 |
+
$handle = fopen($this->dbStorePath, 'w+');
|
285 |
+
$tables = $wpdb->get_col('SHOW TABLES');
|
286 |
+
|
287 |
+
$filterTables = isset($this->FilterTables) ? explode(',', $this->FilterTables) : null;
|
288 |
+
$tblAllCount = count($tables);
|
289 |
+
$tblFilterOn = ($this->FilterOn) ? 'ON' : 'OFF';
|
290 |
+
$qryLimit = DUP_Settings::Get('package_phpdump_qrylimit');
|
291 |
+
|
292 |
+
if (is_array($filterTables) && $this->FilterOn) {
|
293 |
+
foreach ($tables as $key => $val) {
|
294 |
+
if (in_array($tables[$key], $filterTables)) {
|
295 |
+
unset($tables[$key]);
|
296 |
+
}
|
297 |
+
}
|
298 |
+
}
|
299 |
+
$tblCreateCount = count($tables);
|
300 |
+
$tblFilterCount = $tblAllCount - $tblCreateCount;
|
301 |
+
|
302 |
+
DUP_Log::Info("TABLES: total:{$tblAllCount} | filtered:{$tblFilterCount} | create:{$tblCreateCount}");
|
303 |
+
DUP_Log::Info("FILTERED: [{$this->FilterTables}]");
|
304 |
+
|
305 |
+
$sql_header = "/* DUPLICATOR MYSQL SCRIPT CREATED ON : ".@date("Y-m-d H:i:s")." */\n\n";
|
306 |
+
$sql_header .= "SET FOREIGN_KEY_CHECKS = 0;\n\n";
|
307 |
+
fwrite($handle, $sql_header);
|
308 |
+
|
309 |
+
//BUILD CREATES:
|
310 |
+
//All creates must be created before inserts do to foreign key constraints
|
311 |
+
foreach ($tables as $table) {
|
312 |
+
//$sql_del = ($GLOBALS['duplicator_opts']['dbadd_drop']) ? "DROP TABLE IF EXISTS {$table};\n\n" : "";
|
313 |
+
//@fwrite($handle, $sql_del);
|
314 |
+
$create = $wpdb->get_row("SHOW CREATE TABLE `{$table}`", ARRAY_N);
|
315 |
+
@fwrite($handle, "{$create[1]};\n\n");
|
316 |
+
}
|
317 |
+
|
318 |
+
//BUILD INSERTS:
|
319 |
+
//Create Insert in 100 row increments to better handle memory
|
320 |
+
foreach ($tables as $table) {
|
321 |
+
|
322 |
+
$row_count = $wpdb->get_var("SELECT Count(*) FROM `{$table}`");
|
323 |
+
//DUP_Log::Info("{$table} ({$row_count})");
|
324 |
+
|
325 |
+
if ($row_count > $qryLimit) {
|
326 |
+
$row_count = ceil($row_count / $qryLimit);
|
327 |
+
} else if ($row_count > 0) {
|
328 |
+
$row_count = 1;
|
329 |
+
}
|
330 |
+
|
331 |
+
if ($row_count >= 1) {
|
332 |
+
fwrite($handle, "\n/* INSERT TABLE DATA: {$table} */\n");
|
333 |
+
}
|
334 |
+
|
335 |
+
for ($i = 0; $i < $row_count; $i++) {
|
336 |
+
$sql = "";
|
337 |
+
$limit = $i * $qryLimit;
|
338 |
+
$query = "SELECT * FROM `{$table}` LIMIT {$limit}, {$qryLimit}";
|
339 |
+
$rows = $wpdb->get_results($query, ARRAY_A);
|
340 |
+
if (is_array($rows)) {
|
341 |
+
foreach ($rows as $row) {
|
342 |
+
$sql .= "INSERT INTO `{$table}` VALUES(";
|
343 |
+
$num_values = count($row);
|
344 |
+
$num_counter = 1;
|
345 |
+
foreach ($row as $value) {
|
346 |
+
if (is_null($value) || !isset($value)) {
|
347 |
+
($num_values == $num_counter) ? $sql .= 'NULL' : $sql .= 'NULL, ';
|
348 |
+
} else {
|
349 |
+
($num_values == $num_counter) ? $sql .= '"'.@esc_sql($value).'"' : $sql .= '"'.@esc_sql($value).'", ';
|
350 |
+
}
|
351 |
+
$num_counter++;
|
352 |
+
}
|
353 |
+
$sql .= ");\n";
|
354 |
+
}
|
355 |
+
fwrite($handle, $sql);
|
356 |
+
}
|
357 |
+
}
|
358 |
+
|
359 |
+
//Flush buffer if enabled
|
360 |
+
if ($this->networkFlush) {
|
361 |
+
DUP_Util::fcgiFlush();
|
362 |
+
}
|
363 |
+
$sql = null;
|
364 |
+
$rows = null;
|
365 |
+
}
|
366 |
+
|
367 |
+
$sql_footer = "\nSET FOREIGN_KEY_CHECKS = 1; \n\n";
|
368 |
+
$sql_footer .= "/* Duplicator WordPress Timestamp: ".date("Y-m-d H:i:s")."*/\n";
|
369 |
+
$sql_footer .= "/* ".DUPLICATOR_DB_EOF_MARKER." */\n";
|
370 |
+
fwrite($handle, $sql_footer);
|
371 |
+
$wpdb->flush();
|
372 |
+
fclose($handle);
|
373 |
+
}
|
374 |
+
}
|
375 |
+
?>
|
classes/package/class.pack.installer.php
ADDED
@@ -0,0 +1,214 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
if (!defined('DUPLICATOR_VERSION')) exit; // Exit if accessed directly
|
3 |
+
|
4 |
+
class DUP_Installer
|
5 |
+
{
|
6 |
+
//PUBLIC
|
7 |
+
public $File;
|
8 |
+
public $Size = 0;
|
9 |
+
public $OptsDBHost;
|
10 |
+
public $OptsDBPort;
|
11 |
+
public $OptsDBName;
|
12 |
+
public $OptsDBUser;
|
13 |
+
public $OptsSSLAdmin;
|
14 |
+
public $OptsSSLLogin;
|
15 |
+
public $OptsCacheWP;
|
16 |
+
public $OptsCachePath;
|
17 |
+
public $OptsURLNew;
|
18 |
+
//PROTECTED
|
19 |
+
protected $Package;
|
20 |
+
|
21 |
+
/**
|
22 |
+
* Init this object
|
23 |
+
*/
|
24 |
+
function __construct($package)
|
25 |
+
{
|
26 |
+
$this->Package = $package;
|
27 |
+
}
|
28 |
+
|
29 |
+
/**
|
30 |
+
* Build the installer script
|
31 |
+
*
|
32 |
+
* @param obj $package A reference to the package that this installer object belongs to
|
33 |
+
*
|
34 |
+
* @return null
|
35 |
+
*/
|
36 |
+
public function build($package)
|
37 |
+
{
|
38 |
+
|
39 |
+
$this->Package = $package;
|
40 |
+
|
41 |
+
DUP_Log::Info("\n********************************************************************************");
|
42 |
+
DUP_Log::Info("MAKE INSTALLER:");
|
43 |
+
DUP_Log::Info("********************************************************************************");
|
44 |
+
DUP_Log::Info("Build Start");
|
45 |
+
|
46 |
+
$template_uniqid = uniqid('').'_'.time();
|
47 |
+
$template_path = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP."/installer.template_{$template_uniqid}.php");
|
48 |
+
$main_path = DUP_Util::safePath(DUPLICATOR_PLUGIN_PATH.'installer/build/main.installer.php');
|
49 |
+
@chmod($template_path, 0777);
|
50 |
+
@chmod($main_path, 0777);
|
51 |
+
|
52 |
+
@touch($template_path);
|
53 |
+
$main_data = file_get_contents("{$main_path}");
|
54 |
+
$template_result = file_put_contents($template_path, $main_data);
|
55 |
+
if ($main_data === false || $template_result == false) {
|
56 |
+
$err_info = "These files may have permission issues. Please validate that PHP has read/write access.\n";
|
57 |
+
$err_info .= "Main Installer: '{$main_path}' \nTemplate Installer: '$template_path'";
|
58 |
+
DUP_Log::Error("Install builder failed to generate files.", "{$err_info}");
|
59 |
+
}
|
60 |
+
|
61 |
+
$embeded_files = array(
|
62 |
+
"assets/inc.libs.css.php" => "@@INC.LIBS.CSS.PHP@@",
|
63 |
+
"assets/inc.css.php" => "@@INC.CSS.PHP@@",
|
64 |
+
"assets/inc.libs.js.php" => "@@INC.LIBS.JS.PHP@@",
|
65 |
+
"assets/inc.js.php" => "@@INC.JS.PHP@@",
|
66 |
+
"classes/util/class.utils.php" => "@@CLASS.UTILS.PHP@@",
|
67 |
+
"classes/util/class.db.php" => "@@CLASS.DB.PHP@@",
|
68 |
+
"classes/class.logging.php" => "@@CLASS.LOGGING.PHP@@",
|
69 |
+
"classes/class.engine.php" => "@@CLASS.ENGINE.PHP@@",
|
70 |
+
"classes/config/class.conf.wp.php" => "@@CLASS.CONF.WP.PHP@@",
|
71 |
+
"classes/config/class.conf.srv.php" => "@@CLASS.CONF.SRV.PHP@@",
|
72 |
+
"ajax.step1.php" => "@@AJAX.STEP1.PHP@@",
|
73 |
+
"ajax.step2.php" => "@@AJAX.STEP2.PHP@@",
|
74 |
+
"view.step1.php" => "@@VIEW.STEP1.PHP@@",
|
75 |
+
"view.step2.php" => "@@VIEW.STEP2.PHP@@",
|
76 |
+
"view.step3.php" => "@@VIEW.STEP3.PHP@@",
|
77 |
+
"view.help.php" => "@@VIEW.HELP.PHP@@",);
|
78 |
+
|
79 |
+
foreach ($embeded_files as $name => $token) {
|
80 |
+
$file_path = DUPLICATOR_PLUGIN_PATH."installer/build/{$name}";
|
81 |
+
@chmod($file_path, 0777);
|
82 |
+
|
83 |
+
$search_data = @file_get_contents($template_path);
|
84 |
+
$insert_data = @file_get_contents($file_path);
|
85 |
+
file_put_contents($template_path, str_replace("${token}", "{$insert_data}", $search_data));
|
86 |
+
if ($search_data === false || $insert_data == false) {
|
87 |
+
DUP_Log::Error("Installer generation failed at {$token}.");
|
88 |
+
}
|
89 |
+
@chmod($file_path, 0644);
|
90 |
+
}
|
91 |
+
|
92 |
+
@chmod($template_path, 0644);
|
93 |
+
@chmod($main_path, 0644);
|
94 |
+
|
95 |
+
DUP_Log::Info("Build Finished");
|
96 |
+
$this->createFromTemplate($template_path);
|
97 |
+
$storePath = "{$this->Package->StorePath}/{$this->File}";
|
98 |
+
$this->Size = @filesize($storePath);
|
99 |
+
$this->addBackup();
|
100 |
+
}
|
101 |
+
|
102 |
+
/**
|
103 |
+
* Puts an installer zip file in the archive for backup purposes.
|
104 |
+
*
|
105 |
+
* @return null
|
106 |
+
*/
|
107 |
+
private function addBackup()
|
108 |
+
{
|
109 |
+
|
110 |
+
$zipPath = DUP_Util::safePath("{$this->Package->StorePath}/{$this->Package->Archive->File}");
|
111 |
+
$installer = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP)."/{$this->Package->NameHash}_installer.php";
|
112 |
+
|
113 |
+
$zipArchive = new ZipArchive();
|
114 |
+
if ($zipArchive->open($zipPath, ZIPARCHIVE::CREATE) === TRUE) {
|
115 |
+
if ($zipArchive->addFile($installer, "installer-backup.php")) {
|
116 |
+
DUP_Log::Info("Added to archive");
|
117 |
+
} else {
|
118 |
+
DUP_Log::Info("Unable to add installer-backup.php to archive.", "Installer File Path [{$installer}]");
|
119 |
+
}
|
120 |
+
$zipArchive->close();
|
121 |
+
}
|
122 |
+
}
|
123 |
+
|
124 |
+
/**
|
125 |
+
* Generates the final installer file from the template file
|
126 |
+
*
|
127 |
+
* @param string $template The path to the installer template which is orginally copied from main.installer.php
|
128 |
+
*
|
129 |
+
* @return null
|
130 |
+
*/
|
131 |
+
private function createFromTemplate($template)
|
132 |
+
{
|
133 |
+
|
134 |
+
global $wpdb;
|
135 |
+
|
136 |
+
DUP_Log::Info("Preping for use");
|
137 |
+
$installer = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP)."/{$this->Package->NameHash}_installer.php";
|
138 |
+
|
139 |
+
//Option values to delete at install time
|
140 |
+
$deleteOpts = $GLOBALS['DUPLICATOR_OPTS_DELETE'];
|
141 |
+
|
142 |
+
$replace_items = Array(
|
143 |
+
//COMPARE VALUES
|
144 |
+
"fwrite_created" => $this->Package->Created,
|
145 |
+
"fwrite_version_dup" => DUPLICATOR_VERSION,
|
146 |
+
"fwrite_version_wp" => $this->Package->VersionWP,
|
147 |
+
"fwrite_version_db" => $this->Package->VersionDB,
|
148 |
+
"fwrite_version_php" => $this->Package->VersionPHP,
|
149 |
+
"fwrite_version_os" => $this->Package->VersionOS,
|
150 |
+
//GENERAL
|
151 |
+
"fwrite_url_old" => get_option('siteurl'),
|
152 |
+
"fwrite_package_name" => "{$this->Package->NameHash}_archive.zip",
|
153 |
+
"fwrite_package_notes" => $this->Package->Notes,
|
154 |
+
"fwrite_secure_name" => $this->Package->NameHash,
|
155 |
+
"fwrite_url_new" => $this->Package->Installer->OptsURLNew,
|
156 |
+
"fwrite_dbhost" => $this->Package->Installer->OptsDBHost,
|
157 |
+
"fwrite_dbport" => $this->Package->Installer->OptsDBPort,
|
158 |
+
"fwrite_dbname" => $this->Package->Installer->OptsDBName,
|
159 |
+
"fwrite_dbuser" => $this->Package->Installer->OptsDBUser,
|
160 |
+
"fwrite_dbpass" => '',
|
161 |
+
"fwrite_ssl_admin" => $this->Package->Installer->OptsSSLAdmin,
|
162 |
+
"fwrite_ssl_login" => $this->Package->Installer->OptsSSLLogin,
|
163 |
+
"fwrite_cache_wp" => $this->Package->Installer->OptsCacheWP,
|
164 |
+
"fwrite_cache_path" => $this->Package->Installer->OptsCachePath,
|
165 |
+
"fwrite_wp_tableprefix" => $wpdb->prefix,
|
166 |
+
"fwrite_opts_delete" => json_encode($deleteOpts),
|
167 |
+
"fwrite_blogname" => esc_html(get_option('blogname')),
|
168 |
+
"fwrite_wproot" => DUPLICATOR_WPROOTPATH,
|
169 |
+
"fwrite_duplicator_version" => DUPLICATOR_VERSION);
|
170 |
+
|
171 |
+
if (file_exists($template) && is_readable($template)) {
|
172 |
+
$err_msg = "ERROR: Unable to read/write installer. \nERROR INFO: Check permission/owner on file and parent folder.\nInstaller File = <{$installer}>";
|
173 |
+
$install_str = $this->parseTemplate($template, $replace_items);
|
174 |
+
(empty($install_str)) ? DUP_Log::Error("{$err_msg}", "DUP_Installer::createFromTemplate => file-empty-read") : DUP_Log::Info("Template parsed with new data");
|
175 |
+
|
176 |
+
//INSTALLER FILE
|
177 |
+
$fp = (!file_exists($installer)) ? fopen($installer, 'x+') : fopen($installer, 'w');
|
178 |
+
if (!$fp || !fwrite($fp, $install_str, strlen($install_str))) {
|
179 |
+
DUP_Log::Error("{$err_msg}", "DUP_Installer::createFromTemplate => file-write-error");
|
180 |
+
}
|
181 |
+
|
182 |
+
@fclose($fp);
|
183 |
+
} else {
|
184 |
+
DUP_Log::Error("Installer Template missing or unreadable.", "Template [{$template}]");
|
185 |
+
}
|
186 |
+
@unlink($template);
|
187 |
+
DUP_Log::Info("Complete [{$installer}]");
|
188 |
+
}
|
189 |
+
|
190 |
+
/**
|
191 |
+
* Tokenize a file based on an array key
|
192 |
+
*
|
193 |
+
* @param string $filename The filename to tokenize
|
194 |
+
* @param array $data The array of key value items to tokenize
|
195 |
+
*/
|
196 |
+
private function parseTemplate($filename, $data)
|
197 |
+
{
|
198 |
+
$q = file_get_contents($filename);
|
199 |
+
foreach ($data as $key => $value) {
|
200 |
+
//NOTE: Use var_export as it's probably best and most "thorough" way to
|
201 |
+
//make sure the values are set correctly in the template. But in the template,
|
202 |
+
//need to make things properly formatted so that when real syntax errors
|
203 |
+
//exist they are easy to spot. So the values will be surrounded by quotes
|
204 |
+
|
205 |
+
$find = array("'%{$key}%'", "\"%{$key}%\"");
|
206 |
+
$q = str_replace($find, var_export($value, true), $q);
|
207 |
+
//now, account for places that do not surround with quotes... these
|
208 |
+
//places do NOT need to use var_export as they are not inside strings
|
209 |
+
$q = str_replace('%'.$key.'%', $value, $q);
|
210 |
+
}
|
211 |
+
return $q;
|
212 |
+
}
|
213 |
+
}
|
214 |
+
?>
|
classes/package/class.pack.php
ADDED
@@ -0,0 +1,622 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
if (!defined('DUPLICATOR_VERSION')) exit; // Exit if accessed directly
|
3 |
+
|
4 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/utilities/class.util.php');
|
5 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/package/class.pack.archive.php');
|
6 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/package/class.pack.installer.php');
|
7 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/package/class.pack.database.php');
|
8 |
+
|
9 |
+
final class DUP_PackageStatus
|
10 |
+
{
|
11 |
+
|
12 |
+
private function __construct()
|
13 |
+
{
|
14 |
+
|
15 |
+
}
|
16 |
+
const START = 10;
|
17 |
+
const DBSTART = 20;
|
18 |
+
const DBDONE = 30;
|
19 |
+
const ARCSTART = 40;
|
20 |
+
const ARCDONE = 50;
|
21 |
+
const COMPLETE = 100;
|
22 |
+
|
23 |
+
}
|
24 |
+
|
25 |
+
final class DUP_PackageType
|
26 |
+
{
|
27 |
+
const MANUAL = 0;
|
28 |
+
const SCHEDULED = 1;
|
29 |
+
|
30 |
+
}
|
31 |
+
|
32 |
+
/**
|
33 |
+
* Class used to store and process all Package logic
|
34 |
+
*
|
35 |
+
* @package Dupicator\classes
|
36 |
+
*/
|
37 |
+
class DUP_Package
|
38 |
+
{
|
39 |
+
const OPT_ACTIVE = 'duplicator_package_active';
|
40 |
+
|
41 |
+
//Properties
|
42 |
+
public $Created;
|
43 |
+
public $Version;
|
44 |
+
public $VersionWP;
|
45 |
+
public $VersionDB;
|
46 |
+
public $VersionPHP;
|
47 |
+
public $VersionOS;
|
48 |
+
public $ID;
|
49 |
+
public $Name;
|
50 |
+
public $Hash;
|
51 |
+
public $NameHash;
|
52 |
+
public $Type;
|
53 |
+
public $Notes;
|
54 |
+
public $StorePath;
|
55 |
+
public $StoreURL;
|
56 |
+
public $ScanFile;
|
57 |
+
public $Runtime;
|
58 |
+
public $ExeSize;
|
59 |
+
public $ZipSize;
|
60 |
+
public $Status;
|
61 |
+
public $WPUser;
|
62 |
+
//Objects
|
63 |
+
public $Archive;
|
64 |
+
public $Installer;
|
65 |
+
public $Database;
|
66 |
+
|
67 |
+
/**
|
68 |
+
* Manages the Package Process
|
69 |
+
*/
|
70 |
+
function __construct()
|
71 |
+
{
|
72 |
+
|
73 |
+
$this->ID = null;
|
74 |
+
$this->Version = DUPLICATOR_VERSION;
|
75 |
+
|
76 |
+
$this->Type = DUP_PackageType::MANUAL;
|
77 |
+
$this->Name = self::getDefaultName();
|
78 |
+
$this->Notes = null;
|
79 |
+
$this->StoreURL = DUP_Util::snapshotURL();
|
80 |
+
$this->StorePath = DUPLICATOR_SSDIR_PATH_TMP;
|
81 |
+
$this->Database = new DUP_Database($this);
|
82 |
+
$this->Archive = new DUP_Archive($this);
|
83 |
+
$this->Installer = new DUP_Installer($this);
|
84 |
+
}
|
85 |
+
|
86 |
+
/**
|
87 |
+
* Generates a json scan report
|
88 |
+
*
|
89 |
+
* @return array of scan results
|
90 |
+
*
|
91 |
+
* @notes: Testing = /wp-admin/admin-ajax.php?action=duplicator_package_scan
|
92 |
+
*/
|
93 |
+
public function runScanner()
|
94 |
+
{
|
95 |
+
$timerStart = DUP_Util::getMicrotime();
|
96 |
+
$report = array();
|
97 |
+
$this->ScanFile = "{$this->NameHash}_scan.json";
|
98 |
+
|
99 |
+
$report['RPT']['ScanTime'] = "0";
|
100 |
+
$report['RPT']['ScanFile'] = $this->ScanFile;
|
101 |
+
|
102 |
+
//SERVER
|
103 |
+
$srv = DUP_Server::getChecks();
|
104 |
+
$report['SRV'] = $srv['SRV'];
|
105 |
+
|
106 |
+
//FILES
|
107 |
+
$this->Archive->getScanData();
|
108 |
+
$dirCount = count($this->Archive->Dirs);
|
109 |
+
$fileCount = count($this->Archive->Files);
|
110 |
+
$fullCount = $dirCount + $fileCount;
|
111 |
+
|
112 |
+
$report['ARC']['Size'] = DUP_Util::byteSize($this->Archive->Size) or "unknown";
|
113 |
+
$report['ARC']['DirCount'] = number_format($dirCount);
|
114 |
+
$report['ARC']['FileCount'] = number_format($fileCount);
|
115 |
+
$report['ARC']['FullCount'] = number_format($fullCount);
|
116 |
+
|
117 |
+
$report['ARC']['FilterInfo']['Dirs'] = $this->Archive->FilterInfo->Dirs;
|
118 |
+
$report['ARC']['FilterInfo']['Files'] = $this->Archive->FilterInfo->Files;
|
119 |
+
$report['ARC']['FilterInfo']['Exts'] = $this->Archive->FilterInfo->Exts;
|
120 |
+
|
121 |
+
$report['ARC']['Status']['Size'] = ($this->Archive->Size > DUPLICATOR_SCAN_SITE) ? 'Warn' : 'Good';
|
122 |
+
$report['ARC']['Status']['Names'] = (count($this->Archive->FilterInfo->Files->Warning) + count($this->Archive->FilterInfo->Dirs->Warning)) ? 'Warn' : 'Good';
|
123 |
+
$report['ARC']['Status']['Big'] = count($this->Archive->FilterInfo->Files->Size) ? 'Warn' : 'Good';
|
124 |
+
|
125 |
+
$report['ARC']['Dirs'] = $this->Archive->Dirs;
|
126 |
+
$report['ARC']['Files'] = $this->Archive->Files;
|
127 |
+
|
128 |
+
//DATABASE
|
129 |
+
$db = $this->Database->getScanData();
|
130 |
+
$report['DB'] = $db;
|
131 |
+
|
132 |
+
$warnings = array($report['SRV']['WEB']['ALL'],
|
133 |
+
$report['SRV']['PHP']['ALL'],
|
134 |
+
$report['SRV']['WP']['ALL'],
|
135 |
+
$report['ARC']['Status']['Size'],
|
136 |
+
$report['ARC']['Status']['Names'],
|
137 |
+
$report['ARC']['Status']['Big'],
|
138 |
+
$db['Status']['Size'],
|
139 |
+
$db['Status']['Rows'],
|
140 |
+
$db['Status']['Case']);
|
141 |
+
|
142 |
+
//array_count_values will throw a warning message if it has null values,
|
143 |
+
//so lets replace all nulls with empty string
|
144 |
+
foreach ($warnings as $i => $value) {
|
145 |
+
if (is_null($value)) {
|
146 |
+
$warnings[$i] = '';
|
147 |
+
}
|
148 |
+
}
|
149 |
+
$warn_counts = is_array($warnings) ? array_count_values($warnings) : 0;
|
150 |
+
$report['RPT']['Warnings'] = $warn_counts['Warn'];
|
151 |
+
$report['RPT']['Success'] = $warn_counts['Good'];
|
152 |
+
$report['RPT']['ScanTime'] = DUP_Util::elapsedTime(DUP_Util::getMicrotime(), $timerStart);
|
153 |
+
$fp = fopen(DUPLICATOR_SSDIR_PATH_TMP."/{$this->ScanFile}", 'w');
|
154 |
+
fwrite($fp, json_encode($report));
|
155 |
+
fclose($fp);
|
156 |
+
|
157 |
+
return $report;
|
158 |
+
}
|
159 |
+
|
160 |
+
/**
|
161 |
+
* Starts the package build process
|
162 |
+
*
|
163 |
+
* @return obj Retuns a DUP_Package object
|
164 |
+
*/
|
165 |
+
public function runBuild()
|
166 |
+
{
|
167 |
+
|
168 |
+
global $wp_version;
|
169 |
+
global $wpdb;
|
170 |
+
global $current_user;
|
171 |
+
|
172 |
+
$timerStart = DUP_Util::getMicrotime();
|
173 |
+
|
174 |
+
$this->Archive->File = "{$this->NameHash}_archive.zip";
|
175 |
+
$this->Installer->File = "{$this->NameHash}_installer.php";
|
176 |
+
$this->Database->File = "{$this->NameHash}_database.sql";
|
177 |
+
$this->WPUser = isset($current_user->user_login) ? $current_user->user_login : 'unknown';
|
178 |
+
|
179 |
+
//START LOGGING
|
180 |
+
DUP_Log::Open($this->NameHash);
|
181 |
+
$php_max_time = @ini_get("max_execution_time");
|
182 |
+
$php_max_memory = @ini_set('memory_limit', DUPLICATOR_PHP_MAX_MEMORY);
|
183 |
+
$php_max_time = ($php_max_time == 0) ? "(0) no time limit imposed" : "[{$php_max_time}] not allowed";
|
184 |
+
$php_max_memory = ($php_max_memory === false) ? "Unabled to set php memory_limit" : DUPLICATOR_PHP_MAX_MEMORY." ({$php_max_memory} default)";
|
185 |
+
|
186 |
+
$info = "********************************************************************************\n";
|
187 |
+
$info .= "DUPLICATOR-LITE PACKAGE-LOG: ".@date("Y-m-d H:i:s")."\n";
|
188 |
+
$info .= "NOTICE: Do NOT post to public sites or forums \n";
|
189 |
+
$info .= "********************************************************************************\n";
|
190 |
+
$info .= "VERSION:\t".DUPLICATOR_VERSION."\n";
|
191 |
+
$info .= "WORDPRESS:\t{$wp_version}\n";
|
192 |
+
$info .= "PHP INFO:\t".phpversion().' | '.'SAPI: '.php_sapi_name()."\n";
|
193 |
+
$info .= "SERVER:\t\t{$_SERVER['SERVER_SOFTWARE']} \n";
|
194 |
+
$info .= "PHP TIME LIMIT: {$php_max_time} \n";
|
195 |
+
$info .= "PHP MAX MEMORY: {$php_max_memory} \n";
|
196 |
+
$info .= "MEMORY STACK: ".DUP_Server::getPHPMemory();
|
197 |
+
DUP_Log::Info($info);
|
198 |
+
$info = null;
|
199 |
+
|
200 |
+
//CREATE DB RECORD
|
201 |
+
$packageObj = serialize($this);
|
202 |
+
if (!$packageObj) {
|
203 |
+
DUP_Log::Error("Unable to serialize pacakge object while building record.");
|
204 |
+
}
|
205 |
+
|
206 |
+
$this->ID = $this->getHashKey($this->Hash);
|
207 |
+
|
208 |
+
if ($this->ID != 0) {
|
209 |
+
$this->setStatus(DUP_PackageStatus::START);
|
210 |
+
} else {
|
211 |
+
$results = $wpdb->insert($wpdb->prefix."duplicator_packages",
|
212 |
+
array(
|
213 |
+
'name' => $this->Name,
|
214 |
+
'hash' => $this->Hash,
|
215 |
+
'status' => DUP_PackageStatus::START,
|
216 |
+
'created' => current_time('mysql', get_option('gmt_offset', 1)),
|
217 |
+
'owner' => isset($current_user->user_login) ? $current_user->user_login : 'unknown',
|
218 |
+
'package' => $packageObj)
|
219 |
+
);
|
220 |
+
if ($results === false) {
|
221 |
+
|
222 |
+
$wpdb->print_error();
|
223 |
+
DUP_Log::Error("Duplicator is unable to insert a package record into the database table.", "'{$wpdb->last_error}'");
|
224 |
+
}
|
225 |
+
$this->ID = $wpdb->insert_id;
|
226 |
+
}
|
227 |
+
|
228 |
+
//START BUILD
|
229 |
+
//PHPs serialze method will return the object, but the ID above is not passed
|
230 |
+
//for one reason or another so passing the object back in seems to do the trick
|
231 |
+
$this->Database->build($this);
|
232 |
+
$this->Archive->build($this);
|
233 |
+
$this->Installer->build($this);
|
234 |
+
|
235 |
+
|
236 |
+
//INTEGRITY CHECKS
|
237 |
+
DUP_Log::Info("\n********************************************************************************");
|
238 |
+
DUP_Log::Info("INTEGRITY CHECKS:");
|
239 |
+
DUP_Log::Info("********************************************************************************");
|
240 |
+
$dbSizeRead = DUP_Util::byteSize($this->Database->Size);
|
241 |
+
$zipSizeRead = DUP_Util::byteSize($this->Archive->Size);
|
242 |
+
$exeSizeRead = DUP_Util::byteSize($this->Installer->Size);
|
243 |
+
|
244 |
+
DUP_Log::Info("SQL File: {$dbSizeRead}");
|
245 |
+
DUP_Log::Info("Installer File: {$exeSizeRead}");
|
246 |
+
DUP_Log::Info("Archive File: {$zipSizeRead} ");
|
247 |
+
|
248 |
+
if (!($this->Archive->Size && $this->Database->Size && $this->Installer->Size)) {
|
249 |
+
DUP_Log::Error("A required file contains zero bytes.", "Archive Size: {$zipSizeRead} | SQL Size: {$dbSizeRead} | Installer Size: {$exeSizeRead}");
|
250 |
+
}
|
251 |
+
|
252 |
+
//Validate SQL files completed
|
253 |
+
$sql_tmp_path = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP.'/'.$this->Database->File);
|
254 |
+
$sql_complete_txt = DUP_Util::tailFile($sql_tmp_path, 3);
|
255 |
+
if (!strstr($sql_complete_txt, 'DUPLICATOR_MYSQLDUMP_EOF')) {
|
256 |
+
DUP_Log::Error("ERROR: SQL file not complete. The end of file marker was not found. Please try to re-create the package.");
|
257 |
+
}
|
258 |
+
|
259 |
+
$timerEnd = DUP_Util::getMicrotime();
|
260 |
+
$timerSum = DUP_Util::elapsedTime($timerEnd, $timerStart);
|
261 |
+
|
262 |
+
$this->Runtime = $timerSum;
|
263 |
+
$this->ExeSize = $exeSizeRead;
|
264 |
+
$this->ZipSize = $zipSizeRead;
|
265 |
+
|
266 |
+
$this->buildCleanup();
|
267 |
+
|
268 |
+
//FINAL REPORT
|
269 |
+
$info = "\n********************************************************************************\n";
|
270 |
+
$info .= "RECORD ID:[{$this->ID}]\n";
|
271 |
+
$info .= "TOTAL PROCESS RUNTIME: {$timerSum}\n";
|
272 |
+
$info .= "PEAK PHP MEMORY USED: ".DUP_Server::getPHPMemory(true)."\n";
|
273 |
+
$info .= "DONE PROCESSING => {$this->Name} ".@date("Y-m-d H:i:s")."\n";
|
274 |
+
|
275 |
+
DUP_Log::Info($info);
|
276 |
+
DUP_Log::Close();
|
277 |
+
|
278 |
+
$this->setStatus(DUP_PackageStatus::COMPLETE);
|
279 |
+
return $this;
|
280 |
+
}
|
281 |
+
|
282 |
+
/**
|
283 |
+
* Saves the active options associted with the active(latest) package.
|
284 |
+
*
|
285 |
+
* @see DUP_Package::getActive
|
286 |
+
*
|
287 |
+
* @param $_POST $post The Post server object
|
288 |
+
*
|
289 |
+
* @return null
|
290 |
+
*/
|
291 |
+
public function saveActive($post = null)
|
292 |
+
{
|
293 |
+
global $wp_version;
|
294 |
+
|
295 |
+
if (isset($post)) {
|
296 |
+
$post = stripslashes_deep($post);
|
297 |
+
|
298 |
+
$name_chars = array(".", "-");
|
299 |
+
$name = ( isset($post['package-name']) && !empty($post['package-name'])) ? $post['package-name'] : self::getDefaultName();
|
300 |
+
$name = substr(sanitize_file_name($name), 0, 40);
|
301 |
+
$name = str_replace($name_chars, '', $name);
|
302 |
+
|
303 |
+
$filter_dirs = isset($post['filter-dirs']) ? $this->parseDirectoryFilter($post['filter-dirs']) : '';
|
304 |
+
$filter_exts = isset($post['filter-exts']) ? $this->parseExtensionFilter($post['filter-exts']) : '';
|
305 |
+
$tablelist = isset($post['dbtables']) ? implode(',', $post['dbtables']) : '';
|
306 |
+
$compatlist = isset($post['dbcompat']) ? implode(',', $post['dbcompat']) : '';
|
307 |
+
$dbversion = DUP_DB::getVersion();
|
308 |
+
$dbversion = is_null($dbversion) ? '- unknown -' : $dbversion;
|
309 |
+
$dbcomments = DUP_DB::getVariable('version_comment');
|
310 |
+
$dbcomments = is_null($dbcomments) ? '- unknown -' : $dbcomments;
|
311 |
+
|
312 |
+
//PACKAGE
|
313 |
+
$this->Created = date("Y-m-d H:i:s");
|
314 |
+
$this->Version = DUPLICATOR_VERSION;
|
315 |
+
$this->VersionOS = defined('PHP_OS') ? PHP_OS : 'unknown';
|
316 |
+
$this->VersionWP = $wp_version;
|
317 |
+
$this->VersionPHP = phpversion();
|
318 |
+
$this->VersionDB = $dbversion;
|
319 |
+
$this->Name = $name;
|
320 |
+
$this->Hash = $this->makeHash();
|
321 |
+
$this->NameHash = "{$this->Name}_{$this->Hash}";
|
322 |
+
|
323 |
+
$this->Notes = esc_html($post['package-notes']);
|
324 |
+
//ARCHIVE
|
325 |
+
$this->Archive->PackDir = rtrim(DUPLICATOR_WPROOTPATH, '/');
|
326 |
+
$this->Archive->Format = 'ZIP';
|
327 |
+
$this->Archive->FilterOn = isset($post['filter-on']) ? 1 : 0;
|
328 |
+
$this->Archive->FilterDirs = esc_html($filter_dirs);
|
329 |
+
$this->Archive->FilterExts = str_replace(array('.', ' '), "", esc_html($filter_exts));
|
330 |
+
//INSTALLER
|
331 |
+
$this->Installer->OptsDBHost = esc_html($post['dbhost']);
|
332 |
+
$this->Installer->OptsDBPort = esc_html($post['dbport']);
|
333 |
+
$this->Installer->OptsDBName = esc_html($post['dbname']);
|
334 |
+
$this->Installer->OptsDBUser = esc_html($post['dbuser']);
|
335 |
+
$this->Installer->OptsSSLAdmin = isset($post['ssl-admin']) ? 1 : 0;
|
336 |
+
$this->Installer->OptsSSLLogin = isset($post['ssl-login']) ? 1 : 0;
|
337 |
+
$this->Installer->OptsCacheWP = isset($post['cache-wp']) ? 1 : 0;
|
338 |
+
$this->Installer->OptsCachePath = isset($post['cache-path']) ? 1 : 0;
|
339 |
+
$this->Installer->OptsURLNew = esc_html($post['url-new']);
|
340 |
+
//DATABASE
|
341 |
+
$this->Database->FilterOn = isset($post['dbfilter-on']) ? 1 : 0;
|
342 |
+
$this->Database->FilterTables = esc_html($tablelist);
|
343 |
+
$this->Database->Compatible = $compatlist;
|
344 |
+
$this->Database->Comments = $dbcomments;
|
345 |
+
|
346 |
+
update_option(self::OPT_ACTIVE, $this);
|
347 |
+
}
|
348 |
+
}
|
349 |
+
|
350 |
+
/**
|
351 |
+
* Save any property of this class through reflection
|
352 |
+
*
|
353 |
+
* @param $property A valid public property in this class
|
354 |
+
* @param $value The value for the new dynamic property
|
355 |
+
*
|
356 |
+
* @return null
|
357 |
+
*/
|
358 |
+
public function saveActiveItem($property, $value)
|
359 |
+
{
|
360 |
+
$package = self::getActive();
|
361 |
+
|
362 |
+
$reflectionClass = new ReflectionClass($package);
|
363 |
+
$reflectionClass->getProperty($property)->setValue($package, $value);
|
364 |
+
update_option(self::OPT_ACTIVE, $package);
|
365 |
+
}
|
366 |
+
|
367 |
+
/**
|
368 |
+
* Sets the status to log the state of the build
|
369 |
+
*
|
370 |
+
* @param $status The status level for where the package is
|
371 |
+
*
|
372 |
+
* @return void
|
373 |
+
*/
|
374 |
+
public function setStatus($status)
|
375 |
+
{
|
376 |
+
global $wpdb;
|
377 |
+
|
378 |
+
$packageObj = serialize($this);
|
379 |
+
|
380 |
+
if (!isset($status)) {
|
381 |
+
DUP_Log::Error("Package SetStatus did not receive a proper code.");
|
382 |
+
}
|
383 |
+
|
384 |
+
if (!$packageObj) {
|
385 |
+
DUP_Log::Error("Package SetStatus was unable to serialize package object while updating record.");
|
386 |
+
}
|
387 |
+
|
388 |
+
$wpdb->flush();
|
389 |
+
$table = $wpdb->prefix."duplicator_packages";
|
390 |
+
$sql = "UPDATE `{$table}` SET status = {$status}, package = '{$packageObj}' WHERE ID = {$this->ID}";
|
391 |
+
$wpdb->query($sql);
|
392 |
+
}
|
393 |
+
|
394 |
+
/**
|
395 |
+
* Does a hash already exisit
|
396 |
+
*
|
397 |
+
* @param string $hash An existing hash value
|
398 |
+
*
|
399 |
+
* @return int Returns 0 if no hash is found, if found returns the table ID
|
400 |
+
*/
|
401 |
+
public function getHashKey($hash)
|
402 |
+
{
|
403 |
+
global $wpdb;
|
404 |
+
|
405 |
+
$table = $wpdb->prefix."duplicator_packages";
|
406 |
+
$qry = $wpdb->get_row("SELECT ID, hash FROM `{$table}` WHERE hash = '{$hash}'");
|
407 |
+
if (strlen($qry->hash) == 0) {
|
408 |
+
return 0;
|
409 |
+
} else {
|
410 |
+
return $qry->ID;
|
411 |
+
}
|
412 |
+
}
|
413 |
+
|
414 |
+
/**
|
415 |
+
* Makes the hashkey for the package files
|
416 |
+
*
|
417 |
+
* @return string Returns a unique hashkey
|
418 |
+
*/
|
419 |
+
public function makeHash()
|
420 |
+
{
|
421 |
+
return uniqid().mt_rand(1000, 9999).date("ymdHis");
|
422 |
+
}
|
423 |
+
|
424 |
+
/**
|
425 |
+
* Gets the active package which is defined as the package that was lasted saved.
|
426 |
+
* Do to cache issues with the built in WP function get_option moved call to a direct DB call.
|
427 |
+
*
|
428 |
+
* @see DUP_Package::saveActive
|
429 |
+
*
|
430 |
+
* @return obj A copy of the DUP_Package object
|
431 |
+
*/
|
432 |
+
public static function getActive()
|
433 |
+
{
|
434 |
+
global $wpdb;
|
435 |
+
|
436 |
+
$obj = new DUP_Package();
|
437 |
+
$row = $wpdb->get_row($wpdb->prepare("SELECT option_value FROM `{$wpdb->options}` WHERE option_name = %s LIMIT 1", self::OPT_ACTIVE));
|
438 |
+
if (is_object($row)) {
|
439 |
+
$obj = @unserialize($row->option_value);
|
440 |
+
}
|
441 |
+
//Incase unserilaize fails
|
442 |
+
$obj = (is_object($obj)) ? $obj : new DUP_Package();
|
443 |
+
return $obj;
|
444 |
+
}
|
445 |
+
|
446 |
+
/**
|
447 |
+
* Gets the Package by ID
|
448 |
+
*
|
449 |
+
* @param int $id A valid package id form the duplicator_packages table
|
450 |
+
*
|
451 |
+
* @return obj A copy of the DUP_Package object
|
452 |
+
*/
|
453 |
+
public static function getByID($id)
|
454 |
+
{
|
455 |
+
|
456 |
+
global $wpdb;
|
457 |
+
$obj = new DUP_Package();
|
458 |
+
|
459 |
+
$row = $wpdb->get_row($wpdb->prepare("SELECT * FROM `{$wpdb->prefix}duplicator_packages` WHERE ID = %s", $id));
|
460 |
+
if (is_object($row)) {
|
461 |
+
$obj = @unserialize($row->package);
|
462 |
+
$obj->Status = $row->status;
|
463 |
+
}
|
464 |
+
//Incase unserilaize fails
|
465 |
+
$obj = (is_object($obj)) ? $obj : null;
|
466 |
+
return $obj;
|
467 |
+
}
|
468 |
+
|
469 |
+
/**
|
470 |
+
* Gets a default name for the package
|
471 |
+
*
|
472 |
+
* @return string A default packagename such as 20170218_blogname
|
473 |
+
*/
|
474 |
+
public static function getDefaultName()
|
475 |
+
{
|
476 |
+
//Remove specail_chars from final result
|
477 |
+
$special_chars = array(".", "-");
|
478 |
+
$name = date('Ymd').'_'.sanitize_title(get_bloginfo('name', 'display'));
|
479 |
+
$name = substr(sanitize_file_name($name), 0, 40);
|
480 |
+
$name = str_replace($special_chars, '', $name);
|
481 |
+
return $name;
|
482 |
+
}
|
483 |
+
|
484 |
+
/**
|
485 |
+
* Cleanup all tmp files
|
486 |
+
*
|
487 |
+
* @param all empty all contents
|
488 |
+
*
|
489 |
+
* @return null
|
490 |
+
*/
|
491 |
+
public static function tempFileCleanup($all = false)
|
492 |
+
{
|
493 |
+
//Delete all files now
|
494 |
+
if ($all) {
|
495 |
+
$dir = DUPLICATOR_SSDIR_PATH_TMP."/*";
|
496 |
+
foreach (glob($dir) as $file) {
|
497 |
+
unlink($file);
|
498 |
+
}
|
499 |
+
}
|
500 |
+
//Remove scan files that are 24 hours old
|
501 |
+
else {
|
502 |
+
$dir = DUPLICATOR_SSDIR_PATH_TMP."/*_scan.json";
|
503 |
+
foreach (glob($dir) as $file) {
|
504 |
+
if (filemtime($file) <= time() - 86400) {
|
505 |
+
unlink($file);
|
506 |
+
}
|
507 |
+
}
|
508 |
+
}
|
509 |
+
}
|
510 |
+
|
511 |
+
/**
|
512 |
+
* Provides various date formats
|
513 |
+
*
|
514 |
+
* @param $date The date to format
|
515 |
+
* @param $format Various date formats to apply
|
516 |
+
*
|
517 |
+
* @return a formated date based on the $format
|
518 |
+
*/
|
519 |
+
public static function getCreatedDateFormat($date, $format = 1)
|
520 |
+
{
|
521 |
+
$date = new DateTime($date);
|
522 |
+
switch ($format) {
|
523 |
+
//YEAR
|
524 |
+
case 1: return $date->format('Y-m-d H:i');
|
525 |
+
break;
|
526 |
+
case 2: return $date->format('Y-m-d H:i:s');
|
527 |
+
break;
|
528 |
+
case 3: return $date->format('y-m-d H:i');
|
529 |
+
break;
|
530 |
+
case 4: return $date->format('y-m-d H:i:s');
|
531 |
+
break;
|
532 |
+
//MONTH
|
533 |
+
case 5: return $date->format('m-d-Y H:i');
|
534 |
+
break;
|
535 |
+
case 6: return $date->format('m-d-Y H:i:s');
|
536 |
+
break;
|
537 |
+
case 7: return $date->format('m-d-y H:i');
|
538 |
+
break;
|
539 |
+
case 8: return $date->format('m-d-y H:i:s');
|
540 |
+
break;
|
541 |
+
//DAY
|
542 |
+
case 9: return $date->format('d-m-Y H:i');
|
543 |
+
break;
|
544 |
+
case 10: return $date->format('d-m-Y H:i:s');
|
545 |
+
break;
|
546 |
+
case 11: return $date->format('d-m-y H:i');
|
547 |
+
break;
|
548 |
+
case 12: return $date->format('d-m-y H:i:s');
|
549 |
+
break;
|
550 |
+
default :
|
551 |
+
return $date->format('Y-m-d H:i');
|
552 |
+
}
|
553 |
+
}
|
554 |
+
|
555 |
+
/**
|
556 |
+
* Cleans up all the tmp files as part of the package build process
|
557 |
+
*/
|
558 |
+
private function buildCleanup()
|
559 |
+
{
|
560 |
+
|
561 |
+
$files = DUP_Util::listFiles(DUPLICATOR_SSDIR_PATH_TMP);
|
562 |
+
$newPath = DUPLICATOR_SSDIR_PATH;
|
563 |
+
|
564 |
+
if (function_exists('rename')) {
|
565 |
+
foreach ($files as $file) {
|
566 |
+
$name = basename($file);
|
567 |
+
if (strstr($name, $this->NameHash)) {
|
568 |
+
rename($file, "{$newPath}/{$name}");
|
569 |
+
}
|
570 |
+
}
|
571 |
+
} else {
|
572 |
+
foreach ($files as $file) {
|
573 |
+
$name = basename($file);
|
574 |
+
if (strstr($name, $this->NameHash)) {
|
575 |
+
copy($file, "{$newPath}/{$name}");
|
576 |
+
unlink($file);
|
577 |
+
}
|
578 |
+
}
|
579 |
+
}
|
580 |
+
}
|
581 |
+
|
582 |
+
/**
|
583 |
+
* Properly creates the directory filter list that is used for filtering directories
|
584 |
+
*
|
585 |
+
* @param string $dirs A semi-colon list of dir paths
|
586 |
+
* /path1_/path/;/path1_/path2/;
|
587 |
+
*
|
588 |
+
* @returns string A cleaned up list of directory filters
|
589 |
+
*/
|
590 |
+
private function parseDirectoryFilter($dirs = "")
|
591 |
+
{
|
592 |
+
$dirs = str_replace(array("\n", "\t", "\r"), '', $dirs);
|
593 |
+
$filter_dirs = "";
|
594 |
+
$dir_array = array_unique(explode(";", $dirs));
|
595 |
+
foreach ($dir_array as $val) {
|
596 |
+
if (strlen($val) >= 2) {
|
597 |
+
$filter_dirs .= DUP_Util::safePath(trim(rtrim($val, "/\\"))).";";
|
598 |
+
}
|
599 |
+
}
|
600 |
+
return $filter_dirs;
|
601 |
+
}
|
602 |
+
|
603 |
+
/**
|
604 |
+
* Properly creates the extension filter list that is used for filtering extensions
|
605 |
+
*
|
606 |
+
* @param string $dirs A semi-colon list of dir paths
|
607 |
+
* .jpg;.zip;.gif;
|
608 |
+
*
|
609 |
+
* @returns string A cleaned up list of extension filters
|
610 |
+
*/
|
611 |
+
private function parseExtensionFilter($extensions = "")
|
612 |
+
{
|
613 |
+
$filter_exts = "";
|
614 |
+
if (strlen($extensions) >= 1 && $extensions != ";") {
|
615 |
+
$filter_exts = str_replace(array(' ', '.'), '', $extensions);
|
616 |
+
$filter_exts = str_replace(",", ";", $filter_exts);
|
617 |
+
$filter_exts = DUP_Util::appendOnce($extensions, ";");
|
618 |
+
}
|
619 |
+
return $filter_exts;
|
620 |
+
}
|
621 |
+
}
|
622 |
+
?>
|
classes/scan.validator.php
DELETED
@@ -1,93 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
/*Recursivly scans a directory and finds all sym-links and unreadable files */
|
4 |
-
class DUP_ScanValidator
|
5 |
-
{
|
6 |
-
public $FileCount = 0;
|
7 |
-
public $DirCount = 0;
|
8 |
-
|
9 |
-
/*If the MaxFiles or MaxDirs limit is reached then true */
|
10 |
-
public $LimitReached = false;
|
11 |
-
|
12 |
-
/*The maximum count of files before the recursive function stops */
|
13 |
-
public $MaxFiles = 1000000;
|
14 |
-
|
15 |
-
/*The maximum count of directories before the recursive function stops */
|
16 |
-
public $MaxDirs = 75000;
|
17 |
-
|
18 |
-
public $Recursion = true;
|
19 |
-
|
20 |
-
/*Stores a list of symbolic link files */
|
21 |
-
public $SymLinks = array();
|
22 |
-
|
23 |
-
/*Stores a list of files unreadable by PHP */
|
24 |
-
public $Unreadable = array();
|
25 |
-
|
26 |
-
public function Run($dir, &$results = array())
|
27 |
-
{
|
28 |
-
//Stop Recursion if Max search is reached
|
29 |
-
if ($this->FileCount > $this->MaxFiles || $this->DirCount > $this->MaxDirs)
|
30 |
-
{
|
31 |
-
$this->LimitReached = true;
|
32 |
-
return $results;
|
33 |
-
}
|
34 |
-
|
35 |
-
$files = @scandir($dir);
|
36 |
-
if (is_array($files))
|
37 |
-
{
|
38 |
-
foreach($files as $key => $value)
|
39 |
-
{
|
40 |
-
$path = realpath($dir.DIRECTORY_SEPARATOR.$value);
|
41 |
-
if ($path) {
|
42 |
-
//Files
|
43 |
-
if(!is_dir($path)) {
|
44 |
-
if (!is_readable($path))
|
45 |
-
{
|
46 |
-
$results[] = $path;
|
47 |
-
$this->Unreadable[] = $path;
|
48 |
-
}
|
49 |
-
else if ($this->_is_link($path))
|
50 |
-
{
|
51 |
-
$results[] = $path;
|
52 |
-
$this->SymLinks[] = $path;
|
53 |
-
}
|
54 |
-
$this->FileCount++;
|
55 |
-
}
|
56 |
-
//Dirs
|
57 |
-
else if($value != "." && $value != "..")
|
58 |
-
{
|
59 |
-
if (! $this->_is_link($path) && $this->Recursion)
|
60 |
-
{
|
61 |
-
$this->Run($path, $results);
|
62 |
-
}
|
63 |
-
|
64 |
-
if (!is_readable($path))
|
65 |
-
{
|
66 |
-
$results[] = $path;
|
67 |
-
$this->Unreadable[] = $path;
|
68 |
-
}
|
69 |
-
else if ($this->_is_link($path)) {
|
70 |
-
$results[] = $path;
|
71 |
-
$this->SymLinks[] = $path;
|
72 |
-
}
|
73 |
-
$this->DirCount++;
|
74 |
-
}
|
75 |
-
}
|
76 |
-
}
|
77 |
-
}
|
78 |
-
return $this;
|
79 |
-
}
|
80 |
-
|
81 |
-
//Supports windows and linux
|
82 |
-
private function _is_link($target)
|
83 |
-
{
|
84 |
-
if (defined('PHP_WINDOWS_VERSION_BUILD')) {
|
85 |
-
if(file_exists($target) && @readlink($target) != $target) {
|
86 |
-
return true;
|
87 |
-
}
|
88 |
-
} elseif (is_link($target)) {
|
89 |
-
return true;
|
90 |
-
}
|
91 |
-
return false;
|
92 |
-
}
|
93 |
-
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/server.php
DELETED
@@ -1,200 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/utility.php');
|
5 |
-
|
6 |
-
/**
|
7 |
-
* Class used to get server statis
|
8 |
-
* @package Dupicator\classes
|
9 |
-
*/
|
10 |
-
class DUP_Server
|
11 |
-
{
|
12 |
-
|
13 |
-
/**
|
14 |
-
* Gets the system requirements which must pass to buld a package
|
15 |
-
* @return array An array of requirements
|
16 |
-
*/
|
17 |
-
public static function GetRequirements()
|
18 |
-
{
|
19 |
-
|
20 |
-
global $wpdb;
|
21 |
-
$dup_tests = array();
|
22 |
-
|
23 |
-
//PHP SUPPORT
|
24 |
-
$safe_ini = strtolower(ini_get('safe_mode'));
|
25 |
-
$dup_tests['PHP']['SAFE_MODE'] = $safe_ini != 'on' || $safe_ini != 'yes' || $safe_ini != 'true' || ini_get("safe_mode") != 1 ? 'Pass' : 'Fail';
|
26 |
-
$dup_tests['PHP']['VERSION'] = DUP_Util::$on_php_529_plus ? 'Pass' : 'Fail';
|
27 |
-
$dup_tests['PHP']['ZIP'] = class_exists('ZipArchive') ? 'Pass' : 'Fail';
|
28 |
-
$dup_tests['PHP']['FUNC_1'] = function_exists("file_get_contents") ? 'Pass' : 'Fail';
|
29 |
-
$dup_tests['PHP']['FUNC_2'] = function_exists("file_put_contents") ? 'Pass' : 'Fail';
|
30 |
-
$dup_tests['PHP']['FUNC_3'] = function_exists("mb_strlen") ? 'Pass' : 'Fail';
|
31 |
-
$dup_tests['PHP']['ALL'] = ! in_array('Fail', $dup_tests['PHP']) ? 'Pass' : 'Fail';
|
32 |
-
|
33 |
-
//REQUIRED PATHS
|
34 |
-
if (file_exists(DUPLICATOR_SSDIR_PATH) && is_writeable(DUPLICATOR_SSDIR_PATH))
|
35 |
-
{
|
36 |
-
$dup_tests['IO']['SSDIR'] = 'Pass';
|
37 |
-
$dup_tests['IO']['WPROOT'] = 'Pass';
|
38 |
-
}
|
39 |
-
else
|
40 |
-
{
|
41 |
-
$handle_test = @opendir(DUPLICATOR_WPROOTPATH);
|
42 |
-
$dup_tests['IO']['WPROOT'] = is_writeable(DUPLICATOR_WPROOTPATH) && $handle_test ? 'Pass' : 'Fail';
|
43 |
-
$dup_tests['IO']['SSDIR'] = 'Fail';
|
44 |
-
@closedir($handle_test);
|
45 |
-
}
|
46 |
-
|
47 |
-
$dup_tests['IO']['SSTMP'] = is_writeable(DUPLICATOR_SSDIR_PATH_TMP) ? 'Pass' : 'Fail';
|
48 |
-
$dup_tests['IO']['ALL'] = ! in_array('Fail', $dup_tests['IO']) ? 'Pass' : 'Fail';
|
49 |
-
|
50 |
-
|
51 |
-
//SERVER SUPPORT
|
52 |
-
$dup_tests['SRV']['MYSQLi'] = function_exists('mysqli_connect') ? 'Pass' : 'Fail';
|
53 |
-
$dup_tests['SRV']['MYSQL_VER'] = version_compare($wpdb->db_version(), '5.0', '>=') ? 'Pass' : 'Fail';
|
54 |
-
$dup_tests['SRV']['ALL'] = ! in_array('Fail', $dup_tests['SRV']) ? 'Pass' : 'Fail';
|
55 |
-
|
56 |
-
//RESERVED FILES
|
57 |
-
$dup_tests['RES']['INSTALL'] = !(self::InstallerFilesFound()) ? 'Pass' : 'Fail';
|
58 |
-
$dup_tests['Success'] = $dup_tests['PHP']['ALL'] == 'Pass' && $dup_tests['IO']['ALL'] == 'Pass' &&
|
59 |
-
$dup_tests['SRV']['ALL'] == 'Pass' && $dup_tests['RES']['INSTALL'] == 'Pass';
|
60 |
-
|
61 |
-
return $dup_tests;
|
62 |
-
}
|
63 |
-
|
64 |
-
/**
|
65 |
-
* Gets the system checks which are not required
|
66 |
-
* @return array An array of system checks
|
67 |
-
*/
|
68 |
-
public static function GetChecks()
|
69 |
-
{
|
70 |
-
$checks = array();
|
71 |
-
|
72 |
-
//WEB SERVER
|
73 |
-
$web_test1 = false;
|
74 |
-
foreach ($GLOBALS['DUPLICATOR_SERVER_LIST'] as $value) {
|
75 |
-
if (stristr($_SERVER['SERVER_SOFTWARE'], $value)) {
|
76 |
-
$web_test1 = true;
|
77 |
-
break;
|
78 |
-
}
|
79 |
-
}
|
80 |
-
$checks['SRV']['WEB']['model'] = $web_test1;
|
81 |
-
$checks['SRV']['WEB']['ALL'] = ($web_test1) ? 'Good' : 'Warn';
|
82 |
-
|
83 |
-
//PHP SETTINGS
|
84 |
-
$php_test1 = ini_get("open_basedir");
|
85 |
-
$php_test1 = empty($php_test1) ? true : false;
|
86 |
-
$php_test2 = ini_get("max_execution_time");
|
87 |
-
$php_test2 = ($php_test2 > DUPLICATOR_SCAN_TIMEOUT) || (strcmp($php_test2 , 'Off') == 0 || $php_test2 == 0) ? true : false;
|
88 |
-
$php_test3 = function_exists('mysqli_connect');
|
89 |
-
$php_test4 = DUP_Util::$on_php_53_plus ? true : false;
|
90 |
-
|
91 |
-
$checks['SRV']['PHP']['openbase'] = $php_test1;
|
92 |
-
$checks['SRV']['PHP']['maxtime'] = $php_test2;
|
93 |
-
$checks['SRV']['PHP']['mysqli'] = $php_test3;
|
94 |
-
$checks['SRV']['PHP']['version'] = $php_test4;
|
95 |
-
$checks['SRV']['PHP']['ALL'] = ($php_test1 && $php_test2 && $php_test3 && $php_test4) ? 'Good' : 'Warn';
|
96 |
-
|
97 |
-
|
98 |
-
//WORDPRESS SETTINGS
|
99 |
-
global $wp_version;
|
100 |
-
$wp_test1 = version_compare($wp_version, DUPLICATOR_SCAN_MIN_WP) >= 0 ? true : false;
|
101 |
-
|
102 |
-
//Core Files
|
103 |
-
$files = array();
|
104 |
-
$files['wp-config.php'] = file_exists(DUP_Util::SafePath(DUPLICATOR_WPROOTPATH . '/wp-config.php'));
|
105 |
-
$wp_test2 = $files['wp-config.php'];
|
106 |
-
|
107 |
-
//Cache
|
108 |
-
$Package = DUP_Package::GetActive();
|
109 |
-
$cache_path = DUP_Util::SafePath(WP_CONTENT_DIR) . '/cache';
|
110 |
-
$dirEmpty = DUP_Util::IsDirectoryEmpty($cache_path);
|
111 |
-
$dirSize = DUP_Util::GetDirectorySize($cache_path);
|
112 |
-
$cach_filtered = in_array($cache_path, explode(';', $Package->Archive->FilterDirs));
|
113 |
-
$wp_test3 = ($cach_filtered || $dirEmpty || $dirSize < DUPLICATOR_SCAN_CACHESIZE ) ? true : false;
|
114 |
-
$wp_test4 = is_multisite();
|
115 |
-
|
116 |
-
$checks['SRV']['WP']['version'] = $wp_test1;
|
117 |
-
$checks['SRV']['WP']['core'] = $wp_test2;
|
118 |
-
$checks['SRV']['WP']['cache'] = $wp_test3;
|
119 |
-
$checks['SRV']['WP']['ismu'] = $wp_test4;
|
120 |
-
$checks['SRV']['WP']['ALL'] = $wp_test1 && $wp_test2 && $wp_test3 && ! $wp_test4 ? 'Good' : 'Warn';
|
121 |
-
|
122 |
-
return $checks;
|
123 |
-
}
|
124 |
-
|
125 |
-
/**
|
126 |
-
* Check to see if duplicator installer files are present
|
127 |
-
* @return bool True if any reserved files are found
|
128 |
-
*/
|
129 |
-
public static function InstallerFilesFound()
|
130 |
-
{
|
131 |
-
$files = self::GetInstallerFiles();
|
132 |
-
foreach($files as $file => $path)
|
133 |
-
{
|
134 |
-
if (file_exists($path))
|
135 |
-
return true;
|
136 |
-
}
|
137 |
-
return false;
|
138 |
-
}
|
139 |
-
|
140 |
-
|
141 |
-
/**
|
142 |
-
* Gets a list of all the installer files by name and full path
|
143 |
-
* @return array [file_name, file_path]
|
144 |
-
*/
|
145 |
-
public static function GetInstallerFiles()
|
146 |
-
{
|
147 |
-
/* Files:
|
148 |
-
* installer.php, installer-backup.php, installer-data.sql, installer-log.txt, database.sql */
|
149 |
-
return array(
|
150 |
-
DUPLICATOR_INSTALL_PHP => DUPLICATOR_WPROOTPATH . DUPLICATOR_INSTALL_PHP,
|
151 |
-
DUPLICATOR_INSTALL_BAK => DUPLICATOR_WPROOTPATH . DUPLICATOR_INSTALL_BAK,
|
152 |
-
DUPLICATOR_INSTALL_SQL => DUPLICATOR_WPROOTPATH . DUPLICATOR_INSTALL_SQL,
|
153 |
-
DUPLICATOR_INSTALL_LOG => DUPLICATOR_WPROOTPATH . DUPLICATOR_INSTALL_LOG,
|
154 |
-
DUPLICATOR_INSTALL_DB => DUPLICATOR_WPROOTPATH . DUPLICATOR_INSTALL_DB
|
155 |
-
);
|
156 |
-
}
|
157 |
-
|
158 |
-
|
159 |
-
/**
|
160 |
-
* Get the IP of a client machine
|
161 |
-
* @return string IP of the client machine
|
162 |
-
*/
|
163 |
-
public static function GetClientIP()
|
164 |
-
{
|
165 |
-
|
166 |
-
if (array_key_exists('HTTP_X_FORWARDED_FOR', $_SERVER)){
|
167 |
-
return $_SERVER["HTTP_X_FORWARDED_FOR"];
|
168 |
-
}else if (array_key_exists('REMOTE_ADDR', $_SERVER)) {
|
169 |
-
return $_SERVER["REMOTE_ADDR"];
|
170 |
-
}else if (array_key_exists('HTTP_CLIENT_IP', $_SERVER)) {
|
171 |
-
return $_SERVER["HTTP_CLIENT_IP"];
|
172 |
-
}
|
173 |
-
|
174 |
-
return '';
|
175 |
-
}
|
176 |
-
|
177 |
-
/**
|
178 |
-
* Get PHP memory useage
|
179 |
-
* @return string Returns human readable memory useage.
|
180 |
-
*/
|
181 |
-
public static function GetPHPMemory($peak = false)
|
182 |
-
{
|
183 |
-
|
184 |
-
if ($peak) {
|
185 |
-
$result = 'Unable to read PHP peak memory usage';
|
186 |
-
if (function_exists('memory_get_peak_usage')) {
|
187 |
-
$result = DUP_Util::ByteSize(memory_get_peak_usage(true));
|
188 |
-
}
|
189 |
-
} else {
|
190 |
-
$result = 'Unable to read PHP memory usage';
|
191 |
-
if (function_exists('memory_get_usage')) {
|
192 |
-
$result = DUP_Util::ByteSize(memory_get_usage(true));
|
193 |
-
}
|
194 |
-
}
|
195 |
-
|
196 |
-
return $result;
|
197 |
-
}
|
198 |
-
|
199 |
-
}
|
200 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/ui.php
DELETED
@@ -1,92 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined('DUPLICATOR_VERSION') ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
/**
|
5 |
-
* Helper Class for UI internactions
|
6 |
-
* @package Dupicator\classes
|
7 |
-
*/
|
8 |
-
class DUP_UI
|
9 |
-
{
|
10 |
-
|
11 |
-
/**
|
12 |
-
* The key used in the wp_options table
|
13 |
-
* @var string
|
14 |
-
*/
|
15 |
-
private static $OptionsViewStateKey = 'duplicator_ui_view_state';
|
16 |
-
|
17 |
-
/**
|
18 |
-
* Save the view state of UI elements
|
19 |
-
* @param string $key A unique key to define the ui element
|
20 |
-
* @param string $value A generic value to use for the view state
|
21 |
-
*/
|
22 |
-
public static function SaveViewState($key, $value)
|
23 |
-
{
|
24 |
-
$view_state = array();
|
25 |
-
$view_state = get_option(self::$OptionsViewStateKey);
|
26 |
-
$view_state[$key] = $value;
|
27 |
-
$success = update_option(self::$OptionsViewStateKey, $view_state);
|
28 |
-
return $success;
|
29 |
-
}
|
30 |
-
|
31 |
-
|
32 |
-
/**
|
33 |
-
* Gets all the values from the settings array
|
34 |
-
* @return array Returns and array of all the values stored in the settings array
|
35 |
-
*/
|
36 |
-
public static function GetViewStateArray()
|
37 |
-
{
|
38 |
-
return get_option(self::$OptionsViewStateKey);
|
39 |
-
}
|
40 |
-
|
41 |
-
/**
|
42 |
-
* Return the value of the of view state item
|
43 |
-
* @param type $searchKey The key to search on
|
44 |
-
* @return string Returns the value of the key searched or null if key is not found
|
45 |
-
*/
|
46 |
-
public static function GetViewStateValue($searchKey)
|
47 |
-
{
|
48 |
-
$view_state = get_option(self::$OptionsViewStateKey);
|
49 |
-
if (is_array($view_state)) {
|
50 |
-
foreach ($view_state as $key => $value) {
|
51 |
-
if ($key == $searchKey) {
|
52 |
-
return $value;
|
53 |
-
}
|
54 |
-
}
|
55 |
-
}
|
56 |
-
return null;
|
57 |
-
}
|
58 |
-
|
59 |
-
/**
|
60 |
-
* Shows a display message in the wp-admin if any researved files are found
|
61 |
-
* @return type void
|
62 |
-
*/
|
63 |
-
public static function ShowReservedFilesNotice()
|
64 |
-
{
|
65 |
-
//Show only on Duplicator pages and Dashboard when plugin is active
|
66 |
-
$dup_active = is_plugin_active('duplicator/duplicator.php');
|
67 |
-
$dup_perm = current_user_can( 'manage_options' );
|
68 |
-
if (! $dup_active || ! $dup_perm)
|
69 |
-
return;
|
70 |
-
|
71 |
-
if (DUP_Server::InstallerFilesFound())
|
72 |
-
{
|
73 |
-
$screen = get_current_screen();
|
74 |
-
$on_active_tab = isset($_GET['tab']) && $_GET['tab'] == 'cleanup' ? true : false;
|
75 |
-
|
76 |
-
echo '<div class="error" id="dup-global-error-reserved-files"><p>';
|
77 |
-
if ($screen->id == 'duplicator_page_duplicator-tools' && $on_active_tab)
|
78 |
-
{
|
79 |
-
_e('Reserved Duplicator install files have been detected in the root directory. Please delete these reserved files to avoid security issues.', 'duplicator');
|
80 |
-
}
|
81 |
-
else
|
82 |
-
{
|
83 |
-
$duplicator_nonce = wp_create_nonce('duplicator_cleanup_page');
|
84 |
-
_e('Reserved Duplicator install files have been detected in the root directory. Please delete these reserved files to avoid security issues.', 'duplicator');
|
85 |
-
@printf("<br/><a href='admin.php?page=duplicator-tools&tab=cleanup&_wpnonce=%s'>%s</a>", $duplicator_nonce, __('Take me to the cleanup page!', 'duplicator'));
|
86 |
-
}
|
87 |
-
echo "</p></div>";
|
88 |
-
}
|
89 |
-
}
|
90 |
-
|
91 |
-
}
|
92 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/ui/class.dialog.php
DELETED
@@ -1,165 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
/**
|
4 |
-
* Inline Dialog:
|
5 |
-
* Used to generate a thinkbox inline dialog.
|
6 |
-
*/
|
7 |
-
class DUP_Dialog
|
8 |
-
{
|
9 |
-
//All Dialogs
|
10 |
-
public $title;
|
11 |
-
public $message;
|
12 |
-
public $width;
|
13 |
-
public $height;
|
14 |
-
|
15 |
-
//Confirm Only
|
16 |
-
public $progress_text;
|
17 |
-
public $progress_on = true;
|
18 |
-
public $jscallback;
|
19 |
-
|
20 |
-
private $id;
|
21 |
-
private $uniqid;
|
22 |
-
|
23 |
-
public function __construct()
|
24 |
-
{
|
25 |
-
add_thickbox();
|
26 |
-
$this->progress_text = __('Processing please wait...', 'duplicator');
|
27 |
-
$this->uniqid = uniqid();
|
28 |
-
$this->id = 'dup-dlg-' . $this->uniqid;
|
29 |
-
}
|
30 |
-
|
31 |
-
|
32 |
-
/**
|
33 |
-
* Gets unique ID:
|
34 |
-
* Get the unique id that is assigned to each instance of a dialog
|
35 |
-
*
|
36 |
-
* @access public
|
37 |
-
* @return int
|
38 |
-
*/
|
39 |
-
public function get_id()
|
40 |
-
{
|
41 |
-
return $this->id;
|
42 |
-
}
|
43 |
-
|
44 |
-
/**
|
45 |
-
* Gets unique ID:
|
46 |
-
* Get the unique id that is assigned to each instance of a dialog
|
47 |
-
*
|
48 |
-
* @access public
|
49 |
-
* @return int
|
50 |
-
*/
|
51 |
-
public function get_message_id()
|
52 |
-
{
|
53 |
-
return "{$this->id}_message";
|
54 |
-
}
|
55 |
-
|
56 |
-
|
57 |
-
/**
|
58 |
-
* Init Alert:
|
59 |
-
* Initilizes the alert base html code used to display when needed
|
60 |
-
*
|
61 |
-
* @access public
|
62 |
-
* @return string The html content used for the alert dialog
|
63 |
-
*/
|
64 |
-
public function init_alert()
|
65 |
-
{
|
66 |
-
$ok = __('OK', 'duplicator');
|
67 |
-
|
68 |
-
$html = <<<HTML
|
69 |
-
<div id="{$this->id}" style="display:none">
|
70 |
-
<div class="dup-dlg-alert-txt">
|
71 |
-
{$this->message}
|
72 |
-
<br/><br/>
|
73 |
-
</div>
|
74 |
-
<div class="dup-dlg-alert-btns">
|
75 |
-
<input type="button" class="button button-large" value="{$ok}" onclick="tb_remove()" />
|
76 |
-
</div>
|
77 |
-
</div>
|
78 |
-
HTML;
|
79 |
-
|
80 |
-
echo $html;
|
81 |
-
}
|
82 |
-
|
83 |
-
|
84 |
-
/**
|
85 |
-
* Show Alert:
|
86 |
-
* Shows the alert base js code used to display when needed
|
87 |
-
*
|
88 |
-
* @access public
|
89 |
-
* @return string The javascript content used for the alert dialog
|
90 |
-
*/
|
91 |
-
public function show_alert()
|
92 |
-
{
|
93 |
-
$this->width = is_numeric($this->width) ? $this->width : 475;
|
94 |
-
$this->height = is_numeric($this->height) ? $this->height : 125;
|
95 |
-
|
96 |
-
echo "tb_show('{$this->title}', '#TB_inline?width={$this->width}&height={$this->height}&inlineId={$this->id}');";
|
97 |
-
}
|
98 |
-
|
99 |
-
|
100 |
-
/**
|
101 |
-
* Init Confirm:
|
102 |
-
* Shows the confirm base js code used to display when needed
|
103 |
-
*
|
104 |
-
* @access public
|
105 |
-
* @return string The javascript content used for the confirm dialog
|
106 |
-
*/
|
107 |
-
public function init_confirm()
|
108 |
-
{
|
109 |
-
$ok = __('OK', 'duplicator');
|
110 |
-
$cancel = __('Cancel', 'duplicator');
|
111 |
-
|
112 |
-
$progress_data = '';
|
113 |
-
$progress_func2 = '';
|
114 |
-
|
115 |
-
//Enable the progress spinner
|
116 |
-
if ($this->progress_on)
|
117 |
-
{
|
118 |
-
$progress_func1 = "__dup_dialog_" . $this->uniqid;
|
119 |
-
$progress_func2 = ";{$progress_func1}(this)";
|
120 |
-
$progress_data = <<<HTML
|
121 |
-
<div class='dup-dlg-confirm-progress'><i class='fa fa-circle-o-notch fa-spin fa-lg fa-fw'></i> {$this->progress_text}</div>
|
122 |
-
<script>
|
123 |
-
function {$progress_func1}(obj)
|
124 |
-
{
|
125 |
-
jQuery(obj).parent().parent().find('.dup-dlg-confirm-progress').show();
|
126 |
-
jQuery(obj).closest('.dup-dlg-confirm-btns').find('input').attr('disabled', 'true');
|
127 |
-
}
|
128 |
-
</script>
|
129 |
-
HTML;
|
130 |
-
}
|
131 |
-
|
132 |
-
$html = <<<HTML
|
133 |
-
<div id="{$this->id}" style="display:none">
|
134 |
-
<div class="dup-dlg-confirm-txt">
|
135 |
-
<span id="{$this->id}_message">{$this->message}</span>
|
136 |
-
<br/><br/>
|
137 |
-
{$progress_data}
|
138 |
-
</div>
|
139 |
-
<div class="dup-dlg-confirm-btns">
|
140 |
-
<input type="button" class="button button-large" value="{$ok}" onclick="{$this->jscallback}{$progress_func2}" />
|
141 |
-
<input type="button" class="button button-large" value="{$cancel}" onclick="tb_remove()" />
|
142 |
-
</div>
|
143 |
-
</div>
|
144 |
-
HTML;
|
145 |
-
|
146 |
-
echo $html;
|
147 |
-
}
|
148 |
-
|
149 |
-
|
150 |
-
/**
|
151 |
-
* Show Confirm:
|
152 |
-
* Shows the confirm base js code used to display when needed
|
153 |
-
*
|
154 |
-
* @access public
|
155 |
-
* @return string The javascript content used for the confirm dialog
|
156 |
-
*/
|
157 |
-
public function show_confirm()
|
158 |
-
{
|
159 |
-
$this->width = is_numeric($this->width) ? $this->width : 500;
|
160 |
-
$this->height = is_numeric($this->height) ? $this->height : 150;
|
161 |
-
echo "tb_show('{$this->title}', '#TB_inline?width={$this->width}&height={$this->height}&inlineId={$this->id}');";
|
162 |
-
}
|
163 |
-
|
164 |
-
}
|
165 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/ui/class.ui.dialog.php
ADDED
@@ -0,0 +1,200 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Used to generate a thinkbox inline dialog such as an alert or confirm popup
|
4 |
+
*
|
5 |
+
* Standard: PSR-2
|
6 |
+
* @link http://www.php-fig.org/psr/psr-2
|
7 |
+
*
|
8 |
+
* @package Duplicator
|
9 |
+
* @subpackage classes/ui
|
10 |
+
* @copyright (c) 2017, Snapcreek LLC
|
11 |
+
* @since 1.1.32
|
12 |
+
*
|
13 |
+
*/
|
14 |
+
|
15 |
+
// Exit if accessed directly
|
16 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
17 |
+
exit;
|
18 |
+
}
|
19 |
+
|
20 |
+
class DUP_UI_Dialog
|
21 |
+
{
|
22 |
+
/**
|
23 |
+
* The title that shows up in the dialog
|
24 |
+
*/
|
25 |
+
public $title;
|
26 |
+
|
27 |
+
/**
|
28 |
+
* The message displayed in the body of the dialog
|
29 |
+
*/
|
30 |
+
public $message;
|
31 |
+
|
32 |
+
/**
|
33 |
+
* The width of the dialog the default is used if not set
|
34 |
+
* Alert = 475px (default) | Confirm = 500px (default)
|
35 |
+
*/
|
36 |
+
public $width;
|
37 |
+
|
38 |
+
/**
|
39 |
+
* The height of the dialog the default is used if not set
|
40 |
+
* Alert = 125px (default) | Confirm = 150px (default)
|
41 |
+
*/
|
42 |
+
public $height;
|
43 |
+
|
44 |
+
/**
|
45 |
+
* When the progress meter is running show this text
|
46 |
+
* Available only on confirm dialogs
|
47 |
+
*/
|
48 |
+
public $progressText;
|
49 |
+
|
50 |
+
/**
|
51 |
+
* When true a progress meter will run until page is reloaded
|
52 |
+
* Available only on confirm dialogs
|
53 |
+
*/
|
54 |
+
public $progressOn = true;
|
55 |
+
|
56 |
+
/**
|
57 |
+
* The javascript call back method to call when the 'Yes' button is clicked
|
58 |
+
* Available only on confirm dialogs
|
59 |
+
*/
|
60 |
+
public $jscallback;
|
61 |
+
|
62 |
+
/**
|
63 |
+
* The id given to the full dialog
|
64 |
+
*/
|
65 |
+
private $id;
|
66 |
+
|
67 |
+
/**
|
68 |
+
* A unique id that is added to all id elements
|
69 |
+
*/
|
70 |
+
private $uniqid;
|
71 |
+
|
72 |
+
public function __construct()
|
73 |
+
{
|
74 |
+
add_thickbox();
|
75 |
+
$this->progressText = __('Processing please wait...', 'duplicator');
|
76 |
+
$this->uniqid = uniqid();
|
77 |
+
$this->id = 'dup-dlg-'.$this->uniqid;
|
78 |
+
}
|
79 |
+
|
80 |
+
/**
|
81 |
+
* Gets the unique id that is assigned to each instance of a dialog
|
82 |
+
*
|
83 |
+
* @access public
|
84 |
+
* @return int The unique ID of this dialog
|
85 |
+
*/
|
86 |
+
public function getID()
|
87 |
+
{
|
88 |
+
return $this->id;
|
89 |
+
}
|
90 |
+
|
91 |
+
/**
|
92 |
+
* Gets the unique id that is assigned to each instance of a dialogs message text
|
93 |
+
*
|
94 |
+
* @access public
|
95 |
+
* @return int The unique ID of the message
|
96 |
+
*/
|
97 |
+
public function getMessageID()
|
98 |
+
{
|
99 |
+
return "{$this->id}_message";
|
100 |
+
}
|
101 |
+
|
102 |
+
/**
|
103 |
+
* Initilizes the alert base html code used to display when needed
|
104 |
+
*
|
105 |
+
* @access public
|
106 |
+
* @return string The html content used for the alert dialog
|
107 |
+
*/
|
108 |
+
public function initAlert()
|
109 |
+
{
|
110 |
+
$ok = __('OK', 'duplicator');
|
111 |
+
|
112 |
+
$html = <<<HTML
|
113 |
+
<div id="{$this->id}" style="display:none">
|
114 |
+
<div class="dup-dlg-alert-txt">
|
115 |
+
{$this->message}
|
116 |
+
<br/><br/>
|
117 |
+
</div>
|
118 |
+
<div class="dup-dlg-alert-btns">
|
119 |
+
<input type="button" class="button button-large" value="{$ok}" onclick="tb_remove()" />
|
120 |
+
</div>
|
121 |
+
</div>
|
122 |
+
HTML;
|
123 |
+
|
124 |
+
echo $html;
|
125 |
+
}
|
126 |
+
|
127 |
+
/**
|
128 |
+
* Shows the alert base js code used to display when needed
|
129 |
+
*
|
130 |
+
* @access public
|
131 |
+
* @return string The javascript content used for the alert dialog
|
132 |
+
*/
|
133 |
+
public function showAlert()
|
134 |
+
{
|
135 |
+
$this->width = is_numeric($this->width) ? $this->width : 475;
|
136 |
+
$this->height = is_numeric($this->height) ? $this->height : 125;
|
137 |
+
|
138 |
+
echo "tb_show('{$this->title}', '#TB_inline?width={$this->width}&height={$this->height}&inlineId={$this->id}');";
|
139 |
+
}
|
140 |
+
|
141 |
+
/**
|
142 |
+
* Shows the confirm base js code used to display when needed
|
143 |
+
*
|
144 |
+
* @access public
|
145 |
+
* @return string The javascript content used for the confirm dialog
|
146 |
+
*/
|
147 |
+
public function initConfirm()
|
148 |
+
{
|
149 |
+
$ok = __('OK', 'duplicator');
|
150 |
+
$cancel = __('Cancel', 'duplicator');
|
151 |
+
|
152 |
+
$progress_data = '';
|
153 |
+
$progress_func2 = '';
|
154 |
+
|
155 |
+
//Enable the progress spinner
|
156 |
+
if ($this->progressOn) {
|
157 |
+
$progress_func1 = "__DUP_UI_Dialog_".$this->uniqid;
|
158 |
+
$progress_func2 = ";{$progress_func1}(this)";
|
159 |
+
$progress_data = <<<HTML
|
160 |
+
<div class='dup-dlg-confirm-progress'><i class='fa fa-circle-o-notch fa-spin fa-lg fa-fw'></i> {$this->progressText}</div>
|
161 |
+
<script>
|
162 |
+
function {$progress_func1}(obj)
|
163 |
+
{
|
164 |
+
jQuery(obj).parent().parent().find('.dup-dlg-confirm-progress').show();
|
165 |
+
jQuery(obj).closest('.dup-dlg-confirm-btns').find('input').attr('disabled', 'true');
|
166 |
+
}
|
167 |
+
</script>
|
168 |
+
HTML;
|
169 |
+
}
|
170 |
+
|
171 |
+
$html = <<<HTML
|
172 |
+
<div id="{$this->id}" style="display:none">
|
173 |
+
<div class="dup-dlg-confirm-txt">
|
174 |
+
<span id="{$this->id}_message">{$this->message}</span>
|
175 |
+
<br/><br/>
|
176 |
+
{$progress_data}
|
177 |
+
</div>
|
178 |
+
<div class="dup-dlg-confirm-btns">
|
179 |
+
<input type="button" class="button button-large" value="{$ok}" onclick="{$this->jscallback}{$progress_func2}" />
|
180 |
+
<input type="button" class="button button-large" value="{$cancel}" onclick="tb_remove()" />
|
181 |
+
</div>
|
182 |
+
</div>
|
183 |
+
HTML;
|
184 |
+
|
185 |
+
echo $html;
|
186 |
+
}
|
187 |
+
|
188 |
+
/**
|
189 |
+
* Shows the confirm base js code used to display when needed
|
190 |
+
*
|
191 |
+
* @access public
|
192 |
+
* @return string The javascript content used for the confirm dialog
|
193 |
+
*/
|
194 |
+
public function showConfirm()
|
195 |
+
{
|
196 |
+
$this->width = is_numeric($this->width) ? $this->width : 500;
|
197 |
+
$this->height = is_numeric($this->height) ? $this->height : 150;
|
198 |
+
echo "tb_show('{$this->title}', '#TB_inline?width={$this->width}&height={$this->height}&inlineId={$this->id}');";
|
199 |
+
}
|
200 |
+
}
|
classes/ui/class.ui.notice.php
ADDED
@@ -0,0 +1,51 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Used to display notices in the WordPress Admin area
|
4 |
+
* This class takes advatage of the 'admin_notice' action.
|
5 |
+
*
|
6 |
+
* Standard: PSR-2
|
7 |
+
* @link http://www.php-fig.org/psr/psr-2
|
8 |
+
*
|
9 |
+
* @package Duplicator
|
10 |
+
* @subpackage classes/ui
|
11 |
+
* @copyright (c) 2017, Snapcreek LLC
|
12 |
+
* @since 1.1.0
|
13 |
+
*
|
14 |
+
*/
|
15 |
+
|
16 |
+
// Exit if accessed directly
|
17 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
18 |
+
exit;
|
19 |
+
}
|
20 |
+
|
21 |
+
class DUP_UI_Notice
|
22 |
+
{
|
23 |
+
|
24 |
+
/**
|
25 |
+
* Shows a display message in the wp-admin if any researved files are found
|
26 |
+
*
|
27 |
+
* @return string Html formated text notice warnings
|
28 |
+
*/
|
29 |
+
public static function showReservedFilesNotice()
|
30 |
+
{
|
31 |
+
//Show only on Duplicator pages and Dashboard when plugin is active
|
32 |
+
$dup_active = is_plugin_active('duplicator/duplicator.php');
|
33 |
+
$dup_perm = current_user_can('manage_options');
|
34 |
+
if (!$dup_active || !$dup_perm) return;
|
35 |
+
|
36 |
+
if (DUP_Server::hasInstallerFiles()) {
|
37 |
+
$screen = get_current_screen();
|
38 |
+
$on_active_tab = isset($_GET['tab']) && $_GET['tab'] == 'cleanup' ? true : false;
|
39 |
+
|
40 |
+
echo '<div class="error" id="dup-global-error-reserved-files"><p>';
|
41 |
+
if ($screen->id == 'duplicator_page_duplicator-tools' && $on_active_tab) {
|
42 |
+
_e('Reserved Duplicator install files have been detected in the root directory. Please delete these reserved files to avoid security issues.', 'duplicator');
|
43 |
+
} else {
|
44 |
+
$duplicator_nonce = wp_create_nonce('duplicator_cleanup_page');
|
45 |
+
_e('Reserved Duplicator install files have been detected in the root directory. Please delete these reserved files to avoid security issues.', 'duplicator');
|
46 |
+
@printf("<br/><a href='admin.php?page=duplicator-tools&tab=cleanup&_wpnonce=%s'>%s</a>", $duplicator_nonce, __('Take me to the cleanup page!', 'duplicator'));
|
47 |
+
}
|
48 |
+
echo "</p></div>";
|
49 |
+
}
|
50 |
+
}
|
51 |
+
}
|
classes/ui/class.ui.viewstate.php
ADDED
@@ -0,0 +1,72 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Gets the view state of UI elements to remember its viewable state
|
4 |
+
*
|
5 |
+
* Standard: PSR-2
|
6 |
+
* @link http://www.php-fig.org/psr/psr-2
|
7 |
+
*
|
8 |
+
* @package Duplicator
|
9 |
+
* @subpackage classes/ui
|
10 |
+
* @copyright (c) 2017, Snapcreek LLC
|
11 |
+
* @since 1.1.0
|
12 |
+
*
|
13 |
+
*/
|
14 |
+
|
15 |
+
// Exit if accessed directly
|
16 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
17 |
+
exit;
|
18 |
+
}
|
19 |
+
|
20 |
+
class DUP_UI_ViewState
|
21 |
+
{
|
22 |
+
/**
|
23 |
+
* The key used in the wp_options table
|
24 |
+
*
|
25 |
+
* @var string
|
26 |
+
*/
|
27 |
+
private static $optionsViewStateKey = 'duplicator_ui_view_state';
|
28 |
+
|
29 |
+
/**
|
30 |
+
* Save the view state of UI elements
|
31 |
+
*
|
32 |
+
* @param string $key A unique key to define the ui element
|
33 |
+
* @param string $value A generic value to use for the view state
|
34 |
+
*/
|
35 |
+
public static function save($key, $value)
|
36 |
+
{
|
37 |
+
$view_state = array();
|
38 |
+
$view_state = get_option(self::$optionsViewStateKey);
|
39 |
+
$view_state[$key] = $value;
|
40 |
+
$success = update_option(self::$optionsViewStateKey, $view_state);
|
41 |
+
return $success;
|
42 |
+
}
|
43 |
+
|
44 |
+
/**
|
45 |
+
* Gets all the values from the settings array
|
46 |
+
*
|
47 |
+
* @return array Returns and array of all the values stored in the settings array
|
48 |
+
*/
|
49 |
+
public static function getArray()
|
50 |
+
{
|
51 |
+
return get_option(self::$optionsViewStateKey);
|
52 |
+
}
|
53 |
+
|
54 |
+
/**
|
55 |
+
* Return the value of the of view state item
|
56 |
+
*
|
57 |
+
* @param type $searchKey The key to search on
|
58 |
+
* @return string Returns the value of the key searched or null if key is not found
|
59 |
+
*/
|
60 |
+
public static function getValue($searchKey)
|
61 |
+
{
|
62 |
+
$view_state = get_option(self::$optionsViewStateKey);
|
63 |
+
if (is_array($view_state)) {
|
64 |
+
foreach ($view_state as $key => $value) {
|
65 |
+
if ($key == $searchKey) {
|
66 |
+
return $value;
|
67 |
+
}
|
68 |
+
}
|
69 |
+
}
|
70 |
+
return null;
|
71 |
+
}
|
72 |
+
}
|
classes/ui/ui.php
DELETED
@@ -1,92 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined('DUPLICATOR_VERSION') ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
/**
|
5 |
-
* Helper Class for UI internactions
|
6 |
-
* @package Dupicator\classes
|
7 |
-
*/
|
8 |
-
class DUP_UI
|
9 |
-
{
|
10 |
-
|
11 |
-
/**
|
12 |
-
* The key used in the wp_options table
|
13 |
-
* @var string
|
14 |
-
*/
|
15 |
-
private static $OptionsViewStateKey = 'duplicator_ui_view_state';
|
16 |
-
|
17 |
-
/**
|
18 |
-
* Save the view state of UI elements
|
19 |
-
* @param string $key A unique key to define the ui element
|
20 |
-
* @param string $value A generic value to use for the view state
|
21 |
-
*/
|
22 |
-
public static function SaveViewState($key, $value)
|
23 |
-
{
|
24 |
-
$view_state = array();
|
25 |
-
$view_state = get_option(self::$OptionsViewStateKey);
|
26 |
-
$view_state[$key] = $value;
|
27 |
-
$success = update_option(self::$OptionsViewStateKey, $view_state);
|
28 |
-
return $success;
|
29 |
-
}
|
30 |
-
|
31 |
-
|
32 |
-
/**
|
33 |
-
* Gets all the values from the settings array
|
34 |
-
* @return array Returns and array of all the values stored in the settings array
|
35 |
-
*/
|
36 |
-
public static function GetViewStateArray()
|
37 |
-
{
|
38 |
-
return get_option(self::$OptionsViewStateKey);
|
39 |
-
}
|
40 |
-
|
41 |
-
/**
|
42 |
-
* Return the value of the of view state item
|
43 |
-
* @param type $searchKey The key to search on
|
44 |
-
* @return string Returns the value of the key searched or null if key is not found
|
45 |
-
*/
|
46 |
-
public static function GetViewStateValue($searchKey)
|
47 |
-
{
|
48 |
-
$view_state = get_option(self::$OptionsViewStateKey);
|
49 |
-
if (is_array($view_state)) {
|
50 |
-
foreach ($view_state as $key => $value) {
|
51 |
-
if ($key == $searchKey) {
|
52 |
-
return $value;
|
53 |
-
}
|
54 |
-
}
|
55 |
-
}
|
56 |
-
return null;
|
57 |
-
}
|
58 |
-
|
59 |
-
/**
|
60 |
-
* Shows a display message in the wp-admin if any researved files are found
|
61 |
-
* @return type void
|
62 |
-
*/
|
63 |
-
public static function ShowReservedFilesNotice()
|
64 |
-
{
|
65 |
-
//Show only on Duplicator pages and Dashboard when plugin is active
|
66 |
-
$dup_active = is_plugin_active('duplicator/duplicator.php');
|
67 |
-
$dup_perm = current_user_can( 'manage_options' );
|
68 |
-
if (! $dup_active || ! $dup_perm)
|
69 |
-
return;
|
70 |
-
|
71 |
-
if (DUP_Server::InstallerFilesFound())
|
72 |
-
{
|
73 |
-
$screen = get_current_screen();
|
74 |
-
$on_active_tab = isset($_GET['tab']) && $_GET['tab'] == 'cleanup' ? true : false;
|
75 |
-
|
76 |
-
echo '<div class="error" id="dup-global-error-reserved-files"><p>';
|
77 |
-
if ($screen->id == 'duplicator_page_duplicator-tools' && $on_active_tab)
|
78 |
-
{
|
79 |
-
_e('Reserved Duplicator install files have been detected in the root directory. Please delete these reserved files to avoid security issues.', 'duplicator');
|
80 |
-
}
|
81 |
-
else
|
82 |
-
{
|
83 |
-
$duplicator_nonce = wp_create_nonce('duplicator_cleanup_page');
|
84 |
-
_e('Reserved Duplicator install files have been detected in the root directory. Please delete these reserved files to avoid security issues.', 'duplicator');
|
85 |
-
@printf("<br/><a href='admin.php?page=duplicator-tools&tab=cleanup&_wpnonce=%s'>%s</a>", $duplicator_nonce, __('Take me to the cleanup page!', 'duplicator'));
|
86 |
-
}
|
87 |
-
echo "</p></div>";
|
88 |
-
}
|
89 |
-
}
|
90 |
-
|
91 |
-
}
|
92 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
classes/utilities/class.db.php
ADDED
@@ -0,0 +1,117 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Lightweight abstraction layer for common simple database routines
|
4 |
+
*
|
5 |
+
* Standard: PSR-2
|
6 |
+
* @link http://www.php-fig.org/psr/psr-2
|
7 |
+
*
|
8 |
+
* @package Duplicator
|
9 |
+
* @subpackage classes/utilities
|
10 |
+
* @copyright (c) 2017, Snapcreek LLC
|
11 |
+
* @since 1.1.32
|
12 |
+
*
|
13 |
+
*/
|
14 |
+
|
15 |
+
// Exit if accessed directly
|
16 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
17 |
+
exit;
|
18 |
+
}
|
19 |
+
|
20 |
+
class DUP_DB extends wpdb
|
21 |
+
{
|
22 |
+
|
23 |
+
/**
|
24 |
+
* Get the requested MySQL system variable
|
25 |
+
*
|
26 |
+
* @param string $name The database variable name to lookup
|
27 |
+
*
|
28 |
+
* @return string the server variable to query for
|
29 |
+
*/
|
30 |
+
public static function getVariable($name)
|
31 |
+
{
|
32 |
+
global $wpdb;
|
33 |
+
$row = $wpdb->get_row("SHOW VARIABLES LIKE '{$name}'", ARRAY_N);
|
34 |
+
return isset($row[1]) ? $row[1] : null;
|
35 |
+
}
|
36 |
+
|
37 |
+
/**
|
38 |
+
* Gets the MySQL database version number
|
39 |
+
*
|
40 |
+
* @param bool $full True: Gets the full version
|
41 |
+
* False: Gets only the numeric portion i.e. 5.5.6 or 10.1.2 (for MariaDB)
|
42 |
+
*
|
43 |
+
* @return false|string 0 on failure, version number on success
|
44 |
+
*/
|
45 |
+
public static function getVersion($full = false)
|
46 |
+
{
|
47 |
+
if ($full) {
|
48 |
+
$version = self::getVariable('version');
|
49 |
+
} else {
|
50 |
+
$version = preg_replace('/[^0-9.].*/', '', self::getVariable('version'));
|
51 |
+
}
|
52 |
+
|
53 |
+
return empty($version) ? 0 : $version;
|
54 |
+
}
|
55 |
+
|
56 |
+
|
57 |
+
/**
|
58 |
+
* Returns the mysqldump path if the server is enabled to execute it
|
59 |
+
* @return boolean|string
|
60 |
+
*/
|
61 |
+
public static function getMySqlDumpPath()
|
62 |
+
{
|
63 |
+
|
64 |
+
//Is shell_exec possible
|
65 |
+
if (!DUP_Util::hasShellExec()) {
|
66 |
+
return false;
|
67 |
+
}
|
68 |
+
|
69 |
+
$custom_mysqldump_path = DUP_Settings::Get('package_mysqldump_path');
|
70 |
+
$custom_mysqldump_path = (strlen($custom_mysqldump_path)) ? $custom_mysqldump_path : '';
|
71 |
+
|
72 |
+
//Common Windows Paths
|
73 |
+
if (DUP_Util::isWindows()) {
|
74 |
+
$paths = array(
|
75 |
+
$custom_mysqldump_path,
|
76 |
+
'C:/xampp/mysql/bin/mysqldump.exe',
|
77 |
+
'C:/Program Files/xampp/mysql/bin/mysqldump',
|
78 |
+
'C:/Program Files/MySQL/MySQL Server 6.0/bin/mysqldump',
|
79 |
+
'C:/Program Files/MySQL/MySQL Server 5.5/bin/mysqldump',
|
80 |
+
'C:/Program Files/MySQL/MySQL Server 5.4/bin/mysqldump',
|
81 |
+
'C:/Program Files/MySQL/MySQL Server 5.1/bin/mysqldump',
|
82 |
+
'C:/Program Files/MySQL/MySQL Server 5.0/bin/mysqldump',
|
83 |
+
);
|
84 |
+
|
85 |
+
//Common Linux Paths
|
86 |
+
} else {
|
87 |
+
$path1 = '';
|
88 |
+
$path2 = '';
|
89 |
+
$mysqldump = `which mysqldump`;
|
90 |
+
if (@is_executable($mysqldump)) $path1 = (!empty($mysqldump)) ? $mysqldump : '';
|
91 |
+
|
92 |
+
$mysqldump = dirname(`which mysql`)."/mysqldump";
|
93 |
+
if (@is_executable($mysqldump)) $path2 = (!empty($mysqldump)) ? $mysqldump : '';
|
94 |
+
|
95 |
+
$paths = array(
|
96 |
+
$custom_mysqldump_path,
|
97 |
+
$path1,
|
98 |
+
$path2,
|
99 |
+
'/usr/local/bin/mysqldump',
|
100 |
+
'/usr/local/mysql/bin/mysqldump',
|
101 |
+
'/usr/mysql/bin/mysqldump',
|
102 |
+
'/usr/bin/mysqldump',
|
103 |
+
'/opt/local/lib/mysql6/bin/mysqldump',
|
104 |
+
'/opt/local/lib/mysql5/bin/mysqldump',
|
105 |
+
'/opt/local/lib/mysql4/bin/mysqldump',
|
106 |
+
);
|
107 |
+
}
|
108 |
+
|
109 |
+
// Find the one which works
|
110 |
+
foreach ($paths as $path) {
|
111 |
+
if (@is_executable($path)) return $path;
|
112 |
+
}
|
113 |
+
|
114 |
+
return false;
|
115 |
+
}
|
116 |
+
|
117 |
+
}
|
classes/utilities/class.scan.check.php
ADDED
@@ -0,0 +1,146 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Recursivly scans a directory and finds all sym-links and unreadable files
|
4 |
+
*
|
5 |
+
* Standard: PSR-2
|
6 |
+
* @link http://www.php-fig.org/psr/psr-2
|
7 |
+
*
|
8 |
+
* @package Duplicator
|
9 |
+
* @subpackage classes/utilites
|
10 |
+
* @copyright (c) 2017, Snapcreek LLC
|
11 |
+
* @since 1.1.26
|
12 |
+
*
|
13 |
+
*/
|
14 |
+
|
15 |
+
// Exit if accessed directly
|
16 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
17 |
+
exit;
|
18 |
+
}
|
19 |
+
|
20 |
+
class DUP_ScanCheck
|
21 |
+
{
|
22 |
+
/**
|
23 |
+
* The number of files scanned
|
24 |
+
*/
|
25 |
+
public $fileCount = 0;
|
26 |
+
|
27 |
+
/**
|
28 |
+
* The number of directories scanned
|
29 |
+
*/
|
30 |
+
public $dirCount = 0;
|
31 |
+
|
32 |
+
/**
|
33 |
+
* The maximum count of files before the recursive function stops
|
34 |
+
*/
|
35 |
+
public $maxFiles = 1000000;
|
36 |
+
|
37 |
+
/**
|
38 |
+
* The maximum count of directories before the recursive function stops
|
39 |
+
*/
|
40 |
+
public $maxDirs = 75000;
|
41 |
+
|
42 |
+
/**
|
43 |
+
* Recursivly scan the root directory provided
|
44 |
+
*/
|
45 |
+
public $recursion = true;
|
46 |
+
|
47 |
+
/**
|
48 |
+
* Stores a list of symbolic link files
|
49 |
+
*/
|
50 |
+
public $symLinks = array();
|
51 |
+
|
52 |
+
/**
|
53 |
+
* Stores a list of files unreadable by PHP
|
54 |
+
*/
|
55 |
+
public $unreadable = array();
|
56 |
+
|
57 |
+
/**
|
58 |
+
* If the maxFiles or maxDirs limit is reached then true
|
59 |
+
*/
|
60 |
+
protected $limitReached = false;
|
61 |
+
|
62 |
+
/**
|
63 |
+
* Is the server running on Windows
|
64 |
+
*/
|
65 |
+
private $isWindows = false;
|
66 |
+
|
67 |
+
/**
|
68 |
+
* Init this instance of the object
|
69 |
+
*/
|
70 |
+
function __construct()
|
71 |
+
{
|
72 |
+
$this->isWindows = defined('PHP_WINDOWS_VERSION_BUILD');
|
73 |
+
}
|
74 |
+
|
75 |
+
/**
|
76 |
+
* Start the scan process
|
77 |
+
*
|
78 |
+
* @param string $dir A valid directory path where the scan will run
|
79 |
+
* @param array $results Used for recursion, do not pass in value with calling
|
80 |
+
*
|
81 |
+
* @return obj The scan check object with the results of the scan
|
82 |
+
*/
|
83 |
+
public function run($dir, &$results = array())
|
84 |
+
{
|
85 |
+
//Stop Recursion if Max search is reached
|
86 |
+
if ($this->fileCount > $this->maxFiles || $this->dirCount > $this->maxDirs) {
|
87 |
+
$this->limitReached = true;
|
88 |
+
return $results;
|
89 |
+
}
|
90 |
+
|
91 |
+
$files = @scandir($dir);
|
92 |
+
if (is_array($files)) {
|
93 |
+
foreach ($files as $key => $value) {
|
94 |
+
$path = realpath($dir.DIRECTORY_SEPARATOR.$value);
|
95 |
+
if ($path) {
|
96 |
+
//Files
|
97 |
+
if (!is_dir($path)) {
|
98 |
+
if (!is_readable($path)) {
|
99 |
+
$results[] = $path;
|
100 |
+
$this->unreadable[] = $path;
|
101 |
+
} else if ($this->isLink($path)) {
|
102 |
+
$results[] = $path;
|
103 |
+
$this->symLinks[] = $path;
|
104 |
+
}
|
105 |
+
$this->fileCount++;
|
106 |
+
}
|
107 |
+
//Dirs
|
108 |
+
else if ($value != "." && $value != "..") {
|
109 |
+
if (!$this->isLink($path) && $this->recursion) {
|
110 |
+
$this->Run($path, $results);
|
111 |
+
}
|
112 |
+
|
113 |
+
if (!is_readable($path)) {
|
114 |
+
$results[] = $path;
|
115 |
+
$this->unreadable[] = $path;
|
116 |
+
} else if ($this->isLink($path)) {
|
117 |
+
$results[] = $path;
|
118 |
+
$this->symLinks[] = $path;
|
119 |
+
}
|
120 |
+
$this->dirCount++;
|
121 |
+
}
|
122 |
+
}
|
123 |
+
}
|
124 |
+
}
|
125 |
+
return $this;
|
126 |
+
}
|
127 |
+
|
128 |
+
/**
|
129 |
+
* Seperation logic for supporting how different operating systems work
|
130 |
+
*
|
131 |
+
* @param string $target A valid file path
|
132 |
+
*
|
133 |
+
* @return bool Is the target a sym link
|
134 |
+
*/
|
135 |
+
private function isLink($target)
|
136 |
+
{
|
137 |
+
if ($this->isWindows) {
|
138 |
+
if (file_exists($target) && @readlink($target) != $target) {
|
139 |
+
return true;
|
140 |
+
}
|
141 |
+
} elseif (is_link($target)) {
|
142 |
+
return true;
|
143 |
+
}
|
144 |
+
return false;
|
145 |
+
}
|
146 |
+
}
|
classes/utilities/class.server.php
ADDED
@@ -0,0 +1,204 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Used to get various pieces of information about the server enviroment
|
4 |
+
*
|
5 |
+
* Standard: PSR-2
|
6 |
+
* @link http://www.php-fig.org/psr/psr-2
|
7 |
+
*
|
8 |
+
* @package Duplicator
|
9 |
+
* @subpackage classes/utilites
|
10 |
+
* @copyright (c) 2017, Snapcreek LLC
|
11 |
+
* @since 1.1.0
|
12 |
+
*
|
13 |
+
*/
|
14 |
+
require_once (DUPLICATOR_PLUGIN_PATH.'classes/utilities/class.util.php');
|
15 |
+
|
16 |
+
// Exit if accessed directly
|
17 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
18 |
+
exit;
|
19 |
+
}
|
20 |
+
|
21 |
+
class DUP_Server
|
22 |
+
{
|
23 |
+
|
24 |
+
/**
|
25 |
+
* Gets the system requirements which must pass to buld a package
|
26 |
+
*
|
27 |
+
* @return array An array of requirements
|
28 |
+
*/
|
29 |
+
public static function getRequirements()
|
30 |
+
{
|
31 |
+
global $wpdb;
|
32 |
+
$dup_tests = array();
|
33 |
+
|
34 |
+
//PHP SUPPORT
|
35 |
+
$safe_ini = strtolower(ini_get('safe_mode'));
|
36 |
+
$dup_tests['PHP']['SAFE_MODE'] = $safe_ini != 'on' || $safe_ini != 'yes' || $safe_ini != 'true' || ini_get("safe_mode") != 1 ? 'Pass' : 'Fail';
|
37 |
+
$dup_tests['PHP']['VERSION'] = DUP_Util::$on_php_529_plus ? 'Pass' : 'Fail';
|
38 |
+
$dup_tests['PHP']['ZIP'] = class_exists('ZipArchive') ? 'Pass' : 'Fail';
|
39 |
+
$dup_tests['PHP']['FUNC_1'] = function_exists("file_get_contents") ? 'Pass' : 'Fail';
|
40 |
+
$dup_tests['PHP']['FUNC_2'] = function_exists("file_put_contents") ? 'Pass' : 'Fail';
|
41 |
+
$dup_tests['PHP']['FUNC_3'] = function_exists("mb_strlen") ? 'Pass' : 'Fail';
|
42 |
+
$dup_tests['PHP']['ALL'] = !in_array('Fail', $dup_tests['PHP']) ? 'Pass' : 'Fail';
|
43 |
+
|
44 |
+
//REQUIRED PATHS
|
45 |
+
if (file_exists(DUPLICATOR_SSDIR_PATH) && is_writeable(DUPLICATOR_SSDIR_PATH)) {
|
46 |
+
$dup_tests['IO']['SSDIR'] = 'Pass';
|
47 |
+
$dup_tests['IO']['WPROOT'] = 'Pass';
|
48 |
+
} else {
|
49 |
+
$handle_test = @opendir(DUPLICATOR_WPROOTPATH);
|
50 |
+
$dup_tests['IO']['WPROOT'] = is_writeable(DUPLICATOR_WPROOTPATH) && $handle_test ? 'Pass' : 'Fail';
|
51 |
+
$dup_tests['IO']['SSDIR'] = 'Fail';
|
52 |
+
@closedir($handle_test);
|
53 |
+
}
|
54 |
+
|
55 |
+
$dup_tests['IO']['SSTMP'] = is_writeable(DUPLICATOR_SSDIR_PATH_TMP) ? 'Pass' : 'Fail';
|
56 |
+
$dup_tests['IO']['ALL'] = !in_array('Fail', $dup_tests['IO']) ? 'Pass' : 'Fail';
|
57 |
+
|
58 |
+
//SERVER SUPPORT
|
59 |
+
$dup_tests['SRV']['MYSQLi'] = function_exists('mysqli_connect') ? 'Pass' : 'Fail';
|
60 |
+
$dup_tests['SRV']['MYSQL_VER'] = version_compare(DUP_DB::getVersion(), '5.0', '>=') ? 'Pass' : 'Fail';
|
61 |
+
$dup_tests['SRV']['ALL'] = !in_array('Fail', $dup_tests['SRV']) ? 'Pass' : 'Fail';
|
62 |
+
|
63 |
+
//RESERVED FILES
|
64 |
+
$dup_tests['RES']['INSTALL'] = !(self::hasInstallerFiles()) ? 'Pass' : 'Fail';
|
65 |
+
$dup_tests['Success'] = $dup_tests['PHP']['ALL'] == 'Pass'
|
66 |
+
&& $dup_tests['IO']['ALL'] == 'Pass'
|
67 |
+
&& $dup_tests['SRV']['ALL'] == 'Pass'
|
68 |
+
&& $dup_tests['RES']['INSTALL'] == 'Pass';
|
69 |
+
|
70 |
+
return $dup_tests;
|
71 |
+
}
|
72 |
+
|
73 |
+
/**
|
74 |
+
* Gets the system checks which are not required
|
75 |
+
*
|
76 |
+
* @return array An array of system checks
|
77 |
+
*/
|
78 |
+
public static function getChecks()
|
79 |
+
{
|
80 |
+
$checks = array();
|
81 |
+
|
82 |
+
//WEB SERVER
|
83 |
+
$web_test1 = false;
|
84 |
+
foreach ($GLOBALS['DUPLICATOR_SERVER_LIST'] as $value) {
|
85 |
+
if (stristr($_SERVER['SERVER_SOFTWARE'], $value)) {
|
86 |
+
$web_test1 = true;
|
87 |
+
break;
|
88 |
+
}
|
89 |
+
}
|
90 |
+
$checks['SRV']['WEB']['model'] = $web_test1;
|
91 |
+
$checks['SRV']['WEB']['ALL'] = ($web_test1) ? 'Good' : 'Warn';
|
92 |
+
|
93 |
+
//PHP SETTINGS
|
94 |
+
$php_test1 = ini_get("open_basedir");
|
95 |
+
$php_test1 = empty($php_test1) ? true : false;
|
96 |
+
$php_test2 = ini_get("max_execution_time");
|
97 |
+
$php_test2 = ($php_test2 > DUPLICATOR_SCAN_TIMEOUT) || (strcmp($php_test2, 'Off') == 0 || $php_test2 == 0) ? true : false;
|
98 |
+
$php_test3 = function_exists('mysqli_connect');
|
99 |
+
$php_test4 = DUP_Util::$on_php_53_plus ? true : false;
|
100 |
+
|
101 |
+
$checks['SRV']['PHP']['openbase'] = $php_test1;
|
102 |
+
$checks['SRV']['PHP']['maxtime'] = $php_test2;
|
103 |
+
$checks['SRV']['PHP']['mysqli'] = $php_test3;
|
104 |
+
$checks['SRV']['PHP']['version'] = $php_test4;
|
105 |
+
$checks['SRV']['PHP']['ALL'] = ($php_test1 && $php_test2 && $php_test3 && $php_test4) ? 'Good' : 'Warn';
|
106 |
+
|
107 |
+
|
108 |
+
//WORDPRESS SETTINGS
|
109 |
+
global $wp_version;
|
110 |
+
$wp_test1 = version_compare($wp_version, DUPLICATOR_SCAN_MIN_WP) >= 0 ? true : false;
|
111 |
+
|
112 |
+
//Core Files
|
113 |
+
$files = array();
|
114 |
+
$files['wp-config.php'] = file_exists(DUP_Util::safePath(DUPLICATOR_WPROOTPATH.'/wp-config.php'));
|
115 |
+
$wp_test2 = $files['wp-config.php'];
|
116 |
+
|
117 |
+
//Cache
|
118 |
+
$Package = DUP_Package::getActive();
|
119 |
+
$cache_path = DUP_Util::safePath(WP_CONTENT_DIR).'/cache';
|
120 |
+
$dirEmpty = DUP_Util::isDirectoryEmpty($cache_path);
|
121 |
+
$dirSize = DUP_Util::getDirectorySize($cache_path);
|
122 |
+
$cach_filtered = in_array($cache_path, explode(';', $Package->Archive->FilterDirs));
|
123 |
+
$wp_test3 = ($cach_filtered || $dirEmpty || $dirSize < DUPLICATOR_SCAN_CACHESIZE ) ? true : false;
|
124 |
+
$wp_test4 = is_multisite();
|
125 |
+
|
126 |
+
$checks['SRV']['WP']['version'] = $wp_test1;
|
127 |
+
$checks['SRV']['WP']['core'] = $wp_test2;
|
128 |
+
$checks['SRV']['WP']['cache'] = $wp_test3;
|
129 |
+
$checks['SRV']['WP']['ismu'] = $wp_test4;
|
130 |
+
$checks['SRV']['WP']['ALL'] = $wp_test1 && $wp_test2 && $wp_test3 && !$wp_test4 ? 'Good' : 'Warn';
|
131 |
+
|
132 |
+
return $checks;
|
133 |
+
}
|
134 |
+
|
135 |
+
/**
|
136 |
+
* Check to see if duplicator installer files are present
|
137 |
+
*
|
138 |
+
* @return bool True if any reserved files are found
|
139 |
+
*/
|
140 |
+
public static function hasInstallerFiles()
|
141 |
+
{
|
142 |
+
$files = self::getInstallerFiles();
|
143 |
+
foreach ($files as $file => $path) {
|
144 |
+
if (file_exists($path)) return true;
|
145 |
+
}
|
146 |
+
return false;
|
147 |
+
}
|
148 |
+
|
149 |
+
/**
|
150 |
+
* Gets a list of all the installer files by name and full path
|
151 |
+
*
|
152 |
+
* @return array [file_name, file_path]
|
153 |
+
*/
|
154 |
+
public static function getInstallerFiles()
|
155 |
+
{
|
156 |
+
// Files: installer.php, installer-backup.php, installer-data.sql, installer-log.txt, database.sql
|
157 |
+
return array(
|
158 |
+
DUPLICATOR_INSTALL_PHP => DUPLICATOR_WPROOTPATH.DUPLICATOR_INSTALL_PHP,
|
159 |
+
DUPLICATOR_INSTALL_BAK => DUPLICATOR_WPROOTPATH.DUPLICATOR_INSTALL_BAK,
|
160 |
+
DUPLICATOR_INSTALL_SQL => DUPLICATOR_WPROOTPATH.DUPLICATOR_INSTALL_SQL,
|
161 |
+
DUPLICATOR_INSTALL_LOG => DUPLICATOR_WPROOTPATH.DUPLICATOR_INSTALL_LOG,
|
162 |
+
DUPLICATOR_INSTALL_DB => DUPLICATOR_WPROOTPATH.DUPLICATOR_INSTALL_DB
|
163 |
+
);
|
164 |
+
}
|
165 |
+
|
166 |
+
/**
|
167 |
+
* Get the IP of a client machine
|
168 |
+
*
|
169 |
+
* @return string IP of the client machine
|
170 |
+
*/
|
171 |
+
public static function getClientIP()
|
172 |
+
{
|
173 |
+
if (array_key_exists('HTTP_X_FORWARDED_FOR', $_SERVER)) {
|
174 |
+
return $_SERVER["HTTP_X_FORWARDED_FOR"];
|
175 |
+
} else if (array_key_exists('REMOTE_ADDR', $_SERVER)) {
|
176 |
+
return $_SERVER["REMOTE_ADDR"];
|
177 |
+
} else if (array_key_exists('HTTP_CLIENT_IP', $_SERVER)) {
|
178 |
+
return $_SERVER["HTTP_CLIENT_IP"];
|
179 |
+
}
|
180 |
+
return '';
|
181 |
+
}
|
182 |
+
|
183 |
+
/**
|
184 |
+
* Get PHP memory useage
|
185 |
+
*
|
186 |
+
* @return string Returns human readable memory useage.
|
187 |
+
*/
|
188 |
+
public static function getPHPMemory($peak = false)
|
189 |
+
{
|
190 |
+
if ($peak) {
|
191 |
+
$result = 'Unable to read PHP peak memory usage';
|
192 |
+
if (function_exists('memory_get_peak_usage')) {
|
193 |
+
$result = DUP_Util::byteSize(memory_get_peak_usage(true));
|
194 |
+
}
|
195 |
+
} else {
|
196 |
+
$result = 'Unable to read PHP memory usage';
|
197 |
+
if (function_exists('memory_get_usage')) {
|
198 |
+
$result = DUP_Util::byteSize(memory_get_usage(true));
|
199 |
+
}
|
200 |
+
}
|
201 |
+
return $result;
|
202 |
+
}
|
203 |
+
}
|
204 |
+
?>
|
classes/utilities/class.util.php
ADDED
@@ -0,0 +1,481 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/**
|
3 |
+
* Recursivly scans a directory and finds all sym-links and unreadable files
|
4 |
+
*
|
5 |
+
* Standard: PSR-2
|
6 |
+
* @link http://www.php-fig.org/psr/psr-2
|
7 |
+
*
|
8 |
+
* @package Duplicator
|
9 |
+
* @subpackage classes/utilites
|
10 |
+
* @copyright (c) 2017, Snapcreek LLC
|
11 |
+
* @since 1.1.0
|
12 |
+
*
|
13 |
+
* @todo Refactor out IO methods into class.io.php file
|
14 |
+
*/
|
15 |
+
|
16 |
+
// Exit if accessed directly
|
17 |
+
if (!defined('DUPLICATOR_VERSION')) {
|
18 |
+
exit;
|
19 |
+
}
|
20 |
+
|
21 |
+
class DUP_Util
|
22 |
+
{
|
23 |
+
/**
|
24 |
+
* Is PHP 5.2.9 or better running
|
25 |
+
*/
|
26 |
+
public static $on_php_529_plus;
|
27 |
+
|
28 |
+
/**
|
29 |
+
* Is PHP 5.3 or better running
|
30 |
+
*/
|
31 |
+
public static $on_php_53_plus;
|
32 |
+
|
33 |
+
/**
|
34 |
+
* Is PHP 5.4 or better running
|
35 |
+
*/
|
36 |
+
public static $on_php_54_plus;
|
37 |
+
|
38 |
+
/**
|
39 |
+
* Inited on load (see end of file)
|
40 |
+
*/
|
41 |
+
public static function init()
|
42 |
+
{
|
43 |
+
self::$on_php_529_plus = version_compare(PHP_VERSION, '5.2.9') >= 0;
|
44 |
+
self::$on_php_53_plus = version_compare(PHP_VERSION, '5.3.0') >= 0;
|
45 |
+
self::$on_php_54_plus = version_compare(PHP_VERSION, '5.4.0') >= 0;
|
46 |
+
}
|
47 |
+
|
48 |
+
/**
|
49 |
+
* PHP_SAPI for fcgi requires a data flush of at least 256
|
50 |
+
* bytes every 40 seconds or else it forces a script hault
|
51 |
+
*
|
52 |
+
* @return string A series of 256 space characters
|
53 |
+
*/
|
54 |
+
public static function fcgiFlush()
|
55 |
+
{
|
56 |
+
echo(str_repeat(' ', 300));
|
57 |
+
@flush();
|
58 |
+
}
|
59 |
+
|
60 |
+
/**
|
61 |
+
* Returns the wp-snapshot url
|
62 |
+
*
|
63 |
+
* @return string The full url of the duplicators snapshot storage directory
|
64 |
+
*/
|
65 |
+
public static function snapshotURL()
|
66 |
+
{
|
67 |
+
return get_site_url(null, '', is_ssl() ? 'https' : 'http').'/'.DUPLICATOR_SSDIR_NAME.'/';
|
68 |
+
}
|
69 |
+
|
70 |
+
/**
|
71 |
+
* Returns the last N lines of a file. Equivelent to tail command
|
72 |
+
*
|
73 |
+
* @param string $filepath The full path to the file to be tailed
|
74 |
+
* @param int $lines The number of lines to return with each tail call
|
75 |
+
*
|
76 |
+
* @return string The last N parts of the file
|
77 |
+
*/
|
78 |
+
public static function tailFile($filepath, $lines = 2)
|
79 |
+
{
|
80 |
+
|
81 |
+
// Open file
|
82 |
+
$f = @fopen($filepath, "rb");
|
83 |
+
if ($f === false) return false;
|
84 |
+
|
85 |
+
// Sets buffer size
|
86 |
+
$buffer = 256;
|
87 |
+
|
88 |
+
// Jump to last character
|
89 |
+
fseek($f, -1, SEEK_END);
|
90 |
+
|
91 |
+
// Read it and adjust line number if necessary
|
92 |
+
// (Otherwise the result would be wrong if file doesn't end with a blank line)
|
93 |
+
if (fread($f, 1) != "\n") $lines -= 1;
|
94 |
+
|
95 |
+
// Start reading
|
96 |
+
$output = '';
|
97 |
+
$chunk = '';
|
98 |
+
|
99 |
+
// While we would like more
|
100 |
+
while (ftell($f) > 0 && $lines >= 0) {
|
101 |
+
// Figure out how far back we should jump
|
102 |
+
$seek = min(ftell($f), $buffer);
|
103 |
+
// Do the jump (backwards, relative to where we are)
|
104 |
+
fseek($f, -$seek, SEEK_CUR);
|
105 |
+
// Read a chunk and prepend it to our output
|
106 |
+
$output = ($chunk = fread($f, $seek)).$output;
|
107 |
+
// Jump back to where we started reading
|
108 |
+
fseek($f, -mb_strlen($chunk, '8bit'), SEEK_CUR);
|
109 |
+
// Decrease our line counter
|
110 |
+
$lines -= substr_count($chunk, "\n");
|
111 |
+
}
|
112 |
+
|
113 |
+
// While we have too many lines
|
114 |
+
// (Because of buffer size we might have read too many)
|
115 |
+
while ($lines++ < 0) {
|
116 |
+
// Find first newline and remove all text before that
|
117 |
+
$output = substr($output, strpos($output, "\n") + 1);
|
118 |
+
}
|
119 |
+
fclose($f);
|
120 |
+
return trim($output);
|
121 |
+
}
|
122 |
+
|
123 |
+
/**
|
124 |
+
* Runs the APC cache to pre-cache the php files
|
125 |
+
*
|
126 |
+
* @returns bool True if all files where cached
|
127 |
+
*/
|
128 |
+
public static function runAPC()
|
129 |
+
{
|
130 |
+
if (function_exists('apc_compile_file')) {
|
131 |
+
$file01 = @apc_compile_file(DUPLICATOR_PLUGIN_PATH."duplicator.php");
|
132 |
+
return ($file01);
|
133 |
+
} else {
|
134 |
+
return false;
|
135 |
+
}
|
136 |
+
}
|
137 |
+
|
138 |
+
/**
|
139 |
+
* Display human readable byte sizes
|
140 |
+
*
|
141 |
+
* @param int $size The size in bytes
|
142 |
+
*
|
143 |
+
* @return string The size of bytes readable such as 100KB, 20MB, 1GB etc.
|
144 |
+
*/
|
145 |
+
public static function byteSize($size)
|
146 |
+
{
|
147 |
+
try {
|
148 |
+
$units = array('B', 'KB', 'MB', 'GB', 'TB');
|
149 |
+
for ($i = 0; $size >= 1024 && $i < 4; $i++) {
|
150 |
+
$size /= 1024;
|
151 |
+
}
|
152 |
+
return round($size, 2).$units[$i];
|
153 |
+
} catch (Exception $e) {
|
154 |
+
return "n/a";
|
155 |
+
}
|
156 |
+
}
|
157 |
+
|
158 |
+
/**
|
159 |
+
* Makes path safe for any OS
|
160 |
+
* Paths should ALWAYS READ be "/"
|
161 |
+
* uni: /home/path/file.xt
|
162 |
+
* win: D:/home/path/file.txt
|
163 |
+
*
|
164 |
+
* @param string $path The path to make safe
|
165 |
+
*
|
166 |
+
* @return string A path with all slashes facing "/"
|
167 |
+
*/
|
168 |
+
public static function safePath($path)
|
169 |
+
{
|
170 |
+
return str_replace("\\", "/", $path);
|
171 |
+
}
|
172 |
+
|
173 |
+
/**
|
174 |
+
* Get current microtime as a float. Method is used for simple profiling
|
175 |
+
*
|
176 |
+
* @see elapsedTime
|
177 |
+
*
|
178 |
+
* @return string A float in the form "msec sec", where sec is the number of seconds since the Unix epoch
|
179 |
+
*/
|
180 |
+
public static function getMicrotime()
|
181 |
+
{
|
182 |
+
return microtime(true);
|
183 |
+
}
|
184 |
+
|
185 |
+
/**
|
186 |
+
* Append the value to the string if it doesn't already exist
|
187 |
+
*
|
188 |
+
* @param string $string The string to append to
|
189 |
+
* @param string $value The string to append to the $string
|
190 |
+
*
|
191 |
+
* @return string Returns the string with the $value appended once
|
192 |
+
*/
|
193 |
+
public static function appendOnce($string, $value)
|
194 |
+
|
195 |
+
{
|
196 |
+
return $string.(substr($string, -1) == $value ? '' : $value);
|
197 |
+
}
|
198 |
+
|
199 |
+
/**
|
200 |
+
* Return a string with the elapsed time
|
201 |
+
*
|
202 |
+
* @see getMicrotime()
|
203 |
+
*
|
204 |
+
* @param mixed number $end The final time in the sequence to measure
|
205 |
+
* @param mixed number $start The start time in the sequence to measure
|
206 |
+
*
|
207 |
+
* @return string The time elapsed from $start to $end
|
208 |
+
*/
|
209 |
+
public static function elapsedTime($end, $start)
|
210 |
+
{
|
211 |
+
return sprintf("%.2f sec.", abs($end - $start));
|
212 |
+
}
|
213 |
+
|
214 |
+
/**
|
215 |
+
* List all of the files of a path
|
216 |
+
*
|
217 |
+
* @param string $path The full path to a system directory
|
218 |
+
*
|
219 |
+
* @return array of all files in that path
|
220 |
+
*
|
221 |
+
* Notes:
|
222 |
+
* - Avoid using glob() as GLOB_BRACE is not an option on some operating systems
|
223 |
+
* - Pre PHP 5.3 DirectoryIterator will crash on unreadable files
|
224 |
+
*/
|
225 |
+
public static function listFiles($path = '.')
|
226 |
+
{
|
227 |
+
$files = array();
|
228 |
+
foreach (new DirectoryIterator($path) as $file) {
|
229 |
+
$files[] = str_replace("\\", '/', $file->getPathname());
|
230 |
+
}
|
231 |
+
return $files;
|
232 |
+
}
|
233 |
+
|
234 |
+
/**
|
235 |
+
* List all of the directories of a path
|
236 |
+
*
|
237 |
+
* @param string $path The full path to a system directory
|
238 |
+
*
|
239 |
+
* @return array of all dirs in the $path
|
240 |
+
*/
|
241 |
+
public static function listDirs($path = '.')
|
242 |
+
{
|
243 |
+
$dirs = array();
|
244 |
+
|
245 |
+
foreach (new DirectoryIterator($path) as $file) {
|
246 |
+
if ($file->isDir() && !$file->isDot()) {
|
247 |
+
$dirs[] = DUP_Util::safePath($file->getPathname());
|
248 |
+
}
|
249 |
+
}
|
250 |
+
return $dirs;
|
251 |
+
}
|
252 |
+
|
253 |
+
/**
|
254 |
+
* Does the directory have content
|
255 |
+
*
|
256 |
+
* @param string $path The full path to a system directory
|
257 |
+
*
|
258 |
+
* @return bool Returns true if directory is empty
|
259 |
+
*/
|
260 |
+
public static function isDirectoryEmpty($path)
|
261 |
+
{
|
262 |
+
if (!is_readable($path)) return NULL;
|
263 |
+
return (count(scandir($path)) == 2);
|
264 |
+
}
|
265 |
+
|
266 |
+
/**
|
267 |
+
* Size of the directory recursively in bytes
|
268 |
+
*
|
269 |
+
* @param string $path The full path to a system directory
|
270 |
+
*
|
271 |
+
* @return int Returns the size of the directory in bytes
|
272 |
+
*
|
273 |
+
*/
|
274 |
+
public static function getDirectorySize($path)
|
275 |
+
{
|
276 |
+
if (!file_exists($path)) return 0;
|
277 |
+
if (is_file($path)) return filesize($path);
|
278 |
+
|
279 |
+
$size = 0;
|
280 |
+
$list = glob($path."/*");
|
281 |
+
if (!empty($list)) {
|
282 |
+
foreach ($list as $file)
|
283 |
+
$size += self::getDirectorySize($file);
|
284 |
+
}
|
285 |
+
return $size;
|
286 |
+
}
|
287 |
+
|
288 |
+
/**
|
289 |
+
* Can shell_exec be called on this server
|
290 |
+
*
|
291 |
+
* @return bool Returns true if shell_exec can be called on server
|
292 |
+
*
|
293 |
+
*/
|
294 |
+
public static function hasShellExec()
|
295 |
+
{
|
296 |
+
$cmds = array('shell_exec', 'escapeshellarg', 'escapeshellcmd', 'extension_loaded');
|
297 |
+
|
298 |
+
//Function disabled at server level
|
299 |
+
if (array_intersect($cmds, array_map('trim', explode(',', @ini_get('disable_functions'))))) return false;
|
300 |
+
|
301 |
+
//Suhosin: http://www.hardened-php.net/suhosin/
|
302 |
+
//Will cause PHP to silently fail
|
303 |
+
if (extension_loaded('suhosin')) {
|
304 |
+
$suhosin_ini = @ini_get("suhosin.executor.func.blacklist");
|
305 |
+
if (array_intersect($cmds, array_map('trim', explode(',', $suhosin_ini)))) return false;
|
306 |
+
}
|
307 |
+
|
308 |
+
// Can we issue a simple echo command?
|
309 |
+
if (!@shell_exec('echo duplicator')) return false;
|
310 |
+
|
311 |
+
return true;
|
312 |
+
}
|
313 |
+
|
314 |
+
/**
|
315 |
+
* Is the server running Windows operating system
|
316 |
+
*
|
317 |
+
* @return bool Returns true if operating system is Windows
|
318 |
+
*
|
319 |
+
*/
|
320 |
+
public static function isWindows()
|
321 |
+
{
|
322 |
+
if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') {
|
323 |
+
return true;
|
324 |
+
}
|
325 |
+
return false;
|
326 |
+
}
|
327 |
+
|
328 |
+
/**
|
329 |
+
* Does the current user have the capability
|
330 |
+
*
|
331 |
+
* @return null Dies if user doesn't have the correct capability
|
332 |
+
*/
|
333 |
+
public static function hasCapability($permission = 'read')
|
334 |
+
{
|
335 |
+
$capability = $permission;
|
336 |
+
$capability = apply_filters('wpfront_user_role_editor_duplicator_translate_capability', $capability);
|
337 |
+
|
338 |
+
if (!current_user_can($capability)) {
|
339 |
+
wp_die(__('You do not have sufficient permissions to access this page.', 'duplicator'));
|
340 |
+
return;
|
341 |
+
}
|
342 |
+
}
|
343 |
+
|
344 |
+
/**
|
345 |
+
* Gets the name of the owner of the current PHP script
|
346 |
+
*
|
347 |
+
* @return string The name of the owner of the current PHP script
|
348 |
+
*/
|
349 |
+
public static function getCurrentUser()
|
350 |
+
{
|
351 |
+
$unreadable = 'Undetectable';
|
352 |
+
if (function_exists('get_current_user') && is_callable('get_current_user')) {
|
353 |
+
$user = get_current_user();
|
354 |
+
return strlen($user) ? $user : $unreadable;
|
355 |
+
}
|
356 |
+
return $unreadable;
|
357 |
+
}
|
358 |
+
|
359 |
+
/**
|
360 |
+
* Gets the owner of the PHP process
|
361 |
+
*
|
362 |
+
* @return string Gets the owner of the PHP process
|
363 |
+
*/
|
364 |
+
public static function getProcessOwner()
|
365 |
+
{
|
366 |
+
$unreadable = 'Undetectable';
|
367 |
+
$user = '';
|
368 |
+
try {
|
369 |
+
if (function_exists('exec')) {
|
370 |
+
$user = exec('whoami');
|
371 |
+
}
|
372 |
+
|
373 |
+
if (!strlen($user) && function_exists('posix_getpwuid') && function_exists('posix_geteuid')) {
|
374 |
+
$user = posix_getpwuid(posix_geteuid());
|
375 |
+
$user = $user['name'];
|
376 |
+
}
|
377 |
+
|
378 |
+
return strlen($user) ? $user : $unreadable;
|
379 |
+
} catch (Exception $ex) {
|
380 |
+
return $unreadable;
|
381 |
+
}
|
382 |
+
}
|
383 |
+
|
384 |
+
/**
|
385 |
+
* Creates the snapshot directory if it doesn't already exisit
|
386 |
+
*
|
387 |
+
* @return null
|
388 |
+
*/
|
389 |
+
public static function initSnapshotDirectory()
|
390 |
+
{
|
391 |
+
$path_wproot = DUP_Util::safePath(DUPLICATOR_WPROOTPATH);
|
392 |
+
$path_ssdir = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH);
|
393 |
+
$path_plugin = DUP_Util::safePath(DUPLICATOR_PLUGIN_PATH);
|
394 |
+
|
395 |
+
//--------------------------------
|
396 |
+
//CHMOD DIRECTORY ACCESS
|
397 |
+
//wordpress root directory
|
398 |
+
@chmod($path_wproot, 0755);
|
399 |
+
|
400 |
+
//snapshot directory
|
401 |
+
@mkdir($path_ssdir, 0755);
|
402 |
+
@chmod($path_ssdir, 0755);
|
403 |
+
|
404 |
+
//snapshot tmp directory
|
405 |
+
$path_ssdir_tmp = $path_ssdir.'/tmp';
|
406 |
+
@mkdir($path_ssdir_tmp, 0755);
|
407 |
+
@chmod($path_ssdir_tmp, 0755);
|
408 |
+
|
409 |
+
//plugins dir/files
|
410 |
+
@chmod($path_plugin.'files', 0755);
|
411 |
+
|
412 |
+
//--------------------------------
|
413 |
+
//FILE CREATION
|
414 |
+
//SSDIR: Create Index File
|
415 |
+
$ssfile = @fopen($path_ssdir.'/index.php', 'w');
|
416 |
+
@fwrite($ssfile,
|
417 |
+
'<?php error_reporting(0); if (stristr(php_sapi_name(), "fcgi")) { $url = "http://" . $_SERVER["HTTP_HOST"]; header("Location: {$url}/404.html");} else { header("HTTP/1.1 404 Not Found", true, 404);} exit(); ?>');
|
418 |
+
@fclose($ssfile);
|
419 |
+
|
420 |
+
//SSDIR: Create token file in snapshot
|
421 |
+
$tokenfile = @fopen($path_ssdir.'/dtoken.php', 'w');
|
422 |
+
@fwrite($tokenfile,
|
423 |
+
'<?php error_reporting(0); if (stristr(php_sapi_name(), "fcgi")) { $url = "http://" . $_SERVER["HTTP_HOST"]; header("Location: {$url}/404.html");} else { header("HTTP/1.1 404 Not Found", true, 404);} exit(); ?>');
|
424 |
+
@fclose($tokenfile);
|
425 |
+
|
426 |
+
//SSDIR: Create .htaccess
|
427 |
+
$storage_htaccess_off = DUP_Settings::Get('storage_htaccess_off');
|
428 |
+
if ($storage_htaccess_off) {
|
429 |
+
@unlink($path_ssdir.'/.htaccess');
|
430 |
+
} else {
|
431 |
+
$htfile = @fopen($path_ssdir.'/.htaccess', 'w');
|
432 |
+
$htoutput = "Options -Indexes";
|
433 |
+
@fwrite($htfile, $htoutput);
|
434 |
+
@fclose($htfile);
|
435 |
+
}
|
436 |
+
|
437 |
+
//SSDIR: Robots.txt file
|
438 |
+
$robotfile = @fopen($path_ssdir.'/robots.txt', 'w');
|
439 |
+
@fwrite($robotfile, "User-agent: * \nDisallow: /".DUPLICATOR_SSDIR_NAME.'/');
|
440 |
+
@fclose($robotfile);
|
441 |
+
|
442 |
+
//PLUG DIR: Create token file in plugin
|
443 |
+
$tokenfile2 = @fopen($path_plugin.'installer/dtoken.php', 'w');
|
444 |
+
@fwrite($tokenfile2,
|
445 |
+
'<?php @error_reporting(0); @require_once("../../../../wp-admin/admin.php"); global $wp_query; $wp_query->set_404(); header("HTTP/1.1 404 Not Found", true, 404); header("Status: 404 Not Found"); @include(get_template_directory () . "/404.php"); ?>');
|
446 |
+
@fclose($tokenfile2);
|
447 |
+
}
|
448 |
+
|
449 |
+
/**
|
450 |
+
* Attempts to get the file zip path on a users system
|
451 |
+
*
|
452 |
+
* @return null
|
453 |
+
*/
|
454 |
+
public static function getZipPath()
|
455 |
+
{
|
456 |
+
$filepath = null;
|
457 |
+
|
458 |
+
if (self::hasShellExec()) {
|
459 |
+
if (shell_exec('hash zip 2>&1') == NULL) {
|
460 |
+
$filepath = 'zip';
|
461 |
+
} else {
|
462 |
+
$possible_paths = array(
|
463 |
+
'/usr/bin/zip',
|
464 |
+
'/opt/local/bin/zip'
|
465 |
+
//'C:/Program\ Files\ (x86)/GnuWin32/bin/zip.exe');
|
466 |
+
);
|
467 |
+
|
468 |
+
foreach ($possible_paths as $path) {
|
469 |
+
if (file_exists($path)) {
|
470 |
+
$filepath = $path;
|
471 |
+
break;
|
472 |
+
}
|
473 |
+
}
|
474 |
+
}
|
475 |
+
}
|
476 |
+
|
477 |
+
return $filepath;
|
478 |
+
}
|
479 |
+
}
|
480 |
+
DUP_Util::init();
|
481 |
+
?>
|
classes/utility.php
DELETED
@@ -1,393 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
if ( ! defined( 'DUPLICATOR_VERSION' ) ) exit; // Exit if accessed directly
|
3 |
-
|
4 |
-
class DUP_Util
|
5 |
-
{
|
6 |
-
public static $on_php_529_plus;
|
7 |
-
public static $on_php_53_plus;
|
8 |
-
public static $on_php_54_plus;
|
9 |
-
|
10 |
-
|
11 |
-
public static function init()
|
12 |
-
{
|
13 |
-
self::$on_php_529_plus = version_compare(PHP_VERSION, '5.2.9') >= 0;
|
14 |
-
self::$on_php_53_plus = version_compare(PHP_VERSION, '5.3.0') >= 0;
|
15 |
-
self::$on_php_54_plus = version_compare(PHP_VERSION, '5.4.0') >= 0;
|
16 |
-
}
|
17 |
-
|
18 |
-
/**
|
19 |
-
* PHP_SAPI for fcgi requires a data flush of at least 256
|
20 |
-
* bytes every 40 seconds or else it forces a script hault
|
21 |
-
*/
|
22 |
-
public static function FcgiFlush() {
|
23 |
-
echo(str_repeat(' ', 300));
|
24 |
-
@flush();
|
25 |
-
}
|
26 |
-
|
27 |
-
/**
|
28 |
-
* returns the snapshot url
|
29 |
-
*/
|
30 |
-
public static function SSDirURL() {
|
31 |
-
return get_site_url(null, '', is_ssl() ? 'https' : 'http') . '/' . DUPLICATOR_SSDIR_NAME . '/';
|
32 |
-
}
|
33 |
-
|
34 |
-
/**
|
35 |
-
* Returns the last N lines of a file
|
36 |
-
* Equivelent to tail command
|
37 |
-
*/
|
38 |
-
public static function TailFile($filepath, $lines = 2) {
|
39 |
-
|
40 |
-
// Open file
|
41 |
-
$f = @fopen($filepath, "rb");
|
42 |
-
if ($f === false) return false;
|
43 |
-
|
44 |
-
// Sets buffer size
|
45 |
-
$buffer = 256;
|
46 |
-
|
47 |
-
// Jump to last character
|
48 |
-
fseek($f, -1, SEEK_END);
|
49 |
-
|
50 |
-
// Read it and adjust line number if necessary
|
51 |
-
// (Otherwise the result would be wrong if file doesn't end with a blank line)
|
52 |
-
if (fread($f, 1) != "\n") $lines -= 1;
|
53 |
-
|
54 |
-
// Start reading
|
55 |
-
$output = '';
|
56 |
-
$chunk = '';
|
57 |
-
|
58 |
-
// While we would like more
|
59 |
-
while (ftell($f) > 0 && $lines >= 0) {
|
60 |
-
// Figure out how far back we should jump
|
61 |
-
$seek = min(ftell($f), $buffer);
|
62 |
-
// Do the jump (backwards, relative to where we are)
|
63 |
-
fseek($f, -$seek, SEEK_CUR);
|
64 |
-
// Read a chunk and prepend it to our output
|
65 |
-
$output = ($chunk = fread($f, $seek)) . $output;
|
66 |
-
// Jump back to where we started reading
|
67 |
-
fseek($f, -mb_strlen($chunk, '8bit'), SEEK_CUR);
|
68 |
-
// Decrease our line counter
|
69 |
-
$lines -= substr_count($chunk, "\n");
|
70 |
-
}
|
71 |
-
|
72 |
-
// While we have too many lines
|
73 |
-
// (Because of buffer size we might have read too many)
|
74 |
-
while ($lines++ < 0) {
|
75 |
-
// Find first newline and remove all text before that
|
76 |
-
$output = substr($output, strpos($output, "\n") + 1);
|
77 |
-
}
|
78 |
-
fclose($f);
|
79 |
-
return trim($output);
|
80 |
-
}
|
81 |
-
|
82 |
-
|
83 |
-
/**
|
84 |
-
* Runs the APC cache to pre-cache the php files
|
85 |
-
* returns true if all files where cached
|
86 |
-
*/
|
87 |
-
public static function RunAPC() {
|
88 |
-
if(function_exists('apc_compile_file')){
|
89 |
-
$file01 = @apc_compile_file(DUPLICATOR_PLUGIN_PATH . "duplicator.php");
|
90 |
-
return ($file01);
|
91 |
-
} else {
|
92 |
-
return false;
|
93 |
-
}
|
94 |
-
}
|
95 |
-
|
96 |
-
/**
|
97 |
-
* Display human readable byte sizes
|
98 |
-
* @param string $size The size in bytes
|
99 |
-
*/
|
100 |
-
public static function ByteSize($size) {
|
101 |
-
try {
|
102 |
-
$units = array('B', 'KB', 'MB', 'GB', 'TB');
|
103 |
-
for ($i = 0; $size >= 1024 && $i < 4; $i++)
|
104 |
-
$size /= 1024;
|
105 |
-
return round($size, 2) . $units[$i];
|
106 |
-
} catch (Exception $e) {
|
107 |
-
return "n/a";
|
108 |
-
}
|
109 |
-
}
|
110 |
-
|
111 |
-
/**
|
112 |
-
* Makes path safe for any OS
|
113 |
-
* Paths should ALWAYS READ be "/"
|
114 |
-
* uni: /home/path/file.xt
|
115 |
-
* win: D:/home/path/file.txt
|
116 |
-
* @param string $path The path to make safe
|
117 |
-
*/
|
118 |
-
public static function SafePath($path) {
|
119 |
-
return str_replace("\\", "/", $path);
|
120 |
-
}
|
121 |
-
|
122 |
-
/**
|
123 |
-
* Get current microtime as a float. Can be used for simple profiling.
|
124 |
-
*/
|
125 |
-
public static function GetMicrotime() {
|
126 |
-
return microtime(true);
|
127 |
-
}
|
128 |
-
|
129 |
-
/**
|
130 |
-
* Append the value to the string if it doesn't already exist
|
131 |
-
*/
|
132 |
-
public static function StringAppend($string, $value ) {
|
133 |
-
return $string . (substr($string, -1) == $value ? '' : $value);
|
134 |
-
}
|
135 |
-
|
136 |
-
/**
|
137 |
-
* Return a string with the elapsed time.
|
138 |
-
* Order of $end and $start can be switched.
|
139 |
-
*/
|
140 |
-
public static function ElapsedTime($end, $start) {
|
141 |
-
return sprintf("%.2f sec.", abs($end - $start));
|
142 |
-
}
|
143 |
-
|
144 |
-
/**
|
145 |
-
* Get the MySQL system variables
|
146 |
-
* @param conn $dbh Database connection handle
|
147 |
-
* @return string the server variable to query for
|
148 |
-
*/
|
149 |
-
public static function MysqlVariableValue($variable) {
|
150 |
-
global $wpdb;
|
151 |
-
$row = $wpdb->get_row("SHOW VARIABLES LIKE '{$variable}'", ARRAY_N);
|
152 |
-
return isset($row[1]) ? $row[1] : null;
|
153 |
-
}
|
154 |
-
|
155 |
-
/**
|
156 |
-
* List all of the files of a path
|
157 |
-
* @path path to a system directory
|
158 |
-
* @return array of all files in that path
|
159 |
-
*
|
160 |
-
* Compatibility Notes:
|
161 |
-
* - Avoid using glob() as GLOB_BRACE is not an option on some operating systems
|
162 |
-
* - Pre PHP 5.3 DirectoryIterator will crash on unreadable files
|
163 |
-
*/
|
164 |
-
public static function ListFiles($path = '.')
|
165 |
-
{
|
166 |
-
$files = array();
|
167 |
-
foreach (new DirectoryIterator($path) as $file)
|
168 |
-
{
|
169 |
-
$files[] = str_replace("\\", '/', $file->getPathname());
|
170 |
-
}
|
171 |
-
return $files;
|
172 |
-
}
|
173 |
-
|
174 |
-
/**
|
175 |
-
* List all of the directories of a path
|
176 |
-
* @path path to a system directory
|
177 |
-
* @return array of all directories in that path
|
178 |
-
*/
|
179 |
-
public static function ListDirs($path = '.') {
|
180 |
-
$dirs = array();
|
181 |
-
|
182 |
-
foreach (new DirectoryIterator($path) as $file) {
|
183 |
-
if ($file->isDir() && !$file->isDot()) {
|
184 |
-
$dirs[] = DUP_Util::SafePath($file->getPathname());
|
185 |
-
}
|
186 |
-
}
|
187 |
-
return $dirs;
|
188 |
-
}
|
189 |
-
|
190 |
-
/**
|
191 |
-
* Does the directory have content
|
192 |
-
*/
|
193 |
-
public static function IsDirectoryEmpty($dir) {
|
194 |
-
if (!is_readable($dir)) return NULL;
|
195 |
-
return (count(scandir($dir)) == 2);
|
196 |
-
}
|
197 |
-
|
198 |
-
/**
|
199 |
-
* Size of the directory recuresivly in bytes
|
200 |
-
*/
|
201 |
-
public static function GetDirectorySize($dir) {
|
202 |
-
if(!file_exists($dir))
|
203 |
-
return 0;
|
204 |
-
if(is_file($dir))
|
205 |
-
return filesize($dir);
|
206 |
-
|
207 |
-
$size = 0;
|
208 |
-
$list = glob($dir."/*");
|
209 |
-
if (! empty($list)) {
|
210 |
-
foreach($list as $file)
|
211 |
-
$size += self::GetDirectorySize($file);
|
212 |
-
}
|
213 |
-
return $size;
|
214 |
-
}
|
215 |
-
|
216 |
-
/**
|
217 |
-
* Can shell_exec be called on this server
|
218 |
-
*/
|
219 |
-
public static function IsShellExecAvailable()
|
220 |
-
{
|
221 |
-
$cmds = array('shell_exec', 'escapeshellarg', 'escapeshellcmd', 'extension_loaded');
|
222 |
-
|
223 |
-
//Function disabled at server level
|
224 |
-
if (array_intersect($cmds, array_map('trim', explode(',', @ini_get('disable_functions')))))
|
225 |
-
return false;
|
226 |
-
|
227 |
-
//Suhosin: http://www.hardened-php.net/suhosin/
|
228 |
-
//Will cause PHP to silently fail
|
229 |
-
if (extension_loaded('suhosin'))
|
230 |
-
{
|
231 |
-
$suhosin_ini = @ini_get("suhosin.executor.func.blacklist");
|
232 |
-
if (array_intersect($cmds, array_map('trim', explode(',', $suhosin_ini))))
|
233 |
-
return false;
|
234 |
-
}
|
235 |
-
|
236 |
-
// Can we issue a simple echo command?
|
237 |
-
if (!@shell_exec('echo duplicator'))
|
238 |
-
return false;
|
239 |
-
|
240 |
-
return true;
|
241 |
-
}
|
242 |
-
|
243 |
-
public static function IsOSWindows() {
|
244 |
-
if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') {
|
245 |
-
return true;
|
246 |
-
}
|
247 |
-
return false;
|
248 |
-
}
|
249 |
-
|
250 |
-
public static function CheckPermissions($permission = 'read') {
|
251 |
-
$capability = $permission;
|
252 |
-
$capability = apply_filters('wpfront_user_role_editor_duplicator_translate_capability', $capability);
|
253 |
-
|
254 |
-
if(!current_user_can($capability)) {
|
255 |
-
wp_die(__('You do not have sufficient permissions to access this page.', 'duplicator'));
|
256 |
-
return;
|
257 |
-
}
|
258 |
-
}
|
259 |
-
|
260 |
-
/**
|
261 |
-
* Creates the snapshot directory if it doesn't already exisit
|
262 |
-
*/
|
263 |
-
public static function GetCurrentUser() {
|
264 |
-
$unreadable = 'Undetectable';
|
265 |
-
if (function_exists('get_current_user') && is_callable('get_current_user')) {
|
266 |
-
$user = get_current_user();
|
267 |
-
return strlen($user) ? $user : $unreadable;
|
268 |
-
}
|
269 |
-
return $unreadable;
|
270 |
-
}
|
271 |
-
|
272 |
-
/**
|
273 |
-
* Gets the owner of the PHP process
|
274 |
-
*/
|
275 |
-
public static function GetProcessOwner() {
|
276 |
-
$unreadable = 'Undetectable';
|
277 |
-
$user = '';
|
278 |
-
try {
|
279 |
-
if (function_exists('exec')) {
|
280 |
-
$user = exec('whoami');
|
281 |
-
}
|
282 |
-
|
283 |
-
if (! strlen($user) && function_exists('posix_getpwuid') && function_exists('posix_geteuid')) {
|
284 |
-
$user = posix_getpwuid(posix_geteuid());
|
285 |
-
$user = $user['name'];
|
286 |
-
}
|
287 |
-
|
288 |
-
return strlen($user) ? $user : $unreadable;
|
289 |
-
|
290 |
-
} catch (Exception $ex) {
|
291 |
-
return $unreadable;
|
292 |
-
}
|
293 |
-
}
|
294 |
-
|
295 |
-
/**
|
296 |
-
* Creates the snapshot directory if it doesn't already exisit
|
297 |
-
*/
|
298 |
-
public static function InitSnapshotDirectory() {
|
299 |
-
$path_wproot = DUP_Util::SafePath(DUPLICATOR_WPROOTPATH);
|
300 |
-
$path_ssdir = DUP_Util::SafePath(DUPLICATOR_SSDIR_PATH);
|
301 |
-
$path_plugin = DUP_Util::SafePath(DUPLICATOR_PLUGIN_PATH);
|
302 |
-
|
303 |
-
//--------------------------------
|
304 |
-
//CHMOD DIRECTORY ACCESS
|
305 |
-
//wordpress root directory
|
306 |
-
@chmod($path_wproot, 0755);
|
307 |
-
|
308 |
-
//snapshot directory
|
309 |
-
@mkdir($path_ssdir, 0755);
|
310 |
-
@chmod($path_ssdir, 0755);
|
311 |
-
|
312 |
-
//snapshot tmp directory
|
313 |
-
$path_ssdir_tmp = $path_ssdir . '/tmp';
|
314 |
-
@mkdir($path_ssdir_tmp, 0755);
|
315 |
-
@chmod($path_ssdir_tmp, 0755);
|
316 |
-
|
317 |
-
//plugins dir/files
|
318 |
-
@chmod($path_plugin . 'files', 0755);
|
319 |
-
|
320 |
-
//--------------------------------
|
321 |
-
//FILE CREATION
|
322 |
-
//SSDIR: Create Index File
|
323 |
-
$ssfile = @fopen($path_ssdir . '/index.php', 'w');
|
324 |
-
@fwrite($ssfile, '<?php error_reporting(0); if (stristr(php_sapi_name(), "fcgi")) { $url = "http://" . $_SERVER["HTTP_HOST"]; header("Location: {$url}/404.html");} else { header("HTTP/1.1 404 Not Found", true, 404);} exit(); ?>');
|
325 |
-
@fclose($ssfile);
|
326 |
-
|
327 |
-
//SSDIR: Create token file in snapshot
|
328 |
-
$tokenfile = @fopen($path_ssdir . '/dtoken.php', 'w');
|
329 |
-
@fwrite($tokenfile, '<?php error_reporting(0); if (stristr(php_sapi_name(), "fcgi")) { $url = "http://" . $_SERVER["HTTP_HOST"]; header("Location: {$url}/404.html");} else { header("HTTP/1.1 404 Not Found", true, 404);} exit(); ?>');
|
330 |
-
@fclose($tokenfile);
|
331 |
-
|
332 |
-
//SSDIR: Create .htaccess
|
333 |
-
$storage_htaccess_off = DUP_Settings::Get('storage_htaccess_off');
|
334 |
-
if ($storage_htaccess_off) {
|
335 |
-
@unlink($path_ssdir . '/.htaccess');
|
336 |
-
} else {
|
337 |
-
$htfile = @fopen($path_ssdir . '/.htaccess', 'w');
|
338 |
-
$htoutput = "Options -Indexes" ;
|
339 |
-
@fwrite($htfile, $htoutput);
|
340 |
-
@fclose($htfile);
|
341 |
-
}
|
342 |
-
|
343 |
-
//SSDIR: Robots.txt file
|
344 |
-
$robotfile = @fopen($path_ssdir . '/robots.txt', 'w');
|
345 |
-
@fwrite($robotfile, "User-agent: * \nDisallow: /" . DUPLICATOR_SSDIR_NAME . '/');
|
346 |
-
@fclose($robotfile);
|
347 |
-
|
348 |
-
//PLUG DIR: Create token file in plugin
|
349 |
-
$tokenfile2 = @fopen($path_plugin . 'installer/dtoken.php', 'w');
|
350 |
-
@fwrite($tokenfile2, '<?php @error_reporting(0); @require_once("../../../../wp-admin/admin.php"); global $wp_query; $wp_query->set_404(); header("HTTP/1.1 404 Not Found", true, 404); header("Status: 404 Not Found"); @include(get_template_directory () . "/404.php"); ?>');
|
351 |
-
@fclose($tokenfile2);
|
352 |
-
}
|
353 |
-
|
354 |
-
/**
|
355 |
-
* Attempts to file zip on a users system
|
356 |
-
*/
|
357 |
-
public static function GetZipPath()
|
358 |
-
{
|
359 |
-
$filepath = null;
|
360 |
-
|
361 |
-
if(self::IsShellExecAvailable())
|
362 |
-
{
|
363 |
-
if (shell_exec('hash zip 2>&1') == NULL)
|
364 |
-
{
|
365 |
-
$filepath = 'zip';
|
366 |
-
}
|
367 |
-
else
|
368 |
-
{
|
369 |
-
$possible_paths = array(
|
370 |
-
'/usr/bin/zip',
|
371 |
-
'/opt/local/bin/zip'
|
372 |
-
//'C:/Program\ Files\ (x86)/GnuWin32/bin/zip.exe');
|
373 |
-
);
|
374 |
-
|
375 |
-
foreach ($possible_paths as $path)
|
376 |
-
{
|
377 |
-
if (file_exists($path))
|
378 |
-
{
|
379 |
-
$filepath = $path;
|
380 |
-
break;
|
381 |
-
}
|
382 |
-
}
|
383 |
-
}
|
384 |
-
}
|
385 |
-
|
386 |
-
return $filepath;
|
387 |
-
}
|
388 |
-
|
389 |
-
}
|
390 |
-
|
391 |
-
|
392 |
-
DUP_Util::init();
|
393 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
ctrls/ctrl.base.php
CHANGED
@@ -1,6 +1,6 @@
|
|
1 |
<?php
|
2 |
|
3 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/
|
4 |
|
5 |
//Enum used to define the various test statues
|
6 |
final class DUP_CTRL_Status
|
@@ -78,7 +78,7 @@ class DUP_CTRL_Result
|
|
78 |
|
79 |
function __construct(DUP_CTRL_Base $CTRL_OBJ)
|
80 |
{
|
81 |
-
DUP_Util::
|
82 |
$this->time_start = $this->microtimeFloat();
|
83 |
$this->CTRL = $CTRL_OBJ;
|
84 |
|
1 |
<?php
|
2 |
|
3 |
+
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/utilities/class.util.php');
|
4 |
|
5 |
//Enum used to define the various test statues
|
6 |
final class DUP_CTRL_Status
|
78 |
|
79 |
function __construct(DUP_CTRL_Base $CTRL_OBJ)
|
80 |
{
|
81 |
+
DUP_Util::hasCapability('read');
|
82 |
$this->time_start = $this->microtimeFloat();
|
83 |
$this->CTRL = $CTRL_OBJ;
|
84 |
|
ctrls/ctrl.package.php
CHANGED
@@ -10,20 +10,20 @@
|
|
10 |
function duplicator_package_scan() {
|
11 |
|
12 |
header('Content-Type: application/json;');
|
13 |
-
DUP_Util::
|
14 |
|
15 |
@set_time_limit(0);
|
16 |
$errLevel = error_reporting();
|
17 |
error_reporting(E_ERROR);
|
18 |
-
DUP_Util::
|
19 |
|
20 |
-
$Package = DUP_Package::
|
21 |
-
$report = $Package->
|
22 |
|
23 |
-
$Package->
|
24 |
$json_response = json_encode($report);
|
25 |
|
26 |
-
DUP_Package::
|
27 |
error_reporting($errLevel);
|
28 |
die($json_response);
|
29 |
}
|
@@ -36,7 +36,7 @@ function duplicator_package_scan() {
|
|
36 |
*/
|
37 |
function duplicator_package_build() {
|
38 |
|
39 |
-
DUP_Util::
|
40 |
|
41 |
check_ajax_referer( 'dup_package_build', 'nonce');
|
42 |
|
@@ -45,15 +45,15 @@ function duplicator_package_build() {
|
|
45 |
@set_time_limit(0);
|
46 |
$errLevel = error_reporting();
|
47 |
error_reporting(E_ERROR);
|
48 |
-
DUP_Util::
|
49 |
|
50 |
-
$Package = DUP_Package::
|
51 |
|
52 |
if (!is_readable(DUPLICATOR_SSDIR_PATH_TMP . "/{$Package->ScanFile}")) {
|
53 |
die("The scan result file was not found. Please run the scan step before building the package.");
|
54 |
}
|
55 |
|
56 |
-
$Package->
|
57 |
|
58 |
//JSON:Debug Response
|
59 |
//Pass = 1, Warn = 2, Fail = 3
|
@@ -78,7 +78,7 @@ function duplicator_package_build() {
|
|
78 |
*/
|
79 |
function duplicator_package_delete() {
|
80 |
|
81 |
-
DUP_Util::
|
82 |
check_ajax_referer( 'package_list', 'nonce' );
|
83 |
|
84 |
try {
|
@@ -102,29 +102,28 @@ function duplicator_package_delete() {
|
|
102 |
$delResult = $wpdb->query($wpdb->prepare( "DELETE FROM `{$tblName}` WHERE id = %d", $id ));
|
103 |
if ($delResult != 0) {
|
104 |
//Perms
|
105 |
-
@chmod(DUP_Util::
|
106 |
-
@chmod(DUP_Util::
|
107 |
-
@chmod(DUP_Util::
|
108 |
-
@chmod(DUP_Util::
|
109 |
-
@chmod(DUP_Util::
|
110 |
-
@chmod(DUP_Util::
|
111 |
-
@chmod(DUP_Util::
|
112 |
-
@chmod(DUP_Util::
|
113 |
//Remove
|
114 |
-
@unlink(DUP_Util::
|
115 |
-
@unlink(DUP_Util::
|
116 |
-
@unlink(DUP_Util::
|
117 |
-
@unlink(DUP_Util::
|
118 |
-
@unlink(DUP_Util::
|
119 |
-
@unlink(DUP_Util::
|
120 |
-
@unlink(DUP_Util::
|
121 |
-
@unlink(DUP_Util::
|
122 |
//Unfinished Zip files
|
123 |
$tmpZip = DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_archive.zip.*";
|
124 |
if ($tmpZip !== false) {
|
125 |
array_map('unlink', glob($tmpZip));
|
126 |
}
|
127 |
-
@unlink(DUP_Util::SafePath());
|
128 |
$delCount++;
|
129 |
}
|
130 |
}
|
10 |
function duplicator_package_scan() {
|
11 |
|
12 |
header('Content-Type: application/json;');
|
13 |
+
DUP_Util::hasCapability('export');
|
14 |
|
15 |
@set_time_limit(0);
|
16 |
$errLevel = error_reporting();
|
17 |
error_reporting(E_ERROR);
|
18 |
+
DUP_Util::initSnapshotDirectory();
|
19 |
|
20 |
+
$Package = DUP_Package::getActive();
|
21 |
+
$report = $Package->runScanner();
|
22 |
|
23 |
+
$Package->saveActiveItem('ScanFile', $Package->ScanFile);
|
24 |
$json_response = json_encode($report);
|
25 |
|
26 |
+
DUP_Package::tempFileCleanup();
|
27 |
error_reporting($errLevel);
|
28 |
die($json_response);
|
29 |
}
|
36 |
*/
|
37 |
function duplicator_package_build() {
|
38 |
|
39 |
+
DUP_Util::hasCapability('export');
|
40 |
|
41 |
check_ajax_referer( 'dup_package_build', 'nonce');
|
42 |
|
45 |
@set_time_limit(0);
|
46 |
$errLevel = error_reporting();
|
47 |
error_reporting(E_ERROR);
|
48 |
+
DUP_Util::initSnapshotDirectory();
|
49 |
|
50 |
+
$Package = DUP_Package::getActive();
|
51 |
|
52 |
if (!is_readable(DUPLICATOR_SSDIR_PATH_TMP . "/{$Package->ScanFile}")) {
|
53 |
die("The scan result file was not found. Please run the scan step before building the package.");
|
54 |
}
|
55 |
|
56 |
+
$Package->runBuild();
|
57 |
|
58 |
//JSON:Debug Response
|
59 |
//Pass = 1, Warn = 2, Fail = 3
|
78 |
*/
|
79 |
function duplicator_package_delete() {
|
80 |
|
81 |
+
DUP_Util::hasCapability('export');
|
82 |
check_ajax_referer( 'package_list', 'nonce' );
|
83 |
|
84 |
try {
|
102 |
$delResult = $wpdb->query($wpdb->prepare( "DELETE FROM `{$tblName}` WHERE id = %d", $id ));
|
103 |
if ($delResult != 0) {
|
104 |
//Perms
|
105 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_archive.zip"), 0644);
|
106 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_database.sql"), 0644);
|
107 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_installer.php"), 0644);
|
108 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_archive.zip"), 0644);
|
109 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_database.sql"), 0644);
|
110 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_installer.php"), 0644);
|
111 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_scan.json"), 0644);
|
112 |
+
@chmod(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}.log"), 0644);
|
113 |
//Remove
|
114 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_archive.zip"));
|
115 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_database.sql"));
|
116 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_installer.php"));
|
117 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_archive.zip"));
|
118 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_database.sql"));
|
119 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_installer.php"));
|
120 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}_scan.json"));
|
121 |
+
@unlink(DUP_Util::safePath(DUPLICATOR_SSDIR_PATH . "/{$nameHash}.log"));
|
122 |
//Unfinished Zip files
|
123 |
$tmpZip = DUPLICATOR_SSDIR_PATH_TMP . "/{$nameHash}_archive.zip.*";
|
124 |
if ($tmpZip !== false) {
|
125 |
array_map('unlink', glob($tmpZip));
|
126 |
}
|
|
|
127 |
$delCount++;
|
128 |
}
|
129 |
}
|
ctrls/ctrl.tools.php
CHANGED
@@ -2,7 +2,7 @@
|
|
2 |
if ( ! defined('DUPLICATOR_VERSION') ) exit; // Exit if accessed directly
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/ctrls/ctrl.base.php');
|
5 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/scan.
|
6 |
|
7 |
/**
|
8 |
* Controller for Tools
|
@@ -10,7 +10,9 @@ require_once(DUPLICATOR_PLUGIN_PATH . '/classes/scan.validator.php');
|
|
10 |
*/
|
11 |
class DUP_CTRL_Tools extends DUP_CTRL_Base
|
12 |
{
|
13 |
-
|
|
|
|
|
14 |
function __construct()
|
15 |
{
|
16 |
add_action('wp_ajax_DUP_CTRL_Tools_RunScanValidator', array($this, 'RunScanValidator'));
|
@@ -26,6 +28,7 @@ class DUP_CTRL_Tools extends DUP_CTRL_Base
|
|
26 |
*/
|
27 |
public function RunScanValidator($post)
|
28 |
{
|
|
|
29 |
$post = $this->PostParamMerge($post);
|
30 |
check_ajax_referer($post['action'], 'nonce');
|
31 |
|
@@ -38,12 +41,12 @@ class DUP_CTRL_Tools extends DUP_CTRL_Base
|
|
38 |
if (!is_dir($path)) {
|
39 |
throw new Exception("Invalid directory provided '{$path}'!");
|
40 |
}
|
41 |
-
$scanner = new
|
42 |
-
$scanner->
|
43 |
-
$payload = $scanner->
|
44 |
|
45 |
//RETURN RESULT
|
46 |
-
$test = ($payload->
|
47 |
? DUP_CTRL_Status::SUCCESS
|
48 |
: DUP_CTRL_Status::FAILED;
|
49 |
$result->Process($payload, $test);
|
2 |
if ( ! defined('DUPLICATOR_VERSION') ) exit; // Exit if accessed directly
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/ctrls/ctrl.base.php');
|
5 |
+
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/utilities/class.scan.check.php');
|
6 |
|
7 |
/**
|
8 |
* Controller for Tools
|
10 |
*/
|
11 |
class DUP_CTRL_Tools extends DUP_CTRL_Base
|
12 |
{
|
13 |
+
/**
|
14 |
+
* Init this instance of the object
|
15 |
+
*/
|
16 |
function __construct()
|
17 |
{
|
18 |
add_action('wp_ajax_DUP_CTRL_Tools_RunScanValidator', array($this, 'RunScanValidator'));
|
28 |
*/
|
29 |
public function RunScanValidator($post)
|
30 |
{
|
31 |
+
@set_time_limit(0);
|
32 |
$post = $this->PostParamMerge($post);
|
33 |
check_ajax_referer($post['action'], 'nonce');
|
34 |
|
41 |
if (!is_dir($path)) {
|
42 |
throw new Exception("Invalid directory provided '{$path}'!");
|
43 |
}
|
44 |
+
$scanner = new DUP_ScanCheck();
|
45 |
+
$scanner->recursion = (isset($post['scan-recursive']) && $post['scan-recursive'] != 'false') ? true : false;
|
46 |
+
$payload = $scanner->run($path);
|
47 |
|
48 |
//RETURN RESULT
|
49 |
+
$test = ($payload->fileCount > 0)
|
50 |
? DUP_CTRL_Status::SUCCESS
|
51 |
: DUP_CTRL_Status::FAILED;
|
52 |
$result->Process($payload, $test);
|
ctrls/ctrl.ui.php
CHANGED
@@ -2,7 +2,7 @@
|
|
2 |
if ( ! defined('DUPLICATOR_VERSION') ) exit; // Exit if accessed directly
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/ctrls/ctrl.base.php');
|
5 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/ui/ui.php');
|
6 |
|
7 |
/**
|
8 |
* Controller for Tools
|
@@ -32,7 +32,7 @@ class DUP_CTRL_UI extends DUP_CTRL_Base
|
|
32 |
* Duplicator.UI.SaveViewState('dup-pack-archive-panel', 1);
|
33 |
*
|
34 |
* //Call PHP Code
|
35 |
-
* $view_state =
|
36 |
* $ui_css_archive = ($view_state == 1) ? 'display:block' : 'display:none';
|
37 |
* </code>
|
38 |
*/
|
@@ -47,7 +47,7 @@ class DUP_CTRL_UI extends DUP_CTRL_Base
|
|
47 |
$post = stripslashes_deep($_POST);
|
48 |
$key = esc_html($post['key']);
|
49 |
$value = esc_html($post['value']);
|
50 |
-
$success =
|
51 |
|
52 |
$payload = array();
|
53 |
$payload['key'] = $key;
|
@@ -83,7 +83,7 @@ class DUP_CTRL_UI extends DUP_CTRL_Base
|
|
83 |
try
|
84 |
{
|
85 |
//CONTROLLER LOGIC
|
86 |
-
$payload =
|
87 |
|
88 |
//RETURN RESULT
|
89 |
$test = (count($payload))
|
2 |
if ( ! defined('DUPLICATOR_VERSION') ) exit; // Exit if accessed directly
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/ctrls/ctrl.base.php');
|
5 |
+
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/ui/class.ui.viewstate.php');
|
6 |
|
7 |
/**
|
8 |
* Controller for Tools
|
32 |
* Duplicator.UI.SaveViewState('dup-pack-archive-panel', 1);
|
33 |
*
|
34 |
* //Call PHP Code
|
35 |
+
* $view_state = DUP_UI_ViewState::getValue('dup-pack-archive-panel');
|
36 |
* $ui_css_archive = ($view_state == 1) ? 'display:block' : 'display:none';
|
37 |
* </code>
|
38 |
*/
|
47 |
$post = stripslashes_deep($_POST);
|
48 |
$key = esc_html($post['key']);
|
49 |
$value = esc_html($post['value']);
|
50 |
+
$success = DUP_UI_ViewState::save($key, $value);
|
51 |
|
52 |
$payload = array();
|
53 |
$payload['key'] = $key;
|
83 |
try
|
84 |
{
|
85 |
//CONTROLLER LOGIC
|
86 |
+
$payload = DUP_UI_ViewState::getArray();
|
87 |
|
88 |
//RETURN RESULT
|
89 |
$test = (count($payload))
|
debug/main.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<?php
|
2 |
-
DUP_Util::
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
1 |
<?php
|
2 |
+
DUP_Util::hasCapability('read');
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
define.php
CHANGED
@@ -2,7 +2,7 @@
|
|
2 |
//Prevent directly browsing to the file
|
3 |
if (function_exists('plugin_dir_url'))
|
4 |
{
|
5 |
-
define('DUPLICATOR_VERSION', '1.1.
|
6 |
define('DUPLICATOR_HOMEPAGE', 'http://lifeinthegrid.com/labs/duplicator');
|
7 |
define('DUPLICATOR_PLUGIN_URL', plugin_dir_url(__FILE__));
|
8 |
define('DUPLICATOR_SITE_URL', get_site_url());
|
2 |
//Prevent directly browsing to the file
|
3 |
if (function_exists('plugin_dir_url'))
|
4 |
{
|
5 |
+
define('DUPLICATOR_VERSION', '1.1.34');
|
6 |
define('DUPLICATOR_HOMEPAGE', 'http://lifeinthegrid.com/labs/duplicator');
|
7 |
define('DUPLICATOR_PLUGIN_URL', plugin_dir_url(__FILE__));
|
8 |
define('DUPLICATOR_SITE_URL', get_site_url());
|
duplicator.php
CHANGED
@@ -1,9 +1,9 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
Plugin Name: Duplicator
|
4 |
Plugin URI: http://www.lifeinthegrid.com/duplicator/
|
5 |
Description: Create and transfer a copy of your WordPress files and database. Duplicate and move a site from one location to another quickly.
|
6 |
-
Version: 1.1.
|
7 |
Author: Snap Creek
|
8 |
Author URI: http://www.snapcreek.com/duplicator/
|
9 |
Text Domain: duplicator
|
@@ -30,25 +30,27 @@ require_once("define.php");
|
|
30 |
if (is_admin() == true)
|
31 |
{
|
32 |
//Classes
|
33 |
-
require_once 'classes/logging.php';
|
34 |
-
require_once 'classes/
|
35 |
-
require_once 'classes/
|
36 |
-
require_once 'classes/
|
37 |
-
require_once 'classes/
|
38 |
-
require_once 'classes/ui/ui.php';
|
|
|
|
|
39 |
|
40 |
//Controllers
|
41 |
require_once 'ctrls/ctrl.package.php';
|
42 |
require_once 'ctrls/ctrl.tools.php';
|
43 |
require_once 'ctrls/ctrl.ui.php';
|
44 |
|
45 |
-
|
46 |
-
* ACTIVATE/DEACTIVE/UPDATE HOOKS
|
|
|
47 |
register_activation_hook(__FILE__, 'duplicator_activate');
|
48 |
register_deactivation_hook(__FILE__, 'duplicator_deactivate');
|
49 |
|
50 |
/**
|
51 |
-
* Activation Hook:
|
52 |
* Hooked into `register_activation_hook`. Routines used to activate the plugin
|
53 |
*
|
54 |
* @access global
|
@@ -84,12 +86,10 @@ if (is_admin() == true)
|
|
84 |
update_option('duplicator_version_plugin', DUPLICATOR_VERSION);
|
85 |
|
86 |
//Setup All Directories
|
87 |
-
DUP_Util::
|
88 |
}
|
89 |
|
90 |
-
|
91 |
/**
|
92 |
-
* Activation Hook:
|
93 |
* Hooked into `plugins_loaded`. Routines used to update the plugin
|
94 |
*
|
95 |
* @access global
|
@@ -103,9 +103,7 @@ if (is_admin() == true)
|
|
103 |
load_plugin_textdomain( 'duplicator' );
|
104 |
}
|
105 |
|
106 |
-
|
107 |
/**
|
108 |
-
* Deactivation Hook:
|
109 |
* Hooked into `register_deactivation_hook`. Routines used to deactivae the plugin
|
110 |
* For uninstall see uninstall.php Wordpress by default will call the uninstall.php file
|
111 |
*
|
@@ -117,14 +115,14 @@ if (is_admin() == true)
|
|
117 |
//Logic has been added to uninstall.php
|
118 |
}
|
119 |
|
120 |
-
|
121 |
-
|
122 |
-
|
123 |
add_action('plugins_loaded', 'duplicator_update');
|
124 |
add_action('plugins_loaded', 'duplicator_wpfront_integrate');
|
125 |
add_action('admin_init', 'duplicator_init');
|
126 |
add_action('admin_menu', 'duplicator_menu');
|
127 |
-
add_action('admin_notices', array('
|
128 |
|
129 |
//CTRL ACTIONS
|
130 |
add_action('wp_ajax_duplicator_package_scan', 'duplicator_package_scan');
|
@@ -133,9 +131,7 @@ if (is_admin() == true)
|
|
133 |
$GLOBALS['CTRLS_DUP_CTRL_UI'] = new DUP_CTRL_UI();
|
134 |
$GLOBALS['CTRLS_DUP_CTRL_Tools'] = new DUP_CTRL_Tools();
|
135 |
|
136 |
-
|
137 |
/**
|
138 |
-
* Action Hook:
|
139 |
* User role editor integration
|
140 |
*
|
141 |
* @access global
|
@@ -148,9 +144,7 @@ if (is_admin() == true)
|
|
148 |
}
|
149 |
}
|
150 |
|
151 |
-
|
152 |
/**
|
153 |
-
* Action Hook:
|
154 |
* Hooked into `admin_init`. Init routines for all admin pages
|
155 |
*
|
156 |
* @access global
|
@@ -169,9 +163,7 @@ if (is_admin() == true)
|
|
169 |
wp_register_script('dup-jquery-qtip', DUPLICATOR_PLUGIN_URL . 'assets/js/jquery.qtip/jquery.qtip.min.js', array('jquery'), '2.2.1');
|
170 |
}
|
171 |
|
172 |
-
|
173 |
/**
|
174 |
-
* Menu Redirect:
|
175 |
* Redirects the clicked menu item to the correct location
|
176 |
*
|
177 |
* @access global
|
@@ -192,9 +184,7 @@ if (is_admin() == true)
|
|
192 |
}
|
193 |
}
|
194 |
|
195 |
-
|
196 |
/**
|
197 |
-
* Action Hook:
|
198 |
* Hooked into `admin_menu`. Loads all of the wp left nav admin menus for Duplicator
|
199 |
*
|
200 |
* @access global
|
@@ -271,9 +261,7 @@ if (is_admin() == true)
|
|
271 |
|
272 |
}
|
273 |
|
274 |
-
|
275 |
/**
|
276 |
-
* Enqueue Scripts:
|
277 |
* Loads all required javascript libs/source for DupPro
|
278 |
*
|
279 |
* @access global
|
@@ -289,9 +277,7 @@ if (is_admin() == true)
|
|
289 |
|
290 |
}
|
291 |
|
292 |
-
|
293 |
/**
|
294 |
-
* Enqueue CSS Styles:
|
295 |
* Loads all CSS style libs/source for DupPro
|
296 |
*
|
297 |
* @access global
|
@@ -306,13 +292,13 @@ if (is_admin() == true)
|
|
306 |
}
|
307 |
|
308 |
|
309 |
-
|
310 |
-
* FILTERS
|
|
|
311 |
add_filter('plugin_action_links', 'duplicator_manage_link', 10, 2);
|
312 |
add_filter('plugin_row_meta', 'duplicator_meta_links', 10, 2);
|
313 |
|
314 |
/**
|
315 |
-
* Plugin MetaData:
|
316 |
* Adds the manage link in the plugins list
|
317 |
*
|
318 |
* @access global
|
@@ -331,9 +317,7 @@ if (is_admin() == true)
|
|
331 |
return $links;
|
332 |
}
|
333 |
|
334 |
-
|
335 |
/**
|
336 |
-
* Plugin MetaData:
|
337 |
* Adds links to the plugins manager page
|
338 |
*
|
339 |
* @access global
|
1 |
<?php
|
2 |
+
/** ===============================================================================
|
3 |
Plugin Name: Duplicator
|
4 |
Plugin URI: http://www.lifeinthegrid.com/duplicator/
|
5 |
Description: Create and transfer a copy of your WordPress files and database. Duplicate and move a site from one location to another quickly.
|
6 |
+
Version: 1.1.34
|
7 |
Author: Snap Creek
|
8 |
Author URI: http://www.snapcreek.com/duplicator/
|
9 |
Text Domain: duplicator
|
30 |
if (is_admin() == true)
|
31 |
{
|
32 |
//Classes
|
33 |
+
require_once 'classes/class.logging.php';
|
34 |
+
require_once 'classes/class.settings.php';
|
35 |
+
require_once 'classes/utilities/class.util.php';
|
36 |
+
require_once 'classes/utilities/class.db.php';
|
37 |
+
require_once 'classes/utilities/class.server.php';
|
38 |
+
require_once 'classes/ui/class.ui.viewstate.php';
|
39 |
+
require_once 'classes/ui/class.ui.notice.php';
|
40 |
+
require_once 'classes/package/class.pack.php';
|
41 |
|
42 |
//Controllers
|
43 |
require_once 'ctrls/ctrl.package.php';
|
44 |
require_once 'ctrls/ctrl.tools.php';
|
45 |
require_once 'ctrls/ctrl.ui.php';
|
46 |
|
47 |
+
/** ========================================================
|
48 |
+
* ACTIVATE/DEACTIVE/UPDATE HOOKS
|
49 |
+
* ===================================================== */
|
50 |
register_activation_hook(__FILE__, 'duplicator_activate');
|
51 |
register_deactivation_hook(__FILE__, 'duplicator_deactivate');
|
52 |
|
53 |
/**
|
|
|
54 |
* Hooked into `register_activation_hook`. Routines used to activate the plugin
|
55 |
*
|
56 |
* @access global
|
86 |
update_option('duplicator_version_plugin', DUPLICATOR_VERSION);
|
87 |
|
88 |
//Setup All Directories
|
89 |
+
DUP_Util::initSnapshotDirectory();
|
90 |
}
|
91 |
|
|
|
92 |
/**
|
|
|
93 |
* Hooked into `plugins_loaded`. Routines used to update the plugin
|
94 |
*
|
95 |
* @access global
|
103 |
load_plugin_textdomain( 'duplicator' );
|
104 |
}
|
105 |
|
|
|
106 |
/**
|
|
|
107 |
* Hooked into `register_deactivation_hook`. Routines used to deactivae the plugin
|
108 |
* For uninstall see uninstall.php Wordpress by default will call the uninstall.php file
|
109 |
*
|
115 |
//Logic has been added to uninstall.php
|
116 |
}
|
117 |
|
118 |
+
/** ========================================================
|
119 |
+
* ACTION HOOKS
|
120 |
+
* ===================================================== */
|
121 |
add_action('plugins_loaded', 'duplicator_update');
|
122 |
add_action('plugins_loaded', 'duplicator_wpfront_integrate');
|
123 |
add_action('admin_init', 'duplicator_init');
|
124 |
add_action('admin_menu', 'duplicator_menu');
|
125 |
+
add_action('admin_notices', array('DUP_UI_Notice', 'showReservedFilesNotice'));
|
126 |
|
127 |
//CTRL ACTIONS
|
128 |
add_action('wp_ajax_duplicator_package_scan', 'duplicator_package_scan');
|
131 |
$GLOBALS['CTRLS_DUP_CTRL_UI'] = new DUP_CTRL_UI();
|
132 |
$GLOBALS['CTRLS_DUP_CTRL_Tools'] = new DUP_CTRL_Tools();
|
133 |
|
|
|
134 |
/**
|
|
|
135 |
* User role editor integration
|
136 |
*
|
137 |
* @access global
|
144 |
}
|
145 |
}
|
146 |
|
|
|
147 |
/**
|
|
|
148 |
* Hooked into `admin_init`. Init routines for all admin pages
|
149 |
*
|
150 |
* @access global
|
163 |
wp_register_script('dup-jquery-qtip', DUPLICATOR_PLUGIN_URL . 'assets/js/jquery.qtip/jquery.qtip.min.js', array('jquery'), '2.2.1');
|
164 |
}
|
165 |
|
|
|
166 |
/**
|
|
|
167 |
* Redirects the clicked menu item to the correct location
|
168 |
*
|
169 |
* @access global
|
184 |
}
|
185 |
}
|
186 |
|
|
|
187 |
/**
|
|
|
188 |
* Hooked into `admin_menu`. Loads all of the wp left nav admin menus for Duplicator
|
189 |
*
|
190 |
* @access global
|
261 |
|
262 |
}
|
263 |
|
|
|
264 |
/**
|
|
|
265 |
* Loads all required javascript libs/source for DupPro
|
266 |
*
|
267 |
* @access global
|
277 |
|
278 |
}
|
279 |
|
|
|
280 |
/**
|
|
|
281 |
* Loads all CSS style libs/source for DupPro
|
282 |
*
|
283 |
* @access global
|
292 |
}
|
293 |
|
294 |
|
295 |
+
/** ========================================================
|
296 |
+
* FILTERS
|
297 |
+
* ===================================================== */
|
298 |
add_filter('plugin_action_links', 'duplicator_manage_link', 10, 2);
|
299 |
add_filter('plugin_row_meta', 'duplicator_meta_links', 10, 2);
|
300 |
|
301 |
/**
|
|
|
302 |
* Adds the manage link in the plugins list
|
303 |
*
|
304 |
* @access global
|
317 |
return $links;
|
318 |
}
|
319 |
|
|
|
320 |
/**
|
|
|
321 |
* Adds links to the plugins manager page
|
322 |
*
|
323 |
* @access global
|
installer/build/ajax.step1.php
CHANGED
@@ -44,7 +44,7 @@ if (isset($_GET['dbtest']))
|
|
44 |
{
|
45 |
$html = "";
|
46 |
$baseport = parse_url($_POST['dbhost'], PHP_URL_PORT);
|
47 |
-
$dbConn =
|
48 |
$dbErr = mysqli_connect_error();
|
49 |
|
50 |
$dbFound = mysqli_select_db($dbConn, $_POST['dbname']);
|
@@ -52,14 +52,23 @@ if (isset($_GET['dbtest']))
|
|
52 |
|
53 |
$tstSrv = ($dbConn) ? "<div class='dup-pass'>Success</div>" : "<div class='dup-fail'>Fail</div>";
|
54 |
$tstDB = ($dbFound) ? "<div class='dup-pass'>Success</div>" : "<div class='dup-fail'>Fail</div>";
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
63 |
$html .= <<<DATA
|
64 |
<div class='dup-db-test'>
|
65 |
<small>
|
@@ -77,8 +86,12 @@ if (isset($_GET['dbtest']))
|
|
77 |
</tr>
|
78 |
<tr>
|
79 |
<td>Version:</td>
|
|
|
|
|
|
|
|
|
80 |
<td>{$tstCompat}</td>
|
81 |
-
</tr>
|
82 |
</table>
|
83 |
DATA;
|
84 |
|
@@ -86,7 +99,7 @@ DATA;
|
|
86 |
//WARNING: DB has tables with create option
|
87 |
if ($_POST['dbaction'] == 'create')
|
88 |
{
|
89 |
-
$tblcount =
|
90 |
$html .= ($tblcount > 0)
|
91 |
? "<div class='warn-msg'><b>WARNING:</b> " . sprintf(ERR_DBEMPTY, $_POST['dbname'], $tblcount) . "</div>"
|
92 |
: '';
|
@@ -102,13 +115,20 @@ DATA;
|
|
102 |
break;
|
103 |
}
|
104 |
}
|
|
|
|
|
105 |
$html .= (! $dbConn && $dbUTF8_tst)
|
106 |
? "<div class='warn-msg'><b>WARNING:</b> " . ERR_TESTDB_UTF8 . "</div>"
|
107 |
: '';
|
108 |
|
109 |
-
//
|
110 |
-
$html .= ($
|
111 |
-
? "<div class='warn-msg'><b>NOTICE:</b> " .
|
|
|
|
|
|
|
|
|
|
|
112 |
: '';
|
113 |
|
114 |
$html .= "</div>";
|
@@ -119,60 +139,60 @@ DATA;
|
|
119 |
//ERROR MESSAGES
|
120 |
//===============================
|
121 |
//ERR_MAKELOG
|
122 |
-
($GLOBALS['LOG_FILE_HANDLE'] != false) or DUPX_Log::
|
123 |
|
124 |
//ERR_MYSQLI_SUPPORT
|
125 |
-
function_exists('mysqli_connect') or DUPX_Log::
|
126 |
|
127 |
//ERR_DBCONNECT
|
128 |
-
$dbh =
|
129 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
130 |
-
($dbh) or DUPX_Log::
|
131 |
if ($_POST['dbaction'] == 'empty') {
|
132 |
-
mysqli_select_db($dbh, $_POST['dbname']) or DUPX_Log::
|
133 |
}
|
134 |
//ERR_DBEMPTY
|
135 |
if ($_POST['dbaction'] == 'create' ) {
|
136 |
-
$tblcount =
|
137 |
if ($tblcount > 0) {
|
138 |
-
DUPX_Log::
|
139 |
}
|
140 |
}
|
141 |
|
142 |
//ERR_ZIPMANUAL
|
143 |
if ($_POST['zip_manual']) {
|
144 |
if (!file_exists("wp-config.php") && !file_exists("database.sql")) {
|
145 |
-
DUPX_Log::
|
146 |
}
|
147 |
} else {
|
148 |
//ERR_CONFIG_FOUND
|
149 |
(!file_exists('wp-config.php'))
|
150 |
-
or DUPX_Log::
|
151 |
//ERR_ZIPNOTFOUND
|
152 |
(is_readable("{$package_path}"))
|
153 |
-
or DUPX_Log::
|
154 |
}
|
155 |
|
156 |
-
DUPX_Log::
|
157 |
-
DUPX_Log::
|
158 |
-
DUPX_Log::
|
159 |
-
DUPX_Log::
|
160 |
-
DUPX_Log::
|
161 |
-
DUPX_Log::
|
162 |
-
DUPX_Log::
|
163 |
-
DUPX_Log::
|
164 |
-
DUPX_Log::
|
165 |
-
DUPX_Log::
|
166 |
-
DUPX_Log::
|
167 |
-
DUPX_Log::
|
168 |
-
DUPX_Log::
|
169 |
-
DUPX_Log::
|
170 |
|
171 |
$log = "--------------------------------------\n";
|
172 |
$log .= "POST DATA\n";
|
173 |
$log .= "--------------------------------------\n";
|
174 |
$log .= print_r($POST_LOG, true);
|
175 |
-
DUPX_Log::
|
176 |
|
177 |
|
178 |
//====================================================================================================
|
@@ -184,13 +204,13 @@ $log .= "***********************************************************************
|
|
184 |
$log .= "NAME:\t{$_POST['package_name']}\n";
|
185 |
$log .= "SIZE:\t" . DUPX_Util::readable_bytesize(@filesize($_POST['package_name'])) . "\n";
|
186 |
$log .= "ZIP:\t{$zip_support} (ZipArchive Support)";
|
187 |
-
DUPX_Log::
|
188 |
|
189 |
$zip_start = DUPX_Util::get_microtime();
|
190 |
|
191 |
if ($_POST['zip_manual'])
|
192 |
{
|
193 |
-
DUPX_Log::
|
194 |
}
|
195 |
else
|
196 |
{
|
@@ -200,21 +220,21 @@ else
|
|
200 |
$log .= "To guarantee accuracy the installer and archive should match. For details see the online FAQs.";
|
201 |
$log .= "\nCREATED WITH:\t{$GLOBALS['FW_PACKAGE_NAME']} \nPROCESSED WITH:\t{$_POST['package_name']} \n";
|
202 |
$log .= "--------------------------------------\n";
|
203 |
-
DUPX_Log::
|
204 |
}
|
205 |
|
206 |
if (! class_exists('ZipArchive')) {
|
207 |
-
DUPX_Log::
|
208 |
-
DUPX_Log::
|
209 |
}
|
210 |
|
211 |
$target = $root_path;
|
212 |
$zip = new ZipArchive();
|
213 |
if ($zip->open($_POST['package_name']) === TRUE)
|
214 |
{
|
215 |
-
DUPX_Log::
|
216 |
if (! $zip->extractTo($target)) {
|
217 |
-
DUPX_Log::
|
218 |
}
|
219 |
$log = print_r($zip, true);
|
220 |
|
@@ -234,9 +254,9 @@ else
|
|
234 |
|
235 |
$close_response = $zip->close();
|
236 |
$log .= "COMPLETE: " . var_export($close_response, true);
|
237 |
-
DUPX_Log::
|
238 |
} else {
|
239 |
-
DUPX_Log::
|
240 |
}
|
241 |
$zip = null;
|
242 |
}
|
@@ -245,7 +265,7 @@ else
|
|
245 |
//CONFIG FILE RESETS
|
246 |
$log = '';
|
247 |
DUPX_WPConfig::UpdateStep1();
|
248 |
-
DUPX_ServerConfig::
|
249 |
|
250 |
|
251 |
//====================================================================================================
|
@@ -267,7 +287,7 @@ if ($db_file_size >= $php_mem_range && $php_mem_range != 0)
|
|
267 |
$msg .= "a memory allocation error when trying to load the database.sql file. It is\n";
|
268 |
$msg .= "recommended to increase the 'memory_limit' setting in the php.ini config file.\n";
|
269 |
$msg .= "see: {$faq_url}#faq-trouble-056-q \n";
|
270 |
-
DUPX_Log::
|
271 |
}
|
272 |
|
273 |
@chmod("{$root_path}/database.sql", 0777);
|
@@ -282,14 +302,14 @@ if ($sql_file === FALSE || strlen($sql_file) < 10)
|
|
282 |
$msg .= "<i>see: <a href='{$faq_url}#faq-trouble-055-q' target='_blank'>{$faq_url}#faq-trouble-055-q</a></i> <br/>";
|
283 |
$msg .= "2. Validate the database.sql file exists and is in the root of the archive.zip file <br/>";
|
284 |
$msg .= "<i>see: <a href='{$faq_url}#faq-installer-020-q' target='_blank'>{$faq_url}#faq-installer-020-q</a></i> <br/>";
|
285 |
-
DUPX_Log::
|
286 |
}
|
287 |
|
288 |
//Removes invalid space characters
|
289 |
//Complex Subject See: http://webcollab.sourceforge.net/unicode.html
|
290 |
if ($_POST['dbnbsp'])
|
291 |
{
|
292 |
-
DUPX_Log::
|
293 |
$sql_file = preg_replace('/\xC2\xA0/', ' ', $sql_file);
|
294 |
}
|
295 |
|
@@ -307,20 +327,20 @@ if ($sql_file_copy_status === FALSE || filesize($sql_result_file_path) == 0 || !
|
|
307 |
$msg = "\nWARNING: Unable to properly copy database.sql ({$sql_file_size}) to {$GLOBALS['SQL_FILE_NAME']}. Please check these items:\n";
|
308 |
$msg .= "- Validate permissions and/or group-owner rights on database.sql and directory [{$root_path}] \n";
|
309 |
$msg .= "- see: {$faq_url}#faq-trouble-055-q \n";
|
310 |
-
DUPX_Log::
|
311 |
}
|
312 |
|
313 |
-
DUPX_Log::
|
314 |
-
DUPX_Log::
|
315 |
-
DUPX_Log::
|
316 |
-
DUPX_Log::
|
317 |
DUPX_Util::fcgi_flush();
|
318 |
|
319 |
//=================================
|
320 |
//START DB RUN
|
321 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
322 |
@mysqli_query($dbh, "SET max_allowed_packet = {$GLOBALS['DB_MAX_PACKETS']}");
|
323 |
-
|
324 |
|
325 |
//Will set mode to null only for this db handle session
|
326 |
//sql_mode can cause db create issues on some systems
|
@@ -342,32 +362,32 @@ switch ($_POST['dbmysqlmode']) {
|
|
342 |
}
|
343 |
|
344 |
//Set defaults in-case the variable could not be read
|
345 |
-
$dbvar_maxtime =
|
346 |
-
$dbvar_maxpacks =
|
347 |
-
$dbvar_sqlmode =
|
348 |
$dbvar_maxtime = is_null($dbvar_maxtime) ? 300 : $dbvar_maxtime;
|
349 |
$dbvar_maxpacks = is_null($dbvar_maxpacks) ? 1048576 : $dbvar_maxpacks;
|
350 |
$dbvar_sqlmode = empty($dbvar_sqlmode) ? 'NOT_SET' : $dbvar_sqlmode;
|
351 |
-
$dbvar_version =
|
352 |
$sql_file_size1 = DUPX_Util::readable_bytesize(@filesize("database.sql"));
|
353 |
$sql_file_size2 = DUPX_Util::readable_bytesize(@filesize("{$GLOBALS['SQL_FILE_NAME']}"));
|
354 |
|
355 |
|
356 |
-
DUPX_Log::
|
357 |
-
DUPX_Log::
|
358 |
-
DUPX_Log::
|
359 |
-
DUPX_Log::
|
360 |
-
DUPX_Log::
|
361 |
-
DUPX_Log::
|
362 |
-
DUPX_Log::
|
363 |
-
DUPX_Log::
|
364 |
-
DUPX_Log::
|
365 |
-
DUPX_Log::
|
366 |
-
DUPX_Log::
|
367 |
|
368 |
if ($qry_session_custom == false)
|
369 |
{
|
370 |
-
DUPX_Log::
|
371 |
}
|
372 |
|
373 |
//CREATE DB
|
@@ -375,7 +395,7 @@ switch ($_POST['dbaction']) {
|
|
375 |
case "create":
|
376 |
mysqli_query($dbh, "CREATE DATABASE IF NOT EXISTS `{$_POST['dbname']}`");
|
377 |
mysqli_select_db($dbh, $_POST['dbname'])
|
378 |
-
or DUPX_Log::
|
379 |
break;
|
380 |
case "empty":
|
381 |
//DROP DB TABLES
|
@@ -390,7 +410,7 @@ switch ($_POST['dbaction']) {
|
|
390 |
foreach ($found_tables as $table_name) {
|
391 |
$sql = "DROP TABLE `{$_POST['dbname']}`.`{$table_name}`";
|
392 |
if (!$result = mysqli_query($dbh, $sql)) {
|
393 |
-
DUPX_Log::
|
394 |
}
|
395 |
}
|
396 |
}
|
@@ -401,9 +421,9 @@ switch ($_POST['dbaction']) {
|
|
401 |
|
402 |
|
403 |
//WRITE DATA
|
404 |
-
DUPX_Log::
|
405 |
-
DUPX_Log::
|
406 |
-
DUPX_Log::
|
407 |
$profile_start = DUPX_Util::get_microtime();
|
408 |
$fcgi_buffer_pool = 5000;
|
409 |
$fcgi_buffer_count = 0;
|
@@ -416,7 +436,7 @@ while ($counter < $sql_result_file_length) {
|
|
416 |
|
417 |
$query_strlen = strlen(trim($sql_result_file_data[$counter]));
|
418 |
if ($dbvar_maxpacks < $query_strlen) {
|
419 |
-
DUPX_Log::
|
420 |
$dbquery_errs++;
|
421 |
} elseif ($query_strlen > 0) {
|
422 |
@mysqli_free_result(@mysqli_query($dbh, ($sql_result_file_data[$counter])));
|
@@ -426,12 +446,12 @@ while ($counter < $sql_result_file_length) {
|
|
426 |
|
427 |
if (!mysqli_ping($dbh)) {
|
428 |
mysqli_close($dbh);
|
429 |
-
$dbh =
|
430 |
// Reset session setup
|
431 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
432 |
-
|
433 |
}
|
434 |
-
DUPX_Log::
|
435 |
$dbquery_errs++;
|
436 |
|
437 |
//Buffer data to browser to keep connection open
|
@@ -448,23 +468,23 @@ while ($counter < $sql_result_file_length) {
|
|
448 |
@mysqli_commit($dbh);
|
449 |
@mysqli_autocommit($dbh, true);
|
450 |
|
451 |
-
DUPX_Log::
|
452 |
-
DUPX_Log::
|
453 |
-
DUPX_Log::
|
454 |
|
455 |
$dbtable_count = 0;
|
456 |
if ($result = mysqli_query($dbh, "SHOW TABLES")) {
|
457 |
while ($row = mysqli_fetch_array($result, MYSQLI_NUM)) {
|
458 |
-
$table_rows =
|
459 |
$dbtable_rows += $table_rows;
|
460 |
-
DUPX_Log::
|
461 |
$dbtable_count++;
|
462 |
}
|
463 |
@mysqli_free_result($result);
|
464 |
}
|
465 |
|
466 |
if ($dbtable_count == 0) {
|
467 |
-
DUPX_Log::
|
468 |
ERROR messages. You may have to manually run the installer-data.sql with a tool like phpmyadmin to validate the data input. If you have enabled compatibility mode
|
469 |
during the package creation process then the database server version your using may not be compatible with this script.\n");
|
470 |
}
|
@@ -478,7 +498,7 @@ $dbdelete_count1 = @mysqli_affected_rows($dbh) or 0;
|
|
478 |
@mysqli_query($dbh, "DELETE FROM `{$GLOBALS['FW_TABLEPREFIX']}options` WHERE `option_name` LIKE ('_transient%') OR `option_name` LIKE ('_site_transient%')");
|
479 |
$dbdelete_count2 = @mysqli_affected_rows($dbh) or 0;
|
480 |
$dbdelete_count = (abs($dbdelete_count1) + abs($dbdelete_count2));
|
481 |
-
DUPX_Log::
|
482 |
//Reset Duplicator Options
|
483 |
foreach ($GLOBALS['FW_OPTS_DELETE'] as $value) {
|
484 |
mysqli_query($dbh, "DELETE FROM `{$GLOBALS['FW_TABLEPREFIX']}options` WHERE `option_name` = '{$value}'");
|
@@ -487,14 +507,14 @@ foreach ($GLOBALS['FW_OPTS_DELETE'] as $value) {
|
|
487 |
@mysqli_close($dbh);
|
488 |
|
489 |
$profile_end = DUPX_Util::get_microtime();
|
490 |
-
DUPX_Log::
|
491 |
|
492 |
//FINAL RESULTS
|
493 |
$ajax1_end = DUPX_Util::get_microtime();
|
494 |
$ajax1_sum = DUPX_Util::elapsed_time($ajax1_end, $ajax1_start);
|
495 |
-
DUPX_Log::
|
496 |
-
DUPX_Log::
|
497 |
-
DUPX_Log::
|
498 |
|
499 |
$JSON['pass'] = 1;
|
500 |
$JSON['table_count'] = $dbtable_count;
|
44 |
{
|
45 |
$html = "";
|
46 |
$baseport = parse_url($_POST['dbhost'], PHP_URL_PORT);
|
47 |
+
$dbConn = DUPX_DB::connect($_POST['dbhost'], $_POST['dbuser'], $_POST['dbpass'], null, $_POST['dbport']);
|
48 |
$dbErr = mysqli_connect_error();
|
49 |
|
50 |
$dbFound = mysqli_select_db($dbConn, $_POST['dbname']);
|
52 |
|
53 |
$tstSrv = ($dbConn) ? "<div class='dup-pass'>Success</div>" : "<div class='dup-fail'>Fail</div>";
|
54 |
$tstDB = ($dbFound) ? "<div class='dup-pass'>Success</div>" : "<div class='dup-fail'>Fail</div>";
|
55 |
+
|
56 |
+
$dbversion_info = DUPX_DB::getServerInfo($dbConn);
|
57 |
+
$dbversion_info = empty($dbversion_info) ? 'no connection' : $dbversion_info;
|
58 |
+
$dbversion_info_fail = version_compare(DUPX_DB::getVersion($dbConn), '5.5.3') < 0;
|
59 |
+
|
60 |
+
$dbversion_compat = DUPX_DB::getVersion($dbConn);
|
61 |
+
$dbversion_compat = empty($dbversion_compat) ? 'no connection' : $dbversion_compat;
|
62 |
+
$dbversion_compat_fail = version_compare($dbversion_compat, $GLOBALS['FW_VERSION_DB']) < 0;
|
63 |
+
|
64 |
+
$tstInfo = ($dbversion_info_fail)
|
65 |
+
? "<div class='dup-notice'>{$dbversion_info}</div>"
|
66 |
+
: "<div class='dup-pass'>{$dbversion_info}</div>";
|
67 |
+
|
68 |
+
$tstCompat = ($dbversion_compat_fail)
|
69 |
+
? "<div class='dup-notice'>This Server: [{$dbversion_compat}] -- Package Server: [{$GLOBALS['FW_VERSION_DB']}]</div>"
|
70 |
+
: "<div class='dup-pass'>This Server: [{$dbversion_compat}] -- Package Server: [{$GLOBALS['FW_VERSION_DB']}]</div>";
|
71 |
+
|
72 |
$html .= <<<DATA
|
73 |
<div class='dup-db-test'>
|
74 |
<small>
|
86 |
</tr>
|
87 |
<tr>
|
88 |
<td>Version:</td>
|
89 |
+
<td>{$tstInfo}</td>
|
90 |
+
</tr>
|
91 |
+
<tr>
|
92 |
+
<td>Compatibility:</td>
|
93 |
<td>{$tstCompat}</td>
|
94 |
+
</tr>
|
95 |
</table>
|
96 |
DATA;
|
97 |
|
99 |
//WARNING: DB has tables with create option
|
100 |
if ($_POST['dbaction'] == 'create')
|
101 |
{
|
102 |
+
$tblcount = DUPX_DB::countTables($dbConn, $_POST['dbname']);
|
103 |
$html .= ($tblcount > 0)
|
104 |
? "<div class='warn-msg'><b>WARNING:</b> " . sprintf(ERR_DBEMPTY, $_POST['dbname'], $tblcount) . "</div>"
|
105 |
: '';
|
115 |
break;
|
116 |
}
|
117 |
}
|
118 |
+
|
119 |
+
//WARNING: UTF8 Data in Connection String
|
120 |
$html .= (! $dbConn && $dbUTF8_tst)
|
121 |
? "<div class='warn-msg'><b>WARNING:</b> " . ERR_TESTDB_UTF8 . "</div>"
|
122 |
: '';
|
123 |
|
124 |
+
//NOTICE: Version Too Low
|
125 |
+
$html .= ($dbversion_info_fail)
|
126 |
+
? "<div class='warn-msg'><b>NOTICE:</b> " . ERR_TESTDB_VERSION_INFO . "</div>"
|
127 |
+
: '';
|
128 |
+
|
129 |
+
//NOTICE: Version Incompatibility
|
130 |
+
$html .= ($dbversion_compat_fail)
|
131 |
+
? "<div class='warn-msg'><b>NOTICE:</b> " . ERR_TESTDB_VERSION_COMPAT . "</div>"
|
132 |
: '';
|
133 |
|
134 |
$html .= "</div>";
|
139 |
//ERROR MESSAGES
|
140 |
//===============================
|
141 |
//ERR_MAKELOG
|
142 |
+
($GLOBALS['LOG_FILE_HANDLE'] != false) or DUPX_Log::error(ERR_MAKELOG);
|
143 |
|
144 |
//ERR_MYSQLI_SUPPORT
|
145 |
+
function_exists('mysqli_connect') or DUPX_Log::error(ERR_MYSQLI_SUPPORT);
|
146 |
|
147 |
//ERR_DBCONNECT
|
148 |
+
$dbh = DUPX_DB::connect($_POST['dbhost'], $_POST['dbuser'], $_POST['dbpass'], null, $_POST['dbport']);
|
149 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
150 |
+
($dbh) or DUPX_Log::error(ERR_DBCONNECT . mysqli_connect_error());
|
151 |
if ($_POST['dbaction'] == 'empty') {
|
152 |
+
mysqli_select_db($dbh, $_POST['dbname']) or DUPX_Log::error(sprintf(ERR_DBCREATE, $_POST['dbname']));
|
153 |
}
|
154 |
//ERR_DBEMPTY
|
155 |
if ($_POST['dbaction'] == 'create' ) {
|
156 |
+
$tblcount = DUPX_DB::countTables($dbh, $_POST['dbname']);
|
157 |
if ($tblcount > 0) {
|
158 |
+
DUPX_Log::error(sprintf(ERR_DBEMPTY, $_POST['dbname'], $tblcount));
|
159 |
}
|
160 |
}
|
161 |
|
162 |
//ERR_ZIPMANUAL
|
163 |
if ($_POST['zip_manual']) {
|
164 |
if (!file_exists("wp-config.php") && !file_exists("database.sql")) {
|
165 |
+
DUPX_Log::error(ERR_ZIPMANUAL);
|
166 |
}
|
167 |
} else {
|
168 |
//ERR_CONFIG_FOUND
|
169 |
(!file_exists('wp-config.php'))
|
170 |
+
or DUPX_Log::error(ERR_CONFIG_FOUND);
|
171 |
//ERR_ZIPNOTFOUND
|
172 |
(is_readable("{$package_path}"))
|
173 |
+
or DUPX_Log::error(ERR_ZIPNOTFOUND);
|
174 |
}
|
175 |
|
176 |
+
DUPX_Log::info("********************************************************************************");
|
177 |
+
DUPX_Log::info('DUPLICATOR-LITE INSTALL-LOG');
|
178 |
+
DUPX_Log::info('STEP1 START @ ' . @date('h:i:s'));
|
179 |
+
DUPX_Log::info('NOTICE: Do NOT post to public sites or forums');
|
180 |
+
DUPX_Log::info("********************************************************************************");
|
181 |
+
DUPX_Log::info("VERSION:\t{$GLOBALS['FW_DUPLICATOR_VERSION']}");
|
182 |
+
DUPX_Log::info("PHP:\t\t" . phpversion() . ' | SAPI: ' . php_sapi_name());
|
183 |
+
DUPX_Log::info("PHP MEMORY:\t" . $GLOBALS['PHP_MEMORY_LIMIT'] . ' | SUHOSIN: ' . $GLOBALS['PHP_SUHOSIN_ON'] );
|
184 |
+
DUPX_Log::info("SERVER:\t\t{$_SERVER['SERVER_SOFTWARE']}");
|
185 |
+
DUPX_Log::info("DOC ROOT:\t{$root_path}");
|
186 |
+
DUPX_Log::info("DOC ROOT 755:\t" . var_export($GLOBALS['CHOWN_ROOT_PATH'], true));
|
187 |
+
DUPX_Log::info("LOG FILE 644:\t" . var_export($GLOBALS['CHOWN_LOG_PATH'], true));
|
188 |
+
DUPX_Log::info("BUILD NAME:\t{$GLOBALS['FW_SECURE_NAME']}");
|
189 |
+
DUPX_Log::info("REQUEST URL:\t{$GLOBALS['URL_PATH']}");
|
190 |
|
191 |
$log = "--------------------------------------\n";
|
192 |
$log .= "POST DATA\n";
|
193 |
$log .= "--------------------------------------\n";
|
194 |
$log .= print_r($POST_LOG, true);
|
195 |
+
DUPX_Log::info($log, 2);
|
196 |
|
197 |
|
198 |
//====================================================================================================
|
204 |
$log .= "NAME:\t{$_POST['package_name']}\n";
|
205 |
$log .= "SIZE:\t" . DUPX_Util::readable_bytesize(@filesize($_POST['package_name'])) . "\n";
|
206 |
$log .= "ZIP:\t{$zip_support} (ZipArchive Support)";
|
207 |
+
DUPX_Log::info($log);
|
208 |
|
209 |
$zip_start = DUPX_Util::get_microtime();
|
210 |
|
211 |
if ($_POST['zip_manual'])
|
212 |
{
|
213 |
+
DUPX_Log::info("\n** PACKAGE EXTRACTION IS IN MANUAL MODE ** \n");
|
214 |
}
|
215 |
else
|
216 |
{
|
220 |
$log .= "To guarantee accuracy the installer and archive should match. For details see the online FAQs.";
|
221 |
$log .= "\nCREATED WITH:\t{$GLOBALS['FW_PACKAGE_NAME']} \nPROCESSED WITH:\t{$_POST['package_name']} \n";
|
222 |
$log .= "--------------------------------------\n";
|
223 |
+
DUPX_Log::info($log);
|
224 |
}
|
225 |
|
226 |
if (! class_exists('ZipArchive')) {
|
227 |
+
DUPX_Log::info("ERROR: Stopping install process. Trying to extract without ZipArchive module installed. Please use the 'Manual Package extraction' mode to extract zip file.");
|
228 |
+
DUPX_Log::error(ERR_ZIPARCHIVE);
|
229 |
}
|
230 |
|
231 |
$target = $root_path;
|
232 |
$zip = new ZipArchive();
|
233 |
if ($zip->open($_POST['package_name']) === TRUE)
|
234 |
{
|
235 |
+
DUPX_Log::info("\nEXTRACTING");
|
236 |
if (! $zip->extractTo($target)) {
|
237 |
+
DUPX_Log::error(ERR_ZIPEXTRACTION);
|
238 |
}
|
239 |
$log = print_r($zip, true);
|
240 |
|
254 |
|
255 |
$close_response = $zip->close();
|
256 |
$log .= "COMPLETE: " . var_export($close_response, true);
|
257 |
+
DUPX_Log::info($log);
|
258 |
} else {
|
259 |
+
DUPX_Log::error(ERR_ZIPOPEN);
|
260 |
}
|
261 |
$zip = null;
|
262 |
}
|
265 |
//CONFIG FILE RESETS
|
266 |
$log = '';
|
267 |
DUPX_WPConfig::UpdateStep1();
|
268 |
+
DUPX_ServerConfig::reset();
|
269 |
|
270 |
|
271 |
//====================================================================================================
|
287 |
$msg .= "a memory allocation error when trying to load the database.sql file. It is\n";
|
288 |
$msg .= "recommended to increase the 'memory_limit' setting in the php.ini config file.\n";
|
289 |
$msg .= "see: {$faq_url}#faq-trouble-056-q \n";
|
290 |
+
DUPX_Log::info($msg);
|
291 |
}
|
292 |
|
293 |
@chmod("{$root_path}/database.sql", 0777);
|
302 |
$msg .= "<i>see: <a href='{$faq_url}#faq-trouble-055-q' target='_blank'>{$faq_url}#faq-trouble-055-q</a></i> <br/>";
|
303 |
$msg .= "2. Validate the database.sql file exists and is in the root of the archive.zip file <br/>";
|
304 |
$msg .= "<i>see: <a href='{$faq_url}#faq-installer-020-q' target='_blank'>{$faq_url}#faq-installer-020-q</a></i> <br/>";
|
305 |
+
DUPX_Log::error($msg);
|
306 |
}
|
307 |
|
308 |
//Removes invalid space characters
|
309 |
//Complex Subject See: http://webcollab.sourceforge.net/unicode.html
|
310 |
if ($_POST['dbnbsp'])
|
311 |
{
|
312 |
+
DUPX_Log::info("NOTICE: Ran fix non-breaking space characters\n");
|
313 |
$sql_file = preg_replace('/\xC2\xA0/', ' ', $sql_file);
|
314 |
}
|
315 |
|
327 |
$msg = "\nWARNING: Unable to properly copy database.sql ({$sql_file_size}) to {$GLOBALS['SQL_FILE_NAME']}. Please check these items:\n";
|
328 |
$msg .= "- Validate permissions and/or group-owner rights on database.sql and directory [{$root_path}] \n";
|
329 |
$msg .= "- see: {$faq_url}#faq-trouble-055-q \n";
|
330 |
+
DUPX_Log::info($msg);
|
331 |
}
|
332 |
|
333 |
+
DUPX_Log::info("\nUPDATED FILES:");
|
334 |
+
DUPX_Log::info("- SQL FILE: '{$sql_result_file_path}'");
|
335 |
+
DUPX_Log::info("- WP-CONFIG: '{$root_path}/wp-config.php' (if present)");
|
336 |
+
DUPX_Log::info("\nARCHIVE RUNTIME: " . DUPX_Util::elapsed_time(DUPX_Util::get_microtime(), $zip_start) . "\n");
|
337 |
DUPX_Util::fcgi_flush();
|
338 |
|
339 |
//=================================
|
340 |
//START DB RUN
|
341 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
342 |
@mysqli_query($dbh, "SET max_allowed_packet = {$GLOBALS['DB_MAX_PACKETS']}");
|
343 |
+
DUPX_DB::setCharset($dbh, $_POST['dbcharset'], $_POST['dbcollate']);
|
344 |
|
345 |
//Will set mode to null only for this db handle session
|
346 |
//sql_mode can cause db create issues on some systems
|
362 |
}
|
363 |
|
364 |
//Set defaults in-case the variable could not be read
|
365 |
+
$dbvar_maxtime = DUPX_DB::getVariable($dbh, 'wait_timeout');
|
366 |
+
$dbvar_maxpacks = DUPX_DB::getVariable($dbh, 'max_allowed_packet');
|
367 |
+
$dbvar_sqlmode = DUPX_DB::getVariable($dbh, 'sql_mode');
|
368 |
$dbvar_maxtime = is_null($dbvar_maxtime) ? 300 : $dbvar_maxtime;
|
369 |
$dbvar_maxpacks = is_null($dbvar_maxpacks) ? 1048576 : $dbvar_maxpacks;
|
370 |
$dbvar_sqlmode = empty($dbvar_sqlmode) ? 'NOT_SET' : $dbvar_sqlmode;
|
371 |
+
$dbvar_version = DUPX_DB::getVersion($dbh);
|
372 |
$sql_file_size1 = DUPX_Util::readable_bytesize(@filesize("database.sql"));
|
373 |
$sql_file_size2 = DUPX_Util::readable_bytesize(@filesize("{$GLOBALS['SQL_FILE_NAME']}"));
|
374 |
|
375 |
|
376 |
+
DUPX_Log::info("{$GLOBALS['SEPERATOR1']}");
|
377 |
+
DUPX_Log::info('DATABASE-ROUTINES');
|
378 |
+
DUPX_Log::info("{$GLOBALS['SEPERATOR1']}");
|
379 |
+
DUPX_Log::info("--------------------------------------");
|
380 |
+
DUPX_Log::info("SERVER ENVIRONMENT");
|
381 |
+
DUPX_Log::info("--------------------------------------");
|
382 |
+
DUPX_Log::info("MYSQL VERSION:\tThis Server: {$dbvar_version} -- Build Server: {$GLOBALS['FW_VERSION_DB']}");
|
383 |
+
DUPX_Log::info("FILE SIZE:\tdatabase.sql ({$sql_file_size1}) - installer-data.sql ({$sql_file_size2})");
|
384 |
+
DUPX_Log::info("TIMEOUT:\t{$dbvar_maxtime}");
|
385 |
+
DUPX_Log::info("MAXPACK:\t{$dbvar_maxpacks}");
|
386 |
+
DUPX_Log::info("SQLMODE:\t{$dbvar_sqlmode}");
|
387 |
|
388 |
if ($qry_session_custom == false)
|
389 |
{
|
390 |
+
DUPX_Log::info("\n{$log}\n");
|
391 |
}
|
392 |
|
393 |
//CREATE DB
|
395 |
case "create":
|
396 |
mysqli_query($dbh, "CREATE DATABASE IF NOT EXISTS `{$_POST['dbname']}`");
|
397 |
mysqli_select_db($dbh, $_POST['dbname'])
|
398 |
+
or DUPX_Log::error(sprintf(ERR_DBCONNECT_CREATE, $_POST['dbname']));
|
399 |
break;
|
400 |
case "empty":
|
401 |
//DROP DB TABLES
|
410 |
foreach ($found_tables as $table_name) {
|
411 |
$sql = "DROP TABLE `{$_POST['dbname']}`.`{$table_name}`";
|
412 |
if (!$result = mysqli_query($dbh, $sql)) {
|
413 |
+
DUPX_Log::error(sprintf(ERR_DBTRYCLEAN, $_POST['dbname']));
|
414 |
}
|
415 |
}
|
416 |
}
|
421 |
|
422 |
|
423 |
//WRITE DATA
|
424 |
+
DUPX_Log::info("--------------------------------------");
|
425 |
+
DUPX_Log::info("DATABASE RESULTS");
|
426 |
+
DUPX_Log::info("--------------------------------------");
|
427 |
$profile_start = DUPX_Util::get_microtime();
|
428 |
$fcgi_buffer_pool = 5000;
|
429 |
$fcgi_buffer_count = 0;
|
436 |
|
437 |
$query_strlen = strlen(trim($sql_result_file_data[$counter]));
|
438 |
if ($dbvar_maxpacks < $query_strlen) {
|
439 |
+
DUPX_Log::info("**ERROR** Query size limit [length={$query_strlen}] [sql=" . substr($sql_result_file_data[$counter], 75) . "...]");
|
440 |
$dbquery_errs++;
|
441 |
} elseif ($query_strlen > 0) {
|
442 |
@mysqli_free_result(@mysqli_query($dbh, ($sql_result_file_data[$counter])));
|
446 |
|
447 |
if (!mysqli_ping($dbh)) {
|
448 |
mysqli_close($dbh);
|
449 |
+
$dbh = DUPX_DB::connect($_POST['dbhost'], $_POST['dbuser'], $_POST['dbpass'], $_POST['dbname'], $_POST['dbport'] );
|
450 |
// Reset session setup
|
451 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
452 |
+
DUPX_DB::setCharset($dbh, $_POST['dbcharset'], $_POST['dbcollate']);
|
453 |
}
|
454 |
+
DUPX_Log::info("**ERROR** database error write '{$err}' - [sql=" . substr($sql_result_file_data[$counter], 0, 75) . "...]");
|
455 |
$dbquery_errs++;
|
456 |
|
457 |
//Buffer data to browser to keep connection open
|
468 |
@mysqli_commit($dbh);
|
469 |
@mysqli_autocommit($dbh, true);
|
470 |
|
471 |
+
DUPX_Log::info("ERRORS FOUND:\t{$dbquery_errs}");
|
472 |
+
DUPX_Log::info("DROP TABLE:\t{$drop_log}");
|
473 |
+
DUPX_Log::info("QUERIES RAN:\t{$dbquery_rows}\n");
|
474 |
|
475 |
$dbtable_count = 0;
|
476 |
if ($result = mysqli_query($dbh, "SHOW TABLES")) {
|
477 |
while ($row = mysqli_fetch_array($result, MYSQLI_NUM)) {
|
478 |
+
$table_rows = DUPX_DB::countTableRows($dbh, $row[0]);
|
479 |
$dbtable_rows += $table_rows;
|
480 |
+
DUPX_Log::info("{$row[0]}: ({$table_rows})");
|
481 |
$dbtable_count++;
|
482 |
}
|
483 |
@mysqli_free_result($result);
|
484 |
}
|
485 |
|
486 |
if ($dbtable_count == 0) {
|
487 |
+
DUPX_Log::error("No tables where created during step 1 of the install. Please review the <a href='installer-log.txt' target='_blank'>installer-log.txt</a> file for
|
488 |
ERROR messages. You may have to manually run the installer-data.sql with a tool like phpmyadmin to validate the data input. If you have enabled compatibility mode
|
489 |
during the package creation process then the database server version your using may not be compatible with this script.\n");
|
490 |
}
|
498 |
@mysqli_query($dbh, "DELETE FROM `{$GLOBALS['FW_TABLEPREFIX']}options` WHERE `option_name` LIKE ('_transient%') OR `option_name` LIKE ('_site_transient%')");
|
499 |
$dbdelete_count2 = @mysqli_affected_rows($dbh) or 0;
|
500 |
$dbdelete_count = (abs($dbdelete_count1) + abs($dbdelete_count2));
|
501 |
+
DUPX_Log::info("Removed '{$dbdelete_count}' cache/transient rows");
|
502 |
//Reset Duplicator Options
|
503 |
foreach ($GLOBALS['FW_OPTS_DELETE'] as $value) {
|
504 |
mysqli_query($dbh, "DELETE FROM `{$GLOBALS['FW_TABLEPREFIX']}options` WHERE `option_name` = '{$value}'");
|
507 |
@mysqli_close($dbh);
|
508 |
|
509 |
$profile_end = DUPX_Util::get_microtime();
|
510 |
+
DUPX_Log::info("\nSECTION RUNTIME: " . DUPX_Util::elapsed_time($profile_end, $profile_start));
|
511 |
|
512 |
//FINAL RESULTS
|
513 |
$ajax1_end = DUPX_Util::get_microtime();
|
514 |
$ajax1_sum = DUPX_Util::elapsed_time($ajax1_end, $ajax1_start);
|
515 |
+
DUPX_Log::info("\n{$GLOBALS['SEPERATOR1']}");
|
516 |
+
DUPX_Log::info('STEP1 COMPLETE @ ' . @date('h:i:s') . " - TOTAL RUNTIME: {$ajax1_sum}");
|
517 |
+
DUPX_Log::info("{$GLOBALS['SEPERATOR1']}");
|
518 |
|
519 |
$JSON['pass'] = 1;
|
520 |
$JSON['table_count'] = $dbtable_count;
|
installer/build/ajax.step2.php
CHANGED
@@ -19,10 +19,10 @@ error_reporting(E_ERROR);
|
|
19 |
$ajax2_start = DUPX_Util::get_microtime();
|
20 |
|
21 |
//MYSQL CONNECTION
|
22 |
-
$dbh =
|
23 |
$charset_server = @mysqli_character_set_name($dbh);
|
24 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
25 |
-
|
26 |
|
27 |
//POST PARAMS
|
28 |
$_POST['blogname'] = mysqli_real_escape_string($dbh, $_POST['blogname']);
|
@@ -55,7 +55,7 @@ NOTICE: Do not post to public sites or forums
|
|
55 |
CHARSET SERVER:\t{$charset_server}
|
56 |
CHARSET CLIENT:\t {$charset_client} \n
|
57 |
LOG;
|
58 |
-
DUPX_Log::
|
59 |
|
60 |
//Detailed logging
|
61 |
$log = "--------------------------------------\n";
|
@@ -74,7 +74,7 @@ $log .= "--------------------------------------\n";
|
|
74 |
$log .= (isset($_POST['plugins']) && count($_POST['plugins'] > 0))
|
75 |
? print_r($_POST['plugins'], true)
|
76 |
: 'No plugins selected for activation';
|
77 |
-
DUPX_Log::
|
78 |
|
79 |
//UPDATE SETTINGS
|
80 |
$serial_plugin_list = (isset($_POST['plugins']) && count($_POST['plugins'] > 0)) ? @serialize($_POST['plugins']) : '';
|
@@ -87,7 +87,7 @@ $log .= "[*] scan every column\n";
|
|
87 |
$log .= "[~] scan only text columns\n";
|
88 |
$log .= "[^] no searchable columns\n";
|
89 |
$log .= "--------------------------------------";
|
90 |
-
DUPX_Log::
|
91 |
|
92 |
$url_old_json = str_replace('"', "", json_encode($_POST['url_old']));
|
93 |
$url_new_json = str_replace('"', "", json_encode($_POST['url_new']));
|
@@ -123,14 +123,14 @@ $JSON['step2'] = $report;
|
|
123 |
$JSON['step2']['warn_all'] = 0;
|
124 |
$JSON['step2']['warnlist'] = array();
|
125 |
|
126 |
-
DUPX_UpdateEngine::
|
127 |
-
DUPX_UpdateEngine::
|
128 |
|
129 |
//Reset the postguid data
|
130 |
if ($_POST['postguid']) {
|
131 |
mysqli_query($dbh, "UPDATE `{$GLOBALS['FW_TABLEPREFIX']}posts` SET guid = REPLACE(guid, '{$_POST['url_new']}', '{$_POST['url_old']}')");
|
132 |
$update_guid = @mysqli_affected_rows($dbh) or 0;
|
133 |
-
DUPX_Log::
|
134 |
}
|
135 |
|
136 |
/* FINAL UPDATES: Must happen after the global replace to prevent double pathing
|
@@ -142,9 +142,9 @@ mysqli_query($dbh, "UPDATE `{$GLOBALS['FW_TABLEPREFIX']}options` SET option_valu
|
|
142 |
//====================================================================================================
|
143 |
//FINAL CLEANUP
|
144 |
//====================================================================================================
|
145 |
-
DUPX_Log::
|
146 |
-
DUPX_Log::
|
147 |
-
DUPX_Log::
|
148 |
|
149 |
/*CREATE NEW USER LOGIC */
|
150 |
if (strlen($_POST['wp_username']) >= 4 && strlen($_POST['wp_password']) >= 6) {
|
@@ -176,17 +176,17 @@ if (strlen($_POST['wp_username']) >= 4 && strlen($_POST['wp_password']) >= 6) {
|
|
176 |
@mysqli_query($dbh, "INSERT INTO `{$GLOBALS['FW_TABLEPREFIX']}usermeta` (`user_id`, `meta_key`, `meta_value`) VALUES ('{$newuser_insert_id}', 'nickname', '{$_POST['wp_username']}')");
|
177 |
|
178 |
if ($newuser_test1 && $newuser_test2 && $newuser_test3) {
|
179 |
-
DUPX_Log::
|
180 |
} else {
|
181 |
$newuser_warnmsg = "NEW WP-ADMIN USER: Failed to create the user '{$_POST['wp_username']}' \n ";
|
182 |
$JSON['step2']['warnlist'][] = $newuser_warnmsg;
|
183 |
-
DUPX_Log::
|
184 |
}
|
185 |
}
|
186 |
else {
|
187 |
$newuser_warnmsg = "NEW WP-ADMIN USER: Username '{$_POST['wp_username']}' already exists in the database. Unable to create new account \n";
|
188 |
$JSON['step2']['warnlist'][] = $newuser_warnmsg;
|
189 |
-
DUPX_Log::
|
190 |
}
|
191 |
}
|
192 |
|
@@ -205,15 +205,15 @@ $mu_oldUrlPath = (empty($mu_oldUrlPath) || ($mu_oldUrlPath == '/')) ? '/' : rtr
|
|
205 |
|
206 |
$mu_updates = @mysqli_query($dbh, "UPDATE `{$GLOBALS['FW_TABLEPREFIX']}blogs` SET domain = '{$mu_newDomainHost}' WHERE domain = '{$mu_oldDomainHost}'");
|
207 |
if ($mu_updates) {
|
208 |
-
DUPX_Log::
|
209 |
} else {
|
210 |
-
DUPX_Log::
|
211 |
}
|
212 |
|
213 |
|
214 |
/* ==============================
|
215 |
* UPDATE WP-CONFIG FILE */
|
216 |
-
$config_file = DUPX_WPConfig::
|
217 |
|
218 |
//Create snapshots directory in order to
|
219 |
//compensate for permissions on some servers
|
@@ -226,9 +226,9 @@ fclose($fp);
|
|
226 |
|
227 |
/* ==============================
|
228 |
NOTICE TESTS */
|
229 |
-
DUPX_Log::
|
230 |
-
DUPX_Log::
|
231 |
-
DUPX_Log::
|
232 |
$config_vars = array('WP_CONTENT_DIR', 'WP_CONTENT_URL', 'WPCACHEHOME', 'COOKIE_DOMAIN', 'WP_SITEURL', 'WP_HOME', 'WP_TEMP_DIR');
|
233 |
$config_items = DUPX_Util::search_list_values($config_vars, $config_file);
|
234 |
|
@@ -237,7 +237,7 @@ if (! empty($config_items)) {
|
|
237 |
$msg = 'NOTICE: The wp-config.php has one or more of the following values set [' . implode(", ", $config_items) . ']. ';
|
238 |
$msg .= 'Please validate these values are correct by opening the file and checking the values. To validate the meaning and proper usage of each parameter used the codex link above.';
|
239 |
$JSON['step2']['warnlist'][] = $msg;
|
240 |
-
DUPX_Log::
|
241 |
}
|
242 |
|
243 |
//Database:
|
@@ -248,14 +248,14 @@ if ($result) {
|
|
248 |
$msg = "NOTICE: The media settings values in the table '{$GLOBALS['FW_TABLEPREFIX']}options' has at least one the following values ['upload_url_path','upload_path'] set. ";
|
249 |
$msg .= "Please validate these settings by logging into your wp-admin and going to Settings->Media area and validating the 'Uploading Files' section";
|
250 |
$JSON['step2']['warnlist'][] = $msg;
|
251 |
-
DUPX_Log::
|
252 |
break;
|
253 |
}
|
254 |
}
|
255 |
}
|
256 |
|
257 |
if (empty($JSON['step2']['warnlist'])) {
|
258 |
-
DUPX_Log::
|
259 |
}
|
260 |
|
261 |
$JSON['step2']['warn_all'] = empty($JSON['step2']['warnlist']) ? 0 : count($JSON['step2']['warnlist']);
|
@@ -264,13 +264,13 @@ mysqli_close($dbh);
|
|
264 |
@unlink('database.sql');
|
265 |
|
266 |
//CONFIG Setup
|
267 |
-
DUPX_ServerConfig::
|
268 |
|
269 |
$ajax2_end = DUPX_Util::get_microtime();
|
270 |
$ajax2_sum = DUPX_Util::elapsed_time($ajax2_end, $ajax2_start);
|
271 |
-
DUPX_Log::
|
272 |
-
DUPX_Log::
|
273 |
-
DUPX_Log::
|
274 |
|
275 |
$JSON['step2']['pass'] = 1;
|
276 |
error_reporting($ajax2_error_level);
|
19 |
$ajax2_start = DUPX_Util::get_microtime();
|
20 |
|
21 |
//MYSQL CONNECTION
|
22 |
+
$dbh = DUPX_DB::connect($_POST['dbhost'], $_POST['dbuser'], html_entity_decode($_POST['dbpass']), $_POST['dbname'], $_POST['dbport']);
|
23 |
$charset_server = @mysqli_character_set_name($dbh);
|
24 |
@mysqli_query($dbh, "SET wait_timeout = {$GLOBALS['DB_MAX_TIME']}");
|
25 |
+
DUPX_DB::setCharset($dbh, $_POST['dbcharset'], $_POST['dbcollate']);
|
26 |
|
27 |
//POST PARAMS
|
28 |
$_POST['blogname'] = mysqli_real_escape_string($dbh, $_POST['blogname']);
|
55 |
CHARSET SERVER:\t{$charset_server}
|
56 |
CHARSET CLIENT:\t {$charset_client} \n
|
57 |
LOG;
|
58 |
+
DUPX_Log::info($log);
|
59 |
|
60 |
//Detailed logging
|
61 |
$log = "--------------------------------------\n";
|
74 |
$log .= (isset($_POST['plugins']) && count($_POST['plugins'] > 0))
|
75 |
? print_r($_POST['plugins'], true)
|
76 |
: 'No plugins selected for activation';
|
77 |
+
DUPX_Log::info($log, 2);
|
78 |
|
79 |
//UPDATE SETTINGS
|
80 |
$serial_plugin_list = (isset($_POST['plugins']) && count($_POST['plugins'] > 0)) ? @serialize($_POST['plugins']) : '';
|
87 |
$log .= "[~] scan only text columns\n";
|
88 |
$log .= "[^] no searchable columns\n";
|
89 |
$log .= "--------------------------------------";
|
90 |
+
DUPX_Log::info($log);
|
91 |
|
92 |
$url_old_json = str_replace('"', "", json_encode($_POST['url_old']));
|
93 |
$url_new_json = str_replace('"', "", json_encode($_POST['url_new']));
|
123 |
$JSON['step2']['warn_all'] = 0;
|
124 |
$JSON['step2']['warnlist'] = array();
|
125 |
|
126 |
+
DUPX_UpdateEngine::logStats($report);
|
127 |
+
DUPX_UpdateEngine::logErrors($report);
|
128 |
|
129 |
//Reset the postguid data
|
130 |
if ($_POST['postguid']) {
|
131 |
mysqli_query($dbh, "UPDATE `{$GLOBALS['FW_TABLEPREFIX']}posts` SET guid = REPLACE(guid, '{$_POST['url_new']}', '{$_POST['url_old']}')");
|
132 |
$update_guid = @mysqli_affected_rows($dbh) or 0;
|
133 |
+
DUPX_Log::info("Reverted '{$update_guid}' post guid columns back to '{$_POST['url_old']}'");
|
134 |
}
|
135 |
|
136 |
/* FINAL UPDATES: Must happen after the global replace to prevent double pathing
|
142 |
//====================================================================================================
|
143 |
//FINAL CLEANUP
|
144 |
//====================================================================================================
|
145 |
+
DUPX_Log::info("\n********************************************************************************");
|
146 |
+
DUPX_Log::info('START FINAL CLEANUP: ' . @date('h:i:s'));
|
147 |
+
DUPX_Log::info("********************************************************************************");
|
148 |
|
149 |
/*CREATE NEW USER LOGIC */
|
150 |
if (strlen($_POST['wp_username']) >= 4 && strlen($_POST['wp_password']) >= 6) {
|
176 |
@mysqli_query($dbh, "INSERT INTO `{$GLOBALS['FW_TABLEPREFIX']}usermeta` (`user_id`, `meta_key`, `meta_value`) VALUES ('{$newuser_insert_id}', 'nickname', '{$_POST['wp_username']}')");
|
177 |
|
178 |
if ($newuser_test1 && $newuser_test2 && $newuser_test3) {
|
179 |
+
DUPX_Log::info("NEW WP-ADMIN USER: New username '{$_POST['wp_username']}' was created successfully \n ");
|
180 |
} else {
|
181 |
$newuser_warnmsg = "NEW WP-ADMIN USER: Failed to create the user '{$_POST['wp_username']}' \n ";
|
182 |
$JSON['step2']['warnlist'][] = $newuser_warnmsg;
|
183 |
+
DUPX_Log::info($newuser_warnmsg);
|
184 |
}
|
185 |
}
|
186 |
else {
|
187 |
$newuser_warnmsg = "NEW WP-ADMIN USER: Username '{$_POST['wp_username']}' already exists in the database. Unable to create new account \n";
|
188 |
$JSON['step2']['warnlist'][] = $newuser_warnmsg;
|
189 |
+
DUPX_Log::info($newuser_warnmsg);
|
190 |
}
|
191 |
}
|
192 |
|
205 |
|
206 |
$mu_updates = @mysqli_query($dbh, "UPDATE `{$GLOBALS['FW_TABLEPREFIX']}blogs` SET domain = '{$mu_newDomainHost}' WHERE domain = '{$mu_oldDomainHost}'");
|
207 |
if ($mu_updates) {
|
208 |
+
DUPX_Log::info("Update MU table blogs: domain {$mu_newDomainHost} ");
|
209 |
} else {
|
210 |
+
DUPX_Log::info("UPDATE `{$GLOBALS['FW_TABLEPREFIX']}blogs` SET domain = '{$mu_newDomainHost}' WHERE domain = '{$mu_oldDomainHost}'");
|
211 |
}
|
212 |
|
213 |
|
214 |
/* ==============================
|
215 |
* UPDATE WP-CONFIG FILE */
|
216 |
+
$config_file = DUPX_WPConfig::updateStep2();
|
217 |
|
218 |
//Create snapshots directory in order to
|
219 |
//compensate for permissions on some servers
|
226 |
|
227 |
/* ==============================
|
228 |
NOTICE TESTS */
|
229 |
+
DUPX_Log::info("\n--------------------------------------");
|
230 |
+
DUPX_Log::info("NOTICES");
|
231 |
+
DUPX_Log::info("--------------------------------------");
|
232 |
$config_vars = array('WP_CONTENT_DIR', 'WP_CONTENT_URL', 'WPCACHEHOME', 'COOKIE_DOMAIN', 'WP_SITEURL', 'WP_HOME', 'WP_TEMP_DIR');
|
233 |
$config_items = DUPX_Util::search_list_values($config_vars, $config_file);
|
234 |
|
237 |
$msg = 'NOTICE: The wp-config.php has one or more of the following values set [' . implode(", ", $config_items) . ']. ';
|
238 |
$msg .= 'Please validate these values are correct by opening the file and checking the values. To validate the meaning and proper usage of each parameter used the codex link above.';
|
239 |
$JSON['step2']['warnlist'][] = $msg;
|
240 |
+
DUPX_Log::info($msg);
|
241 |
}
|
242 |
|
243 |
//Database:
|
248 |
$msg = "NOTICE: The media settings values in the table '{$GLOBALS['FW_TABLEPREFIX']}options' has at least one the following values ['upload_url_path','upload_path'] set. ";
|
249 |
$msg .= "Please validate these settings by logging into your wp-admin and going to Settings->Media area and validating the 'Uploading Files' section";
|
250 |
$JSON['step2']['warnlist'][] = $msg;
|
251 |
+
DUPX_Log::info($msg);
|
252 |
break;
|
253 |
}
|
254 |
}
|
255 |
}
|
256 |
|
257 |
if (empty($JSON['step2']['warnlist'])) {
|
258 |
+
DUPX_Log::info("No Notices Found\n");
|
259 |
}
|
260 |
|
261 |
$JSON['step2']['warn_all'] = empty($JSON['step2']['warnlist']) ? 0 : count($JSON['step2']['warnlist']);
|
264 |
@unlink('database.sql');
|
265 |
|
266 |
//CONFIG Setup
|
267 |
+
DUPX_ServerConfig::setup();
|
268 |
|
269 |
$ajax2_end = DUPX_Util::get_microtime();
|
270 |
$ajax2_sum = DUPX_Util::elapsed_time($ajax2_end, $ajax2_start);
|
271 |
+
DUPX_Log::info("********************************************************************************");
|
272 |
+
DUPX_Log::info('STEP 2 COMPLETE @ ' . @date('h:i:s') . " - TOTAL RUNTIME: {$ajax2_sum}");
|
273 |
+
DUPX_Log::info("********************************************************************************");
|
274 |
|
275 |
$JSON['step2']['pass'] = 1;
|
276 |
error_reporting($ajax2_error_level);
|
installer/build/assets/inc.css.php
CHANGED
@@ -86,7 +86,7 @@
|
|
86 |
table.dup-db-test-dtls {text-align: left; margin: auto}
|
87 |
table.dup-db-test-dtls td:first-child {font-weight: bold}
|
88 |
div#dbconn-test-msg {font-size:12px}
|
89 |
-
div#s1-dbconn-status {border:1px solid silver; border-radius:3px; background-color:#f9f9f9; padding:2px 5px; margin-top:10px; height:
|
90 |
div#s1-dbconn-status div.warn-msg {text-align: left; padding:5px; margin:10px 0 10px 0}
|
91 |
div#s1-dbconn-status div.warn-msg b{color:maroon}
|
92 |
|
86 |
table.dup-db-test-dtls {text-align: left; margin: auto}
|
87 |
table.dup-db-test-dtls td:first-child {font-weight: bold}
|
88 |
div#dbconn-test-msg {font-size:12px}
|
89 |
+
div#s1-dbconn-status {border:1px solid silver; border-radius:3px; background-color:#f9f9f9; padding:2px 5px; margin-top:10px; height:175px; overflow-y: scroll}
|
90 |
div#s1-dbconn-status div.warn-msg {text-align: left; padding:5px; margin:10px 0 10px 0}
|
91 |
div#s1-dbconn-status div.warn-msg b{color:maroon}
|
92 |
|
installer/build/classes/class.conf.srv.php
DELETED
@@ -1,77 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
// Exit if accessed directly
|
3 |
-
if (! defined('DUPLICATOR_INIT')) {
|
4 |
-
$_baseURL = "http://" . strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
-
header("HTTP/1.1 301 Moved Permanently");
|
6 |
-
header("Location: $_baseURL");
|
7 |
-
exit;
|
8 |
-
}
|
9 |
-
|
10 |
-
/** * *****************************************************
|
11 |
-
* Class used to update and edit web server configuration files */
|
12 |
-
class DUPX_ServerConfig {
|
13 |
-
|
14 |
-
/**
|
15 |
-
* Clear .htaccess and web.config files and backup
|
16 |
-
*/
|
17 |
-
static public function Reset() {
|
18 |
-
|
19 |
-
DUPX_Log::Info("\nWEB SERVER CONFIGURATION FILE RESET:");
|
20 |
-
$timeStamp = date("ymdHis");
|
21 |
-
|
22 |
-
//Apache
|
23 |
-
@copy('.htaccess', ".htaccess.{$timeStamp}.orig");
|
24 |
-
@unlink('.htaccess');
|
25 |
-
|
26 |
-
//IIS
|
27 |
-
@copy('web.config', "web.config.{$timeStamp}.orig");
|
28 |
-
@unlink('web.config');
|
29 |
-
|
30 |
-
//.user.ini - For WordFence
|
31 |
-
@copy('.user.ini', ".user.ini.{$timeStamp}.orig");
|
32 |
-
@unlink('.user.ini');
|
33 |
-
|
34 |
-
DUPX_Log::Info("- Backup of .htaccess/web.config made to *.{$timeStamp}.orig");
|
35 |
-
DUPX_Log::Info("- Reset of .htaccess/web.config files");
|
36 |
-
$tmp_htaccess = '# RESET FOR DUPLICATOR INSTALLER USEAGE';
|
37 |
-
file_put_contents('.htaccess', $tmp_htaccess);
|
38 |
-
@chmod('.htaccess', 0644);
|
39 |
-
}
|
40 |
-
|
41 |
-
/** METHOD: ResetHTACCESS
|
42 |
-
* Resets the .htaccess file
|
43 |
-
*/
|
44 |
-
static public function Setup() {
|
45 |
-
|
46 |
-
if (! isset($_POST['url_new'])) {
|
47 |
-
return;
|
48 |
-
}
|
49 |
-
|
50 |
-
DUPX_Log::Info("\nWEB SERVER CONFIGURATION FILE BASIC SETUP:");
|
51 |
-
$currdata = parse_url($_POST['url_old']);
|
52 |
-
$newdata = parse_url($_POST['url_new']);
|
53 |
-
$currpath = DUPX_Util::add_slash(isset($currdata['path']) ? $currdata['path'] : "");
|
54 |
-
$newpath = DUPX_Util::add_slash(isset($newdata['path']) ? $newdata['path'] : "");
|
55 |
-
|
56 |
-
$tmp_htaccess = <<<HTACCESS
|
57 |
-
# BEGIN WordPress
|
58 |
-
<IfModule mod_rewrite.c>
|
59 |
-
RewriteEngine On
|
60 |
-
RewriteBase {$newpath}
|
61 |
-
RewriteRule ^index\.php$ - [L]
|
62 |
-
RewriteCond %{REQUEST_FILENAME} !-f
|
63 |
-
RewriteCond %{REQUEST_FILENAME} !-d
|
64 |
-
RewriteRule . {$newpath}index.php [L]
|
65 |
-
</IfModule>
|
66 |
-
# END WordPress
|
67 |
-
HTACCESS;
|
68 |
-
|
69 |
-
file_put_contents('.htaccess', $tmp_htaccess);
|
70 |
-
@chmod('.htaccess', 0644);
|
71 |
-
DUPX_Log::Info("created basic .htaccess file. If using IIS web.config this process will need to be done manually.");
|
72 |
-
|
73 |
-
}
|
74 |
-
|
75 |
-
|
76 |
-
}
|
77 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
installer/build/classes/class.conf.wp.php
DELETED
@@ -1,113 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
// Exit if accessed directly
|
3 |
-
if (!defined('DUPLICATOR_INIT')) {
|
4 |
-
$_baseURL = "http://" . strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
-
header("HTTP/1.1 301 Moved Permanently");
|
6 |
-
header("Location: {$_baseURL}");
|
7 |
-
exit;
|
8 |
-
}
|
9 |
-
|
10 |
-
/**
|
11 |
-
* Class used to update and edit and update the wp-config.php */
|
12 |
-
class DUPX_WPConfig
|
13 |
-
{
|
14 |
-
/**
|
15 |
-
* Updates the web server config files in Step 1 */
|
16 |
-
public static function UpdateStep1()
|
17 |
-
{
|
18 |
-
if (! file_exists('wp-config.php'))
|
19 |
-
return;
|
20 |
-
|
21 |
-
$root_path = DUPX_Util::set_safe_path($GLOBALS['CURRENT_ROOT_PATH']);
|
22 |
-
$wpconfig = @file_get_contents('wp-config.php', true);
|
23 |
-
|
24 |
-
$patterns = array(
|
25 |
-
"/'DB_NAME',\s*'.*?'/",
|
26 |
-
"/'DB_USER',\s*'.*?'/",
|
27 |
-
"/'DB_PASSWORD',\s*'.*?'/",
|
28 |
-
"/'DB_HOST',\s*'.*?'/");
|
29 |
-
|
30 |
-
$db_host = ($_POST['dbport'] == 3306) ? $_POST['dbhost'] : "{$_POST['dbhost']}:{$_POST['dbport']}";
|
31 |
-
|
32 |
-
$replace = array(
|
33 |
-
"'DB_NAME', " . '\'' . $_POST['dbname'] . '\'',
|
34 |
-
"'DB_USER', " . '\'' . $_POST['dbuser'] . '\'',
|
35 |
-
"'DB_PASSWORD', " . '\'' . DUPX_Util::preg_replacement_quote($_POST['dbpass']) . '\'',
|
36 |
-
"'DB_HOST', " . '\'' . $db_host . '\'');
|
37 |
-
|
38 |
-
//SSL CHECKS
|
39 |
-
if ($_POST['ssl_admin']) {
|
40 |
-
if (! strstr($wpconfig, 'FORCE_SSL_ADMIN')) {
|
41 |
-
$wpconfig = $wpconfig . PHP_EOL . "define('FORCE_SSL_ADMIN', true);";
|
42 |
-
}
|
43 |
-
} else {
|
44 |
-
array_push($patterns, "/'FORCE_SSL_ADMIN',\s*true/");
|
45 |
-
array_push($replace, "'FORCE_SSL_ADMIN', false");
|
46 |
-
}
|
47 |
-
|
48 |
-
if ($_POST['ssl_login']) {
|
49 |
-
if (! strstr($wpconfig, 'FORCE_SSL_LOGIN')) {
|
50 |
-
$wpconfig = $wpconfig . PHP_EOL . "define('FORCE_SSL_LOGIN', true);";
|
51 |
-
}
|
52 |
-
} else {
|
53 |
-
array_push($patterns, "/'FORCE_SSL_LOGIN',\s*true/");
|
54 |
-
array_push($replace, "'FORCE_SSL_LOGIN', false");
|
55 |
-
}
|
56 |
-
|
57 |
-
//CACHE CHECKS
|
58 |
-
if ($_POST['cache_wp']) {
|
59 |
-
if (! strstr($wpconfig, 'WP_CACHE')) {
|
60 |
-
$wpconfig = $wpconfig . PHP_EOL . "define('WP_CACHE', true);";
|
61 |
-
}
|
62 |
-
} else {
|
63 |
-
array_push($patterns, "/'WP_CACHE',\s*true/");
|
64 |
-
array_push($replace, "'WP_CACHE', false");
|
65 |
-
}
|
66 |
-
if (! $_POST['cache_path']) {
|
67 |
-
array_push($patterns, "/'WPCACHEHOME',\s*'.*?'/");
|
68 |
-
array_push($replace, "'WPCACHEHOME', ''");
|
69 |
-
}
|
70 |
-
|
71 |
-
if (! is_writable("{$root_path}/wp-config.php") )
|
72 |
-
{
|
73 |
-
if (file_exists("{$root_path}/wp-config.php"))
|
74 |
-
{
|
75 |
-
chmod("{$root_path}/wp-config.php", 0644)
|
76 |
-
? DUPX_Log::Info('File Permission Update: wp-config.php set to 0644')
|
77 |
-
: DUPX_Log::Info('WARNING: Unable to update file permissions and write to wp-config.php. Please visit the online FAQ for setting file permissions and work with your hosting provider or server administrator to enable this installer.php script to write to the wp-config.php file.');
|
78 |
-
} else {
|
79 |
-
DUPX_Log::Info('WARNING: Unable to locate wp-config.php file. Be sure the file is present in your archive.');
|
80 |
-
}
|
81 |
-
}
|
82 |
-
|
83 |
-
$wpconfig = preg_replace($patterns, $replace, $wpconfig);
|
84 |
-
file_put_contents('wp-config.php', $wpconfig);
|
85 |
-
$wpconfig = null;
|
86 |
-
}
|
87 |
-
|
88 |
-
/**
|
89 |
-
* Updates the web server config files in Step 2 */
|
90 |
-
public static function UpdateStep2()
|
91 |
-
{
|
92 |
-
$config_file = '';
|
93 |
-
if (! file_exists('wp-config.php')) {
|
94 |
-
return $config_file;
|
95 |
-
}
|
96 |
-
|
97 |
-
$patterns = array("/('|\")WP_HOME.*?\)\s*;/",
|
98 |
-
"/('|\")WP_SITEURL.*?\)\s*;/",
|
99 |
-
"/('|\")DOMAIN_CURRENT_SITE.*?\)\s*;/",
|
100 |
-
"/('|\")PATH_CURRENT_SITE.*?\)\s*;/");
|
101 |
-
$replace = array("'WP_HOME', '{$_POST['url_new']}');",
|
102 |
-
"'WP_SITEURL', '{$_POST['url_new']}');",
|
103 |
-
"'DOMAIN_CURRENT_SITE', '{$mu_newDomainHost}');",
|
104 |
-
"'PATH_CURRENT_SITE', '{$mu_newUrlPath}');");
|
105 |
-
|
106 |
-
$config_file = file_get_contents('wp-config.php', true);
|
107 |
-
$config_file = preg_replace($patterns, $replace, $config_file);
|
108 |
-
file_put_contents('wp-config.php', $config_file);
|
109 |
-
|
110 |
-
return $config_file;
|
111 |
-
}
|
112 |
-
}
|
113 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
installer/build/classes/class.engine.php
ADDED
@@ -0,0 +1,441 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
// Exit if accessed directly
|
3 |
+
if (!defined('DUPLICATOR_INIT')) {
|
4 |
+
$_baseURL = "http://".strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
+
header("HTTP/1.1 301 Moved Permanently");
|
6 |
+
header("Location: {$_baseURL}");
|
7 |
+
exit;
|
8 |
+
}
|
9 |
+
|
10 |
+
/**
|
11 |
+
* Walks every table in db that then walks every row and column replacing searches with replaces
|
12 |
+
* large tables are split into 50k row blocks to save on memory.
|
13 |
+
*
|
14 |
+
* Standard: PSR-2
|
15 |
+
* @link http://www.php-fig.org/psr/psr-2 Full Documentation
|
16 |
+
*
|
17 |
+
* @package SC\DUPX\UpdateEngine
|
18 |
+
*
|
19 |
+
*/
|
20 |
+
class DUPX_UpdateEngine
|
21 |
+
{
|
22 |
+
|
23 |
+
/**
|
24 |
+
* Used to report on all log errors into the installer-txt.log
|
25 |
+
*
|
26 |
+
* @param string $report The report error array of all error types
|
27 |
+
*
|
28 |
+
* @return string Writes the results of the update engine tables to the log
|
29 |
+
*/
|
30 |
+
public static function logErrors($report)
|
31 |
+
{
|
32 |
+
if (!empty($report['errsql'])) {
|
33 |
+
DUPX_Log::info("====================================");
|
34 |
+
DUPX_Log::info("DATA-REPLACE ERRORS (MySQL)");
|
35 |
+
foreach ($report['errsql'] as $error) {
|
36 |
+
DUPX_Log::info($error);
|
37 |
+
}
|
38 |
+
DUPX_Log::info("");
|
39 |
+
}
|
40 |
+
if (!empty($report['errser'])) {
|
41 |
+
DUPX_Log::info("====================================");
|
42 |
+
DUPX_Log::info("DATA-REPLACE ERRORS (Serialization):");
|
43 |
+
foreach ($report['errser'] as $error) {
|
44 |
+
DUPX_Log::info($error);
|
45 |
+
}
|
46 |
+
DUPX_Log::info("");
|
47 |
+
}
|
48 |
+
if (!empty($report['errkey'])) {
|
49 |
+
DUPX_Log::info("====================================");
|
50 |
+
DUPX_Log::info("DATA-REPLACE ERRORS (Key):");
|
51 |
+
DUPX_Log::info('Use SQL: SELECT @row := @row + 1 as row, t.* FROM some_table t, (SELECT @row := 0) r');
|
52 |
+
foreach ($report['errkey'] as $error) {
|
53 |
+
DUPX_Log::info($error);
|
54 |
+
}
|
55 |
+
}
|
56 |
+
}
|
57 |
+
|
58 |
+
/**
|
59 |
+
* Used to report on all log stats into the installer-txt.log
|
60 |
+
*
|
61 |
+
* @param string $report The report stats array of all error types
|
62 |
+
*
|
63 |
+
* @return string Writes the results of the update engine tables to the log
|
64 |
+
*/
|
65 |
+
public static function logStats($report)
|
66 |
+
{
|
67 |
+
if (!empty($report) && is_array($report)) {
|
68 |
+
$stats = "--------------------------------------\n";
|
69 |
+
$srchnum = 0;
|
70 |
+
foreach ($GLOBALS['REPLACE_LIST'] as $item) {
|
71 |
+
$srchnum++;
|
72 |
+
$stats .= sprintf("Search{$srchnum}:\t'%s' \nChange{$srchnum}:\t'%s' \n", $item['search'], $item['replace']);
|
73 |
+
}
|
74 |
+
$stats .= sprintf("SCANNED:\tTables:%d \t|\t Rows:%d \t|\t Cells:%d \n", $report['scan_tables'], $report['scan_rows'], $report['scan_cells']);
|
75 |
+
$stats .= sprintf("UPDATED:\tTables:%d \t|\t Rows:%d \t|\t Cells:%d \n", $report['updt_tables'], $report['updt_rows'], $report['updt_cells']);
|
76 |
+
$stats .= sprintf("ERRORS:\t\t%d \nRUNTIME:\t%f sec", $report['err_all'], $report['time']);
|
77 |
+
DUPX_Log::info($stats);
|
78 |
+
}
|
79 |
+
}
|
80 |
+
|
81 |
+
|
82 |
+
/**
|
83 |
+
* Returns only the text type columns of a table ignoring all numeric types
|
84 |
+
*
|
85 |
+
* @param obj $dbh A valid database link handle
|
86 |
+
* @param string $table A valid table name
|
87 |
+
*
|
88 |
+
* @return array All the column names of a table
|
89 |
+
*/
|
90 |
+
public static function getTextColumns($dbh, $table)
|
91 |
+
{
|
92 |
+
$type_where = "type NOT LIKE 'tinyint%' AND ";
|
93 |
+
$type_where .= "type NOT LIKE 'smallint%' AND ";
|
94 |
+
$type_where .= "type NOT LIKE 'mediumint%' AND ";
|
95 |
+
$type_where .= "type NOT LIKE 'int%' AND ";
|
96 |
+
$type_where .= "type NOT LIKE 'bigint%' AND ";
|
97 |
+
$type_where .= "type NOT LIKE 'float%' AND ";
|
98 |
+
$type_where .= "type NOT LIKE 'double%' AND ";
|
99 |
+
$type_where .= "type NOT LIKE 'decimal%' AND ";
|
100 |
+
$type_where .= "type NOT LIKE 'numeric%' AND ";
|
101 |
+
$type_where .= "type NOT LIKE 'date%' AND ";
|
102 |
+
$type_where .= "type NOT LIKE 'time%' AND ";
|
103 |
+
$type_where .= "type NOT LIKE 'year%' ";
|
104 |
+
|
105 |
+
$result = mysqli_query($dbh, "SHOW COLUMNS FROM `{$table}` WHERE {$type_where}");
|
106 |
+
if (!$result) {
|
107 |
+
return null;
|
108 |
+
}
|
109 |
+
$fields = array();
|
110 |
+
if (mysqli_num_rows($result) > 0) {
|
111 |
+
while ($row = mysqli_fetch_assoc($result)) {
|
112 |
+
$fields[] = $row['Field'];
|
113 |
+
}
|
114 |
+
}
|
115 |
+
|
116 |
+
//Return Primary which is needed for index lookup
|
117 |
+
//$result = mysqli_query($dbh, "SHOW INDEX FROM `{$table}` WHERE KEY_NAME LIKE '%PRIMARY%'"); 1.1.15 updated
|
118 |
+
$result = mysqli_query($dbh, "SHOW INDEX FROM `{$table}`");
|
119 |
+
if (mysqli_num_rows($result) > 0) {
|
120 |
+
while ($row = mysqli_fetch_assoc($result)) {
|
121 |
+
$fields[] = $row['Column_name'];
|
122 |
+
}
|
123 |
+
}
|
124 |
+
|
125 |
+
return (count($fields) > 0) ? $fields : null;
|
126 |
+
}
|
127 |
+
|
128 |
+
/**
|
129 |
+
* Begins the processing for replace logic
|
130 |
+
*
|
131 |
+
* @param mysql $dbh The db connection object
|
132 |
+
* @param array $list Key value pair of 'search' and 'replace' arrays
|
133 |
+
* @param array $tables The tables we want to look at
|
134 |
+
* @param array $fullsearch Search every column reguardless of its data type
|
135 |
+
*
|
136 |
+
* @return array Collection of information gathered during the run.
|
137 |
+
*/
|
138 |
+
public static function load($dbh, $list = array(), $tables = array(), $fullsearch = false)
|
139 |
+
{
|
140 |
+
$report = array(
|
141 |
+
'scan_tables' => 0,
|
142 |
+
'scan_rows' => 0,
|
143 |
+
'scan_cells' => 0,
|
144 |
+
'updt_tables' => 0,
|
145 |
+
'updt_rows' => 0,
|
146 |
+
'updt_cells' => 0,
|
147 |
+
'errsql' => array(),
|
148 |
+
'errser' => array(),
|
149 |
+
'errkey' => array(),
|
150 |
+
'errsql_sum' => 0,
|
151 |
+
'errser_sum' => 0,
|
152 |
+
'errkey_sum' => 0,
|
153 |
+
'time' => '',
|
154 |
+
'err_all' => 0
|
155 |
+
);
|
156 |
+
|
157 |
+
$walk_function = create_function('&$str', '$str = "`$str`";');
|
158 |
+
|
159 |
+
$profile_start = DUPX_Util::get_microtime();
|
160 |
+
if (is_array($tables) && !empty($tables)) {
|
161 |
+
|
162 |
+
foreach ($tables as $table) {
|
163 |
+
$report['scan_tables'] ++;
|
164 |
+
$columns = array();
|
165 |
+
|
166 |
+
// Get a list of columns in this table
|
167 |
+
$fields = mysqli_query($dbh, 'DESCRIBE '.$table);
|
168 |
+
while ($column = mysqli_fetch_array($fields)) {
|
169 |
+
$columns[$column['Field']] = $column['Key'] == 'PRI' ? true : false;
|
170 |
+
}
|
171 |
+
|
172 |
+
// Count the number of rows we have in the table if large we'll split into blocks
|
173 |
+
$row_count = mysqli_query($dbh, "SELECT COUNT(*) FROM `{$table}`");
|
174 |
+
$rows_result = mysqli_fetch_array($row_count);
|
175 |
+
@mysqli_free_result($row_count);
|
176 |
+
$row_count = $rows_result[0];
|
177 |
+
if ($row_count == 0) {
|
178 |
+
DUPX_Log::info("{$table}^ ({$row_count})");
|
179 |
+
continue;
|
180 |
+
}
|
181 |
+
|
182 |
+
$page_size = 25000;
|
183 |
+
$offset = ($page_size + 1);
|
184 |
+
$pages = ceil($row_count / $page_size);
|
185 |
+
|
186 |
+
// Grab the columns of the table. Only grab text based columns because
|
187 |
+
// they are the only data types that should allow any type of search/replace logic
|
188 |
+
$colList = '*';
|
189 |
+
$colMsg = '*';
|
190 |
+
if (!$fullsearch) {
|
191 |
+
$colList = self::getTextColumns($dbh, $table);
|
192 |
+
if ($colList != null && is_array($colList)) {
|
193 |
+
array_walk($colList, $walk_function);
|
194 |
+
$colList = implode(',', $colList);
|
195 |
+
}
|
196 |
+
$colMsg = (empty($colList)) ? '*' : '~';
|
197 |
+
}
|
198 |
+
|
199 |
+
if (empty($colList)) {
|
200 |
+
DUPX_Log::info("{$table}^ ({$row_count})");
|
201 |
+
continue;
|
202 |
+
} else {
|
203 |
+
DUPX_Log::info("{$table}{$colMsg} ({$row_count})");
|
204 |
+
}
|
205 |
+
|
206 |
+
//Paged Records
|
207 |
+
for ($page = 0; $page < $pages; $page++) {
|
208 |
+
$current_row = 0;
|
209 |
+
$start = $page * $page_size;
|
210 |
+
$end = $start + $page_size;
|
211 |
+
$sql = sprintf("SELECT {$colList} FROM `%s` LIMIT %d, %d", $table, $start, $offset);
|
212 |
+
$data = mysqli_query($dbh, $sql);
|
213 |
+
|
214 |
+
if (!$data) $report['errsql'][] = mysqli_error($dbh);
|
215 |
+
|
216 |
+
$scan_count = ($row_count < $end) ? $row_count : $end;
|
217 |
+
DUPX_Log::info("\tScan => {$start} of {$scan_count}", 2);
|
218 |
+
|
219 |
+
//Loops every row
|
220 |
+
while ($row = mysqli_fetch_array($data)) {
|
221 |
+
$report['scan_rows'] ++;
|
222 |
+
$current_row++;
|
223 |
+
$upd_col = array();
|
224 |
+
$upd_sql = array();
|
225 |
+
$where_sql = array();
|
226 |
+
$upd = false;
|
227 |
+
$serial_err = 0;
|
228 |
+
|
229 |
+
//Loops every cell
|
230 |
+
foreach ($columns as $column => $primary_key) {
|
231 |
+
$report['scan_cells'] ++;
|
232 |
+
$edited_data = $data_to_fix = $row[$column];
|
233 |
+
$base64coverted = false;
|
234 |
+
$txt_found = false;
|
235 |
+
|
236 |
+
//Only replacing string values
|
237 |
+
if (!empty($row[$column]) && !is_numeric($row[$column])) {
|
238 |
+
//Base 64 detection
|
239 |
+
if (base64_decode($row[$column], true)) {
|
240 |
+
$decoded = base64_decode($row[$column], true);
|
241 |
+
if (self::isSerialized($decoded)) {
|
242 |
+
$edited_data = $decoded;
|
243 |
+
$base64coverted = true;
|
244 |
+
}
|
245 |
+
}
|
246 |
+
|
247 |
+
//Skip table cell if match not found
|
248 |
+
foreach ($list as $item) {
|
249 |
+
if (strpos($edited_data, $item['search']) !== false) {
|
250 |
+
$txt_found = true;
|
251 |
+
break;
|
252 |
+
}
|
253 |
+
}
|
254 |
+
if (!$txt_found) {
|
255 |
+
continue;
|
256 |
+
}
|
257 |
+
|
258 |
+
//Replace logic - level 1: simple check on any string or serlized strings
|
259 |
+
foreach ($list as $item) {
|
260 |
+
$edited_data = self::recursiveUnserializeReplace($item['search'], $item['replace'], $edited_data);
|
261 |
+
}
|
262 |
+
|
263 |
+
//Replace logic - level 2: repair serilized strings that have become broken
|
264 |
+
$serial_check = self::fixSerialString($edited_data);
|
265 |
+
if ($serial_check['fixed']) {
|
266 |
+
$edited_data = $serial_check['data'];
|
267 |
+
} elseif ($serial_check['tried'] && !$serial_check['fixed']) {
|
268 |
+
$serial_err++;
|
269 |
+
}
|
270 |
+
}
|
271 |
+
|
272 |
+
//Change was made
|
273 |
+
if ($edited_data != $data_to_fix || $serial_err > 0) {
|
274 |
+
$report['updt_cells'] ++;
|
275 |
+
//Base 64 encode
|
276 |
+
if ($base64coverted) {
|
277 |
+
$edited_data = base64_encode($edited_data);
|
278 |
+
}
|
279 |
+
$upd_col[] = $column;
|
280 |
+
$upd_sql[] = $column.' = "'.mysqli_real_escape_string($dbh, $edited_data).'"';
|
281 |
+
$upd = true;
|
282 |
+
}
|
283 |
+
|
284 |
+
if ($primary_key) {
|
285 |
+
$where_sql[] = $column.' = "'.mysqli_real_escape_string($dbh, $data_to_fix).'"';
|
286 |
+
}
|
287 |
+
}
|
288 |
+
|
289 |
+
//PERFORM ROW UPDATE
|
290 |
+
if ($upd && !empty($where_sql)) {
|
291 |
+
$sql = "UPDATE `{$table}` SET ".implode(', ', $upd_sql).' WHERE '.implode(' AND ', array_filter($where_sql));
|
292 |
+
$result = mysqli_query($dbh, $sql) or $report['errsql'][] = mysqli_error($dbh);
|
293 |
+
//DEBUG ONLY:
|
294 |
+
DUPX_Log::info("\t{$sql}\n", 3);
|
295 |
+
if ($result) {
|
296 |
+
if ($serial_err > 0) {
|
297 |
+
$report['errser'][] = "SELECT ".implode(', ', $upd_col)." FROM `{$table}` WHERE ".implode(' AND ', array_filter($where_sql)).';';
|
298 |
+
}
|
299 |
+
$report['updt_rows'] ++;
|
300 |
+
}
|
301 |
+
} elseif ($upd) {
|
302 |
+
$report['errkey'][] = sprintf("Row [%s] on Table [%s] requires a manual update.", $current_row, $table);
|
303 |
+
}
|
304 |
+
}
|
305 |
+
DUPX_Util::fcgi_flush();
|
306 |
+
@mysqli_free_result($data);
|
307 |
+
}
|
308 |
+
|
309 |
+
if ($upd) {
|
310 |
+
$report['updt_tables'] ++;
|
311 |
+
}
|
312 |
+
}
|
313 |
+
}
|
314 |
+
$profile_end = DUPX_Util::get_microtime();
|
315 |
+
$report['time'] = DUPX_Util::elapsed_time($profile_end, $profile_start);
|
316 |
+
$report['errsql_sum'] = empty($report['errsql']) ? 0 : count($report['errsql']);
|
317 |
+
$report['errser_sum'] = empty($report['errser']) ? 0 : count($report['errser']);
|
318 |
+
$report['errkey_sum'] = empty($report['errkey']) ? 0 : count($report['errkey']);
|
319 |
+
$report['err_all'] = $report['errsql_sum'] + $report['errser_sum'] + $report['errkey_sum'];
|
320 |
+
return $report;
|
321 |
+
}
|
322 |
+
|
323 |
+
/**
|
324 |
+
* Take a serialised array and unserialise it replacing elements and
|
325 |
+
* unserialising any subordinate arrays and performing the replace.
|
326 |
+
*
|
327 |
+
* @param string $from String we're looking to replace.
|
328 |
+
* @param string $to What we want it to be replaced with
|
329 |
+
* @param array $data Used to pass any subordinate arrays back to in.
|
330 |
+
* @param bool $serialised Does the array passed via $data need serialising.
|
331 |
+
*
|
332 |
+
* @return array The original array with all elements replaced as needed.
|
333 |
+
*/
|
334 |
+
public static function recursiveUnserializeReplace($from = '', $to = '', $data = '', $serialised = false)
|
335 |
+
{
|
336 |
+
// some unseriliased data cannot be re-serialised eg. SimpleXMLElements
|
337 |
+
try {
|
338 |
+
if (is_string($data) && ($unserialized = @unserialize($data)) !== false) {
|
339 |
+
$data = self::recursiveUnserializeReplace($from, $to, $unserialized, true);
|
340 |
+
} elseif (is_array($data)) {
|
341 |
+
$_tmp = array();
|
342 |
+
foreach ($data as $key => $value) {
|
343 |
+
$_tmp[$key] = self::recursiveUnserializeReplace($from, $to, $value, false);
|
344 |
+
}
|
345 |
+
$data = $_tmp;
|
346 |
+
unset($_tmp);
|
347 |
+
|
348 |
+
/* CJL
|
349 |
+
Check for an update to the key of an array e.g. [http://localhost/projects/wpplugins/] => 1.41
|
350 |
+
This could have unintended consequences would need to enable with full-search needs more testing
|
351 |
+
if (array_key_exists($from, $data))
|
352 |
+
{
|
353 |
+
$data[$to] = $data[$from];
|
354 |
+
unset($data[$from]);
|
355 |
+
} */
|
356 |
+
} elseif (is_object($data)) {
|
357 |
+
/* RSR Old logic that didn't work with Beaver Builder - they didn't want to create a brand new
|
358 |
+
object instead reused the existing one...
|
359 |
+
$dataClass = get_class($data);
|
360 |
+
$_tmp = new $dataClass();
|
361 |
+
foreach ($data as $key => $value) {
|
362 |
+
$_tmp->$key = self::recursiveUnserializeReplace($from, $to, $value, false);
|
363 |
+
}
|
364 |
+
$data = $_tmp;
|
365 |
+
unset($_tmp); */
|
366 |
+
|
367 |
+
// RSR NEW LOGIC
|
368 |
+
$_tmp = $data;
|
369 |
+
$props = get_object_vars($data);
|
370 |
+
foreach ($props as $key => $value) {
|
371 |
+
$_tmp->$key = self::recursiveUnserializeReplace($from, $to, $value, false);
|
372 |
+
}
|
373 |
+
$data = $_tmp;
|
374 |
+
unset($_tmp);
|
375 |
+
} else {
|
376 |
+
if (is_string($data)) {
|
377 |
+
$data = str_replace($from, $to, $data);
|
378 |
+
}
|
379 |
+
}
|
380 |
+
|
381 |
+
if ($serialised) return serialize($data);
|
382 |
+
} catch (Exception $error) {
|
383 |
+
DUPX_Log::info("\nRECURSIVE UNSERIALIZE ERROR: With string\n".$error, 2);
|
384 |
+
}
|
385 |
+
return $data;
|
386 |
+
}
|
387 |
+
|
388 |
+
/**
|
389 |
+
* Test if a string in properly serialized
|
390 |
+
*
|
391 |
+
* @param string $data Any string type
|
392 |
+
*
|
393 |
+
* @return bool Is the string a serialized string
|
394 |
+
*/
|
395 |
+
public static function isSerialized($data)
|
396 |
+
{
|
397 |
+
$test = @unserialize(($data));
|
398 |
+
return ($test !== false || $test === 'b:0;') ? true : false;
|
399 |
+
}
|
400 |
+
|
401 |
+
/**
|
402 |
+
* Fixes the string length of a string object that has been serialized but the length is broken
|
403 |
+
*
|
404 |
+
* @param string $data The string ojbect to recalculate the size on.
|
405 |
+
*
|
406 |
+
* @return string A serialized string that fixes and string length types
|
407 |
+
*/
|
408 |
+
public static function fixSerialString($data)
|
409 |
+
{
|
410 |
+
$result = array('data' => $data, 'fixed' => false, 'tried' => false);
|
411 |
+
if (preg_match("/s:[0-9]+:/", $data)) {
|
412 |
+
if (!self::isSerialized($data)) {
|
413 |
+
$regex = '!(?<=^|;)s:(\d+)(?=:"(.*?)";(?:}|a:|s:|b:|d:|i:|o:|N;))!s';
|
414 |
+
$serial_string = preg_match('/^s:[0-9]+:"(.*$)/s', trim($data), $matches);
|
415 |
+
//Nested serial string
|
416 |
+
if ($serial_string) {
|
417 |
+
$inner = preg_replace_callback($regex, 'DUPX_UpdateEngine::fixStringCallback', rtrim($matches[1], '";'));
|
418 |
+
$serialized_fixed = 's:'.strlen($inner).':"'.$inner.'";';
|
419 |
+
} else {
|
420 |
+
$serialized_fixed = preg_replace_callback($regex, 'DUPX_UpdateEngine::fixStringCallback', $data);
|
421 |
+
}
|
422 |
+
|
423 |
+
if (self::isSerialized($serialized_fixed)) {
|
424 |
+
$result['data'] = $serialized_fixed;
|
425 |
+
$result['fixed'] = true;
|
426 |
+
}
|
427 |
+
$result['tried'] = true;
|
428 |
+
}
|
429 |
+
}
|
430 |
+
return $result;
|
431 |
+
}
|
432 |
+
|
433 |
+
/**
|
434 |
+
* The call back method call from via fixSerialString
|
435 |
+
*/
|
436 |
+
private static function fixStringCallback($matches)
|
437 |
+
{
|
438 |
+
return 's:'.strlen(($matches[2]));
|
439 |
+
}
|
440 |
+
}
|
441 |
+
?>
|
installer/build/classes/class.logging.php
CHANGED
@@ -21,34 +21,53 @@ define('ERR_DBTRYCLEAN', 'DATABASE CREATION FAILURE!<br/> Unable to remove all
|
|
21 |
define('ERR_DBCREATE', 'The database "%s" does not exists.<br/> Change mode to create in order to create a new database.');
|
22 |
define('ERR_DBEMPTY', 'The database "%s" has "%s" tables. The Duplicator only works with an EMPTY database. Enable the action "Connect and Remove All Data" radio button to remove all tables and or create a new database. Some hosting providers do not allow table removal from scripts. In this case you will need to login to your hosting providers control panel and remove the tables manually. Please contact your hosting provider for further details. Always backup all your data before proceeding!');
|
23 |
define('ERR_TESTDB_UTF8', 'UTF8 Characters were detected as part of the database connection string. If your connection fails be sure to update the MySQL my.ini configuration file setting to support UTF8 characters by enabling this option [character_set_server=utf8] and restarting the database server.');
|
24 |
-
define('
|
|
|
25 |
|
26 |
-
/** * *****************************************************
|
27 |
-
* DUPX_Log
|
28 |
-
* Class used to log information */
|
29 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
30 |
class DUPX_Log
|
31 |
{
|
32 |
|
33 |
-
/**
|
34 |
* Used to write debug info to the text log file
|
|
|
35 |
* @param string $msg Any text data
|
36 |
* @param int $loglevel Log level
|
|
|
|
|
37 |
*/
|
38 |
-
public static function
|
39 |
{
|
40 |
if ($logging <= $GLOBALS["LOGGING"]) {
|
41 |
@fwrite($GLOBALS["LOG_FILE_HANDLE"], "{$msg}\n");
|
42 |
}
|
43 |
}
|
44 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
45 |
{
|
46 |
$breaks = array("<br />","<br>","<br/>");
|
47 |
-
$log_msg = str_ireplace($breaks, "\r\n", $
|
48 |
$log_msg = strip_tags($log_msg);
|
49 |
@fwrite($GLOBALS["LOG_FILE_HANDLE"], "\nINSTALLER ERROR:\n{$log_msg}\n");
|
50 |
@fclose($GLOBALS["LOG_FILE_HANDLE"]);
|
51 |
-
die("<div class='dup-ui-error'><hr size='1' /><b style='color:#B80000;'>INSTALL ERROR!</b><br/>{$
|
52 |
}
|
53 |
}
|
54 |
-
?>
|
21 |
define('ERR_DBCREATE', 'The database "%s" does not exists.<br/> Change mode to create in order to create a new database.');
|
22 |
define('ERR_DBEMPTY', 'The database "%s" has "%s" tables. The Duplicator only works with an EMPTY database. Enable the action "Connect and Remove All Data" radio button to remove all tables and or create a new database. Some hosting providers do not allow table removal from scripts. In this case you will need to login to your hosting providers control panel and remove the tables manually. Please contact your hosting provider for further details. Always backup all your data before proceeding!');
|
23 |
define('ERR_TESTDB_UTF8', 'UTF8 Characters were detected as part of the database connection string. If your connection fails be sure to update the MySQL my.ini configuration file setting to support UTF8 characters by enabling this option [character_set_server=utf8] and restarting the database server.');
|
24 |
+
define('ERR_TESTDB_VERSION_INFO', 'The current version detected was released prior to MySQL 5.5.3 which had a release date of April 8th 2010. WordPress 4.2 included support for utf8mb4 which is only supported in MySQL server 5.5.3+. It is highly recommended to upgrade your version of MySQL server on this server to be more compatible with recent releases of WordPress and avoid issues with install errors.');
|
25 |
+
define('ERR_TESTDB_VERSION_COMPAT', 'In order to avoid database incompatibility issues make sure the database versions between the build and installer servers are as close as possible. If the package was created on a newer database version than where it is being installed then you might run into issues.<br/><br/> It is best to make sure the server where the installer is running has the same or higher version number than where it was built. If the major and minor version are the same or close for example [5.7 to 5.6], then the migration should work without issues. A version pair of [5.7 to 5.1] is more likely to cause issues unless you have a very simple setup. If the versions are too far apart work with your hosting provider to upgrade the MySQL engine on this server.<br/><br/> <b>MariaDB:</b> If see a version of 10.N.N then the database distribution is a MariaDB flavor of MySQL. While the distributions are very close there are some subtle differences. Some operating systems will report the version such as "5.5.5-10.1.21-MariaDB" showing the correlation of both. Please visit the online <a href="https://mariadb.com/kb/en/mariadb/mariadb-vs-mysql-compatibility/" target="_blank">MariaDB versus MySQL - Compatibility</a> page for more details.<br/><br/> Please note these messages are simply notices. It is highly recommended that you continue with the install process and closely monitor the installer-log.txt file along with the install report found on step 3 of the installer. Be sure to look for any notices/warnings/errors in these locations to validate the install process did not detect any errors. If any issues are found please visit the FAQ pages and see the question <a href="https://snapcreek.com/duplicator/docs/faqs-tech/#faq-installer-260-q" target="_blank">What if I get database errors or general warnings on the install report?</a>.');
|
26 |
|
|
|
|
|
|
|
27 |
|
28 |
+
/**
|
29 |
+
* Class used to log information to the installer-log.txt file
|
30 |
+
*
|
31 |
+
* Standard: PSR-2
|
32 |
+
* @link http://www.php-fig.org/psr/psr-2 Full Documentation
|
33 |
+
*
|
34 |
+
* @package SC\DUPX\Log
|
35 |
+
*
|
36 |
+
*/
|
37 |
class DUPX_Log
|
38 |
{
|
39 |
|
40 |
+
/**
|
41 |
* Used to write debug info to the text log file
|
42 |
+
*
|
43 |
* @param string $msg Any text data
|
44 |
* @param int $loglevel Log level
|
45 |
+
*
|
46 |
+
* @return string Write info to both the log and browser
|
47 |
*/
|
48 |
+
public static function info($msg, $logging = 1)
|
49 |
{
|
50 |
if ($logging <= $GLOBALS["LOGGING"]) {
|
51 |
@fwrite($GLOBALS["LOG_FILE_HANDLE"], "{$msg}\n");
|
52 |
}
|
53 |
}
|
54 |
+
|
55 |
+
/**
|
56 |
+
* Used to write errors to the text log file
|
57 |
+
*
|
58 |
+
* @param string $msg Any text data
|
59 |
+
* @param int $loglevel Log level
|
60 |
+
*
|
61 |
+
* @return string Write errors to both the log and browser
|
62 |
+
*/
|
63 |
+
public static function error($msg)
|
64 |
{
|
65 |
$breaks = array("<br />","<br>","<br/>");
|
66 |
+
$log_msg = str_ireplace($breaks, "\r\n", $msg);
|
67 |
$log_msg = strip_tags($log_msg);
|
68 |
@fwrite($GLOBALS["LOG_FILE_HANDLE"], "\nINSTALLER ERROR:\n{$log_msg}\n");
|
69 |
@fclose($GLOBALS["LOG_FILE_HANDLE"]);
|
70 |
+
die("<div class='dup-ui-error'><hr size='1' /><b style='color:#B80000;'>INSTALL ERROR!</b><br/>{$msg}</div><br/>");
|
71 |
}
|
72 |
}
|
73 |
+
?>
|
installer/build/classes/class.serializer.php
DELETED
@@ -1,452 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
// Exit if accessed directly
|
3 |
-
if (!defined('DUPLICATOR_INIT')) {
|
4 |
-
$_baseURL = "http://" . strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
-
header("HTTP/1.1 301 Moved Permanently");
|
6 |
-
header("Location: {$_baseURL}");
|
7 |
-
exit;
|
8 |
-
}
|
9 |
-
|
10 |
-
/** * *****************************************************
|
11 |
-
* CLASS::DUPX_UpdateEngine
|
12 |
-
* Walks every table in db that then walks every row and column replacing searches with replaces
|
13 |
-
* large tables are split into 50k row blocks to save on memory. */
|
14 |
-
class DUPX_UpdateEngine
|
15 |
-
{
|
16 |
-
/**
|
17 |
-
* LOG ERRORS
|
18 |
-
*/
|
19 |
-
public static function log_errors($report)
|
20 |
-
{
|
21 |
-
if (!empty($report['errsql'])) {
|
22 |
-
DUPX_Log::Info("====================================");
|
23 |
-
DUPX_Log::Info("DATA-REPLACE ERRORS (MySQL)");
|
24 |
-
foreach ($report['errsql'] as $error) {
|
25 |
-
DUPX_Log::Info($error);
|
26 |
-
}
|
27 |
-
DUPX_Log::Info("");
|
28 |
-
}
|
29 |
-
if (!empty($report['errser'])) {
|
30 |
-
DUPX_Log::Info("====================================");
|
31 |
-
DUPX_Log::Info("DATA-REPLACE ERRORS (Serialization):");
|
32 |
-
foreach ($report['errser'] as $error) {
|
33 |
-
DUPX_Log::Info($error);
|
34 |
-
}
|
35 |
-
DUPX_Log::Info("");
|
36 |
-
}
|
37 |
-
if (!empty($report['errkey'])) {
|
38 |
-
DUPX_Log::Info("====================================");
|
39 |
-
DUPX_Log::Info("DATA-REPLACE ERRORS (Key):");
|
40 |
-
DUPX_Log::Info('Use SQL: SELECT @row := @row + 1 as row, t.* FROM some_table t, (SELECT @row := 0) r');
|
41 |
-
foreach ($report['errkey'] as $error) {
|
42 |
-
DUPX_Log::Info($error);
|
43 |
-
}
|
44 |
-
}
|
45 |
-
}
|
46 |
-
|
47 |
-
/**
|
48 |
-
* LOG STATS
|
49 |
-
*/
|
50 |
-
public static function log_stats($report)
|
51 |
-
{
|
52 |
-
if (!empty($report) && is_array($report))
|
53 |
-
{
|
54 |
-
$stats = "--------------------------------------\n";
|
55 |
-
$srchnum = 0;
|
56 |
-
foreach ($GLOBALS['REPLACE_LIST'] as $item)
|
57 |
-
{
|
58 |
-
$srchnum++;
|
59 |
-
$stats .= sprintf("Search{$srchnum}:\t'%s' \nChange{$srchnum}:\t'%s' \n", $item['search'], $item['replace']);
|
60 |
-
}
|
61 |
-
$stats .= sprintf("SCANNED:\tTables:%d \t|\t Rows:%d \t|\t Cells:%d \n", $report['scan_tables'], $report['scan_rows'], $report['scan_cells']);
|
62 |
-
$stats .= sprintf("UPDATED:\tTables:%d \t|\t Rows:%d \t|\t Cells:%d \n", $report['updt_tables'], $report['updt_rows'], $report['updt_cells']);
|
63 |
-
$stats .= sprintf("ERRORS:\t\t%d \nRUNTIME:\t%f sec", $report['err_all'], $report['time']);
|
64 |
-
DUPX_Log::Info($stats);
|
65 |
-
}
|
66 |
-
}
|
67 |
-
|
68 |
-
/**
|
69 |
-
* Returns only the text type columns of a table ignoring all numeric types
|
70 |
-
*/
|
71 |
-
public static function getTextColumns($conn, $table)
|
72 |
-
{
|
73 |
-
$type_where = "type NOT LIKE 'tinyint%' AND ";
|
74 |
-
$type_where .= "type NOT LIKE 'smallint%' AND ";
|
75 |
-
$type_where .= "type NOT LIKE 'mediumint%' AND ";
|
76 |
-
$type_where .= "type NOT LIKE 'int%' AND ";
|
77 |
-
$type_where .= "type NOT LIKE 'bigint%' AND ";
|
78 |
-
$type_where .= "type NOT LIKE 'float%' AND ";
|
79 |
-
$type_where .= "type NOT LIKE 'double%' AND ";
|
80 |
-
$type_where .= "type NOT LIKE 'decimal%' AND ";
|
81 |
-
$type_where .= "type NOT LIKE 'numeric%' AND ";
|
82 |
-
$type_where .= "type NOT LIKE 'date%' AND ";
|
83 |
-
$type_where .= "type NOT LIKE 'time%' AND ";
|
84 |
-
$type_where .= "type NOT LIKE 'year%' ";
|
85 |
-
|
86 |
-
$result = mysqli_query($conn, "SHOW COLUMNS FROM `{$table}` WHERE {$type_where}");
|
87 |
-
if (!$result) {
|
88 |
-
return null;
|
89 |
-
}
|
90 |
-
$fields = array();
|
91 |
-
if (mysqli_num_rows($result) > 0) {
|
92 |
-
while ($row = mysqli_fetch_assoc($result)) {
|
93 |
-
$fields[] = $row['Field'];
|
94 |
-
}
|
95 |
-
}
|
96 |
-
|
97 |
-
//Return Primary which is needed for index lookup
|
98 |
-
//$result = mysqli_query($conn, "SHOW INDEX FROM `{$table}` WHERE KEY_NAME LIKE '%PRIMARY%'"); 1.1.15 updated
|
99 |
-
$result = mysqli_query($conn, "SHOW INDEX FROM `{$table}`");
|
100 |
-
if (mysqli_num_rows($result) > 0) {
|
101 |
-
while ($row = mysqli_fetch_assoc($result)) {
|
102 |
-
$fields[] = $row['Column_name'];
|
103 |
-
}
|
104 |
-
}
|
105 |
-
|
106 |
-
return (count($fields) > 0) ? $fields : null;
|
107 |
-
}
|
108 |
-
|
109 |
-
/**
|
110 |
-
* LOAD
|
111 |
-
* Begins the processing for replace logic
|
112 |
-
* @param mysql $conn The db connection object
|
113 |
-
* @param array $list Key value pair of 'search' and 'replace' arrays
|
114 |
-
* @param array $tables The tables we want to look at
|
115 |
-
* @param array $fullsearch Search every column reguardless of its data type
|
116 |
-
* @return array Collection of information gathered during the run.
|
117 |
-
*/
|
118 |
-
public static function load($conn, $list = array(), $tables = array(), $fullsearch = false)
|
119 |
-
{
|
120 |
-
$report = array(
|
121 |
-
'scan_tables' => 0,
|
122 |
-
'scan_rows' => 0,
|
123 |
-
'scan_cells' => 0,
|
124 |
-
'updt_tables' => 0,
|
125 |
-
'updt_rows' => 0,
|
126 |
-
'updt_cells' => 0,
|
127 |
-
'errsql' => array(),
|
128 |
-
'errser' => array(),
|
129 |
-
'errkey' => array(),
|
130 |
-
'errsql_sum' => 0,
|
131 |
-
'errser_sum' => 0,
|
132 |
-
'errkey_sum' => 0,
|
133 |
-
'time' => '',
|
134 |
-
'err_all' => 0
|
135 |
-
);
|
136 |
-
|
137 |
-
$walk_function = create_function('&$str', '$str = "`$str`";');
|
138 |
-
|
139 |
-
$profile_start = DUPX_Util::get_microtime();
|
140 |
-
if (is_array($tables) && !empty($tables)) {
|
141 |
-
|
142 |
-
foreach ($tables as $table)
|
143 |
-
{
|
144 |
-
$report['scan_tables']++;
|
145 |
-
$columns = array();
|
146 |
-
|
147 |
-
// Get a list of columns in this table
|
148 |
-
$fields = mysqli_query($conn, 'DESCRIBE ' . $table);
|
149 |
-
while ($column = mysqli_fetch_array($fields)) {
|
150 |
-
$columns[$column['Field']] = $column['Key'] == 'PRI' ? true : false;
|
151 |
-
}
|
152 |
-
|
153 |
-
// Count the number of rows we have in the table if large we'll split into blocks
|
154 |
-
$row_count = mysqli_query($conn, "SELECT COUNT(*) FROM `{$table}`");
|
155 |
-
$rows_result = mysqli_fetch_array($row_count);
|
156 |
-
@mysqli_free_result($row_count);
|
157 |
-
$row_count = $rows_result[0];
|
158 |
-
if ($row_count == 0) {
|
159 |
-
DUPX_Log::Info("{$table}^ ({$row_count})");
|
160 |
-
continue;
|
161 |
-
}
|
162 |
-
|
163 |
-
$page_size = 25000;
|
164 |
-
$offset = ($page_size + 1);
|
165 |
-
$pages = ceil($row_count / $page_size);
|
166 |
-
|
167 |
-
// Grab the columns of the table. Only grab text based columns because
|
168 |
-
// they are the only data types that should allow any type of search/replace logic
|
169 |
-
$colList = '*';
|
170 |
-
$colMsg = '*';
|
171 |
-
if (! $fullsearch)
|
172 |
-
{
|
173 |
-
$colList = self::getTextColumns($conn, $table);
|
174 |
-
if ($colList != null && is_array($colList)) {
|
175 |
-
array_walk($colList, $walk_function);
|
176 |
-
$colList = implode(',', $colList);
|
177 |
-
}
|
178 |
-
$colMsg = (empty($colList)) ? '*' : '~';
|
179 |
-
}
|
180 |
-
|
181 |
-
if (empty($colList))
|
182 |
-
{
|
183 |
-
DUPX_Log::Info("{$table}^ ({$row_count})");
|
184 |
-
continue;
|
185 |
-
}
|
186 |
-
else
|
187 |
-
{
|
188 |
-
DUPX_Log::Info("{$table}{$colMsg} ({$row_count})");
|
189 |
-
}
|
190 |
-
|
191 |
-
//Paged Records
|
192 |
-
for ($page = 0; $page < $pages; $page++)
|
193 |
-
{
|
194 |
-
$current_row = 0;
|
195 |
-
$start = $page * $page_size;
|
196 |
-
$end = $start + $page_size;
|
197 |
-
$sql = sprintf("SELECT {$colList} FROM `%s` LIMIT %d, %d", $table, $start, $offset);
|
198 |
-
$data = mysqli_query($conn, $sql);
|
199 |
-
|
200 |
-
if (!$data)
|
201 |
-
$report['errsql'][] = mysqli_error($conn);
|
202 |
-
|
203 |
-
$scan_count = ($row_count < $end) ? $row_count : $end;
|
204 |
-
DUPX_Log::Info("\tScan => {$start} of {$scan_count}", 2);
|
205 |
-
|
206 |
-
//Loops every row
|
207 |
-
while ($row = mysqli_fetch_array($data))
|
208 |
-
{
|
209 |
-
$report['scan_rows']++;
|
210 |
-
$current_row++;
|
211 |
-
$upd_col = array();
|
212 |
-
$upd_sql = array();
|
213 |
-
$where_sql = array();
|
214 |
-
$upd = false;
|
215 |
-
$serial_err = 0;
|
216 |
-
|
217 |
-
//Loops every cell
|
218 |
-
foreach ($columns as $column => $primary_key)
|
219 |
-
{
|
220 |
-
$report['scan_cells']++;
|
221 |
-
$edited_data = $data_to_fix = $row[$column];
|
222 |
-
$base64coverted = false;
|
223 |
-
$txt_found = false;
|
224 |
-
|
225 |
-
//Only replacing string values
|
226 |
-
if (!empty($row[$column]) && !is_numeric($row[$column]))
|
227 |
-
{
|
228 |
-
//Base 64 detection
|
229 |
-
if (base64_decode($row[$column], true))
|
230 |
-
{
|
231 |
-
$decoded = base64_decode($row[$column], true);
|
232 |
-
if (self::is_serialized($decoded))
|
233 |
-
{
|
234 |
-
$edited_data = $decoded;
|
235 |
-
$base64coverted = true;
|
236 |
-
}
|
237 |
-
}
|
238 |
-
|
239 |
-
//Skip table cell if match not found
|
240 |
-
foreach ($list as $item)
|
241 |
-
{
|
242 |
-
if (strpos($edited_data, $item['search']) !== false) {
|
243 |
-
$txt_found = true;
|
244 |
-
break;
|
245 |
-
}
|
246 |
-
}
|
247 |
-
if (! $txt_found) {
|
248 |
-
continue;
|
249 |
-
}
|
250 |
-
|
251 |
-
//Replace logic - level 1: simple check on any string or serlized strings
|
252 |
-
foreach ($list as $item) {
|
253 |
-
$edited_data = self::recursive_unserialize_replace($item['search'], $item['replace'], $edited_data);
|
254 |
-
}
|
255 |
-
|
256 |
-
//Replace logic - level 2: repair serilized strings that have become broken
|
257 |
-
$serial_check = self::fix_serial_string($edited_data);
|
258 |
-
if ($serial_check['fixed'])
|
259 |
-
{
|
260 |
-
$edited_data = $serial_check['data'];
|
261 |
-
}
|
262 |
-
elseif ($serial_check['tried'] && !$serial_check['fixed'])
|
263 |
-
{
|
264 |
-
$serial_err++;
|
265 |
-
}
|
266 |
-
}
|
267 |
-
|
268 |
-
//Change was made
|
269 |
-
if ($edited_data != $data_to_fix || $serial_err > 0)
|
270 |
-
{
|
271 |
-
$report['updt_cells']++;
|
272 |
-
//Base 64 encode
|
273 |
-
if ($base64coverted) {
|
274 |
-
$edited_data = base64_encode($edited_data);
|
275 |
-
}
|
276 |
-
$upd_col[] = $column;
|
277 |
-
$upd_sql[] = $column . ' = "' . mysqli_real_escape_string($conn, $edited_data) . '"';
|
278 |
-
$upd = true;
|
279 |
-
}
|
280 |
-
|
281 |
-
if ($primary_key) {
|
282 |
-
$where_sql[] = $column . ' = "' . mysqli_real_escape_string($conn, $data_to_fix) . '"';
|
283 |
-
}
|
284 |
-
}
|
285 |
-
|
286 |
-
//PERFORM ROW UPDATE
|
287 |
-
if ($upd && !empty($where_sql))
|
288 |
-
{
|
289 |
-
$sql = "UPDATE `{$table}` SET " . implode(', ', $upd_sql) . ' WHERE ' . implode(' AND ', array_filter($where_sql));
|
290 |
-
$result = mysqli_query($conn, $sql) or $report['errsql'][] = mysqli_error($conn);
|
291 |
-
//DEBUG ONLY:
|
292 |
-
DUPX_Log::Info("\t{$sql}\n", 3);
|
293 |
-
if ($result) {
|
294 |
-
if ($serial_err > 0) {
|
295 |
-
$report['errser'][] = "SELECT " . implode(', ', $upd_col) . " FROM `{$table}` WHERE " . implode(' AND ', array_filter($where_sql)) . ';';
|
296 |
-
}
|
297 |
-
$report['updt_rows']++;
|
298 |
-
}
|
299 |
-
} elseif ($upd) {
|
300 |
-
$report['errkey'][] = sprintf("Row [%s] on Table [%s] requires a manual update.", $current_row, $table);
|
301 |
-
}
|
302 |
-
}
|
303 |
-
DUPX_Util::fcgi_flush();
|
304 |
-
@mysqli_free_result($data);
|
305 |
-
}
|
306 |
-
|
307 |
-
if ($upd) {
|
308 |
-
$report['updt_tables']++;
|
309 |
-
}
|
310 |
-
}
|
311 |
-
}
|
312 |
-
$profile_end = DUPX_Util::get_microtime();
|
313 |
-
$report['time'] = DUPX_Util::elapsed_time($profile_end, $profile_start);
|
314 |
-
$report['errsql_sum'] = empty($report['errsql']) ? 0 : count($report['errsql']);
|
315 |
-
$report['errser_sum'] = empty($report['errser']) ? 0 : count($report['errser']);
|
316 |
-
$report['errkey_sum'] = empty($report['errkey']) ? 0 : count($report['errkey']);
|
317 |
-
$report['err_all'] = $report['errsql_sum'] + $report['errser_sum'] + $report['errkey_sum'];
|
318 |
-
return $report;
|
319 |
-
}
|
320 |
-
|
321 |
-
/**
|
322 |
-
* Take a serialised array and unserialise it replacing elements and
|
323 |
-
* unserialising any subordinate arrays and performing the replace.
|
324 |
-
* @param string $from String we're looking to replace.
|
325 |
-
* @param string $to What we want it to be replaced with
|
326 |
-
* @param array $data Used to pass any subordinate arrays back to in.
|
327 |
-
* @param bool $serialised Does the array passed via $data need serialising.
|
328 |
-
* @return array The original array with all elements replaced as needed.
|
329 |
-
*/
|
330 |
-
public static function recursive_unserialize_replace($from = '', $to = '', $data = '', $serialised = false)
|
331 |
-
{
|
332 |
-
// some unseriliased data cannot be re-serialised eg. SimpleXMLElements
|
333 |
-
try
|
334 |
-
{
|
335 |
-
if (is_string($data) && ($unserialized = @unserialize($data)) !== false)
|
336 |
-
{
|
337 |
-
$data = self::recursive_unserialize_replace($from, $to, $unserialized, true);
|
338 |
-
}
|
339 |
-
elseif (is_array($data))
|
340 |
-
{
|
341 |
-
$_tmp = array();
|
342 |
-
foreach ($data as $key => $value)
|
343 |
-
{
|
344 |
-
$_tmp[$key] = self::recursive_unserialize_replace($from, $to, $value, false);
|
345 |
-
}
|
346 |
-
$data = $_tmp;
|
347 |
-
unset($_tmp);
|
348 |
-
|
349 |
-
/* CJL
|
350 |
-
Check for an update to the key of an array e.g. [http://localhost/projects/wpplugins/] => 1.41
|
351 |
-
This could have unintended consequences would need to enable with full-search needs more testing
|
352 |
-
if (array_key_exists($from, $data))
|
353 |
-
{
|
354 |
-
$data[$to] = $data[$from];
|
355 |
-
unset($data[$from]);
|
356 |
-
}*/
|
357 |
-
|
358 |
-
}
|
359 |
-
elseif (is_object($data))
|
360 |
-
{
|
361 |
-
/* RSR Old logic that didn't work with Beaver Builder - they didn't want to create a brand new
|
362 |
-
object instead reused the existing one...
|
363 |
-
$dataClass = get_class($data);
|
364 |
-
$_tmp = new $dataClass();
|
365 |
-
foreach ($data as $key => $value) {
|
366 |
-
$_tmp->$key = self::recursive_unserialize_replace($from, $to, $value, false);
|
367 |
-
}
|
368 |
-
$data = $_tmp;
|
369 |
-
unset($_tmp);*/
|
370 |
-
|
371 |
-
// RSR NEW LOGIC
|
372 |
-
$_tmp = $data;
|
373 |
-
$props = get_object_vars( $data );
|
374 |
-
foreach ($props as $key => $value)
|
375 |
-
{
|
376 |
-
$_tmp->$key = self::recursive_unserialize_replace( $from, $to, $value, false );
|
377 |
-
}
|
378 |
-
$data = $_tmp;
|
379 |
-
unset($_tmp);
|
380 |
-
}
|
381 |
-
|
382 |
-
else
|
383 |
-
{
|
384 |
-
if (is_string($data)) {
|
385 |
-
$data = str_replace($from, $to, $data);
|
386 |
-
}
|
387 |
-
}
|
388 |
-
|
389 |
-
if ($serialised)
|
390 |
-
return serialize($data);
|
391 |
-
|
392 |
-
}
|
393 |
-
catch (Exception $error)
|
394 |
-
{
|
395 |
-
DUPX_Log::Info("\nRECURSIVE UNSERIALIZE ERROR: With string\n" . $error, 2);
|
396 |
-
}
|
397 |
-
return $data;
|
398 |
-
}
|
399 |
-
|
400 |
-
/**
|
401 |
-
* IS_SERIALIZED
|
402 |
-
* Test if a string in properly serialized */
|
403 |
-
public static function is_serialized($data)
|
404 |
-
{
|
405 |
-
$test = @unserialize(($data));
|
406 |
-
return ($test !== false || $test === 'b:0;') ? true : false;
|
407 |
-
}
|
408 |
-
|
409 |
-
/**
|
410 |
-
* FIX_STRING
|
411 |
-
* Fixes the string length of a string object that has been serialized but the length is broken
|
412 |
-
* @param string $data The string ojbect to recalculate the size on.
|
413 |
-
* @return
|
414 |
-
*/
|
415 |
-
public static function fix_serial_string($data)
|
416 |
-
{
|
417 |
-
$result = array('data' => $data, 'fixed' => false, 'tried' => false);
|
418 |
-
if (preg_match("/s:[0-9]+:/", $data))
|
419 |
-
{
|
420 |
-
if (!self::is_serialized($data))
|
421 |
-
{
|
422 |
-
$regex = '!(?<=^|;)s:(\d+)(?=:"(.*?)";(?:}|a:|s:|b:|d:|i:|o:|N;))!s';
|
423 |
-
$serial_string = preg_match('/^s:[0-9]+:"(.*$)/s', trim($data), $matches);
|
424 |
-
//Nested serial string
|
425 |
-
if ($serial_string)
|
426 |
-
{
|
427 |
-
$inner = preg_replace_callback($regex, 'DUPX_UpdateEngine::fix_string_callback', rtrim($matches[1], '";'));
|
428 |
-
$serialized_fixed = 's:' . strlen($inner) . ':"' . $inner . '";';
|
429 |
-
}
|
430 |
-
else
|
431 |
-
{
|
432 |
-
$serialized_fixed = preg_replace_callback($regex, 'DUPX_UpdateEngine::fix_string_callback', $data);
|
433 |
-
}
|
434 |
-
|
435 |
-
if (self::is_serialized($serialized_fixed))
|
436 |
-
{
|
437 |
-
$result['data'] = $serialized_fixed;
|
438 |
-
$result['fixed'] = true;
|
439 |
-
}
|
440 |
-
$result['tried'] = true;
|
441 |
-
}
|
442 |
-
}
|
443 |
-
return $result;
|
444 |
-
}
|
445 |
-
|
446 |
-
private static function fix_string_callback($matches)
|
447 |
-
{
|
448 |
-
return 's:' . strlen(($matches[2]));
|
449 |
-
}
|
450 |
-
|
451 |
-
}
|
452 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
installer/build/classes/class.utils.php
DELETED
@@ -1,376 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
// Exit if accessed directly
|
3 |
-
if (! defined('DUPLICATOR_INIT')) {
|
4 |
-
$_baseURL = "http://" . strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
-
header("HTTP/1.1 301 Moved Permanently");
|
6 |
-
header("Location: $_baseURL");
|
7 |
-
exit;
|
8 |
-
}
|
9 |
-
|
10 |
-
/** * *****************************************************
|
11 |
-
* Various Static Utility methods for working with the installer */
|
12 |
-
class DUPX_Util
|
13 |
-
{
|
14 |
-
|
15 |
-
/**
|
16 |
-
* Get current microtime as a float. Can be used for simple profiling.
|
17 |
-
*/
|
18 |
-
public static function get_microtime() {
|
19 |
-
return microtime(true);
|
20 |
-
}
|
21 |
-
|
22 |
-
/**
|
23 |
-
* Return a string with the elapsed time.
|
24 |
-
* Order of $end and $start can be switched.
|
25 |
-
*/
|
26 |
-
public static function elapsed_time($end, $start) {
|
27 |
-
return sprintf("%.4f sec.", abs($end - $start));
|
28 |
-
}
|
29 |
-
|
30 |
-
/**
|
31 |
-
* @param string $string Thing that needs escaping
|
32 |
-
* @param bool $echo Do we echo or return?
|
33 |
-
* @return string Escaped string.
|
34 |
-
*/
|
35 |
-
public static function esc_html_attr($string = '', $echo = false) {
|
36 |
-
$output = htmlentities($string, ENT_QUOTES, 'UTF-8');
|
37 |
-
if ($echo)
|
38 |
-
echo $output;
|
39 |
-
else
|
40 |
-
return $output;
|
41 |
-
}
|
42 |
-
|
43 |
-
/**
|
44 |
-
* Count the tables in a given database
|
45 |
-
* @param string $_POST['dbname'] Database to count tables in
|
46 |
-
*/
|
47 |
-
public static function dbtable_count($conn, $dbname) {
|
48 |
-
$res = mysqli_query($conn, "SELECT COUNT(*) AS count FROM information_schema.tables WHERE table_schema = '{$dbname}' ");
|
49 |
-
$row = mysqli_fetch_row($res);
|
50 |
-
return is_null($row) ? 0 : $row[0];
|
51 |
-
}
|
52 |
-
|
53 |
-
/**
|
54 |
-
* Returns the table count
|
55 |
-
* @param string $conn A valid link resource
|
56 |
-
* @param string $table_name A valid table name
|
57 |
-
*/
|
58 |
-
public static function table_row_count($conn, $table_name) {
|
59 |
-
$total = mysqli_query($conn, "SELECT COUNT(*) FROM `$table_name`");
|
60 |
-
if ($total) {
|
61 |
-
$total = @mysqli_fetch_array($total);
|
62 |
-
return $total[0];
|
63 |
-
} else {
|
64 |
-
return 0;
|
65 |
-
}
|
66 |
-
}
|
67 |
-
|
68 |
-
/**
|
69 |
-
* Adds a slash to the end of a path
|
70 |
-
* @param string $path A path
|
71 |
-
*/
|
72 |
-
public static function add_slash($path) {
|
73 |
-
$last_char = substr($path, strlen($path) - 1, 1);
|
74 |
-
if ($last_char != '/') {
|
75 |
-
$path .= '/';
|
76 |
-
}
|
77 |
-
return $path;
|
78 |
-
}
|
79 |
-
|
80 |
-
/**
|
81 |
-
* Makes path safe for any OS
|
82 |
-
* Paths should ALWAYS READ be "/"
|
83 |
-
* uni: /home/path/file.xt
|
84 |
-
* win: D:/home/path/file.txt
|
85 |
-
* @param string $path The path to make safe
|
86 |
-
*/
|
87 |
-
public static function set_safe_path($path) {
|
88 |
-
return str_replace("\\", "/", $path);
|
89 |
-
}
|
90 |
-
|
91 |
-
public static function unset_safe_path($path) {
|
92 |
-
return str_replace("/", "\\", $path);
|
93 |
-
}
|
94 |
-
|
95 |
-
/**
|
96 |
-
* PHP_SAPI for fcgi requires a data flush of at least 256
|
97 |
-
* bytes every 40 seconds or else it forces a script hault
|
98 |
-
*/
|
99 |
-
public static function fcgi_flush() {
|
100 |
-
echo(str_repeat(' ', 256));
|
101 |
-
@flush();
|
102 |
-
}
|
103 |
-
|
104 |
-
/**
|
105 |
-
* A safe method used to copy larger files
|
106 |
-
* @param string $source The path to the file being copied
|
107 |
-
* @param string $destination The path to the file being made
|
108 |
-
*/
|
109 |
-
public static function copy_file($source, $destination) {
|
110 |
-
$sp = fopen($source, 'r');
|
111 |
-
$op = fopen($destination, 'w');
|
112 |
-
|
113 |
-
while (!feof($sp)) {
|
114 |
-
$buffer = fread($sp, 512); // use a buffer of 512 bytes
|
115 |
-
fwrite($op, $buffer);
|
116 |
-
}
|
117 |
-
// close handles
|
118 |
-
fclose($op);
|
119 |
-
fclose($sp);
|
120 |
-
}
|
121 |
-
|
122 |
-
/**
|
123 |
-
* Looks for a list of strings in a string and returns each list item that is found
|
124 |
-
* @param array $list A list of strings to search for
|
125 |
-
* @param string $haystack The string to search in
|
126 |
-
*/
|
127 |
-
public static function search_list_values($list, $haystack) {
|
128 |
-
$found = array();
|
129 |
-
foreach ($list as $var) {
|
130 |
-
if (strstr($haystack, $var) !== false) {
|
131 |
-
array_push($found, $var);
|
132 |
-
}
|
133 |
-
}
|
134 |
-
return $found;
|
135 |
-
}
|
136 |
-
|
137 |
-
/** METHOD: get_active_plugins
|
138 |
-
* Returns the active plugins for a package
|
139 |
-
* @param conn $dbh A database connection handle
|
140 |
-
* @return array $list A list of active plugins
|
141 |
-
*/
|
142 |
-
public static function get_active_plugins($dbh) {
|
143 |
-
$query = @mysqli_query($dbh, "SELECT option_value FROM `{$GLOBALS['FW_TABLEPREFIX']}options` WHERE option_name = 'active_plugins' ");
|
144 |
-
if ($query) {
|
145 |
-
$row = @mysqli_fetch_array($query);
|
146 |
-
$all_plugins = unserialize($row[0]);
|
147 |
-
if (is_array($all_plugins)) {
|
148 |
-
return $all_plugins;
|
149 |
-
}
|
150 |
-
}
|
151 |
-
return array();
|
152 |
-
}
|
153 |
-
|
154 |
-
/**
|
155 |
-
* Returns the tables for a database
|
156 |
-
* @param conn $dbh A database connection handle
|
157 |
-
* @return array $list A list of all table names
|
158 |
-
*/
|
159 |
-
public static function get_database_tables($dbh) {
|
160 |
-
$query = @mysqli_query($dbh, 'SHOW TABLES');
|
161 |
-
if ($query) {
|
162 |
-
while ($table = @mysqli_fetch_array($query)) {
|
163 |
-
$all_tables[] = $table[0];
|
164 |
-
}
|
165 |
-
if (isset($all_tables) && is_array($all_tables)) {
|
166 |
-
return $all_tables;
|
167 |
-
}
|
168 |
-
}
|
169 |
-
return array();
|
170 |
-
}
|
171 |
-
|
172 |
-
/**
|
173 |
-
* MySQL connection support for sock
|
174 |
-
* @param same as mysqli_connect
|
175 |
-
* @return database connection handle
|
176 |
-
*/
|
177 |
-
public static function db_connect( $host, $username, $password, $dbname = '', $port = null ) {
|
178 |
-
|
179 |
-
//sock connections
|
180 |
-
if ( 'sock' === substr( $host, -4 ) )
|
181 |
-
{
|
182 |
-
$url_parts = parse_url( $host );
|
183 |
-
$dbh = @mysqli_connect( 'localhost', $username, $password, $dbname, null, $url_parts['path'] );
|
184 |
-
}
|
185 |
-
else
|
186 |
-
{
|
187 |
-
$dbh = @mysqli_connect( $host, $username, $password, $dbname, $port );
|
188 |
-
}
|
189 |
-
return $dbh;
|
190 |
-
}
|
191 |
-
|
192 |
-
/**
|
193 |
-
* MySQL database version number
|
194 |
-
* @param conn $dbh Database connection handle
|
195 |
-
* @return false|string false on failure, version number on success
|
196 |
-
*/
|
197 |
-
public static function mysqldb_version($dbh) {
|
198 |
-
if (function_exists('mysqli_get_server_info')) {
|
199 |
-
return preg_replace('/[^0-9.].*/', '', mysqli_get_server_info($dbh));
|
200 |
-
} else {
|
201 |
-
return 0;
|
202 |
-
}
|
203 |
-
}
|
204 |
-
|
205 |
-
/**
|
206 |
-
* MySQL server variable
|
207 |
-
* @param conn $dbh Database connection handle
|
208 |
-
* @return string the server variable to query for
|
209 |
-
*/
|
210 |
-
public static function mysqldb_variable_value($dbh, $variable) {
|
211 |
-
$result = @mysqli_query($dbh, "SHOW VARIABLES LIKE '{$variable}'");
|
212 |
-
$row = @mysqli_fetch_array($result);
|
213 |
-
@mysqli_free_result($result);
|
214 |
-
return isset($row[1]) ? $row[1] : null;
|
215 |
-
}
|
216 |
-
|
217 |
-
/**
|
218 |
-
* Determine if a MySQL database supports a particular feature
|
219 |
-
* @param conn $dbh Database connection handle
|
220 |
-
* @param string $feature the feature to check for
|
221 |
-
* @return bool
|
222 |
-
*/
|
223 |
-
public static function mysqldb_has_ability($dbh, $feature) {
|
224 |
-
$version = self::mysqldb_version($dbh);
|
225 |
-
|
226 |
-
switch (strtolower($feature)) {
|
227 |
-
case 'collation' :
|
228 |
-
case 'group_concat' :
|
229 |
-
case 'subqueries' :
|
230 |
-
return version_compare($version, '4.1', '>=');
|
231 |
-
case 'set_charset' :
|
232 |
-
return version_compare($version, '5.0.7', '>=');
|
233 |
-
};
|
234 |
-
return false;
|
235 |
-
}
|
236 |
-
|
237 |
-
/**
|
238 |
-
* Sets the MySQL connection's character set.
|
239 |
-
* @param resource $dbh The resource given by mysqli_connect
|
240 |
-
* @param string $charset The character set (optional)
|
241 |
-
* @param string $collate The collation (optional)
|
242 |
-
*/
|
243 |
-
public static function mysqldb_set_charset($dbh, $charset = null, $collate = null) {
|
244 |
-
|
245 |
-
$charset = (!isset($charset) ) ? $GLOBALS['DBCHARSET_DEFAULT'] : $charset;
|
246 |
-
$collate = (!isset($collate) ) ? $GLOBALS['DBCOLLATE_DEFAULT'] : $collate;
|
247 |
-
|
248 |
-
if (self::mysqldb_has_ability($dbh, 'collation') && !empty($charset)) {
|
249 |
-
if (function_exists('mysqli_set_charset') && self::mysqldb_has_ability($dbh, 'set_charset')) {
|
250 |
-
return mysqli_set_charset($dbh, $charset);
|
251 |
-
} else {
|
252 |
-
$sql = " SET NAMES {$charset}";
|
253 |
-
if (!empty($collate))
|
254 |
-
$sql .= " COLLATE {$collate}";
|
255 |
-
return mysqli_query($dbh, $sql);
|
256 |
-
}
|
257 |
-
}
|
258 |
-
}
|
259 |
-
|
260 |
-
/**
|
261 |
-
* Display human readable byte sizes
|
262 |
-
* @param string $size The size in bytes
|
263 |
-
*/
|
264 |
-
public static function readable_bytesize($size) {
|
265 |
-
try {
|
266 |
-
$units = array('B', 'KB', 'MB', 'GB', 'TB');
|
267 |
-
for ($i = 0; $size >= 1024 && $i < 4; $i++)
|
268 |
-
$size /= 1024;
|
269 |
-
return round($size, 2) . $units[$i];
|
270 |
-
} catch (Exception $e) {
|
271 |
-
return "n/a";
|
272 |
-
}
|
273 |
-
}
|
274 |
-
|
275 |
-
/**
|
276 |
-
* Converts shorthand memory notation value to bytes
|
277 |
-
* From http://php.net/manual/en/function.ini-get.php
|
278 |
-
*
|
279 |
-
* @param $val Memory size shorthand notation string
|
280 |
-
*/
|
281 |
-
public static function return_bytes($val)
|
282 |
-
{
|
283 |
-
$val = trim($val);
|
284 |
-
$last = strtolower($val[strlen($val)-1]);
|
285 |
-
switch($last) {
|
286 |
-
// The 'G' modifier is available since PHP 5.1.0
|
287 |
-
case 'g':
|
288 |
-
$val *= 1024;
|
289 |
-
case 'm':
|
290 |
-
$val *= 1024;
|
291 |
-
case 'k':
|
292 |
-
$val *= 1024;
|
293 |
-
break;
|
294 |
-
default :
|
295 |
-
$val = null;
|
296 |
-
}
|
297 |
-
return $val;
|
298 |
-
}
|
299 |
-
|
300 |
-
/**
|
301 |
-
* The characters that are special in the replacement value of preg_replace are not the
|
302 |
-
* same characters that are special in the pattern
|
303 |
-
* @param string $str The string to replace on
|
304 |
-
*/
|
305 |
-
public static function preg_replacement_quote($str) {
|
306 |
-
return preg_replace('/(\$|\\\\)(?=\d)/', '\\\\\1', $str);
|
307 |
-
}
|
308 |
-
|
309 |
-
|
310 |
-
/**
|
311 |
-
* Check to see if the internet is accessable
|
312 |
-
* NOTE: fsocketopen on windows doesn't seem to honor $timeout setting.
|
313 |
-
*
|
314 |
-
* @param string $url A url e.g without prefix "ajax.googleapis.com"
|
315 |
-
* @param string $port A valid port number
|
316 |
-
* @return bool
|
317 |
-
*/
|
318 |
-
public static function is_url_active($url, $port, $timeout=5)
|
319 |
-
{
|
320 |
-
if (function_exists('fsockopen'))
|
321 |
-
{
|
322 |
-
@ini_set("default_socket_timeout", 5);
|
323 |
-
$port = isset($port) && is_integer($port) ? $port : 80;
|
324 |
-
$connected = @fsockopen($url, $port, $errno, $errstr, $timeout); //website and port
|
325 |
-
if ($connected){
|
326 |
-
@fclose($connected);
|
327 |
-
return true;
|
328 |
-
}
|
329 |
-
return false;
|
330 |
-
} else {
|
331 |
-
return false;
|
332 |
-
}
|
333 |
-
}
|
334 |
-
|
335 |
-
/**
|
336 |
-
* Returns an array of zip files found in the current directory
|
337 |
-
* @return array of zip files
|
338 |
-
*/
|
339 |
-
public static function get_zip_files() {
|
340 |
-
|
341 |
-
$files = array();
|
342 |
-
foreach (glob("*.zip") as $name) {
|
343 |
-
if (file_exists($name)) {
|
344 |
-
$files[] = $name;
|
345 |
-
}
|
346 |
-
}
|
347 |
-
|
348 |
-
if (count($files) > 0) {
|
349 |
-
return $files;
|
350 |
-
}
|
351 |
-
|
352 |
-
//FALL BACK: Windows XP has bug with glob,
|
353 |
-
//add secondary check for PHP lameness
|
354 |
-
if ($dh = opendir('.'))
|
355 |
-
{
|
356 |
-
while (false !== ($name = readdir($dh))) {
|
357 |
-
$ext = substr($name, strrpos($name, '.') + 1);
|
358 |
-
if(in_array($ext, array("zip"))) {
|
359 |
-
$files[] = $name;
|
360 |
-
}
|
361 |
-
}
|
362 |
-
closedir($dh);
|
363 |
-
}
|
364 |
-
|
365 |
-
return $files;
|
366 |
-
}
|
367 |
-
|
368 |
-
/**
|
369 |
-
* Does a string have non ascii characters
|
370 |
-
*/
|
371 |
-
public static function is_non_ascii($string)
|
372 |
-
{
|
373 |
-
return preg_match('/[^\x20-\x7f]/', $string);
|
374 |
-
}
|
375 |
-
}
|
376 |
-
?>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
installer/build/classes/config/class.conf.srv.php
ADDED
@@ -0,0 +1,87 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
// Exit if accessed directly
|
3 |
+
if (!defined('DUPLICATOR_INIT')) {
|
4 |
+
$_baseURL = "http://".strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
+
header("HTTP/1.1 301 Moved Permanently");
|
6 |
+
header("Location: $_baseURL");
|
7 |
+
exit;
|
8 |
+
}
|
9 |
+
|
10 |
+
/**
|
11 |
+
* Class used to update and edit web server configuration files
|
12 |
+
*
|
13 |
+
* Standard: PSR-2
|
14 |
+
* @link http://www.php-fig.org/psr/psr-2 Full Documentation
|
15 |
+
*
|
16 |
+
* @package SC\DUPX\ServerConfig
|
17 |
+
*
|
18 |
+
*/
|
19 |
+
class DUPX_ServerConfig
|
20 |
+
{
|
21 |
+
|
22 |
+
/**
|
23 |
+
* Clear .htaccess and web.config files and backup
|
24 |
+
*
|
25 |
+
* @return null
|
26 |
+
*/
|
27 |
+
public static function reset()
|
28 |
+
{
|
29 |
+
DUPX_Log::info("\nWEB SERVER CONFIGURATION FILE RESET:");
|
30 |
+
$timeStamp = date("ymdHis");
|
31 |
+
|
32 |
+
//Apache
|
33 |
+
@copy('.htaccess', ".htaccess.{$timeStamp}.orig");
|
34 |
+
@unlink('.htaccess');
|
35 |
+
|
36 |
+
//IIS
|
37 |
+
@copy('web.config', "web.config.{$timeStamp}.orig");
|
38 |
+
@unlink('web.config');
|
39 |
+
|
40 |
+
//.user.ini - For WordFence
|
41 |
+
@copy('.user.ini', ".user.ini.{$timeStamp}.orig");
|
42 |
+
@unlink('.user.ini');
|
43 |
+
|
44 |
+
DUPX_Log::info("- Backup of .htaccess/web.config made to *.{$timeStamp}.orig");
|
45 |
+
DUPX_Log::info("- Reset of .htaccess/web.config files");
|
46 |
+
$tmp_htaccess = '# RESET FOR DUPLICATOR INSTALLER USEAGE';
|
47 |
+
file_put_contents('.htaccess', $tmp_htaccess);
|
48 |
+
@chmod('.htaccess', 0644);
|
49 |
+
}
|
50 |
+
|
51 |
+
/**
|
52 |
+
* Resets the .htaccess file to a very slimed down version with new paths
|
53 |
+
*
|
54 |
+
* @return null
|
55 |
+
*/
|
56 |
+
public static function setup()
|
57 |
+
{
|
58 |
+
|
59 |
+
if (!isset($_POST['url_new'])) {
|
60 |
+
return;
|
61 |
+
}
|
62 |
+
|
63 |
+
DUPX_Log::info("\nWEB SERVER CONFIGURATION FILE BASIC SETUP:");
|
64 |
+
$currdata = parse_url($_POST['url_old']);
|
65 |
+
$newdata = parse_url($_POST['url_new']);
|
66 |
+
$currpath = DUPX_Util::add_slash(isset($currdata['path']) ? $currdata['path'] : "");
|
67 |
+
$newpath = DUPX_Util::add_slash(isset($newdata['path']) ? $newdata['path'] : "");
|
68 |
+
|
69 |
+
$tmp_htaccess = <<<HTACCESS
|
70 |
+
# BEGIN WordPress
|
71 |
+
<IfModule mod_rewrite.c>
|
72 |
+
RewriteEngine On
|
73 |
+
RewriteBase {$newpath}
|
74 |
+
RewriteRule ^index\.php$ - [L]
|
75 |
+
RewriteCond %{REQUEST_FILENAME} !-f
|
76 |
+
RewriteCond %{REQUEST_FILENAME} !-d
|
77 |
+
RewriteRule . {$newpath}index.php [L]
|
78 |
+
</IfModule>
|
79 |
+
# END WordPress
|
80 |
+
HTACCESS;
|
81 |
+
|
82 |
+
file_put_contents('.htaccess', $tmp_htaccess);
|
83 |
+
@chmod('.htaccess', 0644);
|
84 |
+
DUPX_Log::info("created basic .htaccess file. If using IIS web.config this process will need to be done manually.");
|
85 |
+
}
|
86 |
+
}
|
87 |
+
?>
|
installer/build/classes/config/class.conf.wp.php
ADDED
@@ -0,0 +1,122 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
// Exit if accessed directly
|
3 |
+
if (!defined('DUPLICATOR_INIT')) {
|
4 |
+
$_baseURL = "http://".strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
+
header("HTTP/1.1 301 Moved Permanently");
|
6 |
+
header("Location: {$_baseURL}");
|
7 |
+
exit;
|
8 |
+
}
|
9 |
+
|
10 |
+
/**
|
11 |
+
* Class used to update and edit and update the wp-config.php
|
12 |
+
*
|
13 |
+
* Standard: PSR-2
|
14 |
+
* @link http://www.php-fig.org/psr/psr-2 Full Documentation
|
15 |
+
*
|
16 |
+
* @package SC\DUPX\WPConfig
|
17 |
+
*
|
18 |
+
*/
|
19 |
+
class DUPX_WPConfig
|
20 |
+
{
|
21 |
+
|
22 |
+
/**
|
23 |
+
* Updates the web server config files in Step 1
|
24 |
+
*
|
25 |
+
* @return null
|
26 |
+
*/
|
27 |
+
public static function updateStep1()
|
28 |
+
{
|
29 |
+
if (!file_exists('wp-config.php')) return;
|
30 |
+
|
31 |
+
$root_path = DUPX_Util::set_safe_path($GLOBALS['CURRENT_ROOT_PATH']);
|
32 |
+
$wpconfig = @file_get_contents('wp-config.php', true);
|
33 |
+
|
34 |
+
$patterns = array(
|
35 |
+
"/'DB_NAME',\s*'.*?'/",
|
36 |
+
"/'DB_USER',\s*'.*?'/",
|
37 |
+
"/'DB_PASSWORD',\s*'.*?'/",
|
38 |
+
"/'DB_HOST',\s*'.*?'/");
|
39 |
+
|
40 |
+
$db_host = ($_POST['dbport'] == 3306) ? $_POST['dbhost'] : "{$_POST['dbhost']}:{$_POST['dbport']}";
|
41 |
+
|
42 |
+
$replace = array(
|
43 |
+
"'DB_NAME', ".'\''.$_POST['dbname'].'\'',
|
44 |
+
"'DB_USER', ".'\''.$_POST['dbuser'].'\'',
|
45 |
+
"'DB_PASSWORD', ".'\''.DUPX_Util::preg_replacement_quote($_POST['dbpass']).'\'',
|
46 |
+
"'DB_HOST', ".'\''.$db_host.'\'');
|
47 |
+
|
48 |
+
//SSL CHECKS
|
49 |
+
if ($_POST['ssl_admin']) {
|
50 |
+
if (!strstr($wpconfig, 'FORCE_SSL_ADMIN')) {
|
51 |
+
$wpconfig = $wpconfig.PHP_EOL."define('FORCE_SSL_ADMIN', true);";
|
52 |
+
}
|
53 |
+
} else {
|
54 |
+
array_push($patterns, "/'FORCE_SSL_ADMIN',\s*true/");
|
55 |
+
array_push($replace, "'FORCE_SSL_ADMIN', false");
|
56 |
+
}
|
57 |
+
|
58 |
+
if ($_POST['ssl_login']) {
|
59 |
+
if (!strstr($wpconfig, 'FORCE_SSL_LOGIN')) {
|
60 |
+
$wpconfig = $wpconfig.PHP_EOL."define('FORCE_SSL_LOGIN', true);";
|
61 |
+
}
|
62 |
+
} else {
|
63 |
+
array_push($patterns, "/'FORCE_SSL_LOGIN',\s*true/");
|
64 |
+
array_push($replace, "'FORCE_SSL_LOGIN', false");
|
65 |
+
}
|
66 |
+
|
67 |
+
//CACHE CHECKS
|
68 |
+
if ($_POST['cache_wp']) {
|
69 |
+
if (!strstr($wpconfig, 'WP_CACHE')) {
|
70 |
+
$wpconfig = $wpconfig.PHP_EOL."define('WP_CACHE', true);";
|
71 |
+
}
|
72 |
+
} else {
|
73 |
+
array_push($patterns, "/'WP_CACHE',\s*true/");
|
74 |
+
array_push($replace, "'WP_CACHE', false");
|
75 |
+
}
|
76 |
+
if (!$_POST['cache_path']) {
|
77 |
+
array_push($patterns, "/'WPCACHEHOME',\s*'.*?'/");
|
78 |
+
array_push($replace, "'WPCACHEHOME', ''");
|
79 |
+
}
|
80 |
+
|
81 |
+
if (!is_writable("{$root_path}/wp-config.php")) {
|
82 |
+
if (file_exists("{$root_path}/wp-config.php")) {
|
83 |
+
chmod("{$root_path}/wp-config.php", 0644) ? DUPX_Log::info('File Permission Update: wp-config.php set to 0644') : DUPX_Log::info('WARNING: Unable to update file permissions and write to wp-config.php. Please visit the online FAQ for setting file permissions and work with your hosting provider or server administrator to enable this installer.php script to write to the wp-config.php file.');
|
84 |
+
} else {
|
85 |
+
DUPX_Log::info('WARNING: Unable to locate wp-config.php file. Be sure the file is present in your archive.');
|
86 |
+
}
|
87 |
+
}
|
88 |
+
|
89 |
+
$wpconfig = preg_replace($patterns, $replace, $wpconfig);
|
90 |
+
file_put_contents('wp-config.php', $wpconfig);
|
91 |
+
$wpconfig = null;
|
92 |
+
}
|
93 |
+
|
94 |
+
/**
|
95 |
+
* Updates the web server config files in Step 1
|
96 |
+
*
|
97 |
+
* @return null
|
98 |
+
*/
|
99 |
+
public static function updateStep2()
|
100 |
+
{
|
101 |
+
$config_file = '';
|
102 |
+
if (!file_exists('wp-config.php')) {
|
103 |
+
return $config_file;
|
104 |
+
}
|
105 |
+
|
106 |
+
$patterns = array("/('|\")WP_HOME.*?\)\s*;/",
|
107 |
+
"/('|\")WP_SITEURL.*?\)\s*;/",
|
108 |
+
"/('|\")DOMAIN_CURRENT_SITE.*?\)\s*;/",
|
109 |
+
"/('|\")PATH_CURRENT_SITE.*?\)\s*;/");
|
110 |
+
$replace = array("'WP_HOME', '{$_POST['url_new']}');",
|
111 |
+
"'WP_SITEURL', '{$_POST['url_new']}');",
|
112 |
+
"'DOMAIN_CURRENT_SITE', '{$mu_newDomainHost}');",
|
113 |
+
"'PATH_CURRENT_SITE', '{$mu_newUrlPath}');");
|
114 |
+
|
115 |
+
$config_file = file_get_contents('wp-config.php', true);
|
116 |
+
$config_file = preg_replace($patterns, $replace, $config_file);
|
117 |
+
file_put_contents('wp-config.php', $config_file);
|
118 |
+
|
119 |
+
return $config_file;
|
120 |
+
}
|
121 |
+
}
|
122 |
+
?>
|
installer/build/classes/util/class.db.php
ADDED
@@ -0,0 +1,194 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
// Exit if accessed directly
|
3 |
+
if (!defined('DUPLICATOR_INIT')) {
|
4 |
+
$_baseURL = "http://".strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
+
header("HTTP/1.1 301 Moved Permanently");
|
6 |
+
header("Location: $_baseURL");
|
7 |
+
exit;
|
8 |
+
}
|
9 |
+
|
10 |
+
/**
|
11 |
+
* Lightweight abstraction layer for common simple database routines
|
12 |
+
*
|
13 |
+
* Standard: PSR-2
|
14 |
+
* @link http://www.php-fig.org/psr/psr-2 Full Documentation
|
15 |
+
*
|
16 |
+
* @package SC\DUPX\DB
|
17 |
+
*
|
18 |
+
*/
|
19 |
+
class DUPX_DB
|
20 |
+
{
|
21 |
+
|
22 |
+
/**
|
23 |
+
* MySQL connection wrapper with support for port
|
24 |
+
*
|
25 |
+
* @param string $host The server host name
|
26 |
+
* @param string $username The server DB user name
|
27 |
+
* @param string $password The server DB password
|
28 |
+
* @param string $dbname The server DB name
|
29 |
+
* @param int $port The server DB port
|
30 |
+
*
|
31 |
+
* @return database connection handle
|
32 |
+
*/
|
33 |
+
public static function connect($host, $username, $password, $dbname = '', $port = null)
|
34 |
+
{
|
35 |
+
//sock connections
|
36 |
+
if ('sock' === substr($host, -4)) {
|
37 |
+
$url_parts = parse_url($host);
|
38 |
+
$dbh = @mysqli_connect('localhost', $username, $password, $dbname, null, $url_parts['path']);
|
39 |
+
} else {
|
40 |
+
$dbh = @mysqli_connect($host, $username, $password, $dbname, $port);
|
41 |
+
}
|
42 |
+
return $dbh;
|
43 |
+
}
|
44 |
+
|
45 |
+
/**
|
46 |
+
* Count the tables in a given database
|
47 |
+
*
|
48 |
+
* @param obj $dbh A valid database link handle
|
49 |
+
* @param string $dbname Database to count tables in
|
50 |
+
*
|
51 |
+
* @return int The number of tables in the database
|
52 |
+
*/
|
53 |
+
public static function countTables($dbh, $dbname)
|
54 |
+
{
|
55 |
+
$res = mysqli_query($dbh, "SELECT COUNT(*) AS count FROM information_schema.tables WHERE table_schema = '{$dbname}' ");
|
56 |
+
$row = mysqli_fetch_row($res);
|
57 |
+
return is_null($row) ? 0 : $row[0];
|
58 |
+
}
|
59 |
+
|
60 |
+
/**
|
61 |
+
* Returns the number of rows in a table
|
62 |
+
*
|
63 |
+
* @param obj $dbh A valid database link handle
|
64 |
+
* @param string $name A valid table name
|
65 |
+
*/
|
66 |
+
public static function countTableRows($dbh, $name)
|
67 |
+
{
|
68 |
+
$total = mysqli_query($dbh, "SELECT COUNT(*) FROM `$name`");
|
69 |
+
if ($total) {
|
70 |
+
$total = @mysqli_fetch_array($total);
|
71 |
+
return $total[0];
|
72 |
+
} else {
|
73 |
+
return 0;
|
74 |
+
}
|
75 |
+
}
|
76 |
+
|
77 |
+
/**
|
78 |
+
* Returns the tables for a database as an array
|
79 |
+
*
|
80 |
+
* @param obj $dbh A valid database link handle
|
81 |
+
*
|
82 |
+
* @return array A list of all table names
|
83 |
+
*/
|
84 |
+
public static function getTables($dbh)
|
85 |
+
{
|
86 |
+
$query = @mysqli_query($dbh, 'SHOW TABLES');
|
87 |
+
if ($query) {
|
88 |
+
while ($table = @mysqli_fetch_array($query)) {
|
89 |
+
$all_tables[] = $table[0];
|
90 |
+
}
|
91 |
+
if (isset($all_tables) && is_array($all_tables)) {
|
92 |
+
return $all_tables;
|
93 |
+
}
|
94 |
+
}
|
95 |
+
return array();
|
96 |
+
}
|
97 |
+
|
98 |
+
/**
|
99 |
+
* Get the requested MySQL system variable
|
100 |
+
*
|
101 |
+
* @param obj $dbh A valid database link handle
|
102 |
+
* @param string $name The database variable name to lookup
|
103 |
+
*
|
104 |
+
* @return string the server variable to query for
|
105 |
+
*/
|
106 |
+
public static function getVariable($dbh, $name)
|
107 |
+
{
|
108 |
+
$result = @mysqli_query($dbh, "SHOW VARIABLES LIKE '{$name}'");
|
109 |
+
$row = @mysqli_fetch_array($result);
|
110 |
+
@mysqli_free_result($result);
|
111 |
+
return isset($row[1]) ? $row[1] : null;
|
112 |
+
}
|
113 |
+
|
114 |
+
/**
|
115 |
+
* Gets the MySQL database version number
|
116 |
+
*
|
117 |
+
* @param obj $dbh A valid database link handle
|
118 |
+
* @param bool $full True: Gets the full version
|
119 |
+
* False: Gets only the numeric portion i.e. 5.5.6 or 10.1.2 (for MariaDB)
|
120 |
+
*
|
121 |
+
* @return false|string 0 on failure, version number on success
|
122 |
+
*/
|
123 |
+
public static function getVersion($dbh, $full = false)
|
124 |
+
{
|
125 |
+
if ($full) {
|
126 |
+
$version = self::getVariable($dbh, 'version');
|
127 |
+
} else {
|
128 |
+
$version = preg_replace('/[^0-9.].*/', '', self::getVariable($dbh, 'version'));
|
129 |
+
}
|
130 |
+
|
131 |
+
$version = is_null($version) ? null : $version;
|
132 |
+
return empty($version) ? 0 : $version;
|
133 |
+
}
|
134 |
+
|
135 |
+
/**
|
136 |
+
* Returns a more detailed string about the msyql server version
|
137 |
+
* For example on some systems the result is 5.5.5-10.1.21-MariaDB
|
138 |
+
* this format is helpful for providing the user a full overview
|
139 |
+
*
|
140 |
+
* @param conn $dbh Database connection handle
|
141 |
+
*
|
142 |
+
* @return string The full details of mysql
|
143 |
+
*/
|
144 |
+
public static function getServerInfo($dbh)
|
145 |
+
{
|
146 |
+
return mysqli_get_server_info($dbh);
|
147 |
+
}
|
148 |
+
|
149 |
+
/**
|
150 |
+
* Determine if a MySQL database supports a particular feature
|
151 |
+
*
|
152 |
+
* @param conn $dbh Database connection handle
|
153 |
+
* @param string $feature the feature to check for
|
154 |
+
* @return bool
|
155 |
+
*/
|
156 |
+
public static function hasAbility($dbh, $feature)
|
157 |
+
{
|
158 |
+
$version = self::getVersion($dbh);
|
159 |
+
|
160 |
+
switch (strtolower($feature)) {
|
161 |
+
case 'collation' :
|
162 |
+
case 'group_concat' :
|
163 |
+
case 'subqueries' :
|
164 |
+
return version_compare($version, '4.1', '>=');
|
165 |
+
case 'set_charset' :
|
166 |
+
return version_compare($version, '5.0.7', '>=');
|
167 |
+
};
|
168 |
+
return false;
|
169 |
+
}
|
170 |
+
|
171 |
+
/**
|
172 |
+
* Sets the MySQL connection's character set.
|
173 |
+
*
|
174 |
+
* @param resource $dbh The resource given by mysqli_connect
|
175 |
+
* @param string $charset The character set (optional)
|
176 |
+
* @param string $collate The collation (optional)
|
177 |
+
*/
|
178 |
+
public static function setCharset($dbh, $charset = null, $collate = null)
|
179 |
+
{
|
180 |
+
$charset = (!isset($charset) ) ? $GLOBALS['DBCHARSET_DEFAULT'] : $charset;
|
181 |
+
$collate = (!isset($collate) ) ? $GLOBALS['DBCOLLATE_DEFAULT'] : $collate;
|
182 |
+
|
183 |
+
if (self::hasAbility($dbh, 'collation') && !empty($charset)) {
|
184 |
+
if (function_exists('mysqli_set_charset') && self::hasAbility($dbh, 'set_charset')) {
|
185 |
+
return mysqli_set_charset($dbh, $charset);
|
186 |
+
} else {
|
187 |
+
$sql = " SET NAMES {$charset}";
|
188 |
+
if (!empty($collate)) $sql .= " COLLATE {$collate}";
|
189 |
+
return mysqli_query($dbh, $sql);
|
190 |
+
}
|
191 |
+
}
|
192 |
+
}
|
193 |
+
}
|
194 |
+
?>
|
installer/build/classes/util/class.utils.php
ADDED
@@ -0,0 +1,312 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
// Exit if accessed directly
|
3 |
+
if (!defined('DUPLICATOR_INIT')) {
|
4 |
+
$_baseURL = "http://".strlen($_SERVER['SERVER_NAME']) ? $_SERVER['SERVER_NAME'] : $_SERVER['HTTP_HOST'];
|
5 |
+
header("HTTP/1.1 301 Moved Permanently");
|
6 |
+
header("Location: $_baseURL");
|
7 |
+
exit;
|
8 |
+
}
|
9 |
+
|
10 |
+
/**
|
11 |
+
* Various Static Utility methods for working with the installer
|
12 |
+
*
|
13 |
+
* @package SC\DUPX\Util
|
14 |
+
*
|
15 |
+
*/
|
16 |
+
class DUPX_Util
|
17 |
+
{
|
18 |
+
|
19 |
+
/**
|
20 |
+
* Adds a slash to the end of a file or directory path
|
21 |
+
*
|
22 |
+
* @param string $path A path
|
23 |
+
*
|
24 |
+
* @return string The orginal $path with a with '/'.
|
25 |
+
*/
|
26 |
+
public static function add_slash($path)
|
27 |
+
{
|
28 |
+
$last_char = substr($path, strlen($path) - 1, 1);
|
29 |
+
if ($last_char != '/') {
|
30 |
+
$path .= '/';
|
31 |
+
}
|
32 |
+
return $path;
|
33 |
+
}
|
34 |
+
|
35 |
+
/**
|
36 |
+
* A safe method used to copy larger files
|
37 |
+
*
|
38 |
+
* @param string $source The path to the file being copied
|
39 |
+
* @param string $destination The path to the file being made
|
40 |
+
*/
|
41 |
+
public static function copy_file($source, $destination)
|
42 |
+
{
|
43 |
+
$sp = fopen($source, 'r');
|
44 |
+
$op = fopen($destination, 'w');
|
45 |
+
|
46 |
+
while (!feof($sp)) {
|
47 |
+
$buffer = fread($sp, 512); // use a buffer of 512 bytes
|
48 |
+
fwrite($op, $buffer);
|
49 |
+
}
|
50 |
+
// close handles
|
51 |
+
fclose($op);
|
52 |
+
fclose($sp);
|
53 |
+
}
|
54 |
+
|
55 |
+
/**
|
56 |
+
* Return a string with the elapsed time
|
57 |
+
*
|
58 |
+
* @see get_microtime()
|
59 |
+
*
|
60 |
+
* @param mixed number $end The final time in the sequence to measure
|
61 |
+
* @param mixed number $start The start time in the sequence to measure
|
62 |
+
*
|
63 |
+
* @return string The time elapsed from $start to $end
|
64 |
+
*/
|
65 |
+
public static function elapsed_time($end, $start)
|
66 |
+
{
|
67 |
+
return sprintf("%.4f sec.", abs($end - $start));
|
68 |
+
}
|
69 |
+
|
70 |
+
/**
|
71 |
+
* Convert all applicable characters to HTML entities
|
72 |
+
*
|
73 |
+
* @param string $string String that needs conversion
|
74 |
+
* @param bool $echo Echo or return as a variable
|
75 |
+
*
|
76 |
+
* @return string Escaped string.
|
77 |
+
*/
|
78 |
+
public static function esc_html_attr($string = '', $echo = false)
|
79 |
+
{
|
80 |
+
$output = htmlentities($string, ENT_QUOTES, 'UTF-8');
|
81 |
+
if ($echo) {
|
82 |
+
echo $output;
|
83 |
+
} else {
|
84 |
+
return $output;
|
85 |
+
}
|
86 |
+
}
|
87 |
+
|
88 |
+
/**
|
89 |
+
* Returns 256 spaces
|
90 |
+
*
|
91 |
+
* PHP_SAPI for fcgi requires a data flush of at least 256
|
92 |
+
* bytes every 40 seconds or else it forces a script hault
|
93 |
+
*
|
94 |
+
* @return string A series of 256 spaces ' '
|
95 |
+
*/
|
96 |
+
public static function fcgi_flush()
|
97 |
+
{
|
98 |
+
echo(str_repeat(' ', 256));
|
99 |
+
@flush();
|
100 |
+
}
|
101 |
+
|
102 |
+
/**
|
103 |
+
* Get current microtime as a float. Method is used for simple profiling
|
104 |
+
*
|
105 |
+
* @see elapsed_time
|
106 |
+
*
|
107 |
+
* @return string A float in the form "msec sec", where sec is the number of seconds since the Unix epoch
|
108 |
+
*/
|
109 |
+
public static function get_microtime()
|
110 |
+
{
|
111 |
+
return microtime(true);
|
112 |
+
}
|
113 |
+
|
114 |
+
/**
|
115 |
+
* Returns the active plugins for the WordPress website in the package
|
116 |
+
*
|
117 |
+
* @param obj $dbh A database connection handle
|
118 |
+
* @return array $list A list of active plugins
|
119 |
+
*/
|
120 |
+
public static function get_active_plugins($dbh)
|
121 |
+
{
|
122 |
+
$query = @mysqli_query($dbh, "SELECT option_value FROM `{$GLOBALS['FW_TABLEPREFIX']}options` WHERE option_name = 'active_plugins' ");
|
123 |
+
if ($query) {
|
124 |
+
$row = @mysqli_fetch_array($query);
|
125 |
+
$all_plugins = unserialize($row[0]);
|
126 |
+
if (is_array($all_plugins)) {
|
127 |
+
return $all_plugins;
|
128 |
+
}
|
129 |
+
}
|
130 |
+
return array();
|
131 |
+
}
|
132 |
+
|
133 |
+
/**
|
134 |
+
* Returns an array of zip files found in the current executing directory
|
135 |
+
*
|
136 |
+
* @return array of zip files
|
137 |
+
*/
|
138 |
+
public static function get_zip_files()
|
139 |
+
{
|
140 |
+
$files = array();
|
141 |
+
foreach (glob("*.zip") as $name) {
|
142 |
+
if (file_exists($name)) {
|
143 |
+
$files[] = $name;
|
144 |
+
}
|
145 |
+
}
|
146 |
+
|
147 |
+
if (count($files) > 0) {
|
148 |
+
return $files;
|
149 |
+
}
|
150 |
+
|
151 |
+
//FALL BACK: Windows XP has bug with glob,
|
152 |
+
//add secondary check for PHP lameness
|
153 |
+
if ($dh = opendir('.')) {
|
154 |
+
while (false !== ($name = readdir($dh))) {
|
155 |
+
$ext = substr($name, strrpos($name, '.') + 1);
|
156 |
+
if (in_array($ext, array("zip"))) {
|
157 |
+
$files[] = $name;
|
158 |
+
}
|
159 |
+
}
|
160 |
+
closedir($dh);
|
161 |
+
}
|
162 |
+
|
163 |
+
return $files;
|
164 |
+
}
|
165 |
+
|
166 |
+
/**
|
167 |
+
* Check to see if the internet is accessable
|
168 |
+
*
|
169 |
+
* Note: fsocketopen on windows doesn't seem to honor $timeout setting.
|
170 |
+
*
|
171 |
+
* @param string $url A url e.g without prefix "ajax.googleapis.com"
|
172 |
+
* @param string $port A valid port number
|
173 |
+
*
|
174 |
+
* @return bool
|
175 |
+
*/
|
176 |
+
public static function is_url_active($url, $port, $timeout = 5)
|
177 |
+
{
|
178 |
+
if (function_exists('fsockopen')) {
|
179 |
+
@ini_set("default_socket_timeout", 5);
|
180 |
+
$port = isset($port) && is_integer($port) ? $port : 80;
|
181 |
+
$connected = @fsockopen($url, $port, $errno, $errstr, $timeout); //website and port
|
182 |
+
if ($connected) {
|
183 |
+
@fclose($connected);
|
184 |
+
return true;
|
185 |
+
}
|
186 |
+
return false;
|
187 |
+
} else {
|
188 |
+
return false;
|
189 |
+
}
|
190 |
+
}
|
191 |
+
|
192 |
+
/**
|
193 |
+
* Does a string have non ascii characters
|
194 |
+
*
|
195 |
+
* @param string $string Any string blob
|
196 |
+
*
|
197 |
+
* @return bool Returns true if any non ascii character is found in the blob
|
198 |
+
*
|
199 |
+
*/
|
200 |
+
public static function is_non_ascii($string)
|
201 |
+
{
|
202 |
+
return preg_match('/[^\x20-\x7f]/', $string);
|
203 |
+
}
|
204 |
+
|
205 |
+
|
206 |
+
/**
|
207 |
+
* The characters that are special in the replacement value of preg_replace are not the
|
208 |
+
* same characters that are special in the pattern. Allows for '$' to be safely passed.
|
209 |
+
*
|
210 |
+
* @param string $str The string to replace on
|
211 |
+
*/
|
212 |
+
public static function preg_replacement_quote($str)
|
213 |
+
{
|
214 |
+
return preg_replace('/(\$|\\\\)(?=\d)/', '\\\\\1', $str);
|
215 |
+
}
|
216 |
+
|
217 |
+
/**
|
218 |
+
* Display human readable byte sizes
|
219 |
+
*
|
220 |
+
* @param string $size The size in bytes
|
221 |
+
*
|
222 |
+
* @return string Human readable bytes such as 50MB, 1GB
|
223 |
+
*/
|
224 |
+
public static function readable_bytesize($size)
|
225 |
+
{
|
226 |
+
try {
|
227 |
+
$units = array('B', 'KB', 'MB', 'GB', 'TB');
|
228 |
+
for ($i = 0; $size >= 1024 && $i < 4; $i++)
|
229 |
+
$size /= 1024;
|
230 |
+
return round($size, 2).$units[$i];
|
231 |
+
} catch (Exception $e) {
|
232 |
+
return "n/a";
|
233 |
+
}
|
234 |
+
}
|
235 |
+
|
236 |
+
/**
|
237 |
+
* Converts shorthand memory notation value to bytes
|
238 |
+
*
|
239 |
+
* @param $val Memory size shorthand notation string such as 10M, 1G
|
240 |
+
*
|
241 |
+
* @returns int The byte representation of the shortand $val
|
242 |
+
*/
|
243 |
+
public static function return_bytes($val)
|
244 |
+
{
|
245 |
+
$val = trim($val);
|
246 |
+
$last = strtolower($val[strlen($val) - 1]);
|
247 |
+
switch ($last) {
|
248 |
+
// The 'G' modifier is available since PHP 5.1.0
|
249 |
+
case 'g':
|
250 |
+
$val *= 1024;
|
251 |
+
case 'm':
|
252 |
+
$val *= 1024;
|
253 |
+
case 'k':
|
254 |
+
$val *= 1024;
|
255 |
+
break;
|
256 |
+
default :
|
257 |
+
$val = null;
|
258 |
+
}
|
259 |
+
return $val;
|
260 |
+
}
|
261 |
+
|
262 |
+
/**
|
263 |
+
* Makes path safe for any OS for PHP
|
264 |
+
*
|
265 |
+
* Paths should ALWAYS READ be "/"
|
266 |
+
* uni: /home/path/file.xt
|
267 |
+
* win: D:/home/path/file.txt
|
268 |
+
*
|
269 |
+
* @param string $path The path to make safe
|
270 |
+
*
|
271 |
+
* @return string The orginal $path with a with all slashes facing '/'.
|
272 |
+
*/
|
273 |
+
public static function set_safe_path($path)
|
274 |
+
{
|
275 |
+
return str_replace("\\", "/", $path);
|
276 |
+
}
|
277 |
+
|
278 |
+
/**
|
279 |
+
* Looks for a list of strings in a string and returns each list item that is found
|
280 |
+
*
|
281 |
+
* @param array $list An array of strings to search for
|
282 |
+
* @param string $haystack The string blob to search through
|
283 |
+
*
|
284 |
+
* @return array An array of strings from the $list array fround in the $haystack
|
285 |
+
*/
|
286 |
+
public static function search_list_values($list, $haystack)
|
287 |
+
{
|
288 |
+
$found = array();
|
289 |
+
foreach ($list as $var) {
|
290 |
+
if (strstr($haystack, $var) !== false) {
|
291 |
+
array_push($found, $var);
|
292 |
+
}
|
293 |
+
}
|
294 |
+
return $found;
|
295 |
+
}
|
296 |
+
|
297 |
+
/**
|
298 |
+
* Makes path unsafe for any OS for PHP used primarly to show default
|
299 |
+
* Winodws OS path standard
|
300 |
+
*
|
301 |
+
* @param string $path The path to make unsafe
|
302 |
+
*
|
303 |
+
* @return string The orginal $path with a with all slashes facing '\'.
|
304 |
+
*/
|
305 |
+
public static function unset_safe_path($path)
|
306 |
+
{
|
307 |
+
return str_replace("/", "\\", $path);
|
308 |
+
}
|
309 |
+
|
310 |
+
|
311 |
+
}
|
312 |
+
?>
|
installer/build/main.installer.php
CHANGED
@@ -183,15 +183,18 @@ if ($_POST['action_step'] == 1) {
|
|
183 |
}
|
184 |
?>
|
185 |
|
|
|
|
|
|
|
|
|
186 |
@@CLASS.LOGGING.PHP@@
|
187 |
|
188 |
-
@@CLASS.
|
189 |
|
190 |
@@CLASS.CONF.WP.PHP@@
|
191 |
|
192 |
@@CLASS.CONF.SRV.PHP@@
|
193 |
|
194 |
-
@@CLASS.SERIALIZER.PHP@@
|
195 |
|
196 |
<?php
|
197 |
if (isset($_POST['action_ajax'])) {
|
183 |
}
|
184 |
?>
|
185 |
|
186 |
+
@@CLASS.UTILS.PHP@@
|
187 |
+
|
188 |
+
@@CLASS.DB.PHP@@
|
189 |
+
|
190 |
@@CLASS.LOGGING.PHP@@
|
191 |
|
192 |
+
@@CLASS.ENGINE.PHP@@
|
193 |
|
194 |
@@CLASS.CONF.WP.PHP@@
|
195 |
|
196 |
@@CLASS.CONF.SRV.PHP@@
|
197 |
|
|
|
198 |
|
199 |
<?php
|
200 |
if (isset($_POST['action_ajax'])) {
|
installer/build/view.step2.php
CHANGED
@@ -6,9 +6,9 @@
|
|
6 |
header("Location: $_baseURL");
|
7 |
exit;
|
8 |
}
|
9 |
-
$dbh =
|
10 |
|
11 |
-
$all_tables =
|
12 |
$active_plugins = DUPX_Util::get_active_plugins($dbh);
|
13 |
|
14 |
|
6 |
header("Location: $_baseURL");
|
7 |
exit;
|
8 |
}
|
9 |
+
$dbh = DUPX_DB::connect($_POST['dbhost'], $_POST['dbuser'], $_POST['dbpass'], $_POST['dbname'], $_POST['dbport']);
|
10 |
|
11 |
+
$all_tables = DUPX_DB::getTables($dbh);
|
12 |
$active_plugins = DUPX_Util::get_active_plugins($dbh);
|
13 |
|
14 |
|
readme.txt
CHANGED
@@ -4,7 +4,7 @@ Donate link: www.lifeinthegrid.com/partner
|
|
4 |
Tags: backup, restore, move, migrate, localhost, synchronize, duplicate, clone, automate, niche site
|
5 |
Requires at least: 4.0
|
6 |
Tested up to: 4.7
|
7 |
-
Stable tag: 1.1.
|
8 |
License: GPLv2
|
9 |
|
10 |
Duplicate, clone, backup, move and transfer an entire site from one location to another.
|
4 |
Tags: backup, restore, move, migrate, localhost, synchronize, duplicate, clone, automate, niche site
|
5 |
Requires at least: 4.0
|
6 |
Tested up to: 4.7
|
7 |
+
Stable tag: 1.1.34
|
8 |
License: GPLv2
|
9 |
|
10 |
Duplicate, clone, backup, move and transfer an entire site from one location to another.
|
uninstall.php
CHANGED
@@ -8,8 +8,8 @@ if ( ! defined( 'WP_UNINSTALL_PLUGIN' ) ) {
|
|
8 |
exit;
|
9 |
}
|
10 |
require_once 'define.php';
|
11 |
-
require_once 'classes/settings.php';
|
12 |
-
require_once 'classes/
|
13 |
|
14 |
global $wpdb;
|
15 |
$DUP_Settings = new DUP_Settings();
|
@@ -22,8 +22,8 @@ delete_option('duplicator_version_plugin');
|
|
22 |
//Remvoe entire wp-snapshots directory
|
23 |
if (DUP_Settings::Get('uninstall_files')) {
|
24 |
|
25 |
-
$ssdir = DUP_Util::
|
26 |
-
$ssdir_tmp = DUP_Util::
|
27 |
|
28 |
//Sanity check for strange setup
|
29 |
$check = glob("{$ssdir}/wp-config.php");
|
8 |
exit;
|
9 |
}
|
10 |
require_once 'define.php';
|
11 |
+
require_once 'classes/class.settings.php';
|
12 |
+
require_once 'classes/utilities/class.util.php';
|
13 |
|
14 |
global $wpdb;
|
15 |
$DUP_Settings = new DUP_Settings();
|
22 |
//Remvoe entire wp-snapshots directory
|
23 |
if (DUP_Settings::Get('uninstall_files')) {
|
24 |
|
25 |
+
$ssdir = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH);
|
26 |
+
$ssdir_tmp = DUP_Util::safePath(DUPLICATOR_SSDIR_PATH_TMP);
|
27 |
|
28 |
//Sanity check for strange setup
|
29 |
$check = glob("{$ssdir}/wp-config.php");
|
views/help/about.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<?php
|
2 |
-
DUP_Util::
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
1 |
<?php
|
2 |
+
DUP_Util::hasCapability('read');
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
views/help/gopro.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<?php
|
2 |
-
DUP_Util::
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
1 |
<?php
|
2 |
+
DUP_Util::hasCapability('read');
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
views/help/help.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<?php
|
2 |
-
DUP_Util::
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
1 |
<?php
|
2 |
+
DUP_Util::hasCapability('read');
|
3 |
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
views/help/perks.php
DELETED
@@ -1,183 +0,0 @@
|
|
1 |
-
<?php
|
2 |
-
DUP_Util::CheckPermissions('read');
|
3 |
-
|
4 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
5 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
6 |
-
$_GET['a'] = isset($_GET['a']) ? $_GET['a'] : -1;
|
7 |
-
|
8 |
-
?>
|
9 |
-
<style>
|
10 |
-
div.dup-perks-all {font-size:13px; line-height:20px}
|
11 |
-
div.dup-perks-hlp-area {width:315px; height:160px; float:left; border:1px solid #dfdfdf; border-radius:8px; margin:20px 30px 10px 40px;box-shadow: 0 8px 6px -6px #ccc; background: #fff}
|
12 |
-
div.dup-perks-hlp-hdrs {
|
13 |
-
font-weight:bold; font-size:17px; height: 25px; padding:10px 0 5px 0; text-align: center;
|
14 |
-
background: #eeeeee;
|
15 |
-
background: -moz-linear-gradient(top, #eeeeee 0%, #cccccc 100%);
|
16 |
-
background: -webkit-linear-gradient(top, #eeeeee 0%,#cccccc 100%);
|
17 |
-
background: linear-gradient(to bottom, #eeeeee 0%,#cccccc 100%);
|
18 |
-
filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#eeeeee', endColorstr='#cccccc',GradientType=0 );
|
19 |
-
}
|
20 |
-
div.dup-perks-txt{padding:10px 4px 4px 4px; text-align:center; font-size:16px; font-weight: bold}
|
21 |
-
div.dup-active-item {font-weight: bold; font-style: italic}
|
22 |
-
div.dup-active-item div.dup-perks-hlp-hdrs{ color:#fff; border-top-right-radius: 8px; border-top-left-radius: 8px;
|
23 |
-
background: #4c4c4c;
|
24 |
-
background: -moz-linear-gradient(top, #4c4c4c 0%, #595959 12%, #666666 25%, #474747 39%, #2c2c2c 50%, #000000 51%, #111111 60%, #2b2b2b 76%, #1c1c1c 91%, #131313 100%);
|
25 |
-
background: -webkit-linear-gradient(top, #4c4c4c 0%,#595959 12%,#666666 25%,#474747 39%,#2c2c2c 50%,#000000 51%,#111111 60%,#2b2b2b 76%,#1c1c1c 91%,#131313 100%);
|
26 |
-
background: linear-gradient(to bottom, #4c4c4c 0%,#595959 12%,#666666 25%,#474747 39%,#2c2c2c 50%,#000000 51%,#111111 60%,#2b2b2b 76%,#1c1c1c 91%,#131313 100%);
|
27 |
-
filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#4c4c4c', endColorstr='#131313',GradientType=0 );
|
28 |
-
}
|
29 |
-
</style>
|
30 |
-
|
31 |
-
<div class="wrap dup-wrap dup-perks-all">
|
32 |
-
|
33 |
-
<?php duplicator_header(__("Perks", 'duplicator')) ?>
|
34 |
-
<hr size="1" />
|
35 |
-
|
36 |
-
<div style="width:800px; margin:auto; margin-top:10px;">
|
37 |
-
<div style="text-align: center; font-size:18px; line-height: 24px">
|
38 |
-
<b><?php _e("Get Great Deals and Amazing Products!", 'duplicator'); ?></b><br/>
|
39 |
-
<i><?php _e("While helping to support Duplicator...", 'duplicator'); ?></i>
|
40 |
-
</div>
|
41 |
-
|
42 |
-
<!-- ==========================================================
|
43 |
-
ROW 1 -->
|
44 |
-
<!-- BLUEHOST -->
|
45 |
-
<div class="dup-perks-hlp-area" id="bluehost">
|
46 |
-
<div class="dup-perks-hlp-hdrs">
|
47 |
-
<i class="fa fa-th fa-1x"></i> <?php _e('Bluehost', 'duplicator') ?>
|
48 |
-
</div>
|
49 |
-
<div class="dup-perks-txt">
|
50 |
-
<a href="https://snapcreek.com/visit/bluehost" target="_blank">
|
51 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_bluehost.png" style="padding:10px 0 15px 0" /><br/>
|
52 |
-
<?php _e('50% Off Normal Price!', 'duplicator') ?>
|
53 |
-
</a>
|
54 |
-
</div>
|
55 |
-
</div>
|
56 |
-
|
57 |
-
<!-- INMOTION -->
|
58 |
-
<div class="dup-perks-hlp-area" id="inmotion">
|
59 |
-
<div class="dup-perks-hlp-hdrs">
|
60 |
-
<i class="fa fa-cube fa-1x"></i> <?php _e('InMotion', 'duplicator') ?>
|
61 |
-
</div>
|
62 |
-
<div class="dup-perks-txt">
|
63 |
-
<a href="https://snapcreek.com/visit/inmotion" target="_blank">
|
64 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_inmotion.png" style="padding:10px 0 5px 0" /><br/>
|
65 |
-
<?php _e('Up to 25% Off - With FREE SSDs', 'duplicator') ?>
|
66 |
-
</a>
|
67 |
-
</div>
|
68 |
-
</div>
|
69 |
-
|
70 |
-
<!-- ==========================================================
|
71 |
-
ROW 2 -->
|
72 |
-
<!-- ELEGANT THEMES -->
|
73 |
-
<div class="dup-perks-hlp-area" id="ethemes">
|
74 |
-
<div class="dup-perks-hlp-hdrs">
|
75 |
-
<i class="fa fa-asterisk fa-1x"></i> <?php _e('Elegant Themes', 'duplicator') ?>
|
76 |
-
</div>
|
77 |
-
<div class="dup-perks-txt">
|
78 |
-
<a href="https://snapcreek.com/visit/elegantthemes" target="_blank">
|
79 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_ethemes.png" style="padding:0 0 5px 0" /><br/>
|
80 |
-
<?php _e('10% Off Lifetime Access!', 'duplicator') ?>
|
81 |
-
</a>
|
82 |
-
</div>
|
83 |
-
</div>
|
84 |
-
|
85 |
-
<!-- MAX CDN -->
|
86 |
-
<div class="dup-perks-hlp-area" id="maxcdn">
|
87 |
-
<div class="dup-perks-hlp-hdrs">
|
88 |
-
<i class="fa fa-maxcdn fa-1x"></i> <?php _e('MaxCDN', 'duplicator') ?>
|
89 |
-
</div>
|
90 |
-
<div class="dup-perks-txt">
|
91 |
-
<a href="https://snapcreek.com/visit/maxcdn" target="_blank">
|
92 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_maxcdn.png" style="padding:5px 0 10px 0" /><br/>
|
93 |
-
<?php _e('Get 25% Off With Duplicator', 'duplicator') ?>
|
94 |
-
</a>
|
95 |
-
</div>
|
96 |
-
</div>
|
97 |
-
|
98 |
-
|
99 |
-
<!-- ==========================================================
|
100 |
-
ROW 3 -->
|
101 |
-
<!-- MANAGE WP -->
|
102 |
-
<div class="dup-perks-hlp-area" id="managewp">
|
103 |
-
<div class="dup-perks-hlp-hdrs">
|
104 |
-
<i class="fa fa-sitemap fa-1x"></i> <?php _e('ManageWP', 'duplicator') ?>
|
105 |
-
</div>
|
106 |
-
<div class="dup-perks-txt">
|
107 |
-
<a href="https://snapcreek.com/visit/managewp" target="_blank">
|
108 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_managewp.png" style="padding:5px 0 10px 0" /><br/>
|
109 |
-
<?php _e('Exclusive 10% Off Deal!', 'duplicator') ?>
|
110 |
-
</a>
|
111 |
-
</div>
|
112 |
-
</div>
|
113 |
-
|
114 |
-
<!-- DUPLICATOR PRO -->
|
115 |
-
<div class="dup-perks-hlp-area" id="dpro">
|
116 |
-
<div class="dup-perks-hlp-hdrs">
|
117 |
-
<i class="fa fa-share-alt fa-1x"></i> <?php _e('Duplicator Pro', 'duplicator') ?>
|
118 |
-
</div>
|
119 |
-
<div class="dup-perks-txt">
|
120 |
-
<a href="https://snapcreek.com/visit/managewp" target="_blank">
|
121 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/logo-dpro-300x50-nosnap.png" style="padding:10px 0 10px 0; width:250px" /><br/>
|
122 |
-
<?php _e('Go Professional!', 'duplicator') ?>
|
123 |
-
</a>
|
124 |
-
</div>
|
125 |
-
</div>
|
126 |
-
|
127 |
-
<!-- ==========================================================
|
128 |
-
ROW 4 -->
|
129 |
-
<!-- NINJA FORMS
|
130 |
-
<div class="dup-perks-hlp-area">
|
131 |
-
<div class="dup-perks-hlp-hdrs">
|
132 |
-
<i class="fa fa-check-square-o fa-1x"></i> <?php _e('Ninja Forms', 'duplicator') ?>
|
133 |
-
</div>
|
134 |
-
<div class="dup-perks-txt">
|
135 |
-
<a href="https://snapcreek.com/visit/ninjaforms" target="_blank">
|
136 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_ninjaforms.png" style="padding:5px 0 10px 0; " /><br/>
|
137 |
-
<?php _e('Power Manage It All!', 'duplicator') ?>
|
138 |
-
</a>
|
139 |
-
</div>
|
140 |
-
</div> -->
|
141 |
-
|
142 |
-
<!-- OPTIN MONSTER
|
143 |
-
<div class="dup-perks-hlp-area">
|
144 |
-
<div class="dup-perks-hlp-hdrs">
|
145 |
-
<i class="fa fa-envelope fa-1x"></i> <?php _e('OptinMonster', 'duplicator') ?>
|
146 |
-
</div>
|
147 |
-
<div class="dup-perks-txt">
|
148 |
-
<a href="https://snapcreek.com/visit/managewp" target="_blank">
|
149 |
-
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/perks_optinmonster.png" style="padding:5px 0 10px 0" /><br/>
|
150 |
-
<?php _e('Power Manage It All!', 'duplicator') ?>
|
151 |
-
</a>
|
152 |
-
</div>
|
153 |
-
</div> -->
|
154 |
-
|
155 |
-
<br style="clear:both"/>
|
156 |
-
|
157 |
-
<div style="margin:60px 20px; text-align: center"><small>Some promotions may change</small></div>
|
158 |
-
|
159 |
-
</div>
|
160 |
-
</div>
|
161 |
-
<br/><br/><br/><br/>
|
162 |
-
|
163 |
-
<script type="text/javascript">
|
164 |
-
jQuery(document).ready(function($)
|
165 |
-
{
|
166 |
-
//ATTACHED EVENTS
|
167 |
-
jQuery('#dup-perks-kb-lnks').change(function() {
|
168 |
-
if (jQuery(this).val() != "null")
|
169 |
-
window.open(jQuery(this).val())
|
170 |
-
});
|
171 |
-
|
172 |
-
<?php
|
173 |
-
switch ($_GET['a'])
|
174 |
-
{
|
175 |
-
case "0" : echo "$('#bluehost').addClass('dup-active-item');"; break;
|
176 |
-
case "1" : echo "$('#inmotion').addClass('dup-active-item');"; break;
|
177 |
-
case "2" : echo "$('#ethemes').addClass('dup-active-item');"; break;
|
178 |
-
case "3" : echo "$('#managewp').addClass('dup-active-item');"; break;
|
179 |
-
case "4" : echo "$('#maxcdn').addClass('dup-active-item');"; break;
|
180 |
-
}
|
181 |
-
?>
|
182 |
-
});
|
183 |
-
</script>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
views/packages/controller.php
CHANGED
@@ -1,6 +1,6 @@
|
|
1 |
<?php
|
2 |
|
3 |
-
DUP_Util::
|
4 |
|
5 |
global $wpdb;
|
6 |
|
1 |
<?php
|
2 |
|
3 |
+
DUP_Util::hasCapability('export');
|
4 |
|
5 |
global $wpdb;
|
6 |
|
views/packages/details/controller.php
CHANGED
@@ -1,12 +1,12 @@
|
|
1 |
<?php
|
2 |
-
DUP_Util::
|
3 |
global $wpdb;
|
4 |
|
5 |
//COMMON HEADER DISPLAY
|
6 |
$current_tab = isset($_REQUEST['tab']) ? esc_html($_REQUEST['tab']) : 'detail';
|
7 |
$package_id = isset($_REQUEST["id"]) ? $_REQUEST["id"] : 0;
|
8 |
|
9 |
-
$package = DUP_Package::
|
10 |
$err_found = ($package == null || $package->Status < 100);
|
11 |
$link_log = "{$package->StoreURL}{$package->NameHash}.log";
|
12 |
$err_link_log = "<a target='_blank' href='{$link_log}' >" . __('package log', 'duplicator') . '</a>';
|
1 |
<?php
|
2 |
+
DUP_Util::hasCapability('manage_options');
|
3 |
global $wpdb;
|
4 |
|
5 |
//COMMON HEADER DISPLAY
|
6 |
$current_tab = isset($_REQUEST['tab']) ? esc_html($_REQUEST['tab']) : 'detail';
|
7 |
$package_id = isset($_REQUEST["id"]) ? $_REQUEST["id"] : 0;
|
8 |
|
9 |
+
$package = DUP_Package::getByID($package_id);
|
10 |
$err_found = ($package == null || $package->Status < 100);
|
11 |
$link_log = "{$package->StoreURL}{$package->NameHash}.log";
|
12 |
$err_link_log = "<a target='_blank' href='{$link_log}' >" . __('package log', 'duplicator') . '</a>';
|
views/packages/details/detail.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<?php
|
2 |
-
$view_state =
|
3 |
$ui_css_general = (isset($view_state['dup-package-dtl-general-panel']) && $view_state['dup-package-dtl-general-panel']) ? 'display:block' : 'display:none';
|
4 |
$ui_css_storage = (isset($view_state['dup-package-dtl-storage-panel']) && $view_state['dup-package-dtl-storage-panel']) ? 'display:block' : 'display:none';
|
5 |
$ui_css_archive = (isset($view_state['dup-package-dtl-archive-panel']) && $view_state['dup-package-dtl-archive-panel']) ? 'display:block' : 'display:none';
|
@@ -12,7 +12,7 @@ $link_log = "{$package->StoreURL}{$package->NameHash}.log";
|
|
12 |
$link_scan = "{$package->StoreURL}{$package->NameHash}_scan.json";
|
13 |
|
14 |
$debug_on = DUP_Settings::Get('package_debug');
|
15 |
-
$mysqldump_on = DUP_Settings::Get('package_mysqldump') &&
|
16 |
$mysqlcompat_on = isset($Package->Database->Compatible) && strlen($Package->Database->Compatible);
|
17 |
$mysqlcompat_on = ($mysqldump_on && $mysqlcompat_on) ? true : false;
|
18 |
$dbbuild_mode = ($mysqldump_on) ? 'mysqldump (fast)' : 'PHP (slow)';
|
@@ -84,8 +84,10 @@ GENERAL -->
|
|
84 |
<a href="javascript:void(0);" onclick="jQuery('#dup-version-info').toggle()"><?php echo $package->Version ?></a>
|
85 |
<div id="dup-version-info">
|
86 |
<b><?php _e('WordPress', 'duplicator') ?>:</b> <?php echo strlen($package->VersionWP) ? $package->VersionWP : __('- unknown -', 'duplicator') ?><br/>
|
87 |
-
<b><?php _e('Mysql', 'duplicator') ?>:</b> <?php echo strlen($package->VersionDB) ? $package->VersionDB : __('- unknown -', 'duplicator') ?><br/>
|
88 |
<b><?php _e('PHP', 'duplicator') ?>:</b> <?php echo strlen($package->VersionPHP) ? $package->VersionPHP : __('- unknown -', 'duplicator') ?><br/>
|
|
|
|
|
|
|
89 |
</div>
|
90 |
</td>
|
91 |
</tr>
|
@@ -109,7 +111,7 @@ GENERAL -->
|
|
109 |
|
110 |
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_installer; ?>', this);return false;"><i class="fa fa-bolt"></i> Installer</button>
|
111 |
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_archive; ?>', this);return false;"><i class="fa fa-file-archive-o"></i> Archive - <?php echo $package->ZipSize ?></button>
|
112 |
-
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_sql; ?>', this);return false;"><i class="fa fa-table"></i> SQL - <?php echo DUP_Util::
|
113 |
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_log; ?>', this);return false;"><i class="fa fa-list-alt"></i> Log </button>
|
114 |
<button class="button" onclick="Duplicator.Pack.ShowLinksDialog(<?php echo "'{$link_sql}','{$link_archive}','{$link_installer}','{$link_log}'" ;?>);" class="thickbox"><i class="fa fa-lock"></i> <?php _e("Share", 'duplicator')?></button>
|
115 |
<?php else: ?>
|
1 |
<?php
|
2 |
+
$view_state = DUP_UI_ViewState::getArray();
|
3 |
$ui_css_general = (isset($view_state['dup-package-dtl-general-panel']) && $view_state['dup-package-dtl-general-panel']) ? 'display:block' : 'display:none';
|
4 |
$ui_css_storage = (isset($view_state['dup-package-dtl-storage-panel']) && $view_state['dup-package-dtl-storage-panel']) ? 'display:block' : 'display:none';
|
5 |
$ui_css_archive = (isset($view_state['dup-package-dtl-archive-panel']) && $view_state['dup-package-dtl-archive-panel']) ? 'display:block' : 'display:none';
|
12 |
$link_scan = "{$package->StoreURL}{$package->NameHash}_scan.json";
|
13 |
|
14 |
$debug_on = DUP_Settings::Get('package_debug');
|
15 |
+
$mysqldump_on = DUP_Settings::Get('package_mysqldump') && DUP_DB::getMySqlDumpPath();
|
16 |
$mysqlcompat_on = isset($Package->Database->Compatible) && strlen($Package->Database->Compatible);
|
17 |
$mysqlcompat_on = ($mysqldump_on && $mysqlcompat_on) ? true : false;
|
18 |
$dbbuild_mode = ($mysqldump_on) ? 'mysqldump (fast)' : 'PHP (slow)';
|
84 |
<a href="javascript:void(0);" onclick="jQuery('#dup-version-info').toggle()"><?php echo $package->Version ?></a>
|
85 |
<div id="dup-version-info">
|
86 |
<b><?php _e('WordPress', 'duplicator') ?>:</b> <?php echo strlen($package->VersionWP) ? $package->VersionWP : __('- unknown -', 'duplicator') ?><br/>
|
|
|
87 |
<b><?php _e('PHP', 'duplicator') ?>:</b> <?php echo strlen($package->VersionPHP) ? $package->VersionPHP : __('- unknown -', 'duplicator') ?><br/>
|
88 |
+
<b><?php _e('Mysql', 'duplicator') ?>:</b>
|
89 |
+
<?php echo strlen($package->VersionDB) ? $package->VersionDB : __('- unknown -', 'duplicator') ?> |
|
90 |
+
<?php echo strlen($package->Database->Comments) ? $package->Database->Comments : __('- unknown -', 'duplicator') ?><br/>
|
91 |
</div>
|
92 |
</td>
|
93 |
</tr>
|
111 |
|
112 |
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_installer; ?>', this);return false;"><i class="fa fa-bolt"></i> Installer</button>
|
113 |
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_archive; ?>', this);return false;"><i class="fa fa-file-archive-o"></i> Archive - <?php echo $package->ZipSize ?></button>
|
114 |
+
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_sql; ?>', this);return false;"><i class="fa fa-table"></i> SQL - <?php echo DUP_Util::byteSize($package->Database->Size) ?></button>
|
115 |
<button class="button" onclick="Duplicator.Pack.DownloadFile('<?php echo $link_log; ?>', this);return false;"><i class="fa fa-list-alt"></i> Log </button>
|
116 |
<button class="button" onclick="Duplicator.Pack.ShowLinksDialog(<?php echo "'{$link_sql}','{$link_archive}','{$link_installer}','{$link_log}'" ;?>);" class="thickbox"><i class="fa fa-lock"></i> <?php _e("Share", 'duplicator')?></button>
|
117 |
<?php else: ?>
|
views/packages/main/controller.php
CHANGED
@@ -1,5 +1,5 @@
|
|
1 |
<?php
|
2 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/ui/class.dialog.php');
|
3 |
$current_tab = isset($_REQUEST['tab']) ? esc_html($_REQUEST['tab']) : 'list';
|
4 |
?>
|
5 |
|
1 |
<?php
|
2 |
+
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/ui/class.ui.dialog.php');
|
3 |
$current_tab = isset($_REQUEST['tab']) ? esc_html($_REQUEST['tab']) : 'list';
|
4 |
?>
|
5 |
|
views/packages/main/new1.inc.form.php
CHANGED
@@ -131,7 +131,7 @@ ARCHIVE -->
|
|
131 |
<!-- FILTERS -->
|
132 |
<?php
|
133 |
$uploads = wp_upload_dir();
|
134 |
-
$upload_dir = DUP_Util::
|
135 |
?>
|
136 |
<div class="dup-enable-filters">
|
137 |
<input type="checkbox" id="filter-on" name="filter-on" onclick="Duplicator.Pack.ToggleFileFilters()" <?php echo ($Package->Archive->FilterOn) ? "checked='checked'" :""; ?> />
|
@@ -148,7 +148,7 @@ ARCHIVE -->
|
|
148 |
<div class='dup-quick-links'>
|
149 |
<a href="javascript:void(0)" onclick="Duplicator.Pack.AddExcludePath('<?php echo rtrim(DUPLICATOR_WPROOTPATH, '/'); ?>')">[<?php _e("root path", 'duplicator') ?>]</a>
|
150 |
<a href="javascript:void(0)" onclick="Duplicator.Pack.AddExcludePath('<?php echo rtrim($upload_dir, '/'); ?>')">[<?php _e("wp-uploads", 'duplicator') ?>]</a>
|
151 |
-
<a href="javascript:void(0)" onclick="Duplicator.Pack.AddExcludePath('<?php echo DUP_Util::
|
152 |
<a href="javascript:void(0)" onclick="jQuery('#filter-dirs').val('')"><?php _e("(clear)", 'duplicator') ?></a>
|
153 |
</div>
|
154 |
<textarea name="filter-dirs" id="filter-dirs" placeholder="/full_path/exclude_path1;/full_path/exclude_path2;"><?php echo str_replace(";", ";\n", esc_textarea($Package->Archive->FilterDirs)) ?></textarea><br/>
|
@@ -362,7 +362,7 @@ INSTALLER -->
|
|
362 |
<div style="padding:10px 0 0 12px;">
|
363 |
<span class="dup-pro-text">
|
364 |
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/cpanel-48.png" style="width:16px; height:12px" />
|
365 |
-
<?php _e("
|
366 |
<a href="https://snapcreek.com/duplicator/?utm_source=duplicator_free&utm_medium=wordpress_plugin&utm_content=free_cpanel&utm_campaign=duplicator_pro" target="_blank"><?php _e('Professional', 'duplicator');?></a>
|
367 |
<i class="fa fa-lightbulb-o"
|
368 |
data-tooltip-title="<?php _e("cPanel Access:", 'duplicator'); ?>"
|
@@ -386,11 +386,11 @@ INSTALLER -->
|
|
386 |
THICK-BOX DIALOGS: -->
|
387 |
<?php
|
388 |
|
389 |
-
$confirm1 = new
|
390 |
$confirm1->title = __('Reset Package Settings?', 'duplicator');
|
391 |
$confirm1->message = __('This will clear and reset all of the current package settings. Would you like to continue?', 'duplicator');
|
392 |
$confirm1->jscallback = 'Duplicator.Pack.ResetSettings()';
|
393 |
-
$confirm1->
|
394 |
?>
|
395 |
<script>
|
396 |
jQuery(document).ready(function ($)
|
@@ -445,7 +445,7 @@ jQuery(document).ready(function ($)
|
|
445 |
|
446 |
Duplicator.Pack.ConfirmReset = function ()
|
447 |
{
|
448 |
-
<?php $confirm1->
|
449 |
}
|
450 |
|
451 |
Duplicator.Pack.ResetSettings = function ()
|
131 |
<!-- FILTERS -->
|
132 |
<?php
|
133 |
$uploads = wp_upload_dir();
|
134 |
+
$upload_dir = DUP_Util::safePath($uploads['basedir']);
|
135 |
?>
|
136 |
<div class="dup-enable-filters">
|
137 |
<input type="checkbox" id="filter-on" name="filter-on" onclick="Duplicator.Pack.ToggleFileFilters()" <?php echo ($Package->Archive->FilterOn) ? "checked='checked'" :""; ?> />
|
148 |
<div class='dup-quick-links'>
|
149 |
<a href="javascript:void(0)" onclick="Duplicator.Pack.AddExcludePath('<?php echo rtrim(DUPLICATOR_WPROOTPATH, '/'); ?>')">[<?php _e("root path", 'duplicator') ?>]</a>
|
150 |
<a href="javascript:void(0)" onclick="Duplicator.Pack.AddExcludePath('<?php echo rtrim($upload_dir, '/'); ?>')">[<?php _e("wp-uploads", 'duplicator') ?>]</a>
|
151 |
+
<a href="javascript:void(0)" onclick="Duplicator.Pack.AddExcludePath('<?php echo DUP_Util::safePath(WP_CONTENT_DIR); ?>/cache')">[<?php _e("cache", 'duplicator') ?>]</a>
|
152 |
<a href="javascript:void(0)" onclick="jQuery('#filter-dirs').val('')"><?php _e("(clear)", 'duplicator') ?></a>
|
153 |
</div>
|
154 |
<textarea name="filter-dirs" id="filter-dirs" placeholder="/full_path/exclude_path1;/full_path/exclude_path2;"><?php echo str_replace(";", ";\n", esc_textarea($Package->Archive->FilterDirs)) ?></textarea><br/>
|
362 |
<div style="padding:10px 0 0 12px;">
|
363 |
<span class="dup-pro-text">
|
364 |
<img src="<?php echo DUPLICATOR_PLUGIN_URL ?>assets/img/cpanel-48.png" style="width:16px; height:12px" />
|
365 |
+
<?php _e("Create the database and user directly from the installer with ", 'duplicator'); ?>
|
366 |
<a href="https://snapcreek.com/duplicator/?utm_source=duplicator_free&utm_medium=wordpress_plugin&utm_content=free_cpanel&utm_campaign=duplicator_pro" target="_blank"><?php _e('Professional', 'duplicator');?></a>
|
367 |
<i class="fa fa-lightbulb-o"
|
368 |
data-tooltip-title="<?php _e("cPanel Access:", 'duplicator'); ?>"
|
386 |
THICK-BOX DIALOGS: -->
|
387 |
<?php
|
388 |
|
389 |
+
$confirm1 = new DUP_UI_Dialog();
|
390 |
$confirm1->title = __('Reset Package Settings?', 'duplicator');
|
391 |
$confirm1->message = __('This will clear and reset all of the current package settings. Would you like to continue?', 'duplicator');
|
392 |
$confirm1->jscallback = 'Duplicator.Pack.ResetSettings()';
|
393 |
+
$confirm1->initConfirm();
|
394 |
?>
|
395 |
<script>
|
396 |
jQuery(document).ready(function ($)
|
445 |
|
446 |
Duplicator.Pack.ConfirmReset = function ()
|
447 |
{
|
448 |
+
<?php $confirm1->showConfirm(); ?>
|
449 |
}
|
450 |
|
451 |
Duplicator.Pack.ResetSettings = function ()
|
views/packages/main/new1.setup.php
CHANGED
@@ -1,5 +1,4 @@
|
|
1 |
<?php
|
2 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.php');
|
3 |
|
4 |
global $wpdb;
|
5 |
|
@@ -15,12 +14,12 @@ if (isset($_POST['action']))
|
|
15 |
}
|
16 |
}
|
17 |
|
18 |
-
DUP_Util::
|
19 |
|
20 |
-
$Package = DUP_Package::
|
21 |
$dup_tests = array();
|
22 |
-
$dup_tests = DUP_Server::
|
23 |
-
$default_name = DUP_Package::
|
24 |
|
25 |
//View State
|
26 |
$ctrl_ui = new DUP_CTRL_UI();
|
@@ -30,8 +29,8 @@ $data = $ctrl_ui->GetViewStateList();
|
|
30 |
$ui_css_storage = (isset($data->Payload['dup-pack-storage-panel']) && $data->Payload['dup-pack-storage-panel']) ? 'display:block' : 'display:none';
|
31 |
$ui_css_archive = (isset($data->Payload['dup-pack-archive-panel']) && $data->Payload['dup-pack-archive-panel']) ? 'display:block' : 'display:none';
|
32 |
$ui_css_installer = (isset($data->Payload['dup-pack-installer-panel']) && $data->Payload['dup-pack-installer-panel']) ? 'display:block' : 'display:none';
|
33 |
-
$dup_intaller_files = implode(", ", array_keys(DUP_Server::
|
34 |
-
$dbbuild_mode = (DUP_Settings::Get('package_mysqldump') &&
|
35 |
|
36 |
?>
|
37 |
|
@@ -165,7 +164,7 @@ SYSTEM REQUIREMENTS -->
|
|
165 |
<div class="dup-sys-info dup-info-box">
|
166 |
<table class="dup-sys-info-results">
|
167 |
<tr>
|
168 |
-
<td><?php printf("%s [%s]", __("MySQL Version", 'duplicator'),
|
169 |
<td><?php echo $dup_tests['SRV']['MYSQL_VER'] ?></td>
|
170 |
</tr>
|
171 |
<tr>
|
@@ -175,7 +174,7 @@ SYSTEM REQUIREMENTS -->
|
|
175 |
</table>
|
176 |
<small>
|
177 |
<?php
|
178 |
-
_e("MySQL version 5.0+ or better is required and the PHP MySQLi extension (note the trailing 'i') is also required. Contact your server administrator and request that mysqli extension and MySQL Server 5.0+ be installed.
|
179 |
echo " <i><a href='http://php.net/manual/en/mysqli.installation.php' target='_blank'>[" . __('more info', 'duplicator') . "]</a></i>";
|
180 |
?>
|
181 |
</small>
|
1 |
<?php
|
|
|
2 |
|
3 |
global $wpdb;
|
4 |
|
14 |
}
|
15 |
}
|
16 |
|
17 |
+
DUP_Util::initSnapshotDirectory();
|
18 |
|
19 |
+
$Package = DUP_Package::getActive();
|
20 |
$dup_tests = array();
|
21 |
+
$dup_tests = DUP_Server::getRequirements();
|
22 |
+
$default_name = DUP_Package::getDefaultName();
|
23 |
|
24 |
//View State
|
25 |
$ctrl_ui = new DUP_CTRL_UI();
|
29 |
$ui_css_storage = (isset($data->Payload['dup-pack-storage-panel']) && $data->Payload['dup-pack-storage-panel']) ? 'display:block' : 'display:none';
|
30 |
$ui_css_archive = (isset($data->Payload['dup-pack-archive-panel']) && $data->Payload['dup-pack-archive-panel']) ? 'display:block' : 'display:none';
|
31 |
$ui_css_installer = (isset($data->Payload['dup-pack-installer-panel']) && $data->Payload['dup-pack-installer-panel']) ? 'display:block' : 'display:none';
|
32 |
+
$dup_intaller_files = implode(", ", array_keys(DUP_Server::getInstallerFiles()));
|
33 |
+
$dbbuild_mode = (DUP_Settings::Get('package_mysqldump') && DUP_DB::getMySqlDumpPath()) ? 'mysqldump' : 'PHP';
|
34 |
|
35 |
?>
|
36 |
|
164 |
<div class="dup-sys-info dup-info-box">
|
165 |
<table class="dup-sys-info-results">
|
166 |
<tr>
|
167 |
+
<td><?php printf("%s [%s]", __("MySQL Version", 'duplicator'), DUP_DB::getVersion()); ?></td>
|
168 |
<td><?php echo $dup_tests['SRV']['MYSQL_VER'] ?></td>
|
169 |
</tr>
|
170 |
<tr>
|
174 |
</table>
|
175 |
<small>
|
176 |
<?php
|
177 |
+
_e("MySQL version 5.0+ or better is required and the PHP MySQLi extension (note the trailing 'i') is also required. Contact your server administrator and request that mysqli extension and MySQL Server 5.0+ be installed.", 'duplicator');
|
178 |
echo " <i><a href='http://php.net/manual/en/mysqli.installation.php' target='_blank'>[" . __('more info', 'duplicator') . "]</a></i>";
|
179 |
?>
|
180 |
</small>
|
views/packages/main/new2.scan.php
CHANGED
@@ -1,6 +1,4 @@
|
|
1 |
<?php
|
2 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/package.php');
|
3 |
-
require_once (DUPLICATOR_PLUGIN_PATH . 'classes/utility.php');
|
4 |
|
5 |
if(empty($_POST))
|
6 |
{
|
@@ -19,15 +17,15 @@
|
|
19 |
die('Unauthorized');
|
20 |
}
|
21 |
|
22 |
-
$Package->
|
23 |
-
$Package = DUP_Package::
|
24 |
|
25 |
-
$mysqldump_on = DUP_Settings::Get('package_mysqldump') &&
|
26 |
$mysqlcompat_on = isset($Package->Database->Compatible) && strlen($Package->Database->Compatible);
|
27 |
$mysqlcompat_on = ($mysqldump_on && $mysqlcompat_on) ? true : false;
|
28 |
$dbbuild_mode = ($mysqldump_on) ? 'mysqldump (fast)' : 'PHP (slow)';
|
29 |
|
30 |
-
$zip_check = DUP_Util::
|
31 |
?>
|
32 |
|
33 |
<style>
|
@@ -223,12 +221,12 @@ TOOL BAR: STEPS -->
|
|
223 |
echo '</small>';
|
224 |
|
225 |
//CACHE DIR
|
226 |
-
$cache_path = $cache_path = DUP_Util::
|
227 |
-
$cache_size = DUP_Util::
|
228 |
echo '<hr size="1" /><span id="data-srv-wp-cache"></span> <b>' . __('Cache Path', 'duplicator') . ":</b> '{$cache_path}' ({$cache_size}) <br/>";
|
229 |
echo '<small>';
|
230 |
_e("Cached data will lead to issues at install time and increases your archive size. It is recommended to empty your cache directory at build time. Use caution when removing data from the cache directory. If you have a cache plugin review the documentation for how to empty it; simply removing files might cause errors on your site. The cache size minimum threshold is currently set at ", 'duplicator');
|
231 |
-
echo DUP_Util::
|
232 |
echo '</small>';
|
233 |
|
234 |
//MU SITE
|
@@ -291,8 +289,8 @@ TOOL BAR: STEPS -->
|
|
291 |
<small>
|
292 |
<?php
|
293 |
printf(__('Total size represents all files minus any filters that have been setup. The current thresholds that triggers a warning is %1$s for the total size. Some budget hosts limit the amount of time a PHP/Web request process can run. When working with larger sites this can cause timeout issues. Consider using a file filter in step 1 to shrink and filter the overall size of your package.', 'duplicator'),
|
294 |
-
DUP_Util::
|
295 |
-
DUP_Util::
|
296 |
|
297 |
if ($zip_check != null) {
|
298 |
echo '<br/><br/>';
|
@@ -334,7 +332,7 @@ TOOL BAR: STEPS -->
|
|
334 |
<small>
|
335 |
<?php
|
336 |
printf(__('Large files such as movies or other backuped data can cause issues with timeouts. The current check for large files is %1$s per file. If your having issues creating a package consider excluding these files with the files filter and manually moving them to your new location.', 'duplicator'),
|
337 |
-
DUP_Util::
|
338 |
?>
|
339 |
</small><br/>
|
340 |
<a href="javascript:void(0)" onclick="jQuery('#data-arc-big-data').toggle()">[<?php _e('Show Paths', 'duplicator');?>]</a>
|
@@ -420,7 +418,7 @@ TOOL BAR: STEPS -->
|
|
420 |
//OVERVIEW
|
421 |
echo '<b>' . __('Overview:', 'duplicator') . '</b><br/>';
|
422 |
printf(__('Total size and row count for all database tables are approximate values. The thresholds that trigger warnings are %1$s OR %2$s records total for the entire database. The larger the databases the more time it takes to process and execute. This can cause issues with budget hosts that have cpu/memory limits, and timeout constraints.', 'duplicator'),
|
423 |
-
DUP_Util::
|
424 |
number_format(DUPLICATOR_SCAN_DB_ALL_ROWS));
|
425 |
|
426 |
//OPTIONS
|
@@ -450,7 +448,7 @@ TOOL BAR: STEPS -->
|
|
450 |
//OVERVIEW
|
451 |
echo '<b>' . __('Overview:', 'duplicator') . '</b><br/>';
|
452 |
printf(__('The thresholds that trigger warnings for individual tables are %1$s OR %2$s records OR tables names with upper-case characters. The larger the table the more time it takes to process and execute. This can cause issues with budget hosts that have cpu/memory limits, and timeout constraints.', 'duplicator'),
|
453 |
-
DUP_Util::
|
454 |
number_format(DUPLICATOR_SCAN_DB_TBL_ROWS));
|
455 |
|
456 |
//OPTIONS
|
1 |
<?php
|
|
|
|
|
2 |
|
3 |
if(empty($_POST))
|
4 |
{
|
17 |
die('Unauthorized');
|
18 |
}
|
19 |
|
20 |
+
$Package->saveActive($_POST);
|
21 |
+
$Package = DUP_Package::getActive();
|
22 |
|
23 |
+
$mysqldump_on = DUP_Settings::Get('package_mysqldump') && DUP_DB::getMySqlDumpPath();
|
24 |
$mysqlcompat_on = isset($Package->Database->Compatible) && strlen($Package->Database->Compatible);
|
25 |
$mysqlcompat_on = ($mysqldump_on && $mysqlcompat_on) ? true : false;
|
26 |
$dbbuild_mode = ($mysqldump_on) ? 'mysqldump (fast)' : 'PHP (slow)';
|
27 |
|
28 |
+
$zip_check = DUP_Util::getZipPath();
|
29 |
?>
|
30 |
|
31 |
<style>
|
221 |
echo '</small>';
|
222 |
|
223 |
//CACHE DIR
|
224 |
+
$cache_path = $cache_path = DUP_Util::safePath(WP_CONTENT_DIR) . '/cache';
|
225 |
+
$cache_size = DUP_Util::byteSize(DUP_Util::getDirectorySize($cache_path));
|
226 |
echo '<hr size="1" /><span id="data-srv-wp-cache"></span> <b>' . __('Cache Path', 'duplicator') . ":</b> '{$cache_path}' ({$cache_size}) <br/>";
|
227 |
echo '<small>';
|
228 |
_e("Cached data will lead to issues at install time and increases your archive size. It is recommended to empty your cache directory at build time. Use caution when removing data from the cache directory. If you have a cache plugin review the documentation for how to empty it; simply removing files might cause errors on your site. The cache size minimum threshold is currently set at ", 'duplicator');
|
229 |
+
echo DUP_Util::byteSize(DUPLICATOR_SCAN_CACHESIZE) . '.';
|
230 |
echo '</small>';
|
231 |
|
232 |
//MU SITE
|
289 |
<small>
|
290 |
<?php
|
291 |
printf(__('Total size represents all files minus any filters that have been setup. The current thresholds that triggers a warning is %1$s for the total size. Some budget hosts limit the amount of time a PHP/Web request process can run. When working with larger sites this can cause timeout issues. Consider using a file filter in step 1 to shrink and filter the overall size of your package.', 'duplicator'),
|
292 |
+
DUP_Util::byteSize(DUPLICATOR_SCAN_SITE),
|
293 |
+
DUP_Util::byteSize(DUPLICATOR_SCAN_WARNFILESIZE));
|
294 |
|
295 |
if ($zip_check != null) {
|
296 |
echo '<br/><br/>';
|
332 |
<small>
|
333 |
<?php
|
334 |
printf(__('Large files such as movies or other backuped data can cause issues with timeouts. The current check for large files is %1$s per file. If your having issues creating a package consider excluding these files with the files filter and manually moving them to your new location.', 'duplicator'),
|
335 |
+
DUP_Util::byteSize(DUPLICATOR_SCAN_WARNFILESIZE));
|
336 |
?>
|
337 |
</small><br/>
|
338 |
<a href="javascript:void(0)" onclick="jQuery('#data-arc-big-data').toggle()">[<?php _e('Show Paths', 'duplicator');?>]</a>
|
418 |
//OVERVIEW
|
419 |
echo '<b>' . __('Overview:', 'duplicator') . '</b><br/>';
|
420 |
printf(__('Total size and row count for all database tables are approximate values. The thresholds that trigger warnings are %1$s OR %2$s records total for the entire database. The larger the databases the more time it takes to process and execute. This can cause issues with budget hosts that have cpu/memory limits, and timeout constraints.', 'duplicator'),
|
421 |
+
DUP_Util::byteSize(DUPLICATOR_SCAN_DB_ALL_SIZE),
|
422 |
number_format(DUPLICATOR_SCAN_DB_ALL_ROWS));
|
423 |
|
424 |
//OPTIONS
|
448 |
//OVERVIEW
|
449 |
echo '<b>' . __('Overview:', 'duplicator') . '</b><br/>';
|
450 |
printf(__('The thresholds that trigger warnings for individual tables are %1$s OR %2$s records OR tables names with upper-case characters. The larger the table the more time it takes to process and execute. This can cause issues with budget hosts that have cpu/memory limits, and timeout constraints.', 'duplicator'),
|
451 |
+
DUP_Util::byteSize(DUPLICATOR_SCAN_DB_TBL_SIZE),
|
452 |
number_format(DUPLICATOR_SCAN_DB_TBL_ROWS));
|
453 |
|
454 |
//OPTIONS
|
views/packages/main/new3.build.php
CHANGED
@@ -1,6 +1,5 @@
|
|
1 |
<?php
|
2 |
-
|
3 |
-
$Package = DUP_Package::GetActive();
|
4 |
$ajax_nonce = wp_create_nonce('dup_package_build');
|
5 |
|
6 |
?>
|
1 |
<?php
|
2 |
+
$Package = DUP_Package::getActive();
|
|
|
3 |
$ajax_nonce = wp_create_nonce('dup_package_build');
|
4 |
|
5 |
?>
|
views/packages/main/packages.php
CHANGED
@@ -131,8 +131,8 @@ TOOL-BAR -->
|
|
131 |
<?php if ($row['status'] >= 100) : ?>
|
132 |
<tr class="dup-pack-info <?php echo $css_alt ?>">
|
133 |
<td class="pass"><input name="delete_confirm" type="checkbox" id="<?php echo $row['id'] ;?>" /></td>
|
134 |
-
<td><?php echo DUP_Package::
|
135 |
-
<td><?php echo DUP_Util::
|
136 |
<td class='pack-name'><?php echo $pack_name ;?></td>
|
137 |
<td class="get-btns">
|
138 |
<button id="<?php echo "{$uniqueid}_installer.php" ?>" class="button no-select" onclick="Duplicator.Pack.DownloadFile('<?php echo $installfilelink; ?>', this); return false;">
|
@@ -162,8 +162,8 @@ TOOL-BAR -->
|
|
162 |
?>
|
163 |
<tr class="dup-pack-info <?php echo $css_alt ?>">
|
164 |
<td class="fail"><input name="delete_confirm" type="checkbox" id="<?php echo $row['id'] ;?>" /></td>
|
165 |
-
<td><?php echo DUP_Package::
|
166 |
-
<td><?php echo DUP_Util::
|
167 |
<td class='pack-name'><?php echo $pack_name ;?></td>
|
168 |
<td class="get-btns error-msg" colspan="2">
|
169 |
<span>
|
@@ -185,7 +185,7 @@ TOOL-BAR -->
|
|
185 |
<tr>
|
186 |
<th colspan="11" style='text-align:right; font-size:12px'>
|
187 |
<?php echo _e("Packages", 'duplicator') . ': ' . $totalElements; ?> |
|
188 |
-
<?php echo _e("Total Size", 'duplicator') . ': ' . DUP_Util::
|
189 |
</th>
|
190 |
</tr>
|
191 |
</tfoot>
|
@@ -196,22 +196,22 @@ TOOL-BAR -->
|
|
196 |
<!-- ==========================================
|
197 |
THICK-BOX DIALOGS: -->
|
198 |
<?php
|
199 |
-
$alert1 = new
|
200 |
$alert1->title = __('Bulk Action Required', 'duplicator');
|
201 |
$alert1->message = __('Please select an action from the "Bulk Actions" drop down menu!', 'duplicator');
|
202 |
-
$alert1->
|
203 |
|
204 |
-
$alert2 = new
|
205 |
$alert2->title = __('Selection Required', 'duplicator', 'duplicator');
|
206 |
$alert2->message = __('Please select at least one package to delete!', 'duplicator');
|
207 |
-
$alert2->
|
208 |
|
209 |
-
$confirm1 = new
|
210 |
$confirm1->title = __('Delete Packages?', 'duplicator');
|
211 |
$confirm1->message = __('Are you sure, you want to delete the selected package(s)?', 'duplicator');
|
212 |
-
$confirm1->
|
213 |
$confirm1->jscallback = 'Duplicator.Pack.Delete()';
|
214 |
-
$confirm1->
|
215 |
?>
|
216 |
|
217 |
<script type="text/javascript">
|
@@ -237,17 +237,17 @@ jQuery(document).ready(function($)
|
|
237 |
{
|
238 |
if ($("#dup-pack-bulk-actions").val() != "delete")
|
239 |
{
|
240 |
-
<?php $alert1->
|
241 |
return;
|
242 |
}
|
243 |
|
244 |
var list = Duplicator.Pack.GetDeleteList();
|
245 |
if (list.length == 0)
|
246 |
{
|
247 |
-
<?php $alert2->
|
248 |
return;
|
249 |
}
|
250 |
-
<?php $confirm1->
|
251 |
}
|
252 |
|
253 |
|
@@ -256,13 +256,13 @@ jQuery(document).ready(function($)
|
|
256 |
Duplicator.Pack.Delete = function (event)
|
257 |
{
|
258 |
var list = Duplicator.Pack.GetDeleteList();
|
259 |
-
|
260 |
$.ajax({
|
261 |
type: "POST",
|
262 |
url: ajaxurl,
|
263 |
dataType: "json",
|
264 |
data: {action : 'duplicator_package_delete', duplicator_delid : list, nonce: '<?php echo $ajax_nonce; ?>' },
|
265 |
-
|
266 |
Duplicator.ReloadWindow(data);
|
267 |
}
|
268 |
});
|
131 |
<?php if ($row['status'] >= 100) : ?>
|
132 |
<tr class="dup-pack-info <?php echo $css_alt ?>">
|
133 |
<td class="pass"><input name="delete_confirm" type="checkbox" id="<?php echo $row['id'] ;?>" /></td>
|
134 |
+
<td><?php echo DUP_Package::getCreatedDateFormat($row['created'], $ui_create_frmt);?></td>
|
135 |
+
<td><?php echo DUP_Util::byteSize($pack_archive_size); ?></td>
|
136 |
<td class='pack-name'><?php echo $pack_name ;?></td>
|
137 |
<td class="get-btns">
|
138 |
<button id="<?php echo "{$uniqueid}_installer.php" ?>" class="button no-select" onclick="Duplicator.Pack.DownloadFile('<?php echo $installfilelink; ?>', this); return false;">
|
162 |
?>
|
163 |
<tr class="dup-pack-info <?php echo $css_alt ?>">
|
164 |
<td class="fail"><input name="delete_confirm" type="checkbox" id="<?php echo $row['id'] ;?>" /></td>
|
165 |
+
<td><?php echo DUP_Package::getCreatedDateFormat($row['created'], $ui_create_frmt);?></td>
|
166 |
+
<td><?php echo DUP_Util::byteSize($size); ?></td>
|
167 |
<td class='pack-name'><?php echo $pack_name ;?></td>
|
168 |
<td class="get-btns error-msg" colspan="2">
|
169 |
<span>
|
185 |
<tr>
|
186 |
<th colspan="11" style='text-align:right; font-size:12px'>
|
187 |
<?php echo _e("Packages", 'duplicator') . ': ' . $totalElements; ?> |
|
188 |
+
<?php echo _e("Total Size", 'duplicator') . ': ' . DUP_Util::byteSize($totalSize); ?>
|
189 |
</th>
|
190 |
</tr>
|
191 |
</tfoot>
|
196 |
<!-- ==========================================
|
197 |
THICK-BOX DIALOGS: -->
|
198 |
<?php
|
199 |
+
$alert1 = new DUP_UI_Dialog();
|
200 |
$alert1->title = __('Bulk Action Required', 'duplicator');
|
201 |
$alert1->message = __('Please select an action from the "Bulk Actions" drop down menu!', 'duplicator');
|
202 |
+
$alert1->initAlert();
|
203 |
|
204 |
+
$alert2 = new DUP_UI_Dialog();
|
205 |
$alert2->title = __('Selection Required', 'duplicator', 'duplicator');
|
206 |
$alert2->message = __('Please select at least one package to delete!', 'duplicator');
|
207 |
+
$alert2->initAlert();
|
208 |
|
209 |
+
$confirm1 = new DUP_UI_Dialog();
|
210 |
$confirm1->title = __('Delete Packages?', 'duplicator');
|
211 |
$confirm1->message = __('Are you sure, you want to delete the selected package(s)?', 'duplicator');
|
212 |
+
$confirm1->progressText = __('Removing Packages, Please Wait...', 'duplicator');
|
213 |
$confirm1->jscallback = 'Duplicator.Pack.Delete()';
|
214 |
+
$confirm1->initConfirm();
|
215 |
?>
|
216 |
|
217 |
<script type="text/javascript">
|
237 |
{
|
238 |
if ($("#dup-pack-bulk-actions").val() != "delete")
|
239 |
{
|
240 |
+
<?php $alert1->showAlert(); ?>
|
241 |
return;
|
242 |
}
|
243 |
|
244 |
var list = Duplicator.Pack.GetDeleteList();
|
245 |
if (list.length == 0)
|
246 |
{
|
247 |
+
<?php $alert2->showAlert(); ?>
|
248 |
return;
|
249 |
}
|
250 |
+
<?php $confirm1->showConfirm(); ?>
|
251 |
}
|
252 |
|
253 |
|
256 |
Duplicator.Pack.Delete = function (event)
|
257 |
{
|
258 |
var list = Duplicator.Pack.GetDeleteList();
|
259 |
+
|
260 |
$.ajax({
|
261 |
type: "POST",
|
262 |
url: ajaxurl,
|
263 |
dataType: "json",
|
264 |
data: {action : 'duplicator_package_delete', duplicator_delid : list, nonce: '<?php echo $ajax_nonce; ?>' },
|
265 |
+
complete: function(data) {
|
266 |
Duplicator.ReloadWindow(data);
|
267 |
}
|
268 |
});
|
views/settings/controller.php
CHANGED
@@ -1,6 +1,6 @@
|
|
1 |
<?php
|
2 |
|
3 |
-
DUP_Util::
|
4 |
|
5 |
global $wpdb;
|
6 |
|
1 |
<?php
|
2 |
|
3 |
+
DUP_Util::hasCapability('manage_options');
|
4 |
|
5 |
global $wpdb;
|
6 |
|
views/settings/general.php
CHANGED
@@ -34,7 +34,7 @@ if (isset($_POST['action']) && $_POST['action'] == 'save') {
|
|
34 |
DUP_Settings::Set('wpfront_integrate', isset($_POST['wpfront_integrate']) ? "1" : "0");
|
35 |
|
36 |
$action_updated = DUP_Settings::Save();
|
37 |
-
DUP_Util::
|
38 |
}
|
39 |
|
40 |
$uninstall_settings = DUP_Settings::Get('uninstall_settings');
|
@@ -55,7 +55,7 @@ $package_ui_created = is_numeric(DUP_Settings::Get('package_ui_created')) ? DUP_
|
|
55 |
$wpfront_integrate = DUP_Settings::Get('wpfront_integrate');
|
56 |
$wpfront_ready = apply_filters('wpfront_user_role_editor_duplicator_integration_ready', false);
|
57 |
|
58 |
-
$mysqlDumpPath =
|
59 |
$mysqlDumpFound = ($mysqlDumpPath) ? true : false;
|
60 |
|
61 |
|
@@ -104,7 +104,7 @@ $mysqlDumpFound = ($mysqlDumpPath) ? true : false;
|
|
104 |
<th scope="row"><label><?php _e("Storage", 'duplicator'); ?></label></th>
|
105 |
<td>
|
106 |
<?php _e("Full Path", 'duplicator'); ?>:
|
107 |
-
<?php echo DUP_Util::
|
108 |
<input type="checkbox" name="storage_htaccess_off" id="storage_htaccess_off" <?php echo ($storage_htaccess_off) ? 'checked="checked"' : ''; ?> />
|
109 |
<label for="storage_htaccess_off"><?php _e("Disable .htaccess File In Storage Directory", 'duplicator') ?> </label>
|
110 |
<p class="description">
|
@@ -154,7 +154,7 @@ $mysqlDumpFound = ($mysqlDumpPath) ? true : false;
|
|
154 |
<tr>
|
155 |
<th scope="row"><label><?php _e("Database Script", 'duplicator'); ?></label></th>
|
156 |
<td>
|
157 |
-
<?php if (!DUP_Util::
|
158 |
<input type="radio" disabled="true" />
|
159 |
<label><?php _e("Use mysqldump", 'duplicator'); ?></label>
|
160 |
<p class="description" style="width:550px; margin:5px 0 0 20px">
|
34 |
DUP_Settings::Set('wpfront_integrate', isset($_POST['wpfront_integrate']) ? "1" : "0");
|
35 |
|
36 |
$action_updated = DUP_Settings::Save();
|
37 |
+
DUP_Util::initSnapshotDirectory();
|
38 |
}
|
39 |
|
40 |
$uninstall_settings = DUP_Settings::Get('uninstall_settings');
|
55 |
$wpfront_integrate = DUP_Settings::Get('wpfront_integrate');
|
56 |
$wpfront_ready = apply_filters('wpfront_user_role_editor_duplicator_integration_ready', false);
|
57 |
|
58 |
+
$mysqlDumpPath = DUP_DB::getMySqlDumpPath();
|
59 |
$mysqlDumpFound = ($mysqlDumpPath) ? true : false;
|
60 |
|
61 |
|
104 |
<th scope="row"><label><?php _e("Storage", 'duplicator'); ?></label></th>
|
105 |
<td>
|
106 |
<?php _e("Full Path", 'duplicator'); ?>:
|
107 |
+
<?php echo DUP_Util::safePath(DUPLICATOR_SSDIR_PATH); ?><br/><br/>
|
108 |
<input type="checkbox" name="storage_htaccess_off" id="storage_htaccess_off" <?php echo ($storage_htaccess_off) ? 'checked="checked"' : ''; ?> />
|
109 |
<label for="storage_htaccess_off"><?php _e("Disable .htaccess File In Storage Directory", 'duplicator') ?> </label>
|
110 |
<p class="description">
|
154 |
<tr>
|
155 |
<th scope="row"><label><?php _e("Database Script", 'duplicator'); ?></label></th>
|
156 |
<td>
|
157 |
+
<?php if (!DUP_Util::hasShellExec()) : ?>
|
158 |
<input type="radio" disabled="true" />
|
159 |
<label><?php _e("Use mysqldump", 'duplicator'); ?></label>
|
160 |
<p class="description" style="width:550px; margin:5px 0 0 20px">
|
views/tools/cleanup.php
CHANGED
@@ -20,7 +20,7 @@
|
|
20 |
|
21 |
$txt_found = __('File Found', 'duplicator');
|
22 |
$txt_not_found = __('File Removed', 'duplicator');
|
23 |
-
$installer_files = DUP_Server::
|
24 |
|
25 |
switch ($_GET['action']) {
|
26 |
case 'installer' :
|
@@ -32,7 +32,7 @@
|
|
32 |
$action_response = __('Legacy data removed.', 'duplicator');
|
33 |
break;
|
34 |
case 'tmp-cache':
|
35 |
-
DUP_Package::
|
36 |
$action_response = __('Build cache removed.', 'duplicator');
|
37 |
break;
|
38 |
}
|
@@ -151,17 +151,17 @@ THICK-BOX DIALOGS: -->
|
|
151 |
$msg = __('This action will remove all legacy settings prior to version %1$s. ', 'duplicator');
|
152 |
$msg .= __('Legacy settings are only needed if you plan to migrate back to an older version of this plugin.', 'duplicator');
|
153 |
|
154 |
-
$confirm1 = new
|
155 |
$confirm1->title = __('Delete Packages?', 'duplicator');
|
156 |
$confirm1->message = sprintf(__($msg, 'duplicator'), DUPLICATOR_VERSION);
|
157 |
$confirm1->jscallback = 'Duplicator.Tools.DeleteLegacy()';
|
158 |
-
$confirm1->
|
159 |
|
160 |
-
$confirm2 = new
|
161 |
$confirm2->title = __('Clear Build Cache?', 'duplicator');
|
162 |
$confirm2->message = __('This process will remove all build cache files. Be sure no packages are currently building or else they will be cancelled.', 'duplicator');
|
163 |
$confirm2->jscallback = 'Duplicator.Tools.ClearBuildCache()';
|
164 |
-
$confirm2->
|
165 |
?>
|
166 |
|
167 |
<script>
|
@@ -169,7 +169,7 @@ jQuery(document).ready(function($)
|
|
169 |
{
|
170 |
Duplicator.Tools.ConfirmDeleteLegacy = function ()
|
171 |
{
|
172 |
-
<?php $confirm1->
|
173 |
}
|
174 |
|
175 |
|
@@ -181,7 +181,7 @@ jQuery(document).ready(function($)
|
|
181 |
|
182 |
Duplicator.Tools.ConfirmClearBuildCache = function ()
|
183 |
{
|
184 |
-
<?php $confirm2->
|
185 |
}
|
186 |
|
187 |
Duplicator.Tools.ClearBuildCache = function ()
|
20 |
|
21 |
$txt_found = __('File Found', 'duplicator');
|
22 |
$txt_not_found = __('File Removed', 'duplicator');
|
23 |
+
$installer_files = DUP_Server::getInstallerFiles();
|
24 |
|
25 |
switch ($_GET['action']) {
|
26 |
case 'installer' :
|
32 |
$action_response = __('Legacy data removed.', 'duplicator');
|
33 |
break;
|
34 |
case 'tmp-cache':
|
35 |
+
DUP_Package::tempFileCleanup(true);
|
36 |
$action_response = __('Build cache removed.', 'duplicator');
|
37 |
break;
|
38 |
}
|
151 |
$msg = __('This action will remove all legacy settings prior to version %1$s. ', 'duplicator');
|
152 |
$msg .= __('Legacy settings are only needed if you plan to migrate back to an older version of this plugin.', 'duplicator');
|
153 |
|
154 |
+
$confirm1 = new DUP_UI_Dialog();
|
155 |
$confirm1->title = __('Delete Packages?', 'duplicator');
|
156 |
$confirm1->message = sprintf(__($msg, 'duplicator'), DUPLICATOR_VERSION);
|
157 |
$confirm1->jscallback = 'Duplicator.Tools.DeleteLegacy()';
|
158 |
+
$confirm1->initConfirm();
|
159 |
|
160 |
+
$confirm2 = new DUP_UI_Dialog();
|
161 |
$confirm2->title = __('Clear Build Cache?', 'duplicator');
|
162 |
$confirm2->message = __('This process will remove all build cache files. Be sure no packages are currently building or else they will be cancelled.', 'duplicator');
|
163 |
$confirm2->jscallback = 'Duplicator.Tools.ClearBuildCache()';
|
164 |
+
$confirm2->initConfirm();
|
165 |
?>
|
166 |
|
167 |
<script>
|
169 |
{
|
170 |
Duplicator.Tools.ConfirmDeleteLegacy = function ()
|
171 |
{
|
172 |
+
<?php $confirm1->showConfirm(); ?>
|
173 |
}
|
174 |
|
175 |
|
181 |
|
182 |
Duplicator.Tools.ConfirmClearBuildCache = function ()
|
183 |
{
|
184 |
+
<?php $confirm2->showConfirm(); ?>
|
185 |
}
|
186 |
|
187 |
Duplicator.Tools.ClearBuildCache = function ()
|
views/tools/controller.php
CHANGED
@@ -1,7 +1,7 @@
|
|
1 |
<?php
|
2 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/ui/class.dialog.php');
|
3 |
|
4 |
-
DUP_Util::
|
5 |
|
6 |
global $wpdb;
|
7 |
|
1 |
<?php
|
2 |
+
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/ui/class.ui.dialog.php');
|
3 |
|
4 |
+
DUP_Util::hasCapability('manage_options');
|
5 |
|
6 |
global $wpdb;
|
7 |
|
views/tools/diagnostics/inc.data.php
CHANGED
@@ -44,12 +44,12 @@ OPTIONS DATA -->
|
|
44 |
<!-- ==========================================
|
45 |
THICK-BOX DIALOGS: -->
|
46 |
<?php
|
47 |
-
$confirm1 = new
|
48 |
$confirm1->title = __('Delete Option?', 'duplicator');
|
49 |
$confirm1->message = __('Delete the option value just selected?', 'duplicator');
|
50 |
-
$confirm1->
|
51 |
$confirm1->jscallback = 'Duplicator.Settings.DeleteOption()';
|
52 |
-
$confirm1->
|
53 |
?>
|
54 |
|
55 |
<script>
|
@@ -58,11 +58,11 @@ jQuery(document).ready(function($)
|
|
58 |
Duplicator.Settings.ConfirmDeleteOption = function (anchor)
|
59 |
{
|
60 |
var key = $(anchor).text();
|
61 |
-
var msg_id = '<?php echo $confirm1->
|
62 |
var msg = '<?php _e('Delete the option value', 'duplicator');?>' + ' [' + key + '] ?';
|
63 |
jQuery('#dup-settings-form-action').val(key);
|
64 |
jQuery('#' + msg_id).html(msg)
|
65 |
-
<?php $confirm1->
|
66 |
}
|
67 |
|
68 |
|
44 |
<!-- ==========================================
|
45 |
THICK-BOX DIALOGS: -->
|
46 |
<?php
|
47 |
+
$confirm1 = new DUP_UI_Dialog();
|
48 |
$confirm1->title = __('Delete Option?', 'duplicator');
|
49 |
$confirm1->message = __('Delete the option value just selected?', 'duplicator');
|
50 |
+
$confirm1->progressText = __('Removing Option, Please Wait...', 'duplicator');
|
51 |
$confirm1->jscallback = 'Duplicator.Settings.DeleteOption()';
|
52 |
+
$confirm1->initConfirm();
|
53 |
?>
|
54 |
|
55 |
<script>
|
58 |
Duplicator.Settings.ConfirmDeleteOption = function (anchor)
|
59 |
{
|
60 |
var key = $(anchor).text();
|
61 |
+
var msg_id = '<?php echo $confirm1->getMessageID() ?>';
|
62 |
var msg = '<?php _e('Delete the option value', 'duplicator');?>' + ' [' + key + '] ?';
|
63 |
jQuery('#dup-settings-form-action').val(key);
|
64 |
jQuery('#' + msg_id).html(msg)
|
65 |
+
<?php $confirm1->showConfirm(); ?>
|
66 |
}
|
67 |
|
68 |
|
views/tools/diagnostics/inc.settings.php
CHANGED
@@ -1,16 +1,16 @@
|
|
1 |
<?php
|
2 |
-
$dbvar_maxtime =
|
3 |
-
$dbvar_maxpacks =
|
4 |
$dbvar_maxtime = is_null($dbvar_maxtime) ? __("unknow", 'duplicator') : $dbvar_maxtime;
|
5 |
$dbvar_maxpacks = is_null($dbvar_maxpacks) ? __("unknow", 'duplicator') : $dbvar_maxpacks;
|
6 |
|
7 |
$space = @disk_total_space(DUPLICATOR_WPROOTPATH);
|
8 |
$space_free = @disk_free_space(DUPLICATOR_WPROOTPATH);
|
9 |
$perc = @round((100/$space)*$space_free,2);
|
10 |
-
$mysqldumpPath =
|
11 |
$mysqlDumpSupport = ($mysqldumpPath) ? $mysqldumpPath : 'Path Not Found';
|
12 |
|
13 |
-
$client_ip_address = DUP_Server::
|
14 |
?>
|
15 |
|
16 |
<!-- ==============================
|
@@ -48,7 +48,7 @@ SERVER SETTINGS -->
|
|
48 |
</tr>
|
49 |
<tr>
|
50 |
<td><?php _e("APC Enabled", 'duplicator'); ?></td>
|
51 |
-
<td><?php echo DUP_Util::
|
52 |
</tr>
|
53 |
<tr>
|
54 |
<td><?php _e("Root Path", 'duplicator'); ?></td>
|
@@ -60,7 +60,7 @@ SERVER SETTINGS -->
|
|
60 |
</tr>
|
61 |
<tr>
|
62 |
<td><?php _e("Plugins Path", 'duplicator'); ?></td>
|
63 |
-
<td><?php echo DUP_Util::
|
64 |
</tr>
|
65 |
<tr>
|
66 |
<td><?php _e("Loaded PHP INI", 'duplicator'); ?></td>
|
@@ -106,11 +106,11 @@ SERVER SETTINGS -->
|
|
106 |
</tr>
|
107 |
<tr>
|
108 |
<td><?php _e("User", 'duplicator'); ?></td>
|
109 |
-
<td><?php echo DUP_Util::
|
110 |
</tr>
|
111 |
<tr>
|
112 |
<td><?php _e("Process", 'duplicator'); ?></td>
|
113 |
-
<td><?php echo DUP_Util::
|
114 |
</tr>
|
115 |
<tr>
|
116 |
<td><a href="http://php.net/manual/en/features.safe-mode.php" target="_blank"><?php _e("Safe Mode", 'duplicator'); ?></a></td>
|
@@ -135,18 +135,22 @@ SERVER SETTINGS -->
|
|
135 |
</tr>
|
136 |
<tr>
|
137 |
<td><a href="http://us3.php.net/shell_exec" target="_blank"><?php _e("Shell Exec", 'duplicator'); ?></a></td>
|
138 |
-
<td><?php echo (DUP_Util::
|
139 |
</tr>
|
140 |
<tr>
|
141 |
<td><?php _e("Shell Exec Zip", 'duplicator'); ?></td>
|
142 |
-
<td><?php echo (DUP_Util::
|
143 |
</tr>
|
144 |
<tr>
|
145 |
<td class='dup-settings-diag-header' colspan="2">MySQL</td>
|
146 |
</tr>
|
147 |
<tr>
|
148 |
<td><?php _e("Version", 'duplicator'); ?></td>
|
149 |
-
<td><?php echo
|
|
|
|
|
|
|
|
|
150 |
</tr>
|
151 |
<tr>
|
152 |
<td><?php _e("Charset", 'duplicator'); ?></td>
|
@@ -169,7 +173,7 @@ SERVER SETTINGS -->
|
|
169 |
</tr>
|
170 |
<tr valign="top">
|
171 |
<td><?php _e('Free space', 'hyper-cache'); ?></td>
|
172 |
-
<td><?php echo $perc;?>% -- <?php echo DUP_Util::
|
173 |
<small>
|
174 |
<?php _e("Note: This value is the physical servers hard-drive allocation.", 'duplicator'); ?> <br/>
|
175 |
<?php _e("On shared hosts check your control panel for the 'TRUE' disk space quota value.", 'duplicator'); ?>
|
1 |
<?php
|
2 |
+
$dbvar_maxtime = DUP_DB::getVariable('wait_timeout');
|
3 |
+
$dbvar_maxpacks = DUP_DB::getVariable('max_allowed_packet');
|
4 |
$dbvar_maxtime = is_null($dbvar_maxtime) ? __("unknow", 'duplicator') : $dbvar_maxtime;
|
5 |
$dbvar_maxpacks = is_null($dbvar_maxpacks) ? __("unknow", 'duplicator') : $dbvar_maxpacks;
|
6 |
|
7 |
$space = @disk_total_space(DUPLICATOR_WPROOTPATH);
|
8 |
$space_free = @disk_free_space(DUPLICATOR_WPROOTPATH);
|
9 |
$perc = @round((100/$space)*$space_free,2);
|
10 |
+
$mysqldumpPath = DUP_DB::getMySqlDumpPath();
|
11 |
$mysqlDumpSupport = ($mysqldumpPath) ? $mysqldumpPath : 'Path Not Found';
|
12 |
|
13 |
+
$client_ip_address = DUP_Server::getClientIP();
|
14 |
?>
|
15 |
|
16 |
<!-- ==============================
|
48 |
</tr>
|
49 |
<tr>
|
50 |
<td><?php _e("APC Enabled", 'duplicator'); ?></td>
|
51 |
+
<td><?php echo DUP_Util::runAPC() ? 'Yes' : 'No' ?></td>
|
52 |
</tr>
|
53 |
<tr>
|
54 |
<td><?php _e("Root Path", 'duplicator'); ?></td>
|
60 |
</tr>
|
61 |
<tr>
|
62 |
<td><?php _e("Plugins Path", 'duplicator'); ?></td>
|
63 |
+
<td><?php echo DUP_Util::safePath(WP_PLUGIN_DIR) ?></td>
|
64 |
</tr>
|
65 |
<tr>
|
66 |
<td><?php _e("Loaded PHP INI", 'duplicator'); ?></td>
|
106 |
</tr>
|
107 |
<tr>
|
108 |
<td><?php _e("User", 'duplicator'); ?></td>
|
109 |
+
<td><?php echo DUP_Util::getCurrentUser(); ?></td>
|
110 |
</tr>
|
111 |
<tr>
|
112 |
<td><?php _e("Process", 'duplicator'); ?></td>
|
113 |
+
<td><?php echo DUP_Util::getProcessOwner(); ?></td>
|
114 |
</tr>
|
115 |
<tr>
|
116 |
<td><a href="http://php.net/manual/en/features.safe-mode.php" target="_blank"><?php _e("Safe Mode", 'duplicator'); ?></a></td>
|
135 |
</tr>
|
136 |
<tr>
|
137 |
<td><a href="http://us3.php.net/shell_exec" target="_blank"><?php _e("Shell Exec", 'duplicator'); ?></a></td>
|
138 |
+
<td><?php echo (DUP_Util::hasShellExec()) ? _e("Is Supported", 'duplicator') : _e("Not Supported", 'duplicator'); ?></td>
|
139 |
</tr>
|
140 |
<tr>
|
141 |
<td><?php _e("Shell Exec Zip", 'duplicator'); ?></td>
|
142 |
+
<td><?php echo (DUP_Util::getZipPath() != null) ? _e("Is Supported", 'duplicator') : _e("Not Supported", 'duplicator'); ?></td>
|
143 |
</tr>
|
144 |
<tr>
|
145 |
<td class='dup-settings-diag-header' colspan="2">MySQL</td>
|
146 |
</tr>
|
147 |
<tr>
|
148 |
<td><?php _e("Version", 'duplicator'); ?></td>
|
149 |
+
<td><?php echo DUP_DB::getVersion() ?></td>
|
150 |
+
</tr>
|
151 |
+
<tr>
|
152 |
+
<td><?php _e("Comments", 'duplicator'); ?></td>
|
153 |
+
<td><?php echo DUP_DB::getVariable('version_comment') ?></td>
|
154 |
</tr>
|
155 |
<tr>
|
156 |
<td><?php _e("Charset", 'duplicator'); ?></td>
|
173 |
</tr>
|
174 |
<tr valign="top">
|
175 |
<td><?php _e('Free space', 'hyper-cache'); ?></td>
|
176 |
+
<td><?php echo $perc;?>% -- <?php echo DUP_Util::byteSize($space_free);?> from <?php echo DUP_Util::byteSize($space);?><br/>
|
177 |
<small>
|
178 |
<?php _e("Note: This value is the physical servers hard-drive allocation.", 'duplicator'); ?> <br/>
|
179 |
<?php _e("On shared hosts check your control panel for the 'TRUE' disk space quota value.", 'duplicator'); ?>
|
views/tools/diagnostics/inc.validator.php
CHANGED
@@ -10,12 +10,12 @@
|
|
10 |
<!-- ==========================================
|
11 |
THICK-BOX DIALOGS: -->
|
12 |
<?php
|
13 |
-
$confirm1 = new
|
14 |
$confirm1->title = __('Run Validator', 'duplicator');
|
15 |
$confirm1->message = __('This will run the scan validation check. This may take several minutes. Do you want to Continue?', 'duplicator');
|
16 |
-
$confirm1->
|
17 |
$confirm1->jscallback = 'Duplicator.Tools.RunScanValidator()';
|
18 |
-
$confirm1->
|
19 |
?>
|
20 |
|
21 |
<!-- ==============================
|
@@ -46,17 +46,17 @@ SCAN VALIDATOR -->
|
|
46 |
<table>
|
47 |
<tr>
|
48 |
<td><b>Files:</b></td>
|
49 |
-
<td>{{Payload.
|
50 |
</tr>
|
51 |
<tr>
|
52 |
<td><b>Dirs:</b></td>
|
53 |
-
<td>{{Payload.
|
54 |
</tr>
|
55 |
</table>
|
56 |
|
57 |
<b>Unreadable Files:</b> <br/>
|
58 |
-
{{#if Payload.
|
59 |
-
{{#each Payload.
|
60 |
{{@index}} : {{this}}<br/>
|
61 |
{{/each}}
|
62 |
{{else}}
|
@@ -64,8 +64,8 @@ SCAN VALIDATOR -->
|
|
64 |
{{/if}}
|
65 |
|
66 |
<b>Symbolic Links:</b> <br/>
|
67 |
-
{{#if Payload.
|
68 |
-
{{#each Payload.
|
69 |
{{@index}} : {{this}}<br/>
|
70 |
{{/each}}
|
71 |
{{else}}
|
@@ -84,7 +84,7 @@ jQuery(document).ready(function($)
|
|
84 |
{
|
85 |
Duplicator.Tools.ConfirmScanValidator = function()
|
86 |
{
|
87 |
-
<?php $confirm1->
|
88 |
}
|
89 |
|
90 |
|
10 |
<!-- ==========================================
|
11 |
THICK-BOX DIALOGS: -->
|
12 |
<?php
|
13 |
+
$confirm1 = new DUP_UI_Dialog();
|
14 |
$confirm1->title = __('Run Validator', 'duplicator');
|
15 |
$confirm1->message = __('This will run the scan validation check. This may take several minutes. Do you want to Continue?', 'duplicator');
|
16 |
+
$confirm1->progressOn = false;
|
17 |
$confirm1->jscallback = 'Duplicator.Tools.RunScanValidator()';
|
18 |
+
$confirm1->initConfirm();
|
19 |
?>
|
20 |
|
21 |
<!-- ==============================
|
46 |
<table>
|
47 |
<tr>
|
48 |
<td><b>Files:</b></td>
|
49 |
+
<td>{{Payload.fileCount}} </td>
|
50 |
</tr>
|
51 |
<tr>
|
52 |
<td><b>Dirs:</b></td>
|
53 |
+
<td>{{Payload.dirCount}} </td>
|
54 |
</tr>
|
55 |
</table>
|
56 |
|
57 |
<b>Unreadable Files:</b> <br/>
|
58 |
+
{{#if Payload.unreadable}}
|
59 |
+
{{#each Payload.unreadable}}
|
60 |
{{@index}} : {{this}}<br/>
|
61 |
{{/each}}
|
62 |
{{else}}
|
64 |
{{/if}}
|
65 |
|
66 |
<b>Symbolic Links:</b> <br/>
|
67 |
+
{{#if Payload.symLinks}}
|
68 |
+
{{#each Payload.symLinks}}
|
69 |
{{@index}} : {{this}}<br/>
|
70 |
{{/each}}
|
71 |
{{else}}
|
84 |
{
|
85 |
Duplicator.Tools.ConfirmScanValidator = function()
|
86 |
{
|
87 |
+
<?php $confirm1->showConfirm(); ?>
|
88 |
}
|
89 |
|
90 |
|
views/tools/diagnostics/main.php
CHANGED
@@ -2,7 +2,7 @@
|
|
2 |
wp_enqueue_script('dup-handlebars');
|
3 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
5 |
-
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/scan.
|
6 |
|
7 |
global $wp_version;
|
8 |
global $wpdb;
|
2 |
wp_enqueue_script('dup-handlebars');
|
3 |
require_once(DUPLICATOR_PLUGIN_PATH . '/assets/js/javascript.php');
|
4 |
require_once(DUPLICATOR_PLUGIN_PATH . '/views/inc.header.php');
|
5 |
+
require_once(DUPLICATOR_PLUGIN_PATH . '/classes/utilities/class.scan.check.php');
|
6 |
|
7 |
global $wp_version;
|
8 |
global $wpdb;
|
views/tools/logging.php
CHANGED
@@ -6,7 +6,7 @@ $logs = glob(DUPLICATOR_SSDIR_PATH . '/*.log') ;
|
|
6 |
if ($logs != false && count($logs))
|
7 |
{
|
8 |
usort($logs, create_function('$a,$b', 'return filemtime($b) - filemtime($a);'));
|
9 |
-
@chmod(DUP_Util::
|
10 |
}
|
11 |
|
12 |
$logname = (isset($_GET['logname'])) ? trim(sanitize_text_field($_GET['logname'])) : "";
|
6 |
if ($logs != false && count($logs))
|
7 |
{
|
8 |
usort($logs, create_function('$a,$b', 'return filemtime($b) - filemtime($a);'));
|
9 |
+
@chmod(DUP_Util::safePath($logs[0]), 0644);
|
10 |
}
|
11 |
|
12 |
$logname = (isset($_GET['logname'])) ? trim(sanitize_text_field($_GET['logname'])) : "";
|