GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.

Xcloner_Restore::url_replace()   A
last analyzed

Complexity

Conditions 3
Paths 3

Size

Total Lines 20
Code Lines 11

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 3
eloc 11
nc 3
nop 3
dl 0
loc 20
rs 9.9
c 1
b 0
f 0
1
<?php
2
3
if (!defined('AUTH_KEY'))
4
{
5
	define('AUTH_KEY', '');
6
}
7
8
if (!defined("DS"))
9
{
10
	define("DS", DIRECTORY_SEPARATOR);
11
}
12
13
if (!defined('XCLONER_PLUGIN_ACCESS') || XCLONER_PLUGIN_ACCESS != 1)
14
{	
15
	if (!AUTH_KEY)
16
	{
17
			Xcloner_Restore::send_response("404", "Could not run restore script, AUTH_KEY not set!");
18
			exit;
19
	}
20
	
21
	if (!isset($_REQUEST['hash']))
22
	{
23
			Xcloner_Restore::send_response("404", "Could not run restore script, sent HASH is empty!");
24
			exit;
25
	}
26
	
27
	if ($_REQUEST['hash'] != AUTH_KEY)
28
	{
29
			Xcloner_Restore::send_response("404", "Could not run restore script, AUTH_KEY doesn't match the sent HASH!");
30
			exit;
31
	}
32
}
33
34
//check minimum PHP version
35
if (version_compare(phpversion(), Xcloner_Restore::xcloner_minimum_version, '<'))
36
{
37
	Xcloner_Restore::send_response(500, sprintf(("XCloner requires minimum PHP version %s in order to run correctly. We have detected your version as %s"), Xcloner_Restore::xcloner_minimum_version, phpversion()));
38
	exit;
39
40
}
41
42
$file = dirname(__DIR__).DS.'vendor'.DS.'autoload.php';
43
44
if (file_exists($file))
45
{
46
	
47
	require_once($file);
48
}
49
elseif (file_exists("vendor.phar") and extension_loaded('phar'))
50
{
51
	require_once(__DIR__.DS."vendor.phar");
52
} else {	
53
	
54
	$file = dirname(__FILE__).DS.'vendor'.DS.'autoload.php';
55
	
56
	if (!file_exists($file))
57
	{
58
		Xcloner_Restore::send_response("404", "File $file does not exists, please extract the vendor.tgz archive on the server or enable PHP Phar module!");
59
		exit;
60
	}
61
	
62
	require_once($file);
63
}
64
65
66
use League\Flysystem\Config;
67
use League\Flysystem\Filesystem;
68
use League\Flysystem\Util;
69
use League\Flysystem\Adapter\Local;
70
71
use splitbrain\PHPArchive\Tar;
72
use splitbrain\PHPArchive\Archive;
73
use splitbrain\PHPArchive\FileInfo;
74
75
use Monolog\Logger;
76
use Monolog\Handler\StreamHandler;
77
78
79
//do not modify below
80
$that = "";
81
if (defined('XCLONER_PLUGIN_ACCESS') && XCLONER_PLUGIN_ACCESS)
82
{
83
	$that = $this;
84
}
85
$xcloner_restore = new Xcloner_Restore($that);
86
87
try {
88
	$return = $xcloner_restore->init();
89
	$xcloner_restore->send_response(200, $return);
90
}catch (Exception $e) {
91
	$xcloner_restore->send_response(417, $e->getMessage());
92
}
93
94
class Xcloner_Restore
95
{
96
	
97
	const 	xcloner_minimum_version = "5.4.0";
98
	
99
	private $backup_archive_extensions = array("zip", "tar", "tgz", "tar.gz", "gz", "csv");
100
	private $process_files_limit = 150;
101
	private $process_files_limit_list = 350;
102
	private $process_mysql_records_limit = 250;
103
	private $adapter;
104
	private $filesystem;
105
	private $logger;
106
	private $backup_storage_dir;
107
	private $parent_api;
108
109
	private $target_adapter;
110
	private $target_filesystem;
111
112
	/**
113
	 * Xcloner_Restore constructor.
114
	 * @param string $parent_api
115
	 * @throws Exception
116
	 */
117
	public function __construct($parent_api = "")
118
	{
119
		register_shutdown_function(array($this, 'exception_handler'));
120
121
		if (defined('XCLONER_PLUGIN_ACCESS') && XCLONER_PLUGIN_ACCESS)
122
		{
123
			$dir = $parent_api->get_xcloner_container()->get_xcloner_settings()->get_xcloner_store_path();
124
		}
125
		
126
		if (!isset($dir) || !$dir) {
127
			$dir = dirname(__FILE__);
128
		}
129
		
130
		$this->parent_api = $parent_api;
131
		
132
		$this->backup_storage_dir = $dir;
133
		
134
		$this->adapter = new Local($dir, LOCK_EX, 'SKIP_LINKS');
0 ignored issues
show
Bug introduced by
'SKIP_LINKS' of type string is incompatible with the type integer expected by parameter $linkHandling of League\Flysystem\Adapter\Local::__construct(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

134
		$this->adapter = new Local($dir, LOCK_EX, /** @scrutinizer ignore-type */ 'SKIP_LINKS');
Loading history...
135
		$this->filesystem = new Filesystem($this->adapter, new Config([
136
				'disable_asserts' => true,
137
			]));
138
			
139
		$this->logger = new Logger('xcloner_restore');
140
		
141
		$logger_path = $this->get_logger_filename();
142
		
143
		if (!is_writeable($logger_path) and !touch($logger_path))
144
		{
145
			$logger_path = "php://stderr";
146
		}
147
		
148
		$this->logger->pushHandler(new StreamHandler($logger_path, Logger::DEBUG));
149
		
150
		if (isset($_POST['API_ID'])) {
151
			$this->logger->info("Processing ajax request ID ".substr(filter_input(INPUT_POST, 'API_ID', FILTER_SANITIZE_STRING), 0, 15));
152
		}
153
154
	}
155
156
	/**
157
	 * Exception handler method
158
	 */
159
	public function exception_handler() {
160
		
161
		$error = error_get_last();
162
		
163
		if ($error['type'] and $this->logger)
164
		{
165
			$this->logger->info($this->friendly_error_type($error['type']).": ".var_export($error, true));
166
		}
167
	
168
	}
169
170
	/**
171
	 * @param $type
172
	 * @return mixed|string
173
	 */
174
	private function friendly_error_type($type) {
175
		static $levels = null;
176
		if ($levels === null) {
177
			$levels = [];
178
			foreach (get_defined_constants() as $key=>$value) {
179
				if (strpos($key, 'E_') !== 0) {continue; }
180
					$levels[$value] = $key; //substr($key,2);
181
			}
182
		}
183
		return (isset($levels[$type]) ? $levels[$type] : "Error #{$type}");
184
	}
185
	
186
	public function get_logger_filename()
187
	{
188
		$filename = $this->backup_storage_dir.DS."xcloner_restore.log";
189
		
190
		return $filename;
191
	}
192
193
	/**
194
	 * Init method
195
	 *
196
	 * @return mixed|void
197
	 * @throws Exception
198
	 */
199
	public function init()
200
	{
201
		if (isset($_POST['xcloner_action']) and $_POST['xcloner_action'])
202
		{
203
			$method = filter_input(INPUT_POST, 'xcloner_action', FILTER_SANITIZE_STRING);
204
			
205
			//$method = "list_backup_archives";
206
			
207
			$method .= "_action";
208
			
209
			if (method_exists($this, $method))
210
			{
211
				$this->logger->debug(sprintf('Starting action %s', $method));
212
				return call_user_func(array($this, $method));
213
				
214
			} else {
215
				throw new Exception($method." does not exists");
216
				}
217
		}
218
		
219
		return $this->check_system();
220
	}
221
222
	/**
223
	 * Write file method
224
	 *
225
	 * @return bool|int
226
	 * @throws Exception
227
	 */
228
	public function write_file_action()
229
	{
230
		if (isset($_POST['file']))
231
		{
232
			$target_file = filter_input(INPUT_POST, 'file', FILTER_SANITIZE_STRING);
233
			
234
			if (!$_POST['start'])
235
				$fp = fopen($target_file, "wb+");
236
			else
237
				$fp = fopen($target_file, "ab+");	
238
			
239
			if (!$fp)
0 ignored issues
show
introduced by
$fp is of type false|resource, thus it always evaluated to false.
Loading history...
240
				throw new Exception("Unable to open $target_file file for writing");
241
			
242
			fseek($fp, $_POST['start']);
243
			
244
			if (isset($_FILES['blob']))
245
			{
246
				$this->logger->debug(sprintf('Writing %s bytes to file %s starting position %s using FILES blob', filesize($_FILES['blob']['tmp_name']), $target_file, $_POST['start']));
247
				
248
				$blob = file_get_contents($_FILES['blob']['tmp_name']);
249
				
250
				if (!$bytes_written = fwrite($fp, $blob))
251
					throw new Exception("Unable to write data to file $target_file");
252
253
				try {
254
					unlink($_FILES['blob']['tmp_name']);
255
				}catch (Exception $e) {
256
					//silent message
257
				}
258
259
			}elseif (isset($_POST['blob'])) {
260
				$this->logger->debug(sprintf('Writing %s bytes to file %s starting position %s using POST blob', strlen($_POST['blob']), $target_file, $_POST['start']));
261
				
262
				$blob = $_POST['blob'];
263
264
				if (!$bytes_written = fwrite($fp, $blob))
265
					throw new Exception("Unable to write data to file $target_file");
266
			} else {
267
				throw new Exception("Upload failed, did not receive any binary data");
268
			}
269
			
270
			fclose($fp);
271
		}
272
		
273
		return $bytes_written;
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $bytes_written does not seem to be defined for all execution paths leading up to this point.
Loading history...
274
		
275
	}
276
277
	/**
278
	 * Connect to mysql server method
279
	 *
280
	 * @param $remote_mysql_host
281
	 * @param $remote_mysql_user
282
	 * @param $remote_mysql_pass
283
	 * @param $remote_mysql_db
284
	 * @return mysqli
285
	 * @throws Exception
286
	 */
287
	public function mysql_connect($remote_mysql_host, $remote_mysql_user, $remote_mysql_pass, $remote_mysql_db)
288
	{
289
		$this->logger->info(sprintf('Connecting to mysql database %s with %s@%s', $remote_mysql_db, $remote_mysql_user, $remote_mysql_host));
290
291
		$mysqli = new mysqli($remote_mysql_host, $remote_mysql_user, $remote_mysql_pass, $remote_mysql_db);
292
293
		if ($mysqli->connect_error) {
294
			throw new Exception('Connect Error ('.$mysqli->connect_errno.') '
295
				. $mysqli->connect_error);
296
		}
297
		
298
		$mysqli->query("SET sql_mode='';");
299
		$mysqli->query("SET foreign_key_checks = 0;");
300
		if (isset($_REQUEST['charset_of_file']) and $_REQUEST['charset_of_file'])
301
			$mysqli->query("SET NAMES ".$_REQUEST['charset_of_file']."");
302
		else
303
			$mysqli->query("SET NAMES utf8;");
304
			
305
		return $mysqli;	
306
	}
307
308
	/**
309
	 * Restore mysql backup file
310
	 *
311
	 * @throws Exception
312
	 */
313
	public function restore_mysql_backup_action()
314
	{
315
		$mysqldump_file = filter_input(INPUT_POST, 'mysqldump_file', FILTER_SANITIZE_STRING);
316
		$remote_path = filter_input(INPUT_POST, 'remote_path', FILTER_SANITIZE_STRING);
317
		$remote_mysql_user 	= filter_input(INPUT_POST, 'remote_mysql_user', FILTER_SANITIZE_STRING);
318
		$remote_mysql_pass 	= filter_input(INPUT_POST, 'remote_mysql_pass', FILTER_SANITIZE_STRING);
319
		$remote_mysql_db = filter_input(INPUT_POST, 'remote_mysql_db', FILTER_SANITIZE_STRING);
320
		$remote_mysql_host 	= filter_input(INPUT_POST, 'remote_mysql_host', FILTER_SANITIZE_STRING);
321
		$execute_query = trim(stripslashes($_POST['query']));
322
		$error_line = filter_input(INPUT_POST, 'error_line', FILTER_SANITIZE_NUMBER_INT);
0 ignored issues
show
Unused Code introduced by
The assignment to $error_line is dead and can be removed.
Loading history...
323
		$start = filter_input(INPUT_POST, 'start', FILTER_SANITIZE_NUMBER_INT);
324
		
325
		$wp_home_url 		= filter_input(INPUT_POST, 'wp_home_url', FILTER_SANITIZE_STRING);
326
		$remote_restore_url = filter_input(INPUT_POST, 'remote_restore_url', FILTER_SANITIZE_STRING);
327
		
328
		$wp_site_url 		= filter_input(INPUT_POST, 'wp_site_url', FILTER_SANITIZE_STRING);
329
		$restore_site_url 	= filter_input(INPUT_POST, 'restore_site_url', FILTER_SANITIZE_STRING);
330
		
331
		$mysql_backup_file = $remote_path.DS.$mysqldump_file;
332
		
333
		if (!file_exists($mysql_backup_file))
334
			throw new Exception(sprintf("Mysql backup file %s does not exists", $mysql_backup_file));
335
		
336
		
337
		/*if(defined('XCLONER_PLUGIN_ACCESS') && XCLONER_PLUGIN_ACCESS)
338
		{
339
			global $wpdb;
340
			//$mysqli = $this->parent_api->get_xcloner_container()->get_xcloner_database();
341
			$remote_mysql_host 	= $wpdb->dbhost;
342
			$remote_mysql_user 	= $wpdb->dbuser;
343
			$remote_mysql_pass 	= $wpdb->dbpassword;
344
			$remote_mysql_db 	= $wpdb->dbname;
345
		}*/
346
		
347
		{
348
			$mysqli = $this->mysql_connect($remote_mysql_host, $remote_mysql_user, $remote_mysql_pass, $remote_mysql_db);
349
		}
350
		
351
		$line_count = 0;
352
		$query = "";
353
		$return = array();
354
		$return['finished'] = 1;
355
		$return['backup_file']	= $mysqldump_file;
356
		$return['backup_size']	= filesize($mysql_backup_file);
357
		
358
		$fp = fopen($mysql_backup_file, "r");
359
		if ($fp)
0 ignored issues
show
introduced by
$fp is of type false|resource, thus it always evaluated to false.
Loading history...
360
		{
361
			$this->logger->info(sprintf("Opening mysql dump file %s at position %s.", $mysql_backup_file, $start));
362
			fseek($fp, $start);
363
			while ($line_count <= $this->process_mysql_records_limit and ($line = fgets($fp)) !== false) {
364
			// process the line read.
365
									
366
				//check if line is comment
367
				if (substr($line, 0, 1) == "#")
368
					continue;
369
				
370
				//check if line is empty	
371
				if ($line == "\n" or trim($line) == "")
372
					continue;
373
					
374
				if (substr($line, strlen($line) - 2, strlen($line)) == ";\n")
375
					$query .= $line;
376
				else {
377
					$query .= $line;
378
					continue;
379
				}
380
				
381
				if ($execute_query)
382
				{
383
					$query = (($execute_query));
384
					$execute_query = "";
385
				}	
386
				
387
				//Doing serialized url replace here
388
				
389
				if ($wp_site_url and $wp_home_url and strlen($wp_home_url) < strlen($wp_site_url))
390
				{
391
					list($wp_home_url, $wp_site_url) = array($wp_site_url, $wp_home_url);
392
					list($remote_restore_url, $restore_site_url) = array($restore_site_url, $remote_restore_url);
393
					
394
				}
395
				
396
				if ($wp_home_url and $remote_restore_url and strpos($query, $wp_home_url) !== false)
397
				{
398
					$query = $this->url_replace($wp_home_url, $remote_restore_url, $query);
399
				}
400
				
401
				if ($wp_site_url and $restore_site_url and strpos($query, $wp_site_url) !== false)
402
				{
403
					$query = $this->url_replace($wp_site_url, $restore_site_url, $query);
404
				}
405
				
406
				if (!$mysqli->query($query) && !stristr($mysqli->error, "Duplicate entry"))
407
				{
408
					//$return['error_line'] = $line_count;
409
					$return['start'] = ftell($fp) - strlen($line);
410
					$return['query_error'] = true;
411
					$return['query'] = $query;
412
					$return['message'] = sprintf("Mysql Error: %s\n", $mysqli->error);
413
					
414
					$this->logger->error($return['message']);
415
					
416
					$this->send_response(418, $return);
417
					//throw new Exception(sprintf("Mysql Error: %s\n Mysql Query: %s", $mysqli->error, $query));
418
				}
419
				//else echo $line;
420
					
421
				$query = "";
422
423
				$line_count++;
424
				
425
			}
426
427
			$return['start'] = ftell($fp);
428
429
			$this->logger->info(sprintf("Executed %s queries of size %s bytes", $line_count, ($return['start'] - $start)));
430
431
			if (!feof($fp))
432
			{
433
				$return['finished'] = 0;
434
			} else {
435
				$this->logger->info(sprintf("Mysql Import Done."));
436
			}
437
438
			fclose($fp);
439
		}
440
		
441
		$this->send_response(200, $return);
442
	}
443
444
	/**
445
	 * Url replace method inside database backup file
446
	 *
447
	 * @param $search
448
	 * @param $replace
449
	 * @param $query
450
	 * @return mixed|string|string[]|null
451
	 */
452
	private function url_replace($search, $replace, $query)
453
	{
454
		$this->logger->info(sprintf("Doing url replace on query with length %s", strlen($query)), array("QUERY_REPLACE"));
455
		$query = str_replace($search, $replace, $query);
456
		$original_query = $query;
457
		
458
		if ($this->has_serialized($query))
459
		{
460
			$this->logger->info(sprintf("Query contains serialized data, doing serialized size fix"), array("QUERY_REPLACE"));
461
			$query = $this->do_serialized_fix($query);
462
			
463
			if (!$query)
464
			{
465
				$this->logger->info(sprintf("Serialization probably failed here..."), array("QUERY_REPLACE"));
466
				$query = $original_query;
467
			}
468
		}
469
		$this->logger->info(sprintf("New query length is %s", strlen($query)), array("QUERY_REPLACE"));
470
		
471
		return $query;
472
	}
473
474
	/**
475
	 * List backup files method
476
	 *
477
	 * @throws \League\Flysystem\FileNotFoundException
478
	 */
479
	public function list_backup_files_action()
480
	{
481
		$backup_parts = array();
482
		
483
		$source_backup_file = filter_input(INPUT_POST, 'file', FILTER_SANITIZE_STRING);
484
		$start = (int)filter_input(INPUT_POST, 'start', FILTER_SANITIZE_STRING);
485
		$return['part'] = (int)filter_input(INPUT_POST, 'part', FILTER_SANITIZE_STRING);
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
486
		
487
		$backup_file = $source_backup_file;
488
		
489
		if ($this->is_multipart($backup_file))
490
		{
491
			$backup_parts = $this->get_multipart_files($backup_file);
492
			$backup_file = $backup_parts[$return['part']];
493
		}
494
		
495
		try {
496
			$tar = new Tar();
497
			$tar->open($this->backup_storage_dir.DS.$backup_file, $start);
498
		
499
			$data = $tar->contents($this->process_files_limit_list);
500
		}catch (Exception $e)
501
		{
502
			$return['error'] = true;
503
			$return['message'] = $e->getMessage();
504
			$this->send_response(200, $return);
505
		}
506
		
507
		$return['files'] = array();
508
		$return['finished'] = 1;
509
		$return['total_size'] = filesize($this->backup_storage_dir.DS.$backup_file);
510
		$i = 0;
511
		
512
		if (isset($data['extracted_files']) and is_array($data['extracted_files']))
513
		{
514
			foreach ($data['extracted_files'] as $file)
515
			{
516
				$return['files'][$i]['path'] = $file->getPath();
517
				$return['files'][$i]['size'] = $file->getSize();
518
				$return['files'][$i]['mtime'] = date("d M,Y H:i", $file->getMtime());
519
				
520
				$i++;
521
			}
522
		}
523
		
524
		if (isset($data['start']))
525
		{
526
			$return['start'] = $data['start'];
527
			$return['finished'] = 0;	
528
		} else {
529
			if ($this->is_multipart($source_backup_file))
530
			{
531
				$return['start'] = 0;
532
				
533
				++$return['part'];
534
			
535
				if ($return['part'] < sizeof($backup_parts))	
536
					$return['finished'] = 0;
537
				
538
			}
539
		}	
540
		
541
		$this->send_response(200, $return);
542
	}
543
544
	/**
545
	 * Finish backup restore method
546
	 *
547
	 * @throws \League\Flysystem\FileNotFoundException
548
	 */
549
	public function restore_finish_action()
550
	{
551
		$remote_path 		= filter_input(INPUT_POST, 'remote_path', FILTER_SANITIZE_STRING);
552
		
553
		$wp_home_url 		= filter_input(INPUT_POST, 'wp_home_url', FILTER_SANITIZE_STRING);
0 ignored issues
show
Unused Code introduced by
The assignment to $wp_home_url is dead and can be removed.
Loading history...
554
		$remote_restore_url = filter_input(INPUT_POST, 'remote_restore_url', FILTER_SANITIZE_STRING);
555
		
556
		$remote_mysql_user 	= filter_input(INPUT_POST, 'remote_mysql_user', FILTER_SANITIZE_STRING);
557
		$remote_mysql_pass 	= filter_input(INPUT_POST, 'remote_mysql_pass', FILTER_SANITIZE_STRING);
558
		$remote_mysql_db = filter_input(INPUT_POST, 'remote_mysql_db', FILTER_SANITIZE_STRING);
559
		$remote_mysql_host 	= filter_input(INPUT_POST, 'remote_mysql_host', FILTER_SANITIZE_STRING);
560
		
561
		$update_remote_site_url = filter_input(INPUT_POST, 'update_remote_site_url', FILTER_SANITIZE_NUMBER_INT);
562
		$delete_restore_script = filter_input(INPUT_POST, 'delete_restore_script', FILTER_SANITIZE_NUMBER_INT);
563
		$delete_backup_temporary_folder = filter_input(INPUT_POST, 'delete_backup_temporary_folder', FILTER_SANITIZE_NUMBER_INT);
564
				
565
		if ($update_remote_site_url)
566
		{
567
			$mysqli = $this->mysql_connect($remote_mysql_host, $remote_mysql_user, $remote_mysql_pass, $remote_mysql_db);
568
			$this->update_wp_config($remote_path, $remote_mysql_host, $remote_mysql_user, $remote_mysql_pass, $remote_mysql_db);
569
			$this->update_wp_url($remote_path, $remote_restore_url, $mysqli);
570
		}
571
		
572
		if ($delete_backup_temporary_folder)
573
		{
574
			$this->delete_backup_temporary_folder($remote_path);
575
		}
576
		
577
		if (!defined('XCLONER_PLUGIN_ACCESS') || XCLONER_PLUGIN_ACCESS != 1)
578
		{
579
			if ($delete_restore_script)
580
			{
581
				$this->delete_self();
582
			}
583
		}
584
		
585
		$return = "Restore Process Finished.";
586
		$this->send_response(200, $return);
587
	}
588
589
	/**
590
	 * Delete backup temporary folder
591
	 *
592
	 * @param $remote_path
593
	 * @return bool
594
	 */
595
	private function delete_backup_temporary_folder($remote_path)
596
	{
597
		$this->target_adapter = new Local($remote_path, LOCK_EX, 'SKIP_LINKS');
0 ignored issues
show
Bug introduced by
'SKIP_LINKS' of type string is incompatible with the type integer expected by parameter $linkHandling of League\Flysystem\Adapter\Local::__construct(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

597
		$this->target_adapter = new Local($remote_path, LOCK_EX, /** @scrutinizer ignore-type */ 'SKIP_LINKS');
Loading history...
598
		$this->target_filesystem = new Filesystem($this->target_adapter, new Config([
599
				'disable_asserts' => true,
600
			]));
601
			
602
		$mysqldump_list = array();
0 ignored issues
show
Unused Code introduced by
The assignment to $mysqldump_list is dead and can be removed.
Loading history...
603
		$list = $this->target_filesystem->listContents();
604
		
605
		foreach ($list as $file)
606
		{
607
			$matches = array();
608
			
609
			if ($file['type'] == "dir")
610
			{
611
				if (preg_match("/xcloner-(\w*)/", $file['basename'], $matches)) {
612
					$this->logger->info(sprintf('Deleting temporary folder %s', $file['path']));
613
					$this->target_filesystem->deleteDir($file['path']);
614
				}
615
			}
616
		}
617
		
618
		return true;
619
	
620
	}
621
622
	/**
623
	 * Delete restore script method
624
	 *
625
	 * @throws \League\Flysystem\FileNotFoundException
626
	 */
627
	private function delete_self()
628
	{
629
		if ($this->filesystem->has("vendor.phar"))
630
		{
631
			$this->logger->info(sprintf('Deleting vendor.phar'));
632
			$this->filesystem->delete("vendor.phar");
633
		}
634
		if ($this->filesystem->has("vendor"))
635
		{
636
			$this->logger->info(sprintf('Deleting vendor folder'));
637
			$this->filesystem->deleteDir("vendor");
638
		}
639
		if ($this->filesystem->has("xcloner_restore.php"))
640
		{
641
			$this->logger->info(sprintf('Deleting xcloner_restore.php'));
642
			$this->filesystem->delete("xcloner_restore.php");
643
		}
644
		
645
		if ($this->filesystem->has("xcloner_restore.log"))
646
		{
647
			$this->logger->info(sprintf('Deleting xcloner_restore.log'));
648
			$this->filesystem->delete("xcloner_restore.log");
649
		}
650
		
651
		if ($this->filesystem->has($this->get_logger_filename()))
652
		{
653
			$this->logger->info(sprintf('Deleting logger file %s', $this->get_logger_filename()));
654
			$this->filesystem->delete($this->get_logger_filename());
655
		}
656
		
657
	}
658
659
	/**
660
	 * Update Wordpress url in wp-config.php method
661
	 * @param $wp_path
662
	 * @param $url
663
	 * @param mysqli $mysqli
664
	 * @return bool
665
	 * @throws Exception
666
	 */
667
	private function update_wp_url($wp_path, $url, $mysqli)
668
	{
669
		$wp_config = $wp_path.DS."wp-config.php";
670
		
671
		$this->logger->info(sprintf('Updating site url to %s', $url));
672
		
673
		if (file_exists($wp_config))
674
		{
675
			$config = file_get_contents($wp_config);
676
			preg_match("/.*table_prefix.*=.*'(.*)'/i", $config, $matches);
677
			if (isset($matches[1]))
678
				$table_prefix = $matches[1];
679
			else
680
				throw new Exception("Could not load wordpress table prefix from wp-config.php file.");
681
		}
682
		else
683
			throw new Exception("Could not update the SITEURL and HOME, wp-config.php file not found");
684
			
685
		if (!$mysqli->query("update ".$table_prefix."options set option_value='".($url)."' where option_name='home'"))
686
			throw new Exception(sprintf("Could not update the HOME option, error: %s\n", $mysqli->error));
687
		
688
		if (!$mysqli->query("update ".$table_prefix."options set option_value='".($url)."' where option_name='siteurl'"))
689
			throw new Exception(sprintf("Could not update the SITEURL option, error: %s\n", $mysqli->error));
690
		
691
		return true;
692
	}
693
694
	/**
695
	 * Update local wp-config.php file method
696
	 *
697
	 * @param $remote_path
698
	 * @param $remote_mysql_host
699
	 * @param $remote_mysql_user
700
	 * @param $remote_mysql_pass
701
	 * @param $remote_mysql_db
702
	 * @return string
703
	 * @throws Exception
704
	 */
705
	private function update_wp_config($remote_path, $remote_mysql_host, $remote_mysql_user, $remote_mysql_pass, $remote_mysql_db)
706
	{
707
		$wp_config = $remote_path.DS."wp-config.php";
708
		
709
		if (!file_exists($wp_config))
710
		{
711
			throw new Exception("Could not find the wp-config.php in ".$remote_path);
712
		}
713
		
714
		$content = file_get_contents($wp_config);
715
		
716
		$content = preg_replace("/(?<=DB_NAME', ')(.*?)(?='\);)/", $remote_mysql_db, $content);
717
		$content = preg_replace("/(?<=DB_USER', ')(.*?)(?='\);)/", $remote_mysql_user, $content);
718
		$content = preg_replace("/(?<=DB_PASSWORD', ')(.*?)(?='\);)/", $remote_mysql_pass, $content);
719
		$content = preg_replace("/(?<=DB_HOST', ')(.*?)(?='\);)/", $remote_mysql_host, $content);
720
		
721
		$file_perms = fileperms($wp_config);
722
		
723
		chmod($wp_config, 0777);
724
		
725
		$this->logger->info(sprintf('Updating wp-config.php file with the new mysql details'));
726
		
727
		if (!file_put_contents($wp_config, $content))
728
			throw new Exception("Could not write updated config data to ".$wp_config);
729
		
730
		chmod($wp_config, $file_perms);
731
		
732
		return $wp_config;
733
		
734
	}
735
736
	/**
737
	 * List mysqldump database backup files
738
	 *
739
	 */
740
	public function list_mysqldump_backups_action()
741
	{
742
		$source_backup_file = filter_input(INPUT_POST, 'backup_file', FILTER_SANITIZE_STRING);
743
		$remote_path = filter_input(INPUT_POST, 'remote_path', FILTER_SANITIZE_STRING);
744
	
745
		$hash = $this->get_hash_from_backup($source_backup_file);	
746
		
747
		$this->target_adapter = new Local($remote_path, LOCK_EX, 'SKIP_LINKS');
0 ignored issues
show
Bug introduced by
'SKIP_LINKS' of type string is incompatible with the type integer expected by parameter $linkHandling of League\Flysystem\Adapter\Local::__construct(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

747
		$this->target_adapter = new Local($remote_path, LOCK_EX, /** @scrutinizer ignore-type */ 'SKIP_LINKS');
Loading history...
748
		$this->target_filesystem = new Filesystem($this->target_adapter, new Config([
749
				'disable_asserts' => true,
750
			]));
751
			
752
		$mysqldump_list = array();
753
		$list = $this->target_filesystem->listContents();
754
		
755
		foreach ($list as $file)
756
		{
757
			$matches = array();
758
			
759
			if ($file['type'] == "dir")
760
			{
761
				if (preg_match("/xcloner-(\w*)/", $file['basename'], $matches))
762
				{
763
					$files = $this->target_filesystem->listContents($file['basename']);
764
					foreach ($files as $file)
0 ignored issues
show
Comprehensibility Bug introduced by
$file is overwriting a variable from outer foreach loop.
Loading history...
765
					{
766
						if ($file['extension'] == "sql")
767
						{
768
							$this->logger->info(sprintf('Found %s mysql backup file', $file['path']));
769
							$mysqldump_list[$file['path']]['path'] = $file['path'];
770
							$mysqldump_list[$file['path']]['size'] = $file['size'];
771
							$mysqldump_list[$file['path']]['timestamp'] = date("d M,Y H:i", $file['timestamp']);
772
							
773
							if ($hash and $hash == $matches[1])
774
								$mysqldump_list[$file['path']]['selected'] = "selected";
775
							else
776
								$mysqldump_list[$file['path']]['selected'] = "";	
777
						}
778
					}
779
				}
780
			}	
781
		}
782
		
783
		$this->sort_by($mysqldump_list, 'timestamp', 'desc');
784
		$return['files'] = $mysqldump_list;
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
785
		
786
		$this->send_response(200, $return);
787
	}
788
789
	/**
790
	 * Get backup hash method
791
	 *
792
	 * @param $backup_file
793
	 * @return false|string
794
	 */
795
	private function get_hash_from_backup($backup_file)
796
	{
797
		if (!$backup_file)
798
			return false;
799
			
800
		$result = preg_match("/-(\w*)./", substr($backup_file, strlen($backup_file) - 10, strlen($backup_file)), $matches);
801
		
802
		if ($result and isset($matches[1]))
803
			return ($matches[1]);
804
		
805
		return false;
806
	}
807
808
	/**
809
	 * List backup archives found on local system
810
	 *
811
	 * @throws \League\Flysystem\FileNotFoundException
812
	 */
813
	public function list_backup_archives_action()
814
	{
815
		$local_backup_file = filter_input(INPUT_POST, 'local_backup_file', FILTER_SANITIZE_STRING);
816
		$list = $this->filesystem->listContents();
817
		
818
		$backup_files = array();
819
		$parents = array();
820
		
821
		foreach ($list as $file_info)
822
		{
823
			$data = array();
824
			
825
			if (isset($file_info['extension']) and $file_info['extension'] == "csv")
826
			{
827
				$lines = explode(PHP_EOL, $this->filesystem->read($file_info['path']));
0 ignored issues
show
Bug introduced by
It seems like $this->filesystem->read($file_info['path']) can also be of type false; however, parameter $string of explode() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

827
				$lines = explode(PHP_EOL, /** @scrutinizer ignore-type */ $this->filesystem->read($file_info['path']));
Loading history...
828
				foreach ($lines as $line)
829
					if ($line)
830
					{
831
						$data = str_getcsv($line);
832
						if (is_array($data)) {
833
							$parents[$data[0]] = $file_info['path'];
834
							$file_info['childs'][] = $data;
835
							$file_info['size'] += $data[2];
836
						}
837
					}
838
						
839
			}
840
			
841
			if ($file_info['type'] == 'file' and isset($file_info['extension']) and in_array($file_info['extension'], $this->backup_archive_extensions))
842
				$backup_files[$file_info['path']] = $file_info;
843
		}
844
		
845
		$new_list = array();
846
		
847
		foreach ($backup_files as $key=>$file_info)
848
		{
849
			if (isset($parents[$file_info['path']]))
850
				$backup_files[$key]['parent'] = $parents[$file_info['path']];
851
			else {
852
				
853
				if ($local_backup_file and ($file_info['basename'] == $local_backup_file))
854
					$file_info['selected'] = 'selected';
855
				
856
				$this->logger->info(sprintf('Found %s backup file', $file_info['path']));
857
					
858
				$new_list[$key] = $file_info;
859
			}
860
				
861
		}
862
		
863
		$this->sort_by($new_list, "timestamp", "desc");
864
		
865
		$return['files'] = $new_list;
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
866
		
867
		$this->send_response(200, $return);
868
		
869
	}
870
871
	/**
872
	 * Restore backup archive to local path
873
	 *
874
	 * @throws \League\Flysystem\FileNotFoundException
875
	 * @throws \splitbrain\PHPArchive\ArchiveIOException
876
	 */
877
	public function restore_backup_to_path_action()
878
	{
879
		$source_backup_file = filter_input(INPUT_POST, 'backup_file', FILTER_SANITIZE_STRING);
880
		$remote_path = filter_input(INPUT_POST, 'remote_path', FILTER_SANITIZE_STRING);
881
		$include_filter_files 	= filter_input(INPUT_POST, 'filter_files', FILTER_SANITIZE_STRING);
882
		$exclude_filter_files 	= "";
883
		$start = filter_input(INPUT_POST, 'start', FILTER_SANITIZE_NUMBER_INT);
884
		$return['part'] = (int)filter_input(INPUT_POST, 'part', FILTER_SANITIZE_NUMBER_INT);
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
885
		$return['processed'] 	= (int)filter_input(INPUT_POST, 'processed', FILTER_SANITIZE_NUMBER_INT);
886
				
887
		$this->target_adapter = new Local($remote_path, LOCK_EX, 'SKIP_LINKS');
0 ignored issues
show
Bug introduced by
'SKIP_LINKS' of type string is incompatible with the type integer expected by parameter $linkHandling of League\Flysystem\Adapter\Local::__construct(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

887
		$this->target_adapter = new Local($remote_path, LOCK_EX, /** @scrutinizer ignore-type */ 'SKIP_LINKS');
Loading history...
888
		$this->target_filesystem = new Filesystem($this->target_adapter, new Config([
889
				'disable_asserts' => true,
890
			]));
891
		
892
		$backup_file = $source_backup_file;
893
		
894
		$return['finished'] = 1;
895
		$return['extracted_files'] = array();
896
		$return['total_size'] = $this->get_backup_size($backup_file);
897
		
898
		$backup_archive = new Tar();
899
		if ($this->is_multipart($backup_file))
900
		{
901
			if (!$return['part'])
902
				$return['processed'] += $this->filesystem->getSize($backup_file);
903
				
904
			$backup_parts = $this->get_multipart_files($backup_file);
905
			$backup_file = $backup_parts[$return['part']];	
906
		}
907
908
		if( $this->is_encrypted_file($backup_file) ) {
909
		    $message = sprintf('Backup file %s seems encrypted, please Decrypt it first from your Manage Backups panel.', $backup_file);
910
            $this->logger->error($message);
911
            $this->send_response(500, $message);
912
            return;
913
        }
914
		
915
		$this->logger->info(sprintf('Opening backup archive %s at position %s', $backup_file, $start));
916
		$backup_archive->open($this->backup_storage_dir.DS.$backup_file, $start);
917
918
		$data = $backup_archive->extract($remote_path, '', $exclude_filter_files, $include_filter_files, $this->process_files_limit);
919
		
920
		if (isset($data['extracted_files']))
921
		{
922
			foreach ($data['extracted_files'] as $spl_fileinfo)
923
			{
924
				$this->logger->info(sprintf('Extracted %s file', $spl_fileinfo->getPath()));
925
				$return['extracted_files'][] = $spl_fileinfo->getPath()." (".$spl_fileinfo->getSize()." bytes)";
926
			}
927
		}
928
		
929
		if (isset($data['start']))
930
		//if(isset($data['start']) and $data['start'] <= $this->filesystem->getSize($backup_file))
931
		{
932
			$return['finished'] = 0;
933
			$return['start'] = $data['start'];
934
		} else {
935
			
936
			$return['processed'] += $start;
937
			
938
			if ($this->is_multipart($source_backup_file))
939
			{
940
				$return['start'] = 0;
941
				
942
				++$return['part'];
943
			
944
				if ($return['part'] < sizeof($backup_parts))	
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $backup_parts does not seem to be defined for all execution paths leading up to this point.
Loading history...
945
					$return['finished'] = 0;
946
				
947
			}
948
		}
949
		
950
		if ($return['finished'])
951
			$this->logger->info(sprintf('Done extracting %s', $source_backup_file));
952
		
953
		$return['backup_file'] = $backup_file;
954
		
955
		$this->send_response(200, $return);
956
	}
957
958
    /**
959
     * Check if provided filename has encrypted suffix
960
     *
961
     * @param $filename
962
     * @return bool
963
     */
964
    public function is_encrypted_file($filename) {
965
        $fp = $this->filesystem->readStream( $filename );
966
        if (is_resource($fp)) {
967
            $encryption_length = fread($fp, 16);
968
            fclose($fp);
969
            if (is_numeric($encryption_length)) {
970
                return true;
971
            }
972
        }
973
974
        return false;
975
976
    }
977
978
	/**
979
	 * Get current directory method
980
	 */
981
	public function get_current_directory_action()
982
	{	
983
		global $wpdb;
984
		
985
		$restore_script_url = filter_input(INPUT_POST, 'restore_script_url', FILTER_SANITIZE_STRING);
986
		
987
		$pathinfo = pathinfo(__FILE__);
988
		
989
		$suffix = "";
990
		$return['remote_mysql_host'] 	= "localhost";
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
991
		$return['remote_mysql_user'] 	= "";
992
		$return['remote_mysql_pass'] 	= "";
993
		$return['remote_mysql_db'] = "";
994
		
995
		if (defined('XCLONER_PLUGIN_ACCESS') && XCLONER_PLUGIN_ACCESS)
996
		{
997
			$return['dir'] = realpath(get_home_path().DS.$suffix);
998
			$return['restore_script_url'] = get_site_url();
999
			$return['remote_mysql_host'] 	= $wpdb->dbhost;
1000
			$return['remote_mysql_user'] 	= $wpdb->dbuser;
1001
			$return['remote_mysql_pass'] 	= $wpdb->dbpassword;
1002
			$return['remote_mysql_db'] = $wpdb->dbname;
1003
		}
1004
		else {
1005
			$return['dir'] = ($pathinfo['dirname']).DS.$suffix;
1006
			$return['restore_script_url'] = str_replace($pathinfo['basename'], "", $restore_script_url).$suffix;
1007
		}	
1008
		
1009
		$this->logger->info(sprintf('Determining current url as %s and path as %s', $return['dir'], $return['restore_script_url']));
1010
		
1011
		$this->send_response(200, $return);
1012
	}
1013
1014
	/**
1015
	 * Check current filesystem
1016
	 *
1017
	 * @throws Exception
1018
	 */
1019
	public function check_system()
1020
	{
1021
		//check if i can write
1022
		$tmp_file = md5(time());
1023
		if (!file_put_contents($tmp_file, "++"))
1024
			throw new Exception("Could not write to new host");
1025
		
1026
		if (!unlink($tmp_file))
1027
			throw new Exception("Could not delete temporary file from new host");
1028
		
1029
		$max_upload      = $this->return_bytes((ini_get('upload_max_filesize')));
1030
		$max_post        = $this->return_bytes((ini_get('post_max_size')));
1031
1032
		$return['max_upload_size'] = min($max_upload, $max_post); // bytes
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
1033
		$return['status'] = true;
1034
		
1035
		$this->logger->info(sprintf('Current filesystem max upload size is %s bytes', $return['max_upload_size']));
1036
		
1037
		$this->send_response(200, $return);
1038
	}
1039
1040
	/**
1041
	 * Return bytes from human readable value
1042
	 *
1043
	 * @param string $val
1044
	 * @return int
1045
	 *
1046
	 */
1047
	private function return_bytes($val) {
1048
		$numeric_val = (int)trim($val);
1049
		$last = strtolower($val[strlen($val) - 1]);
1050
		switch ($last) {
1051
			// The 'G' modifier is available since PHP 5.1.0
1052
			case 'g':
1053
				//gigabytes
1054
				$numeric_val *= 1024;
1055
			case 'm':
1056
				//megabytes
1057
				$numeric_val *= 1024;
1058
			case 'k':
1059
				//kilobytes
1060
				$numeric_val *= 1024;
1061
		}
1062
1063
		return $numeric_val;
1064
	}
1065
1066
	/**
1067
	 * Check if backup archive os multipart
1068
	 *
1069
	 * @param $backup_name
1070
	 * @return bool
1071
	 */
1072
	public function is_multipart($backup_name)
1073
	{
1074
		if (stristr($backup_name, "-multipart"))
1075
			return true;
1076
		
1077
		return false;	
1078
	}
1079
1080
	/**
1081
	 * Get backup archive size
1082
	 *
1083
	 * @param $backup_name
1084
	 * @return bool|false|int
1085
	 * @throws \League\Flysystem\FileNotFoundException
1086
	 */
1087
	public function get_backup_size($backup_name)
1088
	{
1089
		$backup_size = $this->filesystem->getSize($backup_name);
1090
		if ($this->is_multipart($backup_name))
1091
		{
1092
			$backup_parts = $this->get_multipart_files($backup_name);
1093
			foreach ($backup_parts as $part_file)
1094
				$backup_size += $this->filesystem->getSize($part_file);
1095
		}
1096
		
1097
		return $backup_size;
1098
	}
1099
1100
	/**
1101
	 * Get multipart backup files list
1102
	 * @param $backup_name
1103
	 * @return array
1104
	 * @throws \League\Flysystem\FileNotFoundException
1105
	 */
1106
	public function get_multipart_files($backup_name)
1107
	{
1108
		$files = array();
1109
		
1110
		if ($this->is_multipart($backup_name))
1111
		{
1112
			$lines = explode(PHP_EOL, $this->filesystem->read($backup_name));
0 ignored issues
show
Bug introduced by
It seems like $this->filesystem->read($backup_name) can also be of type false; however, parameter $string of explode() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1112
			$lines = explode(PHP_EOL, /** @scrutinizer ignore-type */ $this->filesystem->read($backup_name));
Loading history...
1113
			foreach ($lines as $line)
1114
			{
1115
				if ($line)
1116
				{
1117
					$data = str_getcsv($line);
1118
					$files[] = $data[0];
1119
				}
1120
			}
1121
		}
1122
		
1123
		return $files;
1124
	}
1125
1126
	/**
1127
	 * Sort_by method
1128
	 *
1129
	 * @param $array
1130
	 * @param string $field
1131
	 * @param string $direction
1132
	 * @return bool
1133
	 */
1134
	private function sort_by(&$array, $field, $direction = 'asc')
1135
	{
1136
		$direction = strtolower($direction);
1137
1138
		usort($array,
1139
1140
			/**
1141
			 * @param string $b
1142
			 */
1143
			function($a, $b) use($field, $direction){
1144
1145
				$a = $a[$field];
1146
				$b = $b[$field];
1147
1148
				if ($a == $b)
1149
				{
1150
					return 0;
1151
				}
1152
1153
				if ($direction == 'desc') {
1154
					if ($a > $b) {
1155
						return -1;
1156
					}
1157
					else {
1158
						return 1;
1159
					}
1160
				} else {
1161
					if ($a < $b) {
1162
						return -1;
1163
					}
1164
					else {
1165
						return 1;
1166
					}
1167
				}
1168
1169
				//return ($a.($direction == 'desc' ? '>' : '<').$b) ? -1 : 1;
1170
			}
1171
		);
1172
1173
		return true;
1174
	}
1175
1176
	/**
1177
	 * Send response method
1178
	 *
1179
	 * @param int $status
1180
	 * @param $response
1181
	 */
1182
	public static function send_response($status = 200, $response)
1183
	{
1184
		header("Access-Control-Allow-Origin: *");
1185
		header("HTTP/1.1 200");
1186
		header('Content-Type: application/json');
1187
		$return['status'] = $status;
0 ignored issues
show
Comprehensibility Best Practice introduced by
$return was never initialized. Although not strictly required by PHP, it is generally a good practice to add $return = array(); before regardless.
Loading history...
1188
		$return['statusText'] = $response;
1189
		
1190
		if (isset($response['error']) && $response['error'])
1191
		{
1192
			$return['statusText'] = $response['message'];
1193
			$return['error'] = true;
1194
		}elseif ($status != 200 and $status != 418)
1195
		{
1196
			$return['error'] = true;
1197
			$return['message'] = $response;
1198
		}
1199
		
1200
		die (json_encode($return));
0 ignored issues
show
Best Practice introduced by
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
1201
1202
	}
1203
1204
	/**
1205
	 * Serialize fix methods below for mysql query lines
1206
	 *
1207
	 * @param $query
1208
	 * @return string
1209
	 */
1210
	 
1211
	function do_serialized_fix($query)
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
1212
	{
1213
		$query = str_replace(array("\\n", "\\r", "\\'"), array("", "", "\""), ($query));
1214
		
1215
		return preg_replace_callback('!s:(\d+):([\\\\]?"[\\\\]?"|[\\\\]?"((.*?)[^\\\\])[\\\\]?");!', function($m) {
1216
				  $data = "";
0 ignored issues
show
Unused Code introduced by
The assignment to $data is dead and can be removed.
Loading history...
1217
				  	
1218
				  if (!isset($m[3]))
1219
					$m[3] = "";
1220
					
1221
					$data = 's:'.strlen(($m[3])).':\"'.($m[3]).'\";';
1222
				  //return $this->unescape_quotes($data);
1223
	              
1224
				  return $data;
1225
				}, $query);
1226
	}
1227
1228
	/**
1229
	 * Unescape quotes method
1230
	 *
1231
	 * @param $value
1232
	 * @return mixed
1233
	 */
1234
	private function unescape_quotes($value) {
1235
		return str_replace('\"', '"', $value);
1236
	}
1237
1238
	/**
1239
	 * Unescape mysql method
1240
	 *
1241
	 * @param $value
1242
	 * @return mixed
1243
	 */
1244
	private function unescape_mysql($value) {
1245
		return str_replace(array("\\\\", "\\0", "\\n", "\\r", "\Z", "\'", '\"'),
1246
						   array("\\", "\0", "\n", "\r", "\x1a", "'", '"'), 
1247
						   $value);
1248
	}
1249
1250
	/**
1251
	 * Check if string is in serialized format
1252
	 *
1253
	 * @param $s
1254
	 * @return bool
1255
	 */
1256
	private function has_serialized($s)
1257
	{
1258
		if (
1259
			stristr($s, '{') !== false &&
1260
			stristr($s, '}') !== false &&
1261
			stristr($s, ';') !== false &&
1262
			stristr($s, ':') !== false
1263
			) {
1264
			return true;
1265
		} else {
1266
			return false;
1267
		}
1268
1269
	}
1270
}
1271
1272