PluginProbe
TablePress – Tables in WordPress made easy / 3.4
TablePress – Tables in WordPress made easy v3.4
3.4 3.3.4 3.3.3 3.3.2 3.3.1 trunk 1.12 1.14 1.9.2 2.0.4 2.1.7 2.1.8 2.2 2.2.1 2.2.2 2.2.3 2.2.4 2.2.5 2.3 2.3.1 2.3.2 2.4 2.4.1 2.4.2 2.4.3 All 45 releases
← All changes | libraries/freemius/includes/class-fs-plugin-updater.php +77 -41 2.4 → 3.4 View file →
@@ -105,8 +105,10 @@
105 105 ), 11, 2 );
106 106
107 107 if ( ! $this->_fs->has_any_active_valid_license() ) {
108 108 add_action( 'admin_head', array( &$this, 'catch_plugin_information_dialog_contents' ) );
109 + } else {
110 + add_action( 'admin_footer', array( &$this, '_add_fs_allow_updater_and_dialog_request_param' ) );
109 111 }
110 112
111 113 if ( ! WP_FS__IS_PRODUCTION_MODE ) {
112 114 add_filter( 'http_request_host_is_external', array(
@@ -130,15 +132,48 @@
130 132 }
131 133
132 134 /**
133 135 * @author Leo Fajardo (@leorw)
136 + * @since 2.7.4
137 + */
138 + function _add_fs_allow_updater_and_dialog_request_param() {
139 + if ( ! $this->is_plugin_information_dialog_for_plugin() ) {
140 + return;
141 + }
142 + ?>
143 + <script type="text/javascript">
144 + if ( typeof jQuery !== 'undefined' ) {
145 + jQuery( document ).on( 'wp-plugin-updating', function( event, args ) {
146 + if ( typeof args === 'object' && args.slug && typeof args.slug === 'string' ) {
147 + if ( <?php echo json_encode( $this->_fs->get_slug() ) ?> === args.slug ) {
148 + args.fs_allow_updater_and_dialog = true;
149 + }
150 + }
151 + } );
152 + }
153 + </script>
154 + <?php
155 + }
156 +
157 + /**
158 + * @author Leo Fajardo (@leorw)
159 + * @since 2.7.4
160 + *
161 + * @return bool
162 + */
163 + private function is_plugin_information_dialog_for_plugin() {
164 + return (
165 + 'plugin-information' === fs_request_get( 'tab', false ) &&
166 + $this->_fs->get_slug() === fs_request_get_raw( 'plugin', false )
167 + );
168 + }
169 +
170 + /**
171 + * @author Leo Fajardo (@leorw)
134 172 * @since 2.1.4
135 173 */
136 174 function catch_plugin_information_dialog_contents() {
137 - if (
138 - 'plugin-information' !== fs_request_get( 'tab', false ) ||
139 - $this->_fs->get_slug() !== fs_request_get_raw( 'plugin', false )
140 - ) {
175 + if ( ! $this->is_plugin_information_dialog_for_plugin() ) {
141 176 return;
142 177 }
143 178
144 179 add_action( 'admin_footer', array( &$this, 'edit_and_echo_plugin_information_dialog_contents' ), 0, 1 );
@@ -504,38 +539,40 @@
504 539 ) {
505 540 return $transient_data;
506 541 }
507 542
543 + // Alias.
544 + $basename = $this->_fs->premium_plugin_basename();
545 +
508 546 global $wp_current_filter;
509 547
510 - $current_plugin_version = $this->_fs->get_plugin_version();
511 -
512 - if ( ! empty( $wp_current_filter ) && 'upgrader_process_complete' === $wp_current_filter[0] ) {
513 - if (
514 - is_null( $this->_update_details ) ||
515 - ( is_object( $this->_update_details ) && $this->_update_details->new_version !== $current_plugin_version )
516 - ) {
548 + /**
549 + * During bulk updates, avoid re-injecting update data for the plugin itself once it has already been updated.
550 + *
551 + * If the custom package is re-added to the transient after the plugin update, WordPress may detect the package again and incorrectly report "The plugin is at the latest version" for a pending update, since the custom package version matches the currently installed version.
552 + *
553 + * Behavior differs depending on how the bulk update is triggered. Please refer to the inline comments for each flow below for details.
554 + */
555 + if (
556 + ! empty( $wp_current_filter ) && (
517 557 /**
518 - * After an update, clear the stored update details and reparse the plugin's main file in order to get
519 - * the updated version's information and prevent the previous update information from showing up on the
520 - * updates page.
521 - *
522 - * @author Leo Fajardo (@leorw)
523 - * @since 2.3.1
558 + * update-core.php and other upgrader pages:
559 + * The `upgrader_process_complete` action fires only once after all updates have finished. In this case, it is the current action (`$wp_current_filter[0]`), while `self::$_upgrade_basename` may contain any plugin basename.
524 560 */
525 - $this->_update_details = null;
526 - $current_plugin_version = $this->_fs->get_plugin_version( true );
527 - }
561 + 'upgrader_process_complete' === $wp_current_filter[0] ||
562 + /**
563 + * AJAX bulk updates (e.g., from the Plugins page):
564 + * The `upgrader_process_complete` action fires multiple times — once for each plugin after it finishes updating. In this flow, it is not the current action (`$wp_current_filter[0]`) because it is triggered from another action. Instead, we compare `self::$_upgrade_basename` with the basename of the plugin currently being updated, since the `upgrader_process_complete` action runs separately for each plugin.
565 + */
566 + ( in_array( 'upgrader_process_complete', $wp_current_filter ) && self::$_upgrade_basename === $basename )
567 + )
568 + ) {
569 + return $transient_data;
528 570 }
529 571
530 572 if ( ! isset( $this->_update_details ) ) {
531 573 // Get plugin's newest update.
532 - $new_version = $this->_fs->get_update(
533 - false,
534 - fs_request_get_bool( 'force-check' ),
535 - FS_Plugin_Updater::UPDATES_CHECK_CACHE_EXPIRATION,
536 - $current_plugin_version
537 - );
574 + $new_version = $this->_fs->get_update( false, fs_request_get_bool( 'force-check' ) );
538 575
539 576 $this->_update_details = false;
540 577
541 578 if ( is_object( $new_version ) && $this->is_new_version_premium( $new_version ) ) {
@@ -551,11 +588,8 @@
551 588 $this->_update_details = $this->get_update_details( $new_version );
552 589 }
553 590 }
554 591
555 - // Alias.
556 - $basename = $this->_fs->premium_plugin_basename();
557 -
558 592 if ( is_object( $this->_update_details ) ) {
559 593 if ( isset( $transient_data->no_update ) ) {
560 594 unset( $transient_data->no_update[ $basename ] );
561 595 }
@@ -615,9 +649,9 @@
615 649 }
616 650
617 651 $slug = $this->_fs->get_slug();
618 652
619 - if ( $this->_fs->is_org_repo_compliant() && $this->_fs->is_freemium() ) {
653 + if ( $this->can_fetch_data_from_wp_org() ) {
620 654 if ( ! isset( $this->_translation_updates ) ) {
621 655 $this->_translation_updates = array();
622 656
623 657 $translation_updates = $this->fetch_wp_org_module_translation_updates( $module_type, $slug );
@@ -684,18 +718,10 @@
684 718 'default' => $icon,
685 719 );
686 720 }
687 721
688 - if ( $this->_fs->is_premium() ) {
689 - $latest_tag = $this->_fs->_fetch_latest_version( $this->_fs->get_id(), false );
690 -
691 - if (
692 - isset( $latest_tag->readme ) &&
693 - isset( $latest_tag->readme->upgrade_notice ) &&
694 - ! empty( $latest_tag->readme->upgrade_notice )
695 - ) {
696 - $update->upgrade_notice = $latest_tag->readme->upgrade_notice;
697 - }
722 + if ( $this->_fs->is_premium() && ! empty( $new_version->upgrade_notice ) ) {
723 + $update->upgrade_notice = $new_version->upgrade_notice;
698 724 }
699 725
700 726 $update->{$this->_fs->get_module_type()} = $this->_fs->get_plugin_basename();
701 727
@@ -873,8 +899,18 @@
873 899 return $res;
874 900 }
875 901
876 902 /**
903 + * Returns true if the product can fetch data from WordPress.org.
904 + *
905 + * @author Leo Fajardo (@leorw)
906 + * @since 2.7.4
907 + */
908 + private function can_fetch_data_from_wp_org() {
909 + return ( $this->_fs->is_org_repo_compliant() && $this->_fs->is_freemium() );
910 + }
911 +
912 + /**
877 913 * Fetches module translation updates from wordpress.org.
878 914 *
879 915 * @author Leo Fajardo (@leorw)
880 916 * @since 2.1.2
@@ -1056,9 +1092,9 @@
1056 1092 $is_addon = true;
1057 1093 }
1058 1094
1059 1095 $plugin_in_repo = false;
1060 - if ( ! $is_addon ) {
1096 + if ( ! $is_addon && $this->can_fetch_data_from_wp_org() ) {
1061 1097 // Try to fetch info from .org repository.
1062 1098 $data = self::_fetch_plugin_info_from_repository( $action, $args );
1063 1099
1064 1100 $plugin_in_repo = ( false !== $data );