PluginProbe ʕ •ᴥ•ʔ
GiveWP – Donation Plugin and Fundraising Platform / 2.0.5
GiveWP – Donation Plugin and Fundraising Platform v2.0.5
4.16.4 4.16.3 4.16.2 4.16.1 4.16.0 4.15.5 4.15.4 4.15.3 4.15.2 4.15.1 4.15.0 2.3.0 2.3.1 2.3.2 2.30.0 2.31.0 2.31.1 2.32.0 2.33.0 2.33.1 2.33.2 2.33.3 2.33.4 2.33.5 2.4.0 2.4.1 2.4.2 2.4.3 2.4.4 2.4.5 2.4.6 2.4.7 2.5.0 2.5.1 2.5.10 2.5.11 2.5.12 2.5.13 2.5.2 2.5.3 2.5.4 2.5.5 2.5.6 2.5.7 2.5.8 2.5.9 2.6.0 2.6.1 2.6.2 2.6.3 2.7.0 2.7.1 2.7.2 2.7.3 2.7.4 2.7.5 2.8.0 2.8.1 2.9.0 2.9.1 2.9.2 2.9.3 2.9.4 2.9.5 2.9.6 2.9.7 3.0.0 3.0.1 3.0.2 3.0.3 3.0.4 3.1.0 3.1.1 3.1.2 3.10.0 3.11.0 3.12.0 3.12.1 3.12.2 3.12.3 3.13.0 3.14.0 3.14.1 3.14.2 3.15.0 3.15.1 3.16.0 3.16.1 3.16.2 3.16.3 3.16.4 3.16.5 3.17.0 3.17.1 3.17.2 3.18.0 3.19.0 3.19.1 3.19.2 3.19.3 3.19.4 3.2.0 3.2.1 3.2.2 3.20.0 3.21.0 3.21.1 3.22.0 3.22.1 3.22.2 3.3.0 3.3.1 3.4.0 3.4.1 3.4.2 3.5.0 3.5.1 3.6.0 3.6.1 3.6.2 3.7.0 3.8.0 3.9.0 4.0.0 4.1.0 4.1.1 4.10.0 4.10.1 4.11.0 4.12.0 4.13.0 4.13.1 4.13.2 4.14.0 4.14.1 4.14.2 4.14.3 4.14.4 4.14.5 4.14.6 4.2.0 4.2.1 4.3.0 4.3.1 4.3.2 4.4.0 4.5.0 4.6.1 4.7.0 4.7.1 4.8.0 4.8.1 4.9.0 trunk 1.9.0 2.0.0 2.0.1 2.0.2 2.0.3 2.0.4 2.0.5 2.0.6 2.0.7 2.1.0 2.1.1 2.1.2 2.1.3 2.1.4 2.1.5 2.1.6 2.1.7 2.1.8 2.10.0 2.10.1 2.10.2 2.10.3 2.10.4 2.11.0 2.11.1 2.11.2 2.11.3 2.12.0 2.12.1 2.12.2 2.12.3 2.13.0 2.13.1 2.13.2 2.13.3 2.13.4 2.14.0 2.15.0 2.16.0 2.16.1 2.17.0 2.17.1 2.17.3 2.18.0 2.18.1 2.19.1 2.19.2 2.19.3 2.19.4 2.19.5 2.19.6 2.19.7 2.19.8 2.2.0 2.2.1 2.2.2 2.2.3 2.2.4 2.2.5 2.2.6 2.20.0 2.20.1 2.20.2 2.21.0 2.21.1 2.21.2 2.21.3 2.21.4 2.22.0 2.22.1 2.22.2 2.22.3 2.23.0 2.23.1 2.23.2 2.24.0 2.24.1 2.24.2 2.25.0 2.25.1 2.25.2 2.25.3 2.26.0 2.27.0 2.27.1 2.27.2 2.27.3 2.28.0 2.29.0 2.29.1 2.29.2
give / includes / admin / upgrades / class-give-updates.php
give / includes / admin / upgrades Last commit date
views 8 years ago class-give-updates.php 8 years ago upgrade-functions.php 8 years ago
class-give-updates.php
1149 lines
1 <?php
2
3 /**
4 * Class Give_Updates
5 *
6 * @since 1.8.12
7 */
8 class Give_Updates {
9
10 /**
11 * Instance.
12 *
13 * @since
14 * @access static
15 * @var
16 */
17 static private $instance;
18
19 /**
20 * Instance.
21 *
22 * @since
23 * @access public
24 * @var Give_Background_Updater
25 */
26 static public $background_updater;
27
28 /**
29 * Updates
30 *
31 * @since 1.8.12
32 * @access private
33 * @var array
34 */
35 private $updates = array();
36
37 /**
38 * Current update percentage number
39 *
40 * @since 1.8.12
41 * @access private
42 * @var array
43 */
44 public $percentage = 0;
45
46 /**
47 * Current update step number
48 *
49 * @since 1.8.12
50 * @access private
51 * @var array
52 */
53 public $step = 1;
54
55 /**
56 * Current update number
57 *
58 * @since 1.8.12
59 * @access private
60 * @var array
61 */
62 public $update = 1;
63
64 /**
65 * Singleton pattern.
66 *
67 * @since 1.8.12
68 * @access private
69 *
70 * @param Give_Updates .
71 */
72 private function __construct() {
73 }
74
75 /**
76 * Register updates
77 *
78 * @since 1.8.12
79 * @access public
80 *
81 * @param array $args
82 */
83 public function register( $args ) {
84 $args_default = array(
85 'id' => '',
86 'version' => '',
87 'callback' => '',
88 );
89
90 $args = wp_parse_args( $args, $args_default );
91
92 // You can only register database upgrade.
93 $args['type'] = 'database';
94
95 // Bailout.
96 if (
97 empty( $args['id'] ) ||
98 empty( $args['version'] ) ||
99 empty( $args['callback'] ) ||
100 ! is_callable( $args['callback'] )
101 ) {
102 return;
103 }
104
105 // Change depend param to array.
106 if ( isset( $args['depend'] ) && is_string( $args['depend'] ) ) {
107 $args['depend'] = array( $args['depend'] );
108 }
109
110 $this->updates[ $args['type'] ][] = $args;
111 }
112
113 /**
114 * Get instance.
115 *
116 * @since
117 * @access static
118 * @return static
119 */
120 static function get_instance() {
121 if ( is_null( self::$instance ) ) {
122 self::$instance = new self();
123 }
124
125 return self::$instance;
126 }
127
128 /**
129 *
130 * Setup hook
131 *
132 * @since 1.8.12
133 * @access public
134 */
135 public function setup() {
136 /**
137 * Load file
138 */
139 require_once GIVE_PLUGIN_DIR . 'includes/class-give-background-updater.php';
140 require_once GIVE_PLUGIN_DIR . 'includes/admin/upgrades/upgrade-functions.php';
141
142 self::$background_updater = new Give_Background_Updater();
143
144 /**
145 * Setup hooks.
146 */
147 add_action( 'init', array( $this, '__register_upgrade' ), 9999 );
148 add_action( 'give_set_upgrade_completed', array( $this, '__flush_resume_updates' ), 9999 );
149 add_action( 'wp_ajax_give_db_updates_info', array( $this, '__give_db_updates_info' ) );
150 add_action( 'wp_ajax_give_run_db_updates', array( $this, '__give_start_updating' ) );
151 add_action( 'admin_init', array( $this, '__redirect_admin' ) );
152 add_action( 'admin_init', array( $this, '__pause_db_update' ), - 1 );
153 add_action( 'admin_init', array( $this, '__restart_db_update' ), - 1 );
154 add_action( 'admin_notices', array( $this, '__show_notice' ) );
155 add_action( 'give_restart_db_upgrade', array( $this, '__health_background_update' ) );
156
157 if ( is_admin() ) {
158 add_action( 'admin_init', array( $this, '__change_donations_label' ), 9999 );
159 add_action( 'admin_menu', array( $this, '__register_menu' ), 9999 );
160 }
161 }
162
163 /**
164 * Register plugin add-on updates.
165 *
166 * @since 1.8.12
167 * @access public
168 */
169 public function __register_plugin_addon_updates() {
170 $addons = give_get_plugins();
171 $plugin_updates = get_plugin_updates();
172
173 foreach ( $addons as $key => $info ) {
174 if ( 'active' != $info['Status'] || 'add-on' != $info['Type'] || empty( $plugin_updates[ $key ] ) ) {
175 continue;
176 }
177
178 $this->updates['plugin'][] = array_merge( $info, (array) $plugin_updates[ $key ] );
179 }
180 }
181
182
183 /**
184 * Fire custom action hook to register updates
185 *
186 * @since 1.8.12
187 * @access public
188 */
189 public function __register_upgrade() {
190 if ( ! is_admin() ) {
191 return;
192 }
193
194 /**
195 * Fire the hook
196 *
197 * @since 1.8.12
198 */
199 do_action( 'give_register_updates', $this );
200 }
201
202 /**
203 * Rename `Donations` menu title if updates exists
204 *
205 * @since 1.8.12
206 * @access public
207 */
208 function __change_donations_label() {
209 global $menu;
210
211 // Bailout.
212 if ( empty( $menu ) || ! $this->get_total_update_count() ) {
213 return;
214 }
215
216 $is_update = ( $this->is_doing_updates() && ! self::$background_updater->is_paused_process() );
217
218 foreach ( $menu as $index => $menu_item ) {
219 if ( 'edit.php?post_type=give_forms' !== $menu_item[2] ) {
220 continue;
221 }
222
223 $menu[ $index ][0] = sprintf(
224 '%1$s <span class="update-plugins"><span class="plugin-count give-update-progress-count">%2$s%3$s</span></span>',
225 __( 'Donations', 'give' ),
226 $is_update ?
227 $this->get_db_update_processing_percentage() :
228 $this->get_total_update_count(),
229 $is_update ? '%' : ''
230 );
231
232 break;
233 }
234 }
235
236 /**
237 * Register updates menu
238 *
239 * @since 1.8.12
240 * @access public
241 */
242 public function __register_menu() {
243 // Bailout.
244 if ( ! give_test_ajax_works() ) {
245 return;
246 }
247
248 // Load plugin updates.
249 $this->__register_plugin_addon_updates();
250
251 // Bailout.
252 if ( ! $this->get_total_update_count() ) {
253 // Show complete update message if still on update setting page.
254 if ( isset( $_GET['page'] ) && 'give-updates' === $_GET['page'] ) {
255 // Upgrades
256 add_submenu_page(
257 'edit.php?post_type=give_forms',
258 esc_html__( 'Give Updates Complete', 'give' ),
259 __( 'Updates', 'give' ),
260 'manage_give_settings',
261 'give-updates',
262 array( $this, 'render_complete_page' )
263 );
264 }
265
266 return;
267 }
268
269 $is_update = ( $this->is_doing_updates() && ! self::$background_updater->is_paused_process() );
270
271 // Upgrades
272 add_submenu_page(
273 'edit.php?post_type=give_forms',
274 esc_html__( 'Give Updates', 'give' ),
275 sprintf(
276 '%1$s <span class="update-plugins"%2$s><span class="plugin-count give-update-progress-count">%3$s%4$s</span></span>',
277 __( 'Updates', 'give' ),
278 isset( $_GET['give-pause-db-upgrades'] ) ? ' style="display:none;"' : '',
279 $is_update ?
280 $this->get_db_update_processing_percentage() :
281 $this->get_total_update_count(),
282 $is_update ? '%' : ''
283 ),
284 'manage_give_settings',
285 'give-updates',
286 array( $this, 'render_page' )
287 );
288 }
289
290
291 /**
292 * Show update related notices
293 *
294 * @since 2.0
295 * @access public
296 */
297 public function __redirect_admin() {
298 // Show db upgrade completed notice.
299 if (
300 ! wp_doing_ajax() &&
301 current_user_can( 'manage_give_settings' ) &&
302 get_option( 'give_show_db_upgrade_complete_notice' ) &&
303 ! isset( $_GET['give-db-update-completed'] )
304 ) {
305 delete_option( 'give_show_db_upgrade_complete_notice' );
306
307 wp_redirect( add_query_arg( array( 'give-db-update-completed' => 'give_db_upgrade_completed' ) ) );
308 exit();
309 }
310 }
311
312
313 /**
314 * Pause db upgrade
315 *
316 * @since 2.0.1
317 * @access public
318 *
319 * @param bool $force
320 *
321 * @return bool
322 */
323 public function __pause_db_update( $force = false ) {
324 // Bailout.
325 if (
326 ! $force &&
327 (
328 wp_doing_ajax() ||
329 ! isset( $_GET['page'] ) ||
330 'give-updates' !== $_GET['page'] ||
331 ! isset( $_GET['give-pause-db-upgrades'] ) ||
332 self::$background_updater->is_paused_process()
333 )
334
335 ) {
336 return false;
337 }
338
339 delete_option( 'give_upgrade_error' );
340
341 $this->__health_background_update( $this );
342 $batch = self::$background_updater->get_all_batch();
343
344 // Bailout: if batch is empty
345 if ( empty( $batch->data ) ) {
346 return false;
347 }
348
349 // Remove cache.
350 Give_Background_Updater::flush_cache();
351
352 // Do not stop background process immediately if task running.
353 // @see Give_Background_Updater::lock_process
354 if ( ! $force && self::$background_updater->is_process_running() ) {
355 update_option( 'give_pause_upgrade', 1 );
356
357 return true;
358 }
359
360 update_option( 'give_paused_batches', $batch, 'no' );
361 delete_option( $batch->key );
362 delete_site_transient( self::$background_updater->get_identifier() . '_process_lock' );
363 wp_clear_scheduled_hook( self::$background_updater->get_cron_identifier() );
364
365 Give()->logs->add( 'Update Pause', print_r( $batch, true ), 0, 'update' );
366
367 /**
368 * Fire action when pause db updates
369 *
370 * @since 2.0.1
371 */
372 do_action( 'give_pause_db_upgrade', $this );
373
374 return true;
375 }
376
377 /**
378 * Restart db upgrade
379 *
380 * @since 2.0.1
381 * @access public
382 *
383 * @return bool
384 */
385 public function __restart_db_update() {
386 // Bailout.
387 if (
388 wp_doing_ajax() ||
389 ! isset( $_GET['page'] ) ||
390 'give-updates' !== $_GET['page'] ||
391 ! isset( $_GET['give-restart-db-upgrades'] ) ||
392 ! self::$background_updater->is_paused_process()
393 ) {
394 return false;
395 }
396
397 Give_Background_Updater::flush_cache();
398 $batch = get_option( 'give_paused_batches' );
399
400 if ( ! empty( $batch ) ) {
401 wp_cache_delete( $batch->key, 'options' );
402 update_option( $batch->key, $batch->data );
403
404 delete_option( 'give_paused_batches' );
405
406 Give()->logs->add( 'Update Restart', print_r( $batch, true ), 0, 'update' );
407
408
409 /** Fire action when restart db updates
410 *
411 * @since 2.0.1
412 */
413 do_action( 'give_restart_db_upgrade', $this );
414
415 self::$background_updater->dispatch();
416 }
417
418 return true;
419 }
420
421 /**
422 * Health check for updates.
423 *
424 * @since 2.0
425 * @access public
426 *
427 * @param Give_Updates $give_updates
428 */
429 public function __health_background_update( $give_updates ) {
430 if ( ! $this->is_doing_updates() ) {
431 return;
432 }
433
434 Give_Background_Updater::flush_cache();
435
436 $batch = Give_Updates::$background_updater->get_all_batch();
437 $batch_data_count = count( $batch->data );
438 $all_updates = $give_updates->get_updates( 'database', 'all' );
439 $all_update_ids = wp_list_pluck( $all_updates, 'id' );
440 $all_batch_update_ids = ! empty( $batch->data ) ? wp_list_pluck( $batch->data, 'id' ) : array();
441 $log_data = '';
442 $doing_upgrade_args = get_option( 'give_doing_upgrade' );
443
444 if ( ! empty( $doing_upgrade_args ) ) {
445 $log_data .= 'Doing update:' . "\n";
446 $log_data .= print_r( $doing_upgrade_args, true ) . "\n";
447 }
448
449 /**
450 * Add remove upgrade from batch
451 */
452 if ( ! empty( $batch->data ) ) {
453
454 foreach ( $batch->data as $index => $update ) {
455 $log_data = print_r( $update, true ) . "\n";
456
457 if ( ! is_callable( $update['callback'] ) ) {
458 $log_data .= 'Removing missing callback update: ' . "{$update['id']}\n";
459 unset( $batch->data[ $index ] );
460 } elseif ( give_has_upgrade_completed( $update['id'] ) ) {
461 $log_data .= 'Removing already completed update: ' . "{$update['id']}\n";
462 unset( $batch->data[ $index ] );
463 }
464
465 if ( ! empty( $update['depend'] ) ) {
466
467 foreach ( $update['depend'] as $depend ) {
468 if ( give_has_upgrade_completed( $depend ) ) {
469 $log_data .= 'Completed update: ' . "{$depend}\n";
470 continue;
471 }
472
473 if ( in_array( $depend, $all_update_ids ) && ! in_array( $depend, $all_batch_update_ids ) ) {
474 $log_data .= 'Adding missing update: ' . "{$depend}\n";
475 array_unshift( $batch->data, $all_updates[ array_search( $depend, $all_update_ids ) ] );
476 }
477 }
478 }
479 }
480 }
481
482 /**
483 * Add new upgrade to batch
484 */
485 if ( $new_updates = $this->get_updates( 'database', 'new' ) ) {
486 $all_batch_update_ids = ! empty( $batch->data ) ? wp_list_pluck( $batch->data, 'id' ) : array();
487
488 foreach ( $new_updates as $index => $new_update ) {
489 if ( give_has_upgrade_completed( $new_update['id'] ) || in_array( $new_update['id'], $all_batch_update_ids ) ) {
490 unset( $new_updates[ $index ] );
491 }
492 }
493
494 if ( ! empty( $new_updates ) ) {
495 $log_data .= 'Adding new update: ' . "\n";
496 $log_data .= print_r( $new_updates, true ) . "\n";
497
498 $batch->data = array_merge( (array) $batch->data, $new_updates );
499 update_option( 'give_db_update_count', ( absint( get_option( 'give_db_update_count' ) ) + count( $new_updates ) ) );
500 }
501 }
502
503 /**
504 * Fix batch
505 */
506 if ( empty( $batch->data ) ) {
507 // Complete batch if do not have any data to process.
508 self::$background_updater->delete( $batch->key );
509
510 if ( self::$background_updater->has_queue() ) {
511 $this->__health_background_update( $this );
512 } else {
513 delete_site_transient( self::$background_updater->get_identifier() . '_process_lock' );
514 wp_clear_scheduled_hook( self::$background_updater->get_cron_identifier() );
515
516 self::$background_updater->complete();
517 }
518
519 } elseif ( $batch_data_count !== count( $batch->data ) ) {
520
521 $log_data .= 'Updating batch' . "\n";
522 $log_data .= print_r( $batch, true );
523
524 if ( ! empty( $batch->key ) ) {
525 wp_cache_delete( $batch->key, 'options' );
526 update_option( $batch->key, $batch->data );
527 } else {
528
529 foreach ( $batch->data as $data ) {
530 Give_Updates::$background_updater->push_to_queue( $data );
531 }
532
533 Give_Updates::$background_updater->save();
534 }
535 }
536
537
538 /**
539 * Fix give_doing_upgrade option
540 */
541 $fresh_new_db_count = $this->get_total_new_db_update_count( true );
542
543 update_option( 'give_db_update_count', $fresh_new_db_count );
544
545 $doing_upgrade_args['update'] = 1;
546 $doing_upgrade_args['heading'] = sprintf( 'Update %s of %s', 1, $fresh_new_db_count );
547 $doing_upgrade_args['total_percentage'] = $this->get_db_update_processing_percentage( true );
548
549 // Remove already completed update from info.
550 if ( give_has_upgrade_completed( $doing_upgrade_args['update_info']['id'] ) ) {
551 $doing_upgrade_args['update_info'] = current( array_values( $batch->data ) );
552 $doing_upgrade_args['step'] = 1;
553 }
554
555 update_option( 'give_doing_upgrade', $doing_upgrade_args );
556
557 $log_data .= 'Updated doing update:' . "\n";
558 $log_data .= print_r( $doing_upgrade_args, true ) . "\n";
559 Give()->logs->add( 'Update Health Check', $log_data, 0, 'update' );
560 }
561
562
563 /**
564 * Show update related notices
565 *
566 * @since 2.0
567 * @access public
568 */
569 public function __show_notice() {
570 // Bailout.
571 if ( ! current_user_can( 'manage_give_settings' ) ) {
572 return;
573 }
574
575 // Run DB updates.
576 if ( ! empty( $_GET['give-run-db-update'] ) ) {
577 $this->run_db_update();
578 }
579
580
581 // Bailout.
582 if ( isset( $_GET['page'] ) && 'give-updates' === $_GET['page'] ) {
583 return;
584 }
585
586 // Show notice if upgrade paused.
587 if ( self::$background_updater->is_paused_process() ) {
588 ob_start();
589
590 $upgrade_error = get_option( 'give_upgrade_error' );
591 if ( ! $upgrade_error ) : ?>
592 <strong><?php _e( 'Database Update', 'give' ); ?></strong>
593 &nbsp;&#8211;&nbsp;<?php _e( 'GiveWP needs to update your database to the latest version. The following process will make updates to your site\'s database. Please create a backup before proceeding.', 'give' ); ?>
594 <br>
595 <br>
596 <a href="<?php echo esc_url( add_query_arg( array( 'give-restart-db-upgrades' => 1 ), admin_url( 'edit.php?post_type=give_forms&page=give-updates' ) ) ); ?>" class="button button-primary give-restart-updater-btn">
597 <?php _e( 'Restart the updater', 'give' ); ?>
598 </a>
599 <script type="text/javascript">
600 jQuery('.give-restart-updater-btn').click('click', function () {
601 return window.confirm('<?php echo esc_js( __( 'It is recommended that you backup your database before proceeding. Do you want to run the update now?', 'give' ) ); ?>'); // jshint ignore:line
602 });
603 </script>
604 <?php else: ?>
605 <strong><?php _e( 'Database Update', 'give' ); ?></strong>
606 &nbsp;&#8211;&nbsp;<?php _e( 'An unexpected issue occurred during the database update which caused it to stop automatically. Please contact support for assistance.', 'give' ); ?>
607 <?php
608 endif;
609 $desc_html = ob_get_clean();
610
611 Give()->notices->register_notice( array(
612 'id' => 'give_upgrade_db',
613 'type' => 'error',
614 'dismissible' => false,
615 'description' => $desc_html,
616 ) );
617 }
618
619 // Bailout if doing upgrades.
620 if ( $this->is_doing_updates() ) {
621 return;
622 }
623
624 // Show notice if ajax is not working.
625 if ( ! give_test_ajax_works() ) {
626 Give()->notices->register_notice(
627 array(
628 'id' => 'give_db_upgrade_ajax_inaccessible',
629 'type' => 'error',
630 'description' => sprintf( '%1$s <a href="%2$s" target="_blank">%3$s</a>', __( 'Give needs to upgrade the database but cannot because AJAX does not appear accessible. This could be because your website is password protected, in maintenance mode, or has a specific hosting configuration or plugin active that is preventing access.', 'give' ), 'http://docs.givewp.com/admin-ajax-error', __( 'Read More', 'give' ) . ' &raquo;' ),
631 'show' => true,
632 )
633 );
634
635 return;
636 }
637
638 // Show db upgrade completed notice.
639 if ( ! empty( $_GET['give-db-update-completed'] ) ) {
640 Give()->notices->register_notice( array(
641 'id' => 'give_db_upgrade_completed',
642 'type' => 'updated',
643 'description' => __( 'Give database updates completed successfully. Thank you for updating to the latest version!', 'give' ),
644 'show' => true,
645 ) );
646
647 // Start update.
648 } elseif ( ! empty( $_GET['give-run-db-update'] ) ) {
649 $this->run_db_update();
650
651 // Show run the update notice.
652 } elseif ( $this->get_total_new_db_update_count() ) {
653 ob_start();
654 ?>
655 <p>
656 <strong><?php _e( 'Database Update', 'give' ); ?></strong>
657 &nbsp;&#8211;&nbsp;<?php _e( 'GiveWP needs to update your database to the latest version. The following process will make updates to your site\'s database. Please create a complete backup before proceeding.', 'give' ); ?>
658 </p>
659 <p class="submit">
660 <a href="<?php echo esc_url( add_query_arg( array( 'give-run-db-update' => 1 ), admin_url( 'edit.php?post_type=give_forms&page=give-updates' ) ) ); ?>" class="button button-primary give-run-update-now">
661 <?php _e( 'Run the updater', 'give' ); ?>
662 </a>
663 </p>
664 <script type="text/javascript">
665 jQuery('.give-run-update-now').click('click', function () {
666 return window.confirm('<?php echo esc_js( __( 'It is recommended that you backup your database before proceeding. Do you want to run the update now?', 'give' ) ); ?>'); // jshint ignore:line
667 });
668 </script>
669 <?php
670 $desc_html = ob_get_clean();
671
672 Give()->notices->register_notice( array(
673 'id' => 'give_upgrade_db',
674 'type' => 'updated',
675 'dismissible' => false,
676 'description' => $desc_html,
677 ) );
678 }
679 }
680
681 /**
682 * Render Give Updates Completed page
683 *
684 * @since 1.8.12
685 * @access public
686 */
687 public function render_complete_page() {
688 include_once GIVE_PLUGIN_DIR . 'includes/admin/upgrades/views/upgrades-complete.php';
689 }
690
691 /**
692 * Render Give Updates page
693 *
694 * @since 1.8.12
695 * @access public
696 */
697 public function render_page() {
698 include_once GIVE_PLUGIN_DIR . 'includes/admin/upgrades/views/upgrades.php';
699 }
700
701 /**
702 * Run database upgrades
703 *
704 * @since 2.0
705 * @access private
706 */
707 private function run_db_update() {
708 // Bailout.
709 if ( $this->is_doing_updates() || ! $this->get_total_new_db_update_count() ) {
710 return;
711 }
712
713 $updates = $this->get_updates( 'database', 'new' );
714
715 foreach ( $updates as $update ) {
716 self::$background_updater->push_to_queue( $update );
717 }
718
719 add_option( 'give_db_update_count', count( $updates ), '', 'no' );
720
721 add_option( 'give_doing_upgrade', array(
722 'update_info' => $updates[0],
723 'step' => 1,
724 'update' => 1,
725 'heading' => sprintf( 'Update %s of %s', 1, count( $updates ) ),
726 'percentage' => 0,
727 'total_percentage' => 0,
728 ), '', 'no' );
729
730 self::$background_updater->save()->dispatch();
731 }
732
733
734 /**
735 * Delete resume updates
736 *
737 * @since 1.8.12
738 * @access public
739 */
740 public function __flush_resume_updates() {
741 //delete_option( 'give_doing_upgrade' );
742 update_option( 'give_version', preg_replace( '/[^0-9.].*/', '', GIVE_VERSION ) );
743
744 // Reset counter.
745 $this->step = $this->percentage = 0;
746
747 $this->update = ( $this->get_total_db_update_count() > $this->update ) ?
748 ( $this->update + 1 ) :
749 $this->update;
750 }
751
752
753 /**
754 * Initialize updates
755 *
756 * @since 2.0
757 * @access public
758 *
759 * @return void
760 */
761 public function __give_start_updating() {
762 // Check permission.
763 if (
764 ! current_user_can( 'manage_give_settings' ) ||
765 $this->is_doing_updates()
766 ) {
767 wp_send_json_error();
768 }
769
770 // @todo: validate nonce
771 // @todo: set http method to post
772 if ( empty( $_POST['run_db_update'] ) ) {
773 wp_send_json_error();
774 }
775
776 $this->run_db_update();
777
778 wp_send_json_success();
779 }
780
781
782 /**
783 * This function handle ajax query for dn update status.
784 *
785 * @since 2.0
786 * @access public
787 *
788 * @return string
789 */
790 public function __give_db_updates_info() {
791 $update_info = get_option( 'give_doing_upgrade' );
792 $response_type = '';
793
794 if ( self::$background_updater->is_paused_process() ) {
795 $update_info = array(
796 'message' => __( 'The updates have been paused.', 'give' ),
797 'heading' => __( '', 'give' ),
798 'percentage' => 0,
799 );
800
801 if ( get_option( 'give_upgrade_error' ) ) {
802 $update_info['message'] = __( 'An unexpected issue occurred during the database update which caused it to stop automatically. Please contact support for assistance.', 'give' );
803 }
804
805 $response_type = 'error';
806
807 } elseif ( empty( $update_info ) ) {
808 $update_info = array(
809 'message' => __( 'Give database updates completed successfully. Thank you for updating to the latest version!', 'give' ),
810 'heading' => __( 'Updates Completed.', 'give' ),
811 'percentage' => 0,
812 );
813 $response_type = 'success';
814
815 delete_option( 'give_show_db_upgrade_complete_notice' );
816 }
817
818 $this->send_ajax_response( $update_info, $response_type );
819 }
820
821 /**
822 * Send ajax response
823 *
824 * @since 1.8.12
825 * @access public
826 *
827 * @param $data
828 * @param string $type
829 */
830 public function send_ajax_response( $data, $type = '' ) {
831 $default = array(
832 'message' => '',
833 'heading' => '',
834 'percentage' => 0,
835 'step' => 0,
836 'update' => 0,
837 );
838
839 // Set data.
840 $data = wp_parse_args( $data, $default );
841
842 // Enable cache.
843 Give_Cache::enable();
844
845 switch ( $type ) {
846 case 'success':
847 wp_send_json_success( $data );
848 break;
849
850 case 'error':
851 wp_send_json_error( $data );
852 break;
853
854 default:
855 wp_send_json( array(
856 'data' => $data,
857 ) );
858 break;
859 }
860 }
861
862 /**
863 * Set current update percentage.
864 *
865 * @since 1.8.12
866 * @access public
867 *
868 * @param $total
869 * @param $current_total
870 */
871 public function set_percentage( $total, $current_total ) {
872 // Set percentage.
873 $this->percentage = $total ? ( ( $current_total ) / $total ) * 100 : 0;
874
875 // Verify percentage.
876 $this->percentage = ( 100 < $this->percentage ) ? 100 : $this->percentage;
877 }
878
879 /**
880 * Check if parent update completed or not.
881 *
882 * @since 2.0
883 * @access private
884 *
885 * @param array $update
886 *
887 * @return bool|null
888 */
889 public function is_parent_updates_completed( $update ) {
890 // Bailout.
891 if ( empty( $update['depend'] ) ) {
892 return true;
893 }
894
895 // Check if dependency is valid or not.
896 if ( ! $this->has_valid_dependency( $update ) ) {
897 return null;
898 }
899
900 $is_dependency_completed = true;
901
902 foreach ( $update['depend'] as $depend ) {
903
904 if ( ! give_has_upgrade_completed( $depend ) ) {
905 $is_dependency_completed = false;
906 break;
907 }
908 }
909
910 return $is_dependency_completed;
911 }
912
913 /**
914 * Flag to check if DB updates running or not.
915 *
916 * @since 2.0
917 * @access public
918 * @return bool
919 */
920 public function is_doing_updates() {
921 return (bool) get_option( 'give_doing_upgrade' );
922 }
923
924
925 /**
926 * Check if update has valid dependency or not.
927 *
928 * @since 2.0
929 * @access public
930 *
931 * @param $update
932 *
933 * @return bool
934 */
935 public function has_valid_dependency( $update ) {
936 $is_valid_dependency = true;
937 // $update_ids = wp_list_pluck( $this->get_updates( 'database', 'all' ), 'id' );
938 //
939 // foreach ( $update['depend'] as $depend ) {
940 // // Check if dependency is valid or not.
941 // if ( ! in_array( $depend, $update_ids ) ) {
942 // $is_valid_dependency = false;
943 // break;
944 // }
945 // }
946
947 return $is_valid_dependency;
948 }
949
950 /**
951 * Get updates.
952 *
953 * @since 1.8.12
954 * @access public
955 *
956 * @param string $update_type Tye of update.
957 * @param string $status Tye of update.
958 *
959 * @return array
960 */
961 public function get_updates( $update_type = '', $status = 'all' ) {
962 // return all updates.
963 if ( empty( $update_type ) ) {
964 return $this->updates;
965 }
966
967 // Get specific update.
968 $updates = ! empty( $this->updates[ $update_type ] ) ? $this->updates[ $update_type ] : array();
969
970 // Bailout.
971 if ( empty( $updates ) ) {
972 return $updates;
973 }
974
975 switch ( $status ) {
976 case 'new':
977 // Remove already completed updates.
978 wp_cache_delete( 'give_completed_upgrades', 'options' );
979 $completed_updates = give_get_completed_upgrades();
980
981 if ( ! empty( $completed_updates ) ) {
982 foreach ( $updates as $index => $update ) {
983 if ( in_array( $update['id'], $completed_updates ) ) {
984 unset( $updates[ $index ] );
985 }
986 }
987 $updates = array_values( $updates );
988 }
989
990 break;
991 }
992
993 return $updates;
994 }
995
996 /**
997 * Get addon update count.
998 *
999 * @since 1.8.12
1000 * @access public
1001 * @return int
1002 */
1003 public function get_total_plugin_update_count() {
1004 return count( $this->get_updates( 'plugin' ) );
1005 }
1006
1007 /**
1008 * Get total update count
1009 *
1010 * @since 1.8.12
1011 * @access public
1012 *
1013 * @return int
1014 */
1015 public function get_total_update_count() {
1016 $db_update_count = $this->get_pending_db_update_count();
1017 $plugin_update_count = $this->get_total_plugin_update_count();
1018
1019 return ( $db_update_count + $plugin_update_count );
1020 }
1021
1022 /**
1023 * Get total pending updates count
1024 *
1025 * @since 1.8.12
1026 * @access public
1027 *
1028 * @return int
1029 */
1030 public function get_pending_db_update_count() {
1031 return count( $this->get_updates( 'database', 'new' ) );
1032 }
1033
1034 /**
1035 * Get total updates count
1036 *
1037 * @since 1.8.18
1038 * @access public
1039 *
1040 * @return int
1041 */
1042 public function get_total_db_update_count() {
1043 return count( $this->get_updates( 'database', 'all' ) );
1044 }
1045
1046 /**
1047 * Get total new updates count
1048 *
1049 * @since 2.0
1050 * @access public
1051 *
1052 * @param bool $refresh
1053 *
1054 * @return int
1055 */
1056 public function get_total_new_db_update_count( $refresh = false ) {
1057 $update_count = $this->is_doing_updates() && ! $refresh ?
1058 get_option( 'give_db_update_count' ) :
1059 $this->get_pending_db_update_count();
1060
1061 return $update_count;
1062 }
1063
1064 /**
1065 * Get total new updates count
1066 *
1067 * @since 2.0
1068 * @access public
1069 *
1070 * @param bool $refresh
1071 *
1072 * @return int
1073 */
1074 public function get_running_db_update( $refresh = false ) {
1075 $current_update = 1;
1076
1077 if ( $this->is_doing_updates() && ! $refresh ) {
1078 $current_update = get_option( 'give_doing_upgrade' );
1079 $current_update = $current_update['update'];
1080 }
1081
1082 return $current_update;
1083 }
1084
1085 /**
1086 * Get database update processing percentage.
1087 *
1088 * @since 2.0
1089 * @access public
1090 *
1091 * @param bool $refresh
1092 *
1093 * @return float|int
1094 */
1095 public function get_db_update_processing_percentage( $refresh = false ) {
1096 // Bailout.
1097 if ( ! $this->get_total_new_db_update_count( $refresh ) ) {
1098 return 0;
1099 }
1100
1101 $resume_update = get_option( 'give_doing_upgrade' );
1102 $update_count_percentages = ( ( $this->get_running_db_update( $refresh ) - 1 ) / $this->get_total_new_db_update_count( $refresh ) ) * 100;
1103 $update_percentage_share = ( 1 / $this->get_total_new_db_update_count() ) * 100;
1104 $upgrade_percentage = ( ( $resume_update['percentage'] * $update_percentage_share ) / 100 );
1105
1106 $final_percentage = $update_count_percentages + $upgrade_percentage;
1107
1108 return $this->is_doing_updates() ?
1109 ( absint( $final_percentage ) ?
1110 absint( $final_percentage ) :
1111 round( $final_percentage, 2 )
1112 ) :
1113 0;
1114 }
1115
1116
1117 /**
1118 * Get all update ids.
1119 *
1120 * @since 2.0.3
1121 *
1122 * @return array
1123 */
1124 public function get_update_ids() {
1125 $all_updates = $this->get_updates( 'database', 'all' );
1126 $all_update_ids = wp_list_pluck( $all_updates, 'id' );
1127
1128 return $all_update_ids;
1129 }
1130
1131 /**
1132 * Get offset count
1133 *
1134 * @since 2.0.5
1135 * @access public
1136 *
1137 * @param int $process_item_count
1138 *
1139 * @return float|int
1140 */
1141 public function get_offset( $process_item_count ) {
1142 return ( 1 === $this->step ) ?
1143 0 :
1144 ( $this->step - 1 ) * $process_item_count;
1145 }
1146 }
1147
1148 Give_Updates::get_instance()->setup();
1149