show_error_message(__('Please select list', 'email-subscribers')); } } $csv = $this->generate_csv($status, $selected_list_id); $file_name = sprintf('%s-contacts.csv', strtolower($status)); $this->output_CSV($csv, $file_name); } elseif ($report && $link_id && $campaign_id && $can_access_campaign) { $subscribers = ES()->actions_db->get_link_cliked_subscribers($campaign_id, $link_id); if ( count( $subscribers ) > 0 ) { $sub_headers = [ __('First Name', 'email-subscribers'), __('Last Name', 'email-subscribers'), __('Email', 'email-subscribers'), ]; $csv = implode(',', $sub_headers); $csv.="\n"; foreach ($subscribers as $subscriber) { $data = [ 'first_name' => $this->escape_and_trim_data($subscriber['first_name']), 'last_name' => $this->escape_and_trim_data($subscriber['last_name']), 'email' => $this->escape_and_trim_data($subscriber['email']), ]; $csv .= '"' . implode('","', $data) . "\"\n"; } } if (empty($csv)) { $this->show_error_message(__('No data available', 'email-subscribers')); } $this->output_CSV($csv, 'subscriber-contacts.csv'); } } add_filter( 'query_vars', array( $this, 'query_vars' ) ); add_action( 'parse_request', array( $this, 'parse_request' ) ); add_action( 'admin_menu', array( $this, 'plugin_menu' ) ); } private function show_error_message( $message) { ES_Common::show_message($message, 'error'); exit(); } private function escape_and_trim_data( $data) { return trim(str_replace('"', '""', $this->escape_data($data))); } private function output_CSV( $csv_content, $file_name) { header('Pragma: public'); header('Expires: 0'); header('Cache-Control: must-revalidate, post-check=0, pre-check=0'); header('Cache-Control: private', false); header('Content-Type: application/octet-stream'); header("Content-Disposition: attachment; filename=$file_name"); header('Content-Transfer-Encoding: binary'); echo wp_kses_post($csv_content); exit(); } public function plugin_menu() { add_submenu_page( null, 'Export Contacts', __( 'Export Contacts', 'email-subscribers' ), 'edit_posts', 'es_export_subscribers', array( $this, 'export_subscribers_page' ) ); } public function prepare_header_footer_row() { ?> "; $list_dropdown_html .= ES_Common::prepare_list_dropdown_options(); $list_dropdown_html .= ''; $export_lists = array( 'all' => __( 'All contacts', 'email-subscribers' ), 'subscribed' => __( 'Subscribed contacts', 'email-subscribers' ), 'unsubscribed' => __( 'Unsubscribed contacts', 'email-subscribers' ), 'unconfirmed' => __( 'Unconfirmed contacts', 'email-subscribers' ), 'select_list' => $list_dropdown_html, ); $i = 1; $export_nonce = wp_create_nonce( 'ig-es-subscriber-export-nonce' ); foreach ( $export_lists as $key => $export_list ) { $url = "admin.php?page=download_report&report=users&status={$key}&export-nonce={$export_nonce}"; ?> count_subscribers( $key ) ); ?>


prepare_header_footer_row(); ?> prepare_body(); ?> prepare_header_footer_row(); ?>
lists_contacts_db->get_all_contacts_count( 0, false ); break; case 'subscribed': return ES()->lists_contacts_db->get_subscribed_contacts_count( 0, false ); break; case 'unsubscribed': return ES()->lists_contacts_db->get_unsubscribed_contacts_count( 0, false ); break; case 'confirmed': return ES()->lists_contacts_db->get_confirmed_contacts_count( 0, false ); break; case 'unconfirmed': return ES()->lists_contacts_db->get_unconfirmed_contacts_count( 0, false ); break; case 'select_list': default: return '-'; break; } } /** * Allow for custom query variables */ public function query_vars( $query_vars ) { $query_vars[] = 'download_report'; return $query_vars; } /** * Parse the request */ public function parse_request( &$wp ) { if ( array_key_exists( 'download_report', $wp->query_vars ) ) { $this->download_report(); exit; } } /** * Download report */ public function download_report() { ?>

Download Report

lists_contacts_db->get_all_contacts(); } elseif ( 'subscribed' === $status ) { $results = ES()->lists_contacts_db->get_all_subscribed_contacts(); } elseif ( 'unsubscribed' === $status ) { $results = ES()->lists_contacts_db->get_all_unsubscribed_contacts(); } elseif ( 'confirmed' === $status ) { $results = ES()->lists_contacts_db->get_all_confirmed_contacts(); } elseif ( 'unconfirmed' === $status ) { $results = ES()->lists_contacts_db->get_all_unconfirmed_contacts(); } elseif ( 'select_list' === $status ) { $list_id = absint( $list_id ); $results = ES()->lists_contacts_db->get_all_contacts_from_list( $list_id ); } $subscribers = array(); if ( count( $results ) > 0 ) { $contact_list_map = array(); $contact_ids = array(); foreach ( $results as $result ) { if ( ! in_array( $result['contact_id'], $contact_ids, true ) ) { $contact_ids[] = $result['contact_id']; } $contact_list_map[ $result['contact_id'] ][] = array( 'status' => $result['status'], 'list_id' => $result['list_id'], 'optin_type' => $result['optin_type'], ); } $contact_ids_str = implode( ',', $contact_ids ); $select_columns = array( 'id', 'first_name', 'last_name', 'email', 'created_at', ); $custom_fields = ES()->custom_fields_db->get_custom_fields(); if ( ! empty( $custom_fields ) ) { foreach ( $custom_fields as $field ) { $select_columns[] = $field['slug']; } } $query = 'SELECT ' . implode( ',', $select_columns ) . " FROM {$wpbd->prefix}ig_contacts WHERE id IN ({$contact_ids_str})"; $subscribers = $wpbd->get_results( $query, ARRAY_A ); } $csv_output = ''; if ( count( $subscribers ) > 0 ) { $headers = array( __( 'First Name', 'email-subscribers' ), __( 'Last Name', 'email-subscribers' ), __( 'Email', 'email-subscribers' ), __( 'List', 'email-subscribers' ), __( 'Status', 'email-subscribers' ), __( 'Opt-In Type', 'email-subscribers' ), __( 'Created On', 'email-subscribers' ), ); if ( ! empty( $custom_fields ) ) { foreach ( $custom_fields as $field ) { $headers[] = $field['label']; } } $lists_id_name_map = ES()->lists_db->get_list_id_name_map(); $csv_output .= implode( ',', $headers ); foreach ( $subscribers as $key => $subscriber ) { $data = array(); $data['first_name'] = trim( str_replace( '"', '""', $this->escape_data( $subscriber['first_name'] ) ) ); $data['last_name'] = trim( str_replace( '"', '""', $this->escape_data( $subscriber['last_name'] ) ) ); $data['email'] = trim( str_replace( '"', '""', $this->escape_data( $subscriber['email'] ) ) ); $contact_id = $subscriber['id']; if ( ! empty( $contact_list_map[ $contact_id ] ) ) { foreach ( $contact_list_map[ $contact_id ] as $list_details ) { $data['list'] = $lists_id_name_map[ $list_details['list_id'] ]; $data['status'] = ucfirst( $list_details['status'] ); $data['optin_type'] = ( 1 == $list_details['optin_type'] ) ? 'Single Opt-In' : 'Double Opt-In'; $data['created_at'] = $subscriber['created_at']; if ( ! empty( $custom_fields ) ) { foreach ( $custom_fields as $field ) { $column_name = $field['slug']; $data[ $column_name ] = $subscriber[ $column_name ]; } } $csv_output .= "\n"; $csv_output .= '"' . implode( '","', $data ) . '"'; } } } } return $csv_output; } /** * Escape a string to be used in a CSV context * * Malicious input can inject formulas into CSV files, opening up the possibility * for phishing attacks and disclosure of sensitive information. * * Additionally, Excel exposes the ability to launch arbitrary commands through * the DDE protocol. * * @see http://www.contextis.com/resources/blog/comma-separated-vulnerabilities/ * @see https://hackerone.com/reports/72785 * * @since 5.5.3 * @param string $data CSV field to escape. * @return string */ public function escape_data( $data ) { $active_content_triggers = array( '=', '+', '-', '@' ); if ( in_array( mb_substr( $data, 0, 1 ), $active_content_triggers, true ) ) { $data = "'" . $data; } return $data; } }