Test Failed
Push — tests ( 5a43f2 )
by
unknown
03:08
created

email-log.php (8 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
/**
3
 * Plugin Name: Email Log
4
 * Plugin URI: http://sudarmuthu.com/wordpress/email-log
5
 * Description: Logs every email sent through WordPress
6
 * Donate Link: http://sudarmuthu.com/if-you-wanna-thank-me
7
 * Author: Sudar
8
 * Version: 1.9
9
 * Author URI: http://sudarmuthu.com/
10
 * Text Domain: email-log
11
 * Domain Path: languages/
12
 * === RELEASE NOTES ===
13
 * Check readme file for full release notes
14
 */
15
16
/**
17
 * Copyright 2009  Sudar Muthu  (email : [email protected])
18
 * This program is free software; you can redistribute it and/or modify
19
 * it under the terms of the GNU General Public License, version 2, as
20
 * published by the Free Software Foundation.
21
 * This program is distributed in the hope that it will be useful,
22
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24
 * GNU General Public License for more details.
25
 * You should have received a copy of the GNU General Public License
26
 * along with this program; if not, write to the Free Software
27
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
28
 */
29
30
/**
31
 * Plugin Root File
32
 *
33
 * @since 1.7.2
34
 */
35
if ( ! defined( 'EMAIL_LOG_PLUGIN_FILE' ) ) {
36
	define( 'EMAIL_LOG_PLUGIN_FILE', __FILE__ );
37
}
38
39
/**
40
 * Handles installation and table creation.
41
 */
42
require_once plugin_dir_path( __FILE__ ) . 'include/install.php';
43
44
/**
45
 * Helper functions.
46
 */
47
require_once plugin_dir_path( __FILE__ ) . 'include/util/helper.php';
48
49
/**
50
 * The main plugin class.
51
 *
52
 * @since Genesis
53
 */
54
class EmailLog {
55
56
	/**
57
	 * Filesystem directory path with trailing slash.
58
	 *
59
	 * @since Genesis
60
	 * @var string $include_path
61
	 */
62
	public $include_path;
63
64
	/**
65
	 * Admin screen object.
66
	 *
67
	 * @since Genesis
68
	 * @access private
69
	 * @var string $include_path
70
	 */
71
	private $admin_screen;
72
73
	/**
74
	 * Version number.
75
	 *
76
	 * @since Genesis
77
	 * @var const VERSION
78
	 */
79
	const VERSION                  = '1.9';
80
81
	/**
82
	 * Filter name.
83
	 *
84
	 * @since Genesis
85
	 * @var const FILTER_NAME
86
	 */
87
	const FILTER_NAME              = 'wp_mail_log';
88
89
	/**
90
	 * Page slug to be used in admin dashboard hyperlinks.
91
	 *
92
	 * @since Genesis
93
	 * @var const PAGE_SLUG
94
	 */
95
	const PAGE_SLUG                = 'email-log';
96
97
	/**
98
	 * String value to generate nonce.
99
	 *
100
	 * @since Genesis
101
	 * @var const DELETE_LOG_NONCE_FIELD
102
	 */
103
	const DELETE_LOG_NONCE_FIELD   = 'sm-delete-email-log-nonce';
104
105
	/**
106
	 * String value to generate nonce.
107
	 *
108
	 * @since Genesis
109
	 * @var const DELETE_LOG_ACTION
110
	 */
111
	const DELETE_LOG_ACTION        = 'sm-delete-email-log';
112
113
	// DB stuff
114
	const TABLE_NAME               = 'email_log';          /* Database table name */
115
	const DB_OPTION_NAME           = 'email-log-db';       /* Database option name */
116
	const DB_VERSION               = '0.1';                /* Database version */
117
118
	// JS Stuff
119
	const JS_HANDLE                = 'email-log';
120
121
	//hooks
122
	const HOOK_LOG_COLUMNS         = 'email_log_manage_log_columns';
123
	const HOOK_LOG_DISPLAY_COLUMNS = 'email_log_display_log_columns';
124
125
	/**
126
	 * Initialize the plugin by registering the hooks.
127
	 */
128
	function __construct() {
0 ignored issues
show
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
129
		$this->include_path = plugin_dir_path( __FILE__ );
130
131
		// Load localization domain.
132
		$this->translations = dirname( plugin_basename( __FILE__ ) ) . '/languages/' ;
0 ignored issues
show
The property translations does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
133
		load_plugin_textdomain( 'email-log', false, $this->translations );
134
135
		// Register hooks.
136
		add_action( 'admin_menu', array( $this, 'register_settings_page' ) );
137
138
		// Register Filter.
139
		add_filter( 'wp_mail', array( $this, 'log_email' ) );
140
		add_filter( 'set-screen-option', array( $this, 'save_screen_options' ), 10, 3 );
141
		add_filter( 'plugin_row_meta', array( $this, 'add_plugin_links' ), 10, 2 );
142
143
		$plugin = plugin_basename( __FILE__ );
144
		add_filter( "plugin_action_links_$plugin", array( $this, 'add_action_links' ) );
1 ignored issue
show
Coding Style Best Practice introduced by
As per coding-style, please use concatenation or sprintf for the variable $plugin instead of interpolation.

It is generally a best practice as it is often more readable to use concatenation instead of interpolation for variables inside strings.

// Instead of
$x = "foo $bar $baz";

// Better use either
$x = "foo " . $bar . " " . $baz;
$x = sprintf("foo %s %s", $bar, $baz);
Loading history...
145
146
		// Add our ajax call.
147
		add_action( 'wp_ajax_display_content', array( $this, 'display_content_callback' ) );
148
	}
149
150
	/**
151
	 * Adds additional links in the plugin listing page.
152
	 *
153
	 * @since Genesis
154
	 *
155
	 * @see Additional links in the Plugin listing is based on
156
	 * @link http://zourbuth.com/archives/751/creating-additional-wordpress-plugin-links-row-meta/
157
	 *
158
	 * @param array $links Array with default links to display in plugins page.
159
	 * @param string $file The name of the plugin file.
160
	 * @return array Array with links to display in plugins page.
161
	 */
162
	public function add_plugin_links( $links, $file ) {
163
		$plugin = plugin_basename( __FILE__ );
164
165
		if ( $file == $plugin ) {
166
			// only for this plugin
167
			return array_merge( $links,
168
				array( '<a href="http://sudarmuthu.com/wordpress/email-log/pro-addons" target="_blank">' . __( 'Buy Addons', 'email-log' ) . '</a>' )
169
			);
170
		}
171
		return $links;
172
	}
173
174
	/**
175
	 * Registers the settings page.
176
	 *
177
	 * @since Genesis
178
	 */
179
	public function register_settings_page() {
180
		// Save the handle to your admin page - you'll need it to create a WP_Screen object
181
		$this->admin_page = add_submenu_page( 'tools.php', __( 'Email Log', 'email-log' ), __( 'Email Log', 'email-log' ), 'manage_options', self::PAGE_SLUG , array( $this, 'display_logs' ) );
0 ignored issues
show
The property admin_page does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
182
183
		add_action( "load-{$this->admin_page}", array( $this, 'create_settings_panel' ) );
1 ignored issue
show
Coding Style Best Practice introduced by
As per coding-style, please use concatenation or sprintf for the variable $this instead of interpolation.

It is generally a best practice as it is often more readable to use concatenation instead of interpolation for variables inside strings.

// Instead of
$x = "foo $bar $baz";

// Better use either
$x = "foo " . $bar . " " . $baz;
$x = sprintf("foo %s %s", $bar, $baz);
Loading history...
184
	}
185
186
	/**
187
	 * Displays the stored email log.
188
	 *
189
	 * @since Genesis
190
	 */
191
	public function display_logs() {
192
		add_thickbox();
193
194
		$this->logs_table->prepare_items( $this->get_per_page() );
0 ignored issues
show
The property logs_table does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
195
?>
196
	<div class="wrap">
197
		<h2><?php _e( 'Email Logs', 'email-log' );?></h2>
198
		<?php
199
		if ( isset( $this->logs_deleted ) && $this->logs_deleted != '' ) {
200
			$logs_deleted = intval( $this->logs_deleted );
0 ignored issues
show
The property logs_deleted does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
201
202
			if ( $logs_deleted > 0 ) {
203
				echo '<div class="updated"><p>' . sprintf( _n( '1 email log deleted.', '%s email logs deleted', $logs_deleted, 'email-log' ), $logs_deleted ) . '</p></div>';
204
			} else {
205
				echo '<div class="updated"><p>' . __( 'There was some problem in deleting the email logs' , 'email-log' ) . '</p></div>';
206
			}
207
			unset( $this->logs_deleted );
208
		}
209
?>
210
		<form id="email-logs-search" method="get">
211
			<input type="hidden" name="page" value="<?php echo self::PAGE_SLUG; ?>" >
212
<?php
213
		$this->logs_table->search_box( __( 'Search Logs', 'email-log' ), 'search_id' );
214
?>
215
		</form>
216
217
		<form id="email-logs-filter" method="get">
218
			<input type="hidden" name="page" value="<?php echo $_REQUEST['page'] ?>" />
219
<?php
220
		wp_nonce_field( self::DELETE_LOG_ACTION, self::DELETE_LOG_NONCE_FIELD );
221
		$this->logs_table->display();
222
?>
223
		</form>
224
	</div>
225
<?php
226
		/**
227
		 * Action to add additional content to email log admin footer.
228
		 *
229
		 * @since 1.8
230
		 */
231
		do_action( 'el_admin_footer' );
232
233
		// Display credits in Footer
234
		add_action( 'in_admin_footer', array( $this, 'add_footer_links' ) );
235
	}
236
237
	/**
238
	 * Adds settings panel for the plugin.
239
	 *
240
	 * @since Genesis
241
	 */
242
	public function create_settings_panel() {
243
244
		/**
245
		 * Create the WP_Screen object against your admin page handle
246
		 * This ensures we're working with the right admin page
247
		 */
248
		$this->admin_screen = WP_Screen::get( $this->admin_page );
249
250
		/**
251
		 * Content specified inline
252
		 */
253
		$this->admin_screen->add_help_tab(
254
			array(
255
				'title'    => __( 'About Plugin', 'email-log' ),
256
				'id'       => 'about_tab',
257
				'content'  => '<p>' . __( 'Email Log WordPress Plugin, allows you to log all emails that are sent through WordPress.', 'email-log' ) . '</p>',
258
				'callback' => false,
259
			)
260
		);
261
262
		// Add help sidebar
263
		$this->admin_screen->set_help_sidebar(
264
			'<p><strong>' . __( 'More information', 'email-log' ) . '</strong></p>' .
265
			'<p><a href = "http://sudarmuthu.com/wordpress/email-log">' . __( 'Plugin Homepage/support', 'email-log' ) . '</a></p>' .
266
			'<p><a href = "http://sudarmuthu.com/blog">' . __( "Plugin author's blog", 'email-log' ) . '</a></p>' .
267
			'<p><a href = "http://sudarmuthu.com/wordpress/">' . __( "Other Plugin's by Author", 'email-log' ) . '</a></p>'
268
		);
269
270
		// Add screen options
271
		$this->admin_screen->add_option(
272
			'per_page',
273
			array(
274
				'label' => __( 'Entries per page', 'email-log' ),
275
				'default' => 20,
276
				'option' => 'per_page',
277
			)
278
		);
279
280
		if ( ! class_exists( 'WP_List_Table' ) ) {
281
			require_once ABSPATH . WPINC . '/class-wp-list-table.php';
282
		}
283
284
		if ( ! class_exists( 'Email_Log_List_Table' ) ) {
285
			require_once $this->include_path . 'include/class-email-log-list-table.php';
286
		}
287
288
		//Prepare Table of elements
289
		$this->logs_table = new Email_Log_List_Table();
290
	}
291
292
	/**
293
	 * AJAX callback for displaying email content.
294
	 *
295
	 * @since 1.6
296
	 */
297
	public function display_content_callback() {
298
		global $wpdb;
299
300
		$table_name = $wpdb->prefix . self::TABLE_NAME;
301
		$email_id   = absint( $_GET['email_id'] );
302
303
		$query      = $wpdb->prepare( 'SELECT * FROM ' . $table_name . ' WHERE id = %d', $email_id );
304
		$content    = $wpdb->get_results( $query );
305
306
		echo wpautop( $content[0]->message );
307
308
		die(); // this is required to return a proper result
309
	}
310
311
	/**
312
	 * Saves Screen options.
313
	 *
314
	 * @since Genesis
315
	 *
316
	 * @param bool|int $status Screen option value. Default false to skip.
317
	 * @param string   $option The option name.
318
	 * @param int      $value  The number of rows to use.
319
	 * @return bool|int
320
	 */
321
	function save_screen_options( $status, $option, $value ) {
0 ignored issues
show
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
322
		if ( 'per_page' == $option ) {
323
			return $value;
324
		} else {
325
			return $status;
326
		}
327
	}
328
329
	/**
330
	 * Gets the per page option.
331
	 *
332
	 * @since Genesis
333
	 *
334
	 * @return int Number of logs a user wanted to be displayed in a page.
335
	 */
336
	public static function get_per_page() {
337
		$screen = get_current_screen();
338
		$option = $screen->get_option( 'per_page', 'option' );
339
340
		$per_page = get_user_meta( get_current_user_id(), $option, true );
341
342
		if ( empty( $per_page ) || $per_page < 1 ) {
343
			$per_page = $screen->get_option( 'per_page', 'default' );
344
		}
345
346
		return $per_page;
347
	}
348
349
	/**
350
	 * Adds additional links.
351
	 *
352
	 * @since Genesis
353
	 *
354
	 * @param array $links
355
	 * @return array
356
	 */
357
	public function add_action_links( $links ) {
358
		// Add a link to this plugin's settings page
359
		$settings_link = '<a href="tools.php?page=email-log">' . __( 'Log', 'email-log' ) . '</a>';
360
		array_unshift( $links, $settings_link );
361
		return $links;
362
	}
363
364
	/**
365
	 * Adds Footer links.
366
	 *
367
	 * @since Genesis
368
	 *
369
	 * @see Function relied on
370
	 * @link http://striderweb.com/nerdaphernalia/2008/06/give-your-wordpress-plugin-credit/
371
	 */
372
	public function add_footer_links() {
373
		$plugin_data = get_plugin_data( __FILE__ );
374
		printf( '%1$s ' . __( 'plugin', 'email-log' ) . ' | ' . __( 'Version', 'email-log' ) . ' %2$s | ' . __( 'by', 'email-log' ) . ' %3$s<br />', $plugin_data['Title'], $plugin_data['Version'], $plugin_data['Author'] );
375
	}
376
377
	/**
378
	 * Logs email to database.
379
	 *
380
	 * @since Genesis
381
	 *
382
	 * @global object $wpdb
383
	 *
384
	 * @param array $mail_info Information about email.
385
	 * @return array Information about email.
386
	 */
387
	public function log_email( $mail_info ) {
388
		global $wpdb;
389
390
		$attachment_present = ( count( $mail_info['attachments'] ) > 0 ) ? 'true' : 'false';
391
392
		// return filtered array
393
		$mail_info  = apply_filters( self::FILTER_NAME, $mail_info );
394
		$table_name = $wpdb->prefix . self::TABLE_NAME;
395
396
		if ( isset( $mail_info['message'] ) ) {
397
			$message = $mail_info['message'];
398
		} else {
399
			// wpmandrill plugin is changing "message" key to "html". See https://github.com/sudar/email-log/issues/20
400
			// Ideally this should be fixed in wpmandrill, but I am including this hack here till it is fixed by them.
401
			if ( isset( $mail_info['html'] ) ) {
402
				$message = $mail_info['html'];
403
			} else {
404
				$message = '';
405
			}
406
		}
407
408
		// Log into the database
409
		$wpdb->insert( $table_name, array(
410
				'to_email'    => is_array( $mail_info['to'] ) ? implode( ',', $mail_info['to'] ) : $mail_info['to'],
411
				'subject'     => $mail_info['subject'],
412
				'message'     => $message,
413
				'headers'     => is_array( $mail_info['headers'] ) ? implode( "\n", $mail_info['headers'] ) : $mail_info['headers'],
414
				'attachments' => $attachment_present,
415
				'sent_date'   => current_time( 'mysql' ),
416
			) );
417
418
		return $mail_info;
419
	}
420
}
421
422
/**
423
 * Instantiates the plugin class
424
 *
425
 * @since Genesis
426
 *
427
 * @see Class `EmailLog`
428
 * @global EmailLog $EmailLog
429
 */
430
function email_log() {
431
	global $EmailLog;
432
	$EmailLog = new EmailLog();
433
}
434
add_action( 'init', 'email_log' );
435
?>
436