| @@ -6,9 +6,9 @@ | ||
| 6 | 6 | * when the plugin is deactivated. |
| 7 | 7 | * |
| 8 | 8 | * @package Charitable/Charitable_Uninstall |
| 9 | 9 | * @author David Bisset |
| 10 | - * @copyright Copyright (c) 2022, WP Charitable LLC | |
| 10 | + * @copyright Copyright (c) 2023, WP Charitable LLC | |
| 11 | 11 | * @license http://opensource.org/licenses/gpl-2.0.php GNU Public License |
| 12 | 12 | * @since 1.0.0 |
| 13 | 13 | * @version 1.6.42 |
| 14 | 14 | */ |
| @@ -38,8 +38,9 @@ | ||
| 38 | 38 | $this->remove_caps(); |
| 39 | 39 | $this->remove_post_data(); |
| 40 | 40 | $this->remove_tables(); |
| 41 | 41 | $this->remove_settings(); |
| 42 | + $this->remove_abilities_data(); | |
| 42 | 43 | |
| 43 | 44 | do_action( 'charitable_uninstall' ); |
| 44 | 45 | } |
| 45 | 46 | } |
| @@ -66,9 +67,9 @@ | ||
| 66 | 67 | */ |
| 67 | 68 | private function remove_post_data() { |
| 68 | 69 | global $wpdb; |
| 69 | 70 | |
| 70 | - $posts = $wpdb->get_col( "SELECT ID FROM $wpdb->posts WHERE post_type IN ( 'donation', 'campaign' );" ); | |
| 71 | + $posts = $wpdb->get_col( "SELECT ID FROM $wpdb->posts WHERE post_type IN ( 'donation', 'campaign' );" ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching | |
| 71 | 72 | |
| 72 | 73 | foreach ( $posts as $post_id ) { |
| 73 | 74 | wp_delete_post( $post_id, true ); |
| 74 | 75 | } |
| @@ -77,8 +78,9 @@ | ||
| 77 | 78 | /** |
| 78 | 79 | * Remove the custom tables added by Charitable. |
| 79 | 80 | * |
| 80 | 81 | * @since 1.0.0 |
| 82 | + * @version 1.8.1 | |
| 81 | 83 | * |
| 82 | 84 | * @global WPDB $wpdb The WordPress database object. |
| 83 | 85 | * @return void |
| 84 | 86 | */ |
| @@ -84,17 +86,21 @@ | ||
| 84 | 86 | */ |
| 85 | 87 | private function remove_tables() { |
| 86 | 88 | global $wpdb; |
| 87 | 89 | |
| 88 | - $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_campaign_donations' ); | |
| 89 | - $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_donors' ); | |
| 90 | - $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_donormeta' ); | |
| 91 | - $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_benefactors' ); | |
| 90 | + $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_campaign_donations' ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.DirectDatabaseQuery.SchemaChange | |
| 91 | + $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_donors' ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.DirectDatabaseQuery.SchemaChange | |
| 92 | + $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_donormeta' ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.DirectDatabaseQuery.SchemaChange | |
| 93 | + $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_benefactors' ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.DirectDatabaseQuery.SchemaChange | |
| 94 | + $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_donation_activities' ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.DirectDatabaseQuery.SchemaChange | |
| 95 | + $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'charitable_campaign_activities' ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.DirectDatabaseQuery.SchemaChange | |
| 92 | 96 | |
| 93 | 97 | delete_option( $wpdb->prefix . 'charitable_campaign_donations_db_version' ); |
| 94 | 98 | delete_option( $wpdb->prefix . 'charitable_donors_db_version' ); |
| 95 | 99 | delete_option( $wpdb->prefix . 'charitable_donormeta_db_version' ); |
| 96 | 100 | delete_option( $wpdb->prefix . 'charitable_benefactors_db_version' ); |
| 101 | + delete_option( $wpdb->prefix . 'charitable_donation_activities_db_version' ); | |
| 102 | + delete_option( $wpdb->prefix . 'charitable_campaign_activities_db_version' ); | |
| 97 | 103 | } |
| 98 | 104 | |
| 99 | 105 | /** |
| 100 | 106 | * Remove any other options added by Charitable. |
| @@ -107,16 +113,67 @@ | ||
| 107 | 113 | delete_option( 'charitable_settings' ); |
| 108 | 114 | delete_option( 'charitable_version' ); |
| 109 | 115 | delete_option( 'charitable_upgrade_log' ); |
| 110 | 116 | delete_option( 'charitable_skipped_donations_with_empty_donor_id' ); |
| 117 | + delete_option( 'charitable_analysis_token' ); | |
| 111 | 118 | |
| 112 | 119 | delete_transient( 'charitable_notices' ); |
| 113 | 120 | delete_transient( 'charitable_user_dashboard_objects' ); |
| 114 | 121 | delete_transient( 'charitable_custom_styles' ); |
| 122 | + delete_transient( 'charitable_analysis_cache' ); | |
| 115 | 123 | |
| 116 | 124 | /* Stop Charitable from re-adding the notices transient. */ |
| 117 | 125 | if ( function_exists( 'charitable_get_admin_notices' ) ) { |
| 118 | 126 | remove_action( 'shutdown', array( charitable_get_admin_notices(), 'shutdown' ) ); |
| 127 | + } | |
| 128 | + | |
| 129 | + /* | |
| 130 | + * The `ai_mcp_write_enabled` setting (Charitable_Tools_Ai_Mcp::WRITE_SETTING_KEY) | |
| 131 | + * needs NO separate delete_option() call. It is not its own option - | |
| 132 | + * it is a key nested inside the `charitable_settings` array, written by | |
| 133 | + * ajax_toggle_write() as $settings['ai_mcp_write_enabled'], and the | |
| 134 | + * blanket delete_option( 'charitable_settings' ) above already removes | |
| 135 | + * it. Any future AI setting nested the same way needs no change here | |
| 136 | + * either. (1.8.13 briefly also stored `ai_mcp_write_scopes` in that | |
| 137 | + * array; it was removed before release, and the blanket delete covered | |
| 138 | + * it while it existed.) | |
| 139 | + * | |
| 140 | + * @since 1.8.13 | |
| 141 | + */ | |
| 142 | + } | |
| 143 | + | |
| 144 | + /** | |
| 145 | + * Remove data added by the Abilities API integration (1.8.13). | |
| 146 | + * | |
| 147 | + * Scoped to what THIS feature added, not a blanket log wipe. | |
| 148 | + * | |
| 149 | + * `charitable_abilities_usage` (Charitable_Abilities_Usage::OPTION) is a | |
| 150 | + * dedicated top-level option, never nested inside `charitable_settings`, | |
| 151 | + * so remove_settings() above cannot reach it - it needs its own line. | |
| 152 | + * | |
| 153 | + * Log rows are pruned by TYPE rather than the whole table being | |
| 154 | + * dropped: `charitable_logs` holds every log type Charitable writes, | |
| 155 | + * most of them unrelated to this feature, and remove_tables() above | |
| 156 | + * never drops that table at all (logs are not otherwise touched on | |
| 157 | + * uninstall). Guarded on the table existing, since a site that never | |
| 158 | + * triggered log_create_table() (Charitable_Log_DB::create_table()) has | |
| 159 | + * no table for a bare DELETE to run against. | |
| 160 | + * | |
| 161 | + * @since 1.8.13 | |
| 162 | + * | |
| 163 | + * @global WPDB $wpdb | |
| 164 | + * @return void | |
| 165 | + */ | |
| 166 | + private function remove_abilities_data() { | |
| 167 | + global $wpdb; | |
| 168 | + | |
| 169 | + delete_option( 'charitable_abilities_usage' ); | |
| 170 | + | |
| 171 | + $table = $wpdb->prefix . 'charitable_logs'; | |
| 172 | + | |
| 173 | + if ( $wpdb->get_var( $wpdb->prepare( 'SHOW TABLES LIKE %s', $table ) ) === $table ) { // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching | |
| 174 | + // $table is $wpdb->prefix . 'charitable_logs' and carries no user input; MySQL cannot bind a table identifier as a prepared parameter, so interpolation is the only option. | |
| 175 | + $wpdb->query( $wpdb->prepare( "DELETE FROM {$table} WHERE types = %s", 'abilities' ) ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching,WordPress.DB.PreparedSQL.InterpolatedNotPrepared,PluginCheck.Security.DirectDB.UnescapedDBParameter | |
| 119 | 176 | } |
| 120 | 177 | } |
| 121 | 178 | } |
| 122 | 179 | |