PluginProbe
ManageWP Worker / 3.9.4
ManageWP Worker v3.9.4
4.9.38 4.9.37 4.9.36 4.9.35 4.9.34 3.8.7 3.8.8 3.9.0 3.9.1 3.9.10 3.9.11 3.9.12 3.9.13 3.9.14 3.9.15 3.9.16 3.9.17 3.9.18 3.9.19 3.9.2 3.9.20 3.9.21 3.9.22 3.9.23 3.9.24 All 73 releases
worker / backup.class.php

backup.class.php in ManageWP Worker 3.9.4, at backup.class.php

1,242 lines 38.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /*************************************************************
3 *
4 * backup.class.php
5 *
6 * Manage Backups
7 *
8 *
9 * Copyright (c) 2011 Prelovac Media
10 * www.prelovac.com
11 **************************************************************/
12
13 class MMB_Backup extends MMB_Core
14 {
15 function __construct()
16 {
17 parent::__construct();
18 }
19
20 function get_backup_settings()
21 {
22 $backup_settings = get_option('mwp_backup_tasks');
23 if(!empty($backup_settings))
24 return $backup_settings;
25 else
26 return false;
27 }
28
29 function set_backup_task($params)
30 {
31 //$params => [$task_name, $args, $error]
32 if(!empty($params)){
33 extract($params);
34
35 $before = $this->get_backup_settings();
36 if(!$before || empty($before))
37 $before = array();
38
39 if(isset($args['remove'])){
40 unset($before[$task_name]);
41 $return = array('removed' => true);
42 } else {
43 $args['account_info'] = $account_info;
44 $before[$task_name]['task_args'] = $args;
45
46 if(!empty($args['schedule']))
47 $before[$task_name]['task_args']['next'] = $this->schedule_next($args['type'],$args['schedule']);
48
49 $return = $before[$task_name];
50 }
51
52 if($error){
53 $before[$task_name]['task_results'][count($before[$task_name]['task_results'])] = array('error' => $error);
54 }
55 update_option('mwp_backup_tasks',$before);
56
57 if($task_name == 'Backup Now'){
58 $result = $this->backup($args, $task_name);
59 $backup_settings = $this->get_backup_settings();
60 if(is_array($result) && array_key_exists('error',$result)){
61 $return = $result;
62 } else {
63 $return = $backup_settings[$task_name];
64 }
65 }
66 return $return;
67 }
68 return false;
69 }
70
71 //Cron check
72 function check_backup_tasks()
73 {
74 $settings = $this->get_backup_settings();
75 if(is_array($settings) && !empty($settings)){
76 foreach($settings as $task_name => $setting){
77 if($setting['task_args']['next'] && $setting['task_args']['next'] < time()){
78 $result = $this->backup($setting['task_args'], $task_name);
79
80 if(is_array($result) && array_key_exists('error', $result)){
81 $error = $result['error'];
82 } else {
83 $error = '';
84 }
85
86 //Update task with next schedule and possible error
87 $this->set_backup_task(array('task_name' => $task_name, 'args' => $settings[$task_name]['task_args'], 'error' => $error)); //Update
88 break;
89 }
90 }
91 }
92
93 }
94
95
96
97 /*
98 * If Task Name not set then it's manual backup
99 * Backup args:
100 * type -> db, full
101 * what -> daily, weekly, monthly
102 * account_info -> ftp, amazons3, dropbox
103 * exclude-> array of paths to exclude from backup
104 */
105
106 function backup($args, $task_name = false){
107 if(!$args || empty($args))
108 return false;
109
110 extract($args); //extract settings
111
112
113 //try increase memory limit
114 @ini_set('memory_limit', '300M');
115 @set_time_limit(300); //five minutes
116
117 //Remove old backup(s)
118 if($type == 'manual'){
119 $old = get_option('mwp_manual_backup');
120 if($old['file_path'] && file_exists($old['file_path']))
121 @unlink($old['file_path']);
122 } else {
123 $this->remove_old_backups($task_name);
124 }
125
126 $sec_string = md5('mmb-worker');
127 $file = "/$sec_string/mwp_backups";
128 $new_file_path = WP_CONTENT_DIR . $file;
129
130 if (!file_exists($new_file_path)) {
131 if (!mkdir($new_file_path, 0755, true))
132 return array(
133 'error' => 'Permission denied, make sure you have write permission to wp-content folder.'
134 );
135 }
136
137 @file_put_contents($new_file_path . '/index.php', ''); //safe
138 //Delete possible breaked previous backups - don't need it anymore (works only for previous wrokers)
139 foreach (glob($new_file_path."/*.zip") as $filename) {
140 $short = basename($filename);
141 preg_match('/^wp\-content(.*)/Ui',$short,$matches);
142 if($matches)
143 @unlink($filename);
144 }
145
146 //Prepare .zip file name
147 $site_name = $this->remove_http(get_bloginfo('url'));
148 $site_name = str_replace(array(
149 "_",
150 "/"
151 ), array(
152 "",
153 "-"
154 ), $site_name);
155
156 $hash = md5(time());
157 $label = $type ? $type : 'manual';
158 $backup_file = $new_file_path . '/' . $site_name . '_' . $label . '_' . $what . '_' . date('Y-m-d') .'_'.$hash. '.zip';
159 $backup_url = WP_CONTENT_URL . $file . '/' . $site_name . '_' . $label . '_' . $what . '_' . date('Y-m-d') .'_'.$hash. '.zip';
160
161
162 //What to backup - db or full
163 if (trim($what) == 'db') {
164 //take database backup
165
166 $db_result = $this->backup_db();
167 if(!$db_result){
168 return array('error' => 'Failed to extract database.');
169 }
170 else
171 {
172 if ($this->mmb_exec('which zip')) {
173 $command = "zip $backup_file -j $db_result";
174 ob_start();
175 $result = $this->mmb_exec($command);
176 ob_get_clean();
177 } else {
178 require_once ABSPATH . '/wp-admin/includes/class-pclzip.php';
179 $archive = new PclZip($backup_file);
180 $result = $archive->add($db_result, PCLZIP_OPT_REMOVE_ALL_PATH);
181
182 }
183
184 @unlink($db_result);
185 if(!$result)
186 return array(
187 'error' => 'Failed to zip database.'
188 );
189 }
190 }
191 elseif (trim($what) == 'full') {
192 $content_backup = $this->backup_full($backup_file,$exclude);
193 if (is_array($content_backup) && array_key_exists('error', $content_backup)) {
194 return array(
195 'error' => $content_backup['error']
196 );
197 }
198 }
199
200 //Update backup info
201 if($task_name){
202 //backup task (scheduled)
203 $backup_settings = $this->get_backup_settings();
204 $paths = array();
205 $size = ceil(filesize($backup_file) / 1024);
206
207 if($size > 1000){
208 $paths['size'] = ceil($size / 1024).'Mb';
209 } else {
210 $paths['size'] = $size.'kb';
211 }
212 $paths['time'] = time();
213
214 if(!$backup_settings[$task_name]['task_args']['del_host_file']){
215 $paths['server'] = array('file_path' => $backup_file, 'file_url' => $backup_url);
216 }
217
218 if(isset($backup_settings[$task_name]['task_args']['account_info']['mwp_ftp'])) {
219 $paths['ftp'] = basename($backup_url);
220 }
221
222 if(isset($backup_settings[$task_name]['task_args']['account_info']['mwp_amazon_s3'])) {
223 $paths['amazons3'] = basename($backup_url);
224 }
225
226 if(isset($backup_settings[$task_name]['task_args']['account_info']['mwp_dropbox'])) {
227 $paths['dropbox'] = basename($backup_url);
228 }
229
230 if($backup_settings[$task_name]['task_args']['email_backup']) {
231 $paths['email'] = $backup_settings[$task_name]['task_args']['email_backup'];
232 }
233
234 $temp = $backup_settings[$task_name]['task_results'];
235 $temp['temp'] = $paths;
236 $backup_settings[$task_name]['task_results'] = array_values($temp);
237 update_option ('mwp_backup_tasks',$backup_settings);
238 }
239 else
240 {
241 //manual - predefined backup used for cloning
242 $manual_backup = $args;
243 $manual_backup ['file_path'] = $backup_file;
244 $manual_backup ['file_url'] = $backup_url;
245 update_option('mwp_manual_backup', $manual_backup);
246 }
247
248 //Additional: Table optimize, email, ftp, amazon_s3, dropbox...
249 if(isset($optimize_tables) && !empty($optimize_tables)){
250 $this->optimize_tables();
251 }
252
253 if(isset($account_info['mwp_ftp']) && !empty($account_info['mwp_ftp'])){
254 $account_info['mwp_ftp']['backup_file'] = $backup_file;
255 $this->ftp_backup($account_info['mwp_ftp']);
256 }
257
258 if (isset($account_info['mwp_amazon_s3']) && !empty($account_info['mwp_amazon_s3'])){
259 $account_info['mwp_amazon_s3']['backup_file'] = $backup_file;
260 $this->amazons3_backup($account_info['mwp_amazon_s3']);
261 }
262
263 if(isset($account_info['mwp_dropbox']) && !empty($account_info['mwp_dropbox'])){
264 $account_info['mwp_dropbox']['backup_file'] = $backup_file;
265 $this->dropbox_backup($account_info['mwp_dropbox']);
266 }
267
268 if(isset($email_backup) && is_email($email_backup)){
269 $mail_args = array(
270 'email' => $email_backup,
271 'task_name' => $task_name,
272 'file_path' => $backup_file
273 );
274 $this->email_backup($mail_args);
275 }
276
277 if($del_host_file){
278 @unlink($backup_file);
279 }
280
281 return $backup_url; //Return url to backup file (we need return only for manual backup)
282 }
283
284 function backup_full($path, $exclude = array())
285 {
286 $db_result = $this->backup_db();
287 if(!$db_result)
288 return array('error' => 'Failed to backup database.');
289 $sec_string = md5('mmb-worker');
290 $remove = "wp-content/$sec_string/mwp_backups";
291
292 if ($this->mmb_exec('which zip')) {
293 chdir(ABSPATH);
294
295 //exclude paths
296 if(empty($exclude)){
297 $exclude[0] = $remove;
298 } else {
299 $exclude[count($exclude)] = $remove;
300 }
301
302 $exclude_data = "-x";
303 foreach($exclude as $data){
304 $exclude_data .= " '$data/*'";
305 }
306
307 $command = "zip -r $path './' $exclude_data";
308 ob_start();
309 $result = $this->mmb_exec($command);
310 ob_get_clean();
311 @unlink($db_result);
312
313 if($result){
314 return true;
315 }
316 else{
317 return array('error' => 'Failed to backup site.');
318 }
319
320 }
321 else { //php zip
322 require_once ABSPATH . '/wp-admin/includes/class-pclzip.php';
323 $archive = new PclZip($path);
324 $result = $archive->add(ABSPATH, PCLZIP_OPT_REMOVE_PATH, ABSPATH);
325 $exclude_data = array();
326 if(!empty($exclude) && $result){
327 $exclude_data = array();
328 foreach($exclude as $data){
329 $exclude_data [] = $data.'/';
330 }
331
332 }
333 $exclude_data[] = $remove.'/';
334 $result = $archive->delete(PCLZIP_OPT_BY_NAME, $exclude_data);
335
336 @unlink($db_result);
337 if ($result) {
338 return true;
339 }
340 else {
341 if($archive->error_code == '-10'){
342 return array('error' => 'Failed to zip backup. Try increasing memory limit and/or free space on your server.');
343 }
344 else{
345 return array('error' => 'Failed to backup site. Try to enable Zip on your server.');
346 }
347 }
348 }
349 }
350
351
352 function backup_db()
353 {
354 $db_folder = ABSPATH.'mwp_db/';
355 if (!file_exists($db_folder)) {
356 if (!mkdir($db_folder, 0755, true))
357 return array(
358 'error' => 'Error creating database backup folder. Make sure you have write permission to your site root folder.'
359 );
360 }
361
362 $file = $db_folder . DB_NAME . '.sql';
363 $mysqldump = $this->check_mysqldump();
364 if (is_array($mysqldump)) {
365 $result = $this->backup_db_dump($file,$mysqldump);
366
367 } else {
368 $result = $this->backup_db_php($file);
369 }
370 return $result;
371 }
372
373 function backup_db_dump($file,$mysqldump)
374 {
375 global $wpdb;
376 $brace = (substr(PHP_OS, 0, 3) == 'WIN') ? '"' : '';
377 $command = $brace . $mysqldump['mysqldump'] . $brace . ' --host="' . DB_HOST . '" --user="' . DB_USER . '" --password="' . DB_PASSWORD . '" --add-drop-table --skip-lock-tables "' . DB_NAME . '" > ' . $brace . $file . $brace;
378
379 ob_start();
380 $result = $this->mmb_exec($command);
381 ob_get_clean();
382 if (!$result) {
383 $result = $this->backup_db_php($file);
384 return $result;
385 }
386
387 if (filesize($file) == 0 || !is_file($file) || !$result) {
388 @unlink($file);
389 return false;
390 } else {
391 return $file;
392 }
393 }
394
395 function backup_db_php($file)
396 {
397 global $wpdb;
398 $tables = $wpdb->get_results('SHOW TABLES', ARRAY_N);
399 foreach ($tables as $table) {
400 //drop existing table
401 $dump_data = "DROP TABLE IF EXISTS $table[0];";
402 //create table
403 $create_table = $wpdb->get_row("SHOW CREATE TABLE $table[0]", ARRAY_N);
404 $dump_data .= "\n\n" . $create_table[1] . ";\n\n";
405
406 $count = $wpdb->get_var("SELECT count(*) FROM $table[0]");
407 if ($count > 100)
408 $count = ceil($count / 100) - 1;
409 else
410 $count = 1;
411 for ($i = 0; $i < $count; $i++) {
412 $low_limit = $i * 100;
413 $qry = "SELECT * FROM $table[0] LIMIT $low_limit, 100";
414 $rows = $wpdb->get_results($qry, ARRAY_A);
415 if (is_array($rows)) {
416 foreach ($rows as $row) {
417 //insert single row
418 $dump_data .= "INSERT INTO $table[0] VALUES(";
419 $num_values = count($row);
420 $j = 1;
421 foreach ($row as $value) {
422 $value = addslashes($value);
423 $value = preg_replace("/\n/Ui", "\\n", $value);
424 $num_values == $j ? $dump_data .= "'" . $value . "'" : $dump_data .= "'" . $value . "', ";
425 $j++;
426 unset($value);
427 }
428 $dump_data .= ");\n";
429 }
430 }
431 }
432 $dump_data .= "\n\n\n";
433
434 unset($rows);
435 file_put_contents($file, $dump_data, FILE_APPEND);
436 unset($dump_data);
437 }
438
439 if (filesize($file) == 0 || !is_file($file)) {
440 @unlink($file);
441 return false;
442 }
443
444 return $file;
445
446 }
447
448 function restore($args)
449 {
450 global $wpdb;
451 if(empty($args)) {return false;}
452
453 extract($args);
454 @ini_set('memory_limit', '300M');
455 @set_time_limit(300);
456
457 $unlink_file = true; //Delete file after restore
458
459 //Detect source
460 if($backup_url){
461 //This is for clone (overwrite)
462 include_once ABSPATH . 'wp-admin/includes/file.php';
463 $backup_file = download_url($backup_url);
464 if(is_wp_error($backup_file)){
465 return array(
466 'error' => $backup_file->get_error_message()
467 );
468 }
469 $what = 'full';
470 } else {
471 $tasks = $this->get_backup_settings();
472 $task = $tasks[$task_name];
473 if(isset($task['task_results'][$result_id]['server'])) {
474 $backup_file = $task['task_results'][$result_id]['server']['file_path'];
475 $unlink_file = false; //Don't delete file if stored on server
476 }elseif(isset($task['task_results'][$result_id]['ftp'])){
477 $ftp_file = $task['task_results'][$result_id]['ftp'];
478 $args = $task['task_args']['account_info']['mwp_ftp'];
479 $args['backup_file'] = $ftp_file;
480 $backup_file = $this->get_ftp_backup($args);
481 if($backup_file == false){
482 return array(
483 'error' => 'Failed to download file from FTP'
484 );
485 }
486 }elseif(isset($task['task_results'][$result_id]['amazons3'])){
487 $amazons3_file = $task['task_results'][$result_id]['amazons3'];
488 $args = $task['task_args']['account_info']['mwp_amazon_s3'];
489 $args['backup_file'] = $ftp_file;
490 $backup_file = $this->get_amazons3_backup($args);
491 if($backup_file == false){
492 return array(
493 'error' => 'Failed to download file from Amazon S3'
494 );
495 }
496 }
497
498 $what = $tasks[$task_name]['task_args']['what'];
499 }
500
501 if ($backup_file && file_exists($backup_file)) {
502
503 if($overwrite) {
504 //Keep old db credentials before overwrite
505 if(!rename(ABSPATH.'wp-config.php',ABSPATH.'mwp-temp-wp-config.php')){
506 return array('error' => 'Error creating wp-config. Please check your write permisions.');
507 }
508
509 $db_host = DB_HOST;
510 $db_user = DB_USER;
511 $db_password = DB_PASSWORD;
512 $home = get_option('home');
513 $site_url = get_option('site_url');
514 }
515
516 if ($this->mmb_exec('which unzip')) {
517 if($what == 'db')
518 chdir(ABSPATH.'mwp_db/');
519 else {
520 chdir(ABSPATH);
521 }
522 $command = "unzip -o $backup_file";
523 ob_start();
524 $result = $this->mmb_exec($command);
525 ob_get_clean();
526
527 } else {
528 require_once ABSPATH . '/wp-admin/includes/class-pclzip.php';
529 $archive = new PclZip($backup_file);
530 if($what == 'db'){
531 $result = $archive->extract(PCLZIP_OPT_PATH, ABSPATH.'mwp_db/');
532 } else {
533 $result = $archive->extract(PCLZIP_OPT_PATH, ABSPATH);
534 }
535 }
536
537 if($unlink_file){
538 @unlink($backup_file);
539 }
540
541 if (!$result) {
542 return array(
543 'error' => 'Error extracting backup file.'
544 );
545 }
546
547 $db_result = $this->restore_db();
548
549 if (!$db_result) {
550 return array(
551 'error' => 'Error restoring database.'
552 );
553 }
554
555
556
557 } else {
558 return array(
559 'error' => 'Error restoring. Cannot find backup file.'
560 );
561 }
562
563 //Replace options and content urls
564 if($overwrite){
565 //Get New Table prefix
566 $new_table_prefix = trim($this->get_table_prefix());
567
568 //Retrieve old wp_config
569 @unlink(ABSPATH.'wp-config.php');
570
571 //Replace table prefix
572 $lines = file(ABSPATH.'mwp-temp-wp-config.php');
573 foreach ($lines as $line) {
574 if (strstr($line, '$table_prefix')) {
575 $line = '$table_prefix = "'.$new_table_prefix.'";'.PHP_EOL;
576 }
577 file_put_contents(ABSPATH.'wp-config.php', $line, FILE_APPEND);
578 }
579
580 @unlink(ABSPATH.'mwp-temp-wp-config.php');
581
582 //Replace options
583 $query = "SELECT option_value FROM " . $new_table_prefix . "options WHERE option_name = 'home'";
584 $old = $wpdb->get_var($wpdb->prepare($query));
585 $query = "UPDATE " . $new_table_prefix . "options SET option_value = '$home' WHERE option_name = 'home'";
586 $wpdb->query($wpdb->prepare($query));
587 $query = "UPDATE " . $new_table_prefix . "options SET option_value = '$home' WHERE option_name = 'siteurl'";
588 $wpdb->query($wpdb->prepare($query));
589 //Replace content urls
590 $query = "UPDATE " . $new_table_prefix . "posts SET post_content = REPLACE (post_content, '$old','$home') WHERE post_content REGEXP 'src=\"(.*)$old(.*)\"' OR post_content REGEXP 'href=\"(.*)$old(.*)\"'";
591 $wpdb->query($wpdb->prepare($query));
592 }
593
594 return true;
595 }
596
597 function restore_db()
598 {
599 global $wpdb;
600 $mysqldump = $this->check_mysqldump();
601 $file_path = ABSPATH.'mwp_db';
602 $file_name = glob($file_path . '/*.sql');
603 $file_name = $file_name[0];
604
605 if(is_array($mysqldump)) {
606 $brace = (substr(PHP_OS, 0, 3) == 'WIN') ? '"' : '';
607 $command = $brace . $mysqldump['mysql'] . $brace . ' --host="' . DB_HOST . '" --user="' . DB_USER . '" --password="' . DB_PASSWORD . '" ' . DB_NAME . ' < ' . $brace . $file_name . $brace;
608
609 ob_start();
610 $result = $this->mmb_exec($command);
611 ob_get_clean();
612 if (!$result) {
613 //try php
614 $this->restore_db_php($file_name);
615 }
616
617 } else {
618 $this->restore_db_php($file_name);
619 }
620
621 @unlink($file_name);
622 return true;
623 }
624
625 function restore_db_php($file_name)
626 {
627 $current_query = '';
628 // Read in entire file
629 $lines = file($file_name);
630 // Loop through each line
631 foreach ($lines as $line) {
632 // Skip it if it's a comment
633 if (substr($line, 0, 2) == '--' || $line == '')
634 continue;
635
636 // Add this line to the current query
637 $current_query .= $line;
638 // If it has a semicolon at the end, it's the end of the query
639 if (substr(trim($line), -1, 1) == ';') {
640 // Perform the query
641 $result = $wpdb->query($current_query);
642 if ($result === false)
643 return FALSE;
644 // Reset temp variable to empty
645 $current_query = '';
646 }
647 }
648
649 @unlink($file_name);
650 return true;
651 }
652
653 function get_table_prefix()
654 {
655 $lines = file(ABSPATH.'wp-config.php');
656 foreach ($lines as $line) {
657 if (strstr($line, '$table_prefix')) {
658 $pattern = "/(\'|\")[^(\'|\")]*/";
659 preg_match($pattern, $line, $matches);
660 $prefix = substr($matches[0], 1);
661 return $prefix;
662 break;
663 }
664 }
665 return 'wp_'; //default
666 }
667
668 function optimize_tables()
669 {
670 global $wpdb;
671 $query = 'SHOW TABLE STATUS FROM '. DB_NAME;
672 $tables = $wpdb->get_results($wpdb->prepare($query),ARRAY_A);
673 foreach ($tables as $table) {
674 if(in_array($table['Engine'], array('MyISAM', 'ISAM', 'HEAP', 'MEMORY', 'ARCHIVE')))
675 $table_string .= $table['Name'] . ",";
676 elseif($table['Engine'] == 'InnoDB'){
677 $optimize = $wpdb->query("ALTER TABLE {$table['Name']} ENGINE=InnoDB");
678 }
679 }
680
681 $table_string = rtrim($table_string);
682 $optimize = $wpdb->query("OPTIMIZE TABLE $table_string");
683
684 return $optimize ? true : false;
685 }
686
687 ### Function: Auto Detect MYSQL and MYSQL Dump Paths
688 function check_mysqldump()
689 {
690 global $wpdb;
691 $paths = array(
692 'mysq' => '',
693 'mysqldump' => ''
694 );
695 if (substr(PHP_OS, 0, 3) == 'WIN') {
696 $mysql_install = $wpdb->get_row("SHOW VARIABLES LIKE 'basedir'");
697 if ($mysql_install) {
698 $install_path = str_replace('\\', '/', $mysql_install->Value);
699 $paths['mysql'] = $install_path . 'bin/mysql.exe';
700 $paths['mysqldump'] = $install_path . 'bin/mysqldump.exe';
701 } else {
702 $paths['mysql'] = 'mysql.exe';
703 $paths['mysqldump'] = 'mysqldump.exe';
704 }
705 } else {
706 if ($this->check_sys()) {
707 $paths['mysql'] = $this->mmb_exec('which mysql',true);
708 $paths['mysqldump'] = $this->mmb_exec('which mysqldump',true);
709 } else {
710 $paths['mysql'] = 'mysql';
711 $paths['mysqldump'] = 'mysqldump';
712 }
713 }
714
715 if (!@file_exists(stripslashes($paths['mysqldump']))) {
716 return false;
717 }
718 if (!@file_exists(stripslashes($paths['mysql']))) {
719 return false;
720 }
721
722 return $paths;
723 }
724
725 //Check if exec, system, passthru functions exist
726 function check_sys()
727 {
728 if (function_exists('exec'))
729 return 'exec';
730
731 if (function_exists('system'))
732 return 'system';
733
734 if (function_exists('passhtru'))
735 return 'passthru';
736
737 return false;
738
739 }
740
741 function mmb_exec($command,$string = false)
742 {
743 if($command == '')
744 return false;
745
746 if (function_exists('exec'))
747 {
748 $log = @exec($command,$output,$return);
749
750 if($string) return $log;
751 return $return ? false : true;
752 }
753 elseif(function_exists('system')){
754 $log = @system($command,$return);
755
756 if($string) return $log;
757 return $return ? false : true;
758 }
759 elseif (function_exists('passthru')){
760 $log = passthru($command,$return);
761
762 return $return ? false : true;
763 }
764 else {
765 return false;
766 }
767 }
768
769 function check_backup_compat()
770 {
771 $reqs = array();
772 if ( strpos($_SERVER['DOCUMENT_ROOT'], '/') === 0 ) {
773 $reqs['Server OS']['status'] = 'Linux (or compatible)';
774 $reqs['Server OS']['pass'] = true;
775 } else {
776 $reqs['Server OS']['status'] = 'Windows';
777 $reqs['Server OS']['pass'] = false;
778 $pass = false;
779 }
780 $reqs['PHP Version']['status'] = phpversion();
781 if ( (float) phpversion() >= 5.1 ) {
782 $reqs['PHP Version']['pass'] = true;
783 } else {
784 $reqs['PHP Version']['pass'] = false;
785 $pass = false;
786 }
787
788
789 if(is_writable(WP_CONTENT_DIR))
790 {
791 $reqs['Backup Folder']['status'] = "writable";
792 $reqs['Backup Folder']['pass'] = true;
793 }
794 else
795 {
796 $reqs['Backup Folder']['status'] = "not writable";
797 $reqs['Backup Folder']['pass'] = false;
798 }
799
800 $sec_string = md5('mmb-worker');
801 $file = "/$sec_string/mwp_backups";
802 $file_path = WP_CONTENT_DIR . $file;
803 $reqs['Backup Folder']['status'].= ' ('.$file_path.')';
804
805 if($func = $this->check_sys())
806 {
807 $reqs['Execute Function']['status'] =$func;
808 $reqs['Execute Function']['pass'] = true;
809 }
810 else
811 {
812 $reqs['Execute Function']['status'] = "not found";
813 $reqs['Execute Function']['info'] = "(will try with PHP)";
814 $reqs['Execute Function']['pass'] = false;
815 }
816
817 if($this->mmb_exec('which zip'))
818 {
819 $reqs['Zip']['status'] = "enabled";
820 $reqs['Zip']['pass'] = true;
821 }
822 else
823 {
824 $reqs['Zip']['status'] = "not found";
825 $reqs['Zip']['info'] = "(will try with PHP pclZip class)";
826 $reqs['Zip']['pass'] = false;
827 }
828
829 if($this->mmb_exec('which unzip'))
830 {
831 $reqs['Unzip']['status'] = "enabled";
832 $reqs['Unzip']['pass'] = true;
833 }
834 else
835 {
836 $reqs['Unzip']['status'] = "not found";
837 $reqs['Unzip']['info'] = "(will try with PHP pclZip class)";
838 $reqs['Unzip']['pass'] = false;
839 }
840 if(is_array($this->check_mysqldump()))
841 {
842 $reqs['MySQL Dump']['status'] = "enabled";
843 $reqs['MySQL Dump']['pass'] = true;
844 }
845 else
846 {
847 $reqs['MySQL Dump']['status'] = "not found";
848 $reqs['MySQL Dump']['info'] = "(will try PHP)";
849 $reqs['MySQL Dump']['pass'] = false;
850 }
851
852
853
854 return $reqs;
855 }
856
857 function email_backup($args)
858 {
859 $email = $args['email'];
860 $backup_file = $args['file_path'];
861 $task_name = isset($args['task_name']) ? $args['task_name'].' on ' : '';
862 if(file_exists($backup_file) && $email)
863 {
864 $attachments = array($backup_file);
865 $headers = 'From: ManageWP <no-reply@managewp.com>' . "\r\n";
866 $subject = "ManageWP Backup - ".$task_name . date('F jS, y H:s');
867 ob_start();
868 wp_mail($email, $subject, $subject, $headers, $attachments);
869 ob_end_clean();
870
871 }
872
873 }
874
875 function ftp_backup($args){
876 extract($args);
877 //Args: $ftp_username, $ftp_password, $ftp_hostname, $backup_file, $ftp_remote_folder
878
879 if($ftp_ssl && function_exists('ftp_ssl_connect')){
880 $conn_id = ftp_ssl_connect($ftp_hostname);
881 }else if (function_exists('ftp_connect')){
882 $conn_id = ftp_connect($ftp_hostname);
883 if ($conn_id===false){
884 $this->_log("ftp failed to connect");
885 }
886 }
887 else {
888 $this->_log("ftp not supported");
889 }
890
891 $login = @ftp_login($conn_id, $ftp_username, $ftp_password);
892 if ($login === false ) {
893 $this->_log("failed to login");
894 } else {
895 $this->_log("connected to ftp");
896 }
897
898 @ftp_mkdir($conn_id, $ftp_remote_folder);
899
900 $upload = @ftp_put($conn_id, $ftp_remote_folder . '/' . basename($backup_file), $backup_file, FTP_BINARY);
901 if ($upload === false) {
902 $this->_log("not uploaded to ftp");
903 } else {
904 $this->_log("ftp uploaded successfuly");
905 }
906 ftp_close($conn_id);
907
908 }
909
910 function remove_ftp_backup($args)
911 {
912 extract($args);
913 //Args: $ftp_username, $ftp_password, $ftp_hostname, $backup_file, $ftp_remote_folder
914 if($ftp_ssl && function_exists('ftp_ssl_connect')){
915 $conn_id = ftp_ssl_connect($ftp_hostname);
916 $this->_log("sftp failed to connect");
917 }else if (function_exists('ftp_connect')){
918 $conn_id = ftp_connect($ftp_hostname);
919 if ($conn_id===false){
920 $this->_log("ftp failed to connect");
921 }
922 }
923 else {
924 $this->_log("ftp not supported");
925 }
926 $login = @ftp_login($conn_id, $ftp_username, $ftp_password);
927 if ($login === false ) {
928 $this->_log("failed to connect");
929 } else {
930 $this->_log("connected");
931 }
932
933 $delete = ftp_delete($conn_id, $ftp_remote_folder . '/' . $backup_file);
934 if ($delete === false) {
935 $this->_log("not deleted");
936 } else {
937 $this->_log("deleted successfuly");
938 }
939 ftp_close($conn_id);
940
941 }
942
943 function get_ftp_backup($args){
944 extract($args);
945 //Args: $ftp_username, $ftp_password, $ftp_hostname, $backup_file, $ftp_remote_folder
946 if($ftp_ssl && function_exists('ftp_ssl_connect')){
947 $conn_id = ftp_ssl_connect($ftp_hostname);
948 $this->_log("sftp failed to connect");
949 }else if (function_exists('ftp_connect')){
950 $conn_id = ftp_connect($ftp_hostname);
951 if ($conn_id===false){
952 return false;
953 }
954 }
955 else {
956 $this->_log("ftp not supported");
957 }
958 $login = @ftp_login($conn_id, $ftp_username, $ftp_password);
959 if ($login === false ) {
960 return false;
961 } else {
962 $this->_log("connected");
963 }
964
965 $temp = ABSPATH.'mwp_temp_backup.zip';
966 $get = ftp_get($conn_id, $temp, $ftp_remote_folder . '/' . $backup_file, FTP_BINARY);
967 if ($get === false) {
968 return false;
969 } else {
970 $this->_log("download successfuly");
971 }
972 ftp_close($conn_id);
973
974 return $temp;
975 }
976
977 function dropbox_backup($args)
978 {
979 require_once('lib/dropbox.php');
980 extract($args);
981
982 //$email, $password, $backup_file, $destination
983 try{
984 $uploader = new DropboxUploader($dropbox_username, $dropbox_password);
985 $uploader->upload($backup_file, $dropbox_destination);
986 } catch (Exception $e){
987 $this->_log($e->getMessage());
988 }
989 }
990
991 function amazons3_backup($args)
992 {
993 require_once('lib/s3.php');
994 extract($args);
995
996 $s3 = new S3( $as3_access_key, str_replace(' ', '+', $as3_secure_key));
997
998 $s3->putBucket( $as3_bucket, S3::ACL_PUBLIC_READ );
999
1000 if ( $s3->putObjectFile( $backup_file, $as3_bucket, $as3_directory .'/'. basename($backup_file), S3::ACL_PRIVATE) ) {
1001 return array('success' => 'ok');
1002 } else {
1003 return array('success' => 'error');
1004 }
1005
1006 }
1007
1008 function remove_amazons3_backup($args)
1009 {
1010 require_once('lib/s3.php');
1011 extract($args);
1012 $this->_log("delete");
1013 $s3 = new S3( $as3_access_key, str_replace(' ', '+', $as3_secure_key));
1014 $s3->deleteObject($as3_bucket,$as3_directory.'/'. $backup_file);
1015 }
1016
1017 function get_amazons3_backup($args)
1018 {
1019 require_once('lib/s3.php');
1020 extract($args);
1021 $s3 = new S3( $as3_access_key, str_replace(' ', '+', $as3_secure_key));
1022 $s3->deleteObject($as3_bucket,$as3_directory.'/'. $backup_file);
1023 $s3->getObject($as3_bucket, $as3_directory.'/'. $backup_file, $temp);
1024 $temp = ABSPATH.'mwp_temp_backup.zip';
1025 return $temp;
1026 }
1027
1028 function schedule_next($type,$schedule)
1029 {
1030
1031 $schedule = explode("|", $schedule);
1032 if(empty($schedule))
1033 return false;
1034 switch($type){
1035
1036 case 'daily':
1037
1038 if($schedule[1]) { $delay_time = $schedule[1] * 60;}
1039
1040 $current_hour = date("h");
1041 $schedule_hour = $schedule[0];
1042 if($current_hour >= $schedule_hour)
1043 $time = mktime($schedule_hour, 0, 0, date("m"), date("d")+1, date("Y"));
1044 else
1045 $time = mktime($schedule_hour, 0, 0, date("m"), date("d"), date("Y"));
1046 break;
1047
1048
1049 case 'weekly':
1050 if($schedule[2]) { $delay_time = $schedule[2] * 60;}
1051 $current_weekday = date('w');
1052 $schedule_weekday = $schedule[1];
1053 $current_hour = date("h");
1054 $schedule_hour = $schedule[0];
1055
1056 if($current_weekday > $schedule_weekday)
1057 $weekday_offset = 7 - ($week_day - $task_schedule[1]);
1058 else
1059 $weekday_offset = $schedule_weekday - $current_weekday;
1060
1061
1062 if(!$weekday_offset){ //today is scheduled weekday
1063 if($current_hour >= $schedule_hour)
1064 $time = mktime($schedule_hour, 0, 0, date("m"), date("d")+7, date("Y"));
1065 else
1066 $time = mktime($schedule_hour, 0, 0, date("m"), date("d"), date("Y"));
1067 } else {
1068 $time = mktime($schedule_hour, 0, 0, date("m"), date("d")+ $weekday_offset, date("Y"));
1069 }
1070
1071 break;
1072
1073 case 'monthly':
1074 if($schedule[2]) { $delay_time = $schedule[2] * 60;}
1075 $current_monthday = date('j');
1076 $schedule_monthday = $schedule[1];
1077 $current_hour = date("h");
1078 $schedule_hour = $schedule[0];
1079
1080 if($current_monthday > $schedule_monthday){
1081 $time = mktime($schedule_hour, 0, 0, date("m")+1, $schedule_monthday, date("Y"));
1082 } else if($current_monthday < $schedule_monthday) {
1083
1084 $time = mktime($schedule_hour, 0, 0, date("m"), $schedule_monthday, date("Y"));
1085 }
1086 else if($current_monthday == $schedule_monthday) {
1087 if($current_hour >= $schedule_hour)
1088 $time = mktime($schedule_hour, 0, 0, date("m") + 1, $schedule_monthday, date("Y"));
1089 else
1090 $time = mktime($schedule_hour, 0, 0, date("m"), $schedule_monthday, date("Y"));
1091 break;
1092 }
1093
1094 break;
1095 default: break;
1096 }
1097
1098 if($delay_time) {$time += $delay_time; }
1099
1100 return $time;
1101
1102 }
1103
1104 //Parse task arguments for info on master
1105 function get_backup_stats()
1106 {
1107 $stats = array();
1108 $tasks = get_option('mwp_backup_tasks');
1109 if(is_array($tasks) && !empty($tasks)) {
1110 foreach($tasks as $task_name => $info)
1111 {
1112 $stats[$task_name] = $info['task_results'];
1113 }
1114 }
1115 return $stats;
1116 }
1117
1118 function remove_old_backups($task_name){
1119 $backups = $this->get_backup_settings();
1120 if(count($backups[$task_name]['task_results']) >= $backups[$task_name]['task_args']['limit']) {
1121 // ? how many to remove
1122 $remove_num = (count($backups[$task_name]['task_results']) - $backups[$task_name]['task_args']['limit']) + 1;
1123
1124 for($i = 0; $i < $remove_num; $i++){
1125 if(!isset($backups[$task_name]['task_results'][$i]['error'])) {
1126
1127 //Remove from the server
1128 if(isset($backups[$task_name]['task_results'][$i]['server'])){
1129 @unlink($backups[$task_name]['task_results'][$i]['server']['file_path']);
1130 }
1131
1132 //Remove from ftp
1133 if(isset($backups[$task_name]['task_results'][$i]['ftp'])){
1134 $ftp_file = $backups[$task_name]['task_results'][$i]['ftp'];
1135 $args = $backups[$task_name]['task_args']['account_info']['mwp_ftp'];
1136 $args['backup_file'] = $ftp_file;
1137 $this->remove_ftp_backup($args);
1138 }
1139
1140 if(isset($backups[$task_name]['task_results'][$i]['amazons3'])){
1141 $amazons3_file = $backups[$task_name]['task_results'][$i]['amazons3'];
1142 $args = $backups[$task_name]['task_args']['account_info']['mwp_amazon_s3'];
1143 $args['backup_file'] = $amazons3_file;
1144 $this->remove_amazons3_backup($args);
1145 }
1146
1147 if(isset($backups[$task_name]['task_results'][$i]['dropbox'])){
1148
1149 }
1150
1151 }
1152 //Remove database backup info
1153 unset($backups[$task_name]['task_results'][$i]);
1154 update_option('mwp_backup_tasks',$backups);
1155
1156 }//end foreach
1157 }
1158 }
1159
1160 /**
1161 * Delete specified backup
1162 * Args: $task_name, $result_id
1163 */
1164
1165 function delete_backup($args){
1166 if(empty($args))
1167 return false;
1168 extract($args);
1169
1170 $tasks = $this->get_backup_settings();
1171 $task = $tasks[$task_name];
1172 $backups = $task['task_results'];
1173 $backup = $backups[$result_id];
1174
1175 if(isset($backup['server'])){
1176 @unlink($backup['server']['file_path']);
1177 }
1178
1179 //Remove from ftp
1180 if(isset($backup['ftp'])){
1181 $ftp_file = $backup['ftp'];
1182 $args = $tasks[$task_name]['task_args']['account_info']['mwp_ftp'];
1183 $args['backup_file'] = $ftp_file;
1184 $this->remove_ftp_backup($args);
1185 }
1186
1187 if(isset($backup['amazons3'])){
1188 $amazons3_file = $backup['amazons3'];
1189 $args = $tasks[$task_name]['task_args']['account_info']['mwp_amazon_s3'];
1190 $args['backup_file'] = $amazons3_file;
1191 $this->remove_amazons3_backup($args);
1192 }
1193
1194 if(isset($backup['dropbox'])){
1195
1196 }
1197
1198 unset($backups[$result_id]);
1199
1200 if(count($backups)){
1201 $tasks[$task_name]['task_results'] = $backups;
1202 } else {
1203 unset($tasks[$task_name]['task_results']);
1204 }
1205
1206 update_option('mwp_backup_tasks',$tasks);
1207 return true;
1208
1209 }
1210
1211 function cleanup()
1212 {
1213 $tasks = $this->get_backup_settings();
1214 $backup_folder = WP_CONTENT_DIR.'/'.md5('mmb-worker').'/mwp_backups/';
1215 $files = glob($backup_folder."*.*");
1216 if(count($files)){
1217 $results = array();
1218 if(count($tasks)){
1219 foreach($tasks as $task){
1220 if(isset($task['task_results']) && count($task['task_results'])) {
1221 foreach($task['task_results'] as $backup) {
1222 if(isset($backup['server'])) {
1223 $results[] = $backup['server']['file_path'];
1224 }
1225 }
1226 }
1227 }
1228 }
1229
1230 $num_deleted = 0;
1231 foreach($files as $file){
1232 if(!in_array($file,$results)) {
1233 @unlink($file);
1234 $num_deleted++;
1235 }
1236 }
1237 }
1238 }
1239
1240 }
1241
1242 ?>