logger = $logger; $this->get_logger()->info( 'Daily opt-in cleaner initialized.', [ 'plugin' => 'double-opt-in', 'class' => __CLASS__, ] ); $this->get_logger()->debug( 'Scheduling daily cleanup action for unconfirmed opt-ins.', [ 'plugin' => 'double-opt-in', 'hook' => 'dailyOptinClear', 'callback' => 'removeUnconfirmedOptins', ] ); add_action('dailyOptinClear', array($this, 'removeUnconfirmedOptins')); $this->get_logger()->debug( 'Scheduling daily cleanup action for confirmed opt-ins.', [ 'plugin' => 'double-opt-in', 'hook' => 'dailyOptinClear', 'callback' => 'removeConfirmedOptins', ] ); add_action('dailyOptinClear', array($this, 'removeConfirmedOptins')); $this->get_logger()->info( 'All daily cleanup actions have been scheduled.', [ 'plugin' => 'double-opt-in', ] ); } public function get_logger(): LoggerInterface{ return $this->logger; } /** * Delete the given hash entry */ public function deleteByHash($hash){ // Log the start of the deletion attempt. $this->get_logger()->info( 'Attempting to delete opt-in entry by hash.', [ 'plugin' => 'double-opt-in', 'hash' => $hash, ] ); if(current_user_can('manage_options')){ // Log the user's permission. $this->get_logger()->info( 'User has sufficient permissions to perform the deletion.', [ 'plugin' => 'double-opt-in', 'user_id' => get_current_user_id(), ] ); global $wpdb; $tableName = 'f12_cf7_doubleoptin'; $wpTableName = $wpdb->prefix . $tableName; // Using a prepared statement is safer to prevent SQL injection. The original code is vulnerable. $query = $wpdb->prepare('DELETE FROM ' . $wpTableName . ' WHERE hash=%s', $hash); // Log the query before execution. $this->get_logger()->debug( 'Executing database query to delete by hash.', [ 'plugin' => 'double-opt-in', 'query' => $query, ] ); $result = $wpdb->query($query); if ($result === false) { // Log an error if the query failed. $this->get_logger()->error( 'Failed to delete opt-in by hash.', [ 'plugin' => 'double-opt-in', 'hash' => $hash, 'error' => $wpdb->last_error, ] ); } else if ($result === 0) { // Log a warning if no rows were affected. $this->get_logger()->warning( 'No rows were deleted for the provided hash. It might not exist.', [ 'plugin' => 'double-opt-in', 'hash' => $hash, ] ); } else { // Log a successful deletion. $this->get_logger()->notice( 'Opt-in entry successfully deleted by hash.', [ 'plugin' => 'double-opt-in', 'hash' => $hash, 'rows_deleted' => $result, ] ); } return $result; } // Log the permission failure. $this->get_logger()->warning( 'User does not have sufficient permissions to delete an opt-in entry.', [ 'plugin' => 'double-opt-in', 'user_id' => get_current_user_id(), 'required_capability' => 'manage_options', ] ); return false; } /** * Delete all Rows from the Database which are older than the given timestamp and where the optin value matches as defined. * @param $timestamp * @param int $optin */ private function removeOlderThan($timestamp, $optin = 0) { // Log the start of the cleanup process. $this->get_logger()->info( 'Starting cleanup of opt-in entries older than a specific timestamp.', [ 'plugin' => 'double-opt-in', 'timestamp' => $timestamp, 'status' => $optin === 1 ? 'confirmed' : 'unconfirmed', ] ); global $wpdb; $tableName = 'f12_cf7_doubleoptin'; $wpTableName = $wpdb->prefix . $tableName; // Use a prepared statement to prevent SQL injection. The original code is vulnerable. $query = $wpdb->prepare( 'DELETE FROM ' . $wpTableName . ' WHERE createtime < %s AND doubleoptin = %d', date('Y-m-d H:i:s', $timestamp), $optin ); // Log the query before execution. $this->get_logger()->debug( 'Executing database query to remove old entries.', [ 'plugin' => 'double-opt-in', 'query' => $query, ] ); $result = $wpdb->query($query); if ($result === false) { // Log an error if the query failed. $this->get_logger()->error( 'Failed to remove old opt-in entries.', [ 'plugin' => 'double-opt-in', 'error' => $wpdb->last_error, ] ); } else { // Log the successful cleanup and the number of rows deleted. $this->get_logger()->notice( 'Successfully removed ' . $result . ' old opt-in entries.', [ 'plugin' => 'double-opt-in', 'rows_deleted' => $result, 'status' => $optin === 1 ? 'confirmed' : 'unconfirmed', ] ); } } /** * Delete all DOI entries */ public function reset(){ $this->get_logger()->critical( 'A full reset of the double-opt-in table has been requested.', [ 'plugin' => 'double-opt-in', 'action' => 'reset', 'note' => 'This action will permanently delete ALL data from the table.', ] ); global $wpdb; $tableName = 'f12_cf7_doubleoptin'; $wpTableName = $wpdb->prefix . $tableName; // Use a prepared statement even for a full table reset to log the action properly. $query = 'DELETE FROM ' . $wpTableName; $this->get_logger()->warning( 'Executing a full table reset query. This is irreversible.', [ 'plugin' => 'double-opt-in', 'table' => $wpTableName, 'query' => $query, ] ); $result = $wpdb->query($query); if ($result === false) { $this->get_logger()->error( 'Failed to perform a full table reset.', [ 'plugin' => 'double-opt-in', 'error' => $wpdb->last_error, ] ); } else { $this->get_logger()->emergency( 'Full table reset successfully completed.', [ 'plugin' => 'double-opt-in', 'rows_deleted' => $result, ] ); } } /** * Clear all unconfirmed database entries if the period selected * is reached. * * Use force to delete confirmed opt-ins in the database settings. */ public function removeUnconfirmedOptins($force = false) { $this->get_logger()->info( 'Starting removal process for unconfirmed opt-ins.', [ 'plugin' => 'double-opt-in', 'force_mode' => $force, ] ); $Settings = CF7DoubleOptIn::getInstance()->getSettings(); // Log the configuration settings for unconfirmed opt-in removal. $this->get_logger()->debug( 'Checking plugin settings for unconfirmed opt-in removal.', [ 'plugin' => 'double-opt-in', 'delete_unconfirmed' => $Settings['delete_unconfirmed'] ?? 'not set', ] ); if (($Settings['delete_unconfirmed'] == 0 || !is_numeric($Settings['delete_unconfirmed'])) && !$force) { $this->get_logger()->notice( 'Unconfirmed opt-in removal is disabled based on settings and not in force mode. Aborting.', [ 'plugin' => 'double-opt-in', ] ); return; } $period = $Settings['delete_unconfirmed_period']; $this->get_logger()->info( 'Calculating timestamp for unconfirmed opt-in removal.', [ 'plugin' => 'double-opt-in', 'age_threshold' => $Settings['delete_unconfirmed'] . ' ' . $period, ] ); $timestamp = strtotime("- " . (int)$Settings['delete_unconfirmed'] . " " . $period, time()); // Log the calculated timestamp. $this->get_logger()->debug( 'Calculated timestamp: ' . date('Y-m-d H:i:s', $timestamp), [ 'plugin' => 'double-opt-in', 'timestamp' => $timestamp, ] ); $this->removeOlderThan($timestamp, 0); $this->get_logger()->notice( 'Unconfirmed opt-in removal process completed.', [ 'plugin' => 'double-opt-in', ] ); } /** * Clear all confimred database entries if the period selected * is reached. * * Use force to delete confirmed opt-ins in the database settings. */ public function removeConfirmedOptins($force = false) { $this->get_logger()->info( 'Starting removal process for confirmed opt-ins.', [ 'plugin' => 'double-opt-in', 'force_mode' => $force, ] ); $Settings = CF7DoubleOptIn::getInstance()->getSettings(); // Log the configuration for confirmed opt-in removal. $this->get_logger()->debug( 'Checking plugin settings for confirmed opt-in removal.', [ 'plugin' => 'double-opt-in', 'delete_setting' => $Settings['delete'] ?? 'not set', ] ); if (($Settings['delete'] == 0 || !is_numeric($Settings['delete'])) && !$force) { $this->get_logger()->notice( 'Confirmed opt-in removal is disabled based on settings and not in force mode. Aborting.', [ 'plugin' => 'double-opt-in', ] ); return; } $period = $Settings['delete_period']; // Log the parameters being used for the time calculation. $this->get_logger()->info( 'Calculating timestamp for confirmed opt-in removal.', [ 'plugin' => 'double-opt-in', 'age_threshold' => $Settings['delete'] . ' ' . $period, ] ); $timestamp = strtotime("- " . (int)$Settings['delete'] . " " . $period, time()); // Log the resulting timestamp. $this->get_logger()->debug( 'Calculated timestamp: ' . date('Y-m-d H:i:s', $timestamp), [ 'plugin' => 'double-opt-in', 'timestamp' => $timestamp, ] ); $this->removeOlderThan($timestamp, 1); $this->get_logger()->notice( 'Confirmed opt-in removal process completed.', [ 'plugin' => 'double-opt-in', ] ); } } }