Akismet Anti-Spam - Version 3.1.2

Version Description

Release Date - 7 June 2015

  • Reduced the amount of space Akismet uses in the commentmeta table.
  • Fixed a bug where some comments with quotes in the author name weren't getting history entries
  • Pre-emptive security improvements to ensure that the Akismet plugin can't be used by attackers to compromise a WordPress installation.
  • Better UI for the key entry field: allow whitespace to be included at the beginning or end of the key and strip it out automatically when the form is submitted.
  • When deactivating the plugin, notify the Akismet API so the site can be marked as inactive.
  • Clearer error messages.
Download this release

Release Info

Developer eoigal
Plugin Icon 128x128 Akismet Anti-Spam
Version 3.1.2
Comparing to
See all releases

Code changes from version 3.1.1 to 3.1.2

akismet.php CHANGED
@@ -6,7 +6,7 @@
6
  Plugin Name: Akismet
7
  Plugin URI: http://akismet.com/
8
  Description: Used by millions, Akismet is quite possibly the best way in the world to <strong>protect your blog from comment and trackback spam</strong>. It keeps your site protected from spam even while you sleep. To get started: 1) Click the "Activate" link to the left of this description, 2) <a href="http://akismet.com/get/">Sign up for an Akismet API key</a>, and 3) Go to your Akismet configuration page, and save your API key.
9
- Version: 3.1.1
10
  Author: Automattic
11
  Author URI: http://automattic.com/wordpress-plugins/
12
  License: GPLv2 or later
@@ -35,7 +35,7 @@ if ( !function_exists( 'add_action' ) ) {
35
  exit;
36
  }
37
 
38
- define( 'AKISMET_VERSION', '3.1.1' );
39
  define( 'AKISMET__MINIMUM_WP_VERSION', '3.2' );
40
  define( 'AKISMET__PLUGIN_URL', plugin_dir_url( __FILE__ ) );
41
  define( 'AKISMET__PLUGIN_DIR', plugin_dir_path( __FILE__ ) );
6
  Plugin Name: Akismet
7
  Plugin URI: http://akismet.com/
8
  Description: Used by millions, Akismet is quite possibly the best way in the world to <strong>protect your blog from comment and trackback spam</strong>. It keeps your site protected from spam even while you sleep. To get started: 1) Click the "Activate" link to the left of this description, 2) <a href="http://akismet.com/get/">Sign up for an Akismet API key</a>, and 3) Go to your Akismet configuration page, and save your API key.
9
+ Version: 3.1.2
10
  Author: Automattic
11
  Author URI: http://automattic.com/wordpress-plugins/
12
  License: GPLv2 or later
35
  exit;
36
  }
37
 
38
+ define( 'AKISMET_VERSION', '3.1.2' );
39
  define( 'AKISMET__MINIMUM_WP_VERSION', '3.2' );
40
  define( 'AKISMET__PLUGIN_URL', plugin_dir_url( __FILE__ ) );
41
  define( 'AKISMET__PLUGIN_DIR', plugin_dir_path( __FILE__ ) );
class.akismet-admin.php CHANGED
@@ -232,7 +232,7 @@ class Akismet_Admin {
232
  if ( defined( 'WPCOM_API_KEY' ) )
233
  return false; //shouldn't have option to save key if already defined
234
 
235
- $new_key = preg_replace( '/[^a-h0-9]/i', '', $_POST['key'] );
236
  $old_key = Akismet::get_api_key();
237
 
238
  if ( empty( $new_key ) ) {
@@ -290,15 +290,6 @@ class Akismet_Admin {
290
 
291
  // WP 2.5+
292
  public static function rightnow_stats() {
293
- global $submenu, $wp_db_version;
294
-
295
- if ( 8645 < $wp_db_version ) // 2.7
296
- $link = add_query_arg( array( 'comment_status' => 'spam' ), admin_url( 'edit-comments.php' ) );
297
- elseif ( isset( $submenu['edit-comments.php'] ) )
298
- $link = add_query_arg( array( 'page' => 'akismet-admin' ), admin_url( 'edit-comments.php' ) );
299
- else
300
- $link = add_query_arg( array( 'page' => 'akismet-admin' ), admin_url( 'edit.php' ) );
301
-
302
  if ( $count = get_option('akismet_spam_count') ) {
303
  $intro = sprintf( _n(
304
  '<a href="%1$s">Akismet</a> has protected your site from %2$s spam comment already. ',
@@ -309,15 +300,16 @@ class Akismet_Admin {
309
  $intro = sprintf( __('<a href="%s">Akismet</a> blocks spam from getting to your blog. ', 'akismet'), 'https://akismet.com/wordpress/' );
310
  }
311
 
312
- $link = function_exists( 'esc_url' ) ? esc_url( $link ) : clean_url( $link );
 
313
  if ( $queue_count = self::get_spam_count() ) {
314
  $queue_text = sprintf( _n(
315
  'There&#8217;s <a href="%2$s">%1$s comment</a> in your spam queue right now.',
316
  'There are <a href="%2$s">%1$s comments</a> in your spam queue right now.',
317
  $queue_count
318
- , 'akismet'), number_format_i18n( $queue_count ), $link );
319
  } else {
320
- $queue_text = sprintf( __( "There&#8217;s nothing in your <a href='%s'>spam queue</a> at the moment." , 'akismet'), $link );
321
  }
322
 
323
  $text = $intro . '<br />' . $queue_text;
@@ -379,17 +371,22 @@ class Akismet_Admin {
379
  update_comment_meta( $c['comment_ID'], 'akismet_result', 'true' );
380
  delete_comment_meta( $c['comment_ID'], 'akismet_error' );
381
  delete_comment_meta( $c['comment_ID'], 'akismet_delayed_moderation_email' );
382
- Akismet::update_comment_history( $c['comment_ID'], __('Akismet re-checked and caught this comment as spam', 'akismet'), 'check-spam' );
383
 
384
  } elseif ( 'false' == $response[1] ) {
385
  update_comment_meta( $c['comment_ID'], 'akismet_result', 'false' );
386
  delete_comment_meta( $c['comment_ID'], 'akismet_error' );
387
  delete_comment_meta( $c['comment_ID'], 'akismet_delayed_moderation_email' );
388
- Akismet::update_comment_history( $c['comment_ID'], __('Akismet re-checked and cleared this comment', 'akismet'), 'check-ham' );
389
  // abnormal result: error
390
  } else {
391
  update_comment_meta( $c['comment_ID'], 'akismet_result', 'error' );
392
- Akismet::update_comment_history( $c['comment_ID'], sprintf( __('Akismet was unable to re-check this comment (response: %s)', 'akismet'), substr($response[1], 0, 50)), 'check-error' );
 
 
 
 
 
393
  }
394
 
395
  delete_comment_meta( $c['comment_ID'], 'akismet_rechecking' );
@@ -494,11 +491,95 @@ class Akismet_Admin {
494
 
495
  if ( $history ) {
496
  echo '<div class="akismet-history" style="margin: 13px;">';
 
497
  foreach ( $history as $row ) {
498
  $time = date( 'D d M Y @ h:i:m a', $row['time'] ) . ' GMT';
499
- echo '<div style="margin-bottom: 13px;"><span style="color: #999;" alt="' . $time . '" title="' . $time . '">' . sprintf( esc_html__('%s ago', 'akismet'), human_time_diff( $row['time'] ) ) . '</span> - ';
500
- echo esc_html( $row['message'] ) . '</div>';
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
501
  }
 
502
  echo '</div>';
503
  }
504
  }
@@ -631,7 +712,7 @@ class Akismet_Admin {
631
  }
632
 
633
  public static function get_akismet_user( $api_key ) {
634
- $akismet_user = Akismet::http_post( Akismet::build_query( array( 'key' => $api_key ) ), 'get-subscription' );
635
 
636
  if ( ! empty( $akismet_user[1] ) )
637
  $akismet_user = json_decode( $akismet_user[1] );
@@ -645,12 +726,13 @@ class Akismet_Admin {
645
  $stat_totals = array();
646
 
647
  foreach( array( '6-months', 'all' ) as $interval ) {
648
- $response = Akismet::http_post( Akismet::build_query( array( 'blog' => urlencode( get_bloginfo('url') ), 'key' => $api_key, 'from' => $interval ) ), 'get-stats' );
649
 
650
  if ( ! empty( $response[1] ) ) {
651
  $stat_totals[$interval] = json_decode( $response[1] );
652
  }
653
  }
 
654
  return $stat_totals;
655
  }
656
 
232
  if ( defined( 'WPCOM_API_KEY' ) )
233
  return false; //shouldn't have option to save key if already defined
234
 
235
+ $new_key = preg_replace( '/[^a-f0-9]/i', '', $_POST['key'] );
236
  $old_key = Akismet::get_api_key();
237
 
238
  if ( empty( $new_key ) ) {
290
 
291
  // WP 2.5+
292
  public static function rightnow_stats() {
 
 
 
 
 
 
 
 
 
293
  if ( $count = get_option('akismet_spam_count') ) {
294
  $intro = sprintf( _n(
295
  '<a href="%1$s">Akismet</a> has protected your site from %2$s spam comment already. ',
300
  $intro = sprintf( __('<a href="%s">Akismet</a> blocks spam from getting to your blog. ', 'akismet'), 'https://akismet.com/wordpress/' );
301
  }
302
 
303
+ $link = add_query_arg( array( 'comment_status' => 'spam' ), admin_url( 'edit-comments.php' ) );
304
+
305
  if ( $queue_count = self::get_spam_count() ) {
306
  $queue_text = sprintf( _n(
307
  'There&#8217;s <a href="%2$s">%1$s comment</a> in your spam queue right now.',
308
  'There are <a href="%2$s">%1$s comments</a> in your spam queue right now.',
309
  $queue_count
310
+ , 'akismet'), number_format_i18n( $queue_count ), esc_url( $link ) );
311
  } else {
312
+ $queue_text = sprintf( __( "There&#8217;s nothing in your <a href='%s'>spam queue</a> at the moment." , 'akismet'), esc_url( $link ) );
313
  }
314
 
315
  $text = $intro . '<br />' . $queue_text;
371
  update_comment_meta( $c['comment_ID'], 'akismet_result', 'true' );
372
  delete_comment_meta( $c['comment_ID'], 'akismet_error' );
373
  delete_comment_meta( $c['comment_ID'], 'akismet_delayed_moderation_email' );
374
+ Akismet::update_comment_history( $c['comment_ID'], '', 'recheck-spam' );
375
 
376
  } elseif ( 'false' == $response[1] ) {
377
  update_comment_meta( $c['comment_ID'], 'akismet_result', 'false' );
378
  delete_comment_meta( $c['comment_ID'], 'akismet_error' );
379
  delete_comment_meta( $c['comment_ID'], 'akismet_delayed_moderation_email' );
380
+ Akismet::update_comment_history( $c['comment_ID'], '', 'recheck-ham' );
381
  // abnormal result: error
382
  } else {
383
  update_comment_meta( $c['comment_ID'], 'akismet_result', 'error' );
384
+ Akismet::update_comment_history(
385
+ $c['comment_ID'],
386
+ '',
387
+ 'recheck-error',
388
+ array( 'response' => substr( $response[1], 0, 50 ) )
389
+ );
390
  }
391
 
392
  delete_comment_meta( $c['comment_ID'], 'akismet_rechecking' );
491
 
492
  if ( $history ) {
493
  echo '<div class="akismet-history" style="margin: 13px;">';
494
+
495
  foreach ( $history as $row ) {
496
  $time = date( 'D d M Y @ h:i:m a', $row['time'] ) . ' GMT';
497
+
498
+ $message = '';
499
+
500
+ if ( ! empty( $row['message'] ) ) {
501
+ // Old versions of Akismet stored the message as a literal string in the commentmeta.
502
+ // New versions don't do that for two reasons:
503
+ // 1) Save space.
504
+ // 2) The message can be translated into the current language of the blog, not stuck
505
+ // in the language of the blog when the comment was made.
506
+ $message = $row['message'];
507
+ }
508
+
509
+ // If possible, use a current translation.
510
+ switch ( $row['event'] ) {
511
+ case 'recheck-spam';
512
+ $message = __( 'Akismet re-checked and caught this comment as spam.', 'akismet' );
513
+ break;
514
+ case 'check-spam':
515
+ $message = __( 'Akismet caught this comment as spam.', 'akismet' );
516
+ break;
517
+ case 'recheck-ham':
518
+ $message = __( 'Akismet re-checked and cleared this comment.', 'akismet' );
519
+ break;
520
+ case 'check-ham':
521
+ $message = __( 'Akismet cleared this comment.', 'akismet' );
522
+ break;
523
+ case 'wp-blacklisted':
524
+ $message = __( 'Comment was caught by wp_blacklist_check.', 'akismet' );
525
+ break;
526
+ case 'report-spam':
527
+ if ( isset( $row['user'] ) ) {
528
+ $message = sprintf( __( '%s reported this comment as spam.', 'akismet' ), $row['user'] );
529
+ }
530
+ else if ( ! $message ) {
531
+ $message = __( 'This comment was reported as spam.', 'akismet' );
532
+ }
533
+ break;
534
+ case 'report-ham':
535
+ if ( isset( $row['user'] ) ) {
536
+ $message = sprintf( __( '%s reported this comment as not spam.', 'akismet' ), $row['user'] );
537
+ }
538
+ else if ( ! $message ) {
539
+ $message = __( 'This comment was reported as not spam.', 'akismet' );
540
+ }
541
+ break;
542
+ case 'cron-retry-spam':
543
+ $message = __( 'Akismet caught this comment as spam during an automatic retry.' , 'akismet');
544
+ break;
545
+ case 'cron-retry-ham':
546
+ $message = __( 'Akismet cleared this comment during an automatic retry.', 'akismet');
547
+ break;
548
+ case 'check-error':
549
+ if ( isset( $row['meta'], $row['meta']['response'] ) ) {
550
+ $message = sprintf( __( 'Akismet was unable to check this comment (response: %s) but will automatically retry later.', 'akismet'), $row['meta']['response'] );
551
+ }
552
+ break;
553
+ case 'recheck-error':
554
+ if ( isset( $row['meta'], $row['meta']['response'] ) ) {
555
+ $message = sprintf( __( 'Akismet was unable to recheck this comment (response: %s).', 'akismet'), $row['meta']['response'] );
556
+ }
557
+ break;
558
+ default:
559
+ if ( preg_match( '/^status-changed/', $row['event'] ) ) {
560
+ // Half of these used to be saved without the dash after 'status-changed'.
561
+ // See https://plugins.trac.wordpress.org/changeset/1150658/akismet/trunk
562
+ $new_status = preg_replace( '/^status-changed-?/', '', $row['event'] );
563
+ $message = sprintf( __( 'Comment status was changed to %s', 'akismet' ), $new_status );
564
+ }
565
+ else if ( preg_match( '/^status-/', $row['event'] ) ) {
566
+ $new_status = preg_replace( '/^status-/', '', $row['event'] );
567
+
568
+ if ( isset( $row['user'] ) ) {
569
+ $message = sprintf( __( '%1$s changed the comment status to %2$s.', 'akismet' ), $row['user'], $new_status );
570
+ }
571
+ }
572
+ break;
573
+
574
+ }
575
+
576
+ echo '<div style="margin-bottom: 13px;">';
577
+ echo '<span style="color: #999;" alt="' . $time . '" title="' . $time . '">' . sprintf( esc_html__('%s ago', 'akismet'), human_time_diff( $row['time'] ) ) . '</span>';
578
+ echo ' - ';
579
+ echo esc_html( $message );
580
+ echo '</div>';
581
  }
582
+
583
  echo '</div>';
584
  }
585
  }
712
  }
713
 
714
  public static function get_akismet_user( $api_key ) {
715
+ $akismet_user = Akismet::http_post( Akismet::build_query( array( 'key' => $api_key, 'blog' => get_bloginfo( 'url' ) ) ), 'get-subscription' );
716
 
717
  if ( ! empty( $akismet_user[1] ) )
718
  $akismet_user = json_decode( $akismet_user[1] );
726
  $stat_totals = array();
727
 
728
  foreach( array( '6-months', 'all' ) as $interval ) {
729
+ $response = Akismet::http_post( Akismet::build_query( array( 'blog' => get_bloginfo( 'url' ), 'key' => $api_key, 'from' => $interval ) ), 'get-stats' );
730
 
731
  if ( ! empty( $response[1] ) ) {
732
  $stat_totals[$interval] = json_decode( $response[1] );
733
  }
734
  }
735
+
736
  return $stat_totals;
737
  }
738
 
class.akismet.php CHANGED
@@ -9,7 +9,8 @@ class Akismet {
9
  private static $initiated = false;
10
  private static $prevent_moderation_email_for_these_comments = array();
11
  private static $last_comment_result = null;
12
-
 
13
  public static function init() {
14
  if ( ! self::$initiated ) {
15
  self::init_hooks();
@@ -66,7 +67,14 @@ class Akismet {
66
  if ( $response[1] != 'valid' && $response[1] != 'invalid' )
67
  return 'failed';
68
 
69
- self::update_alert( $response );
 
 
 
 
 
 
 
70
 
71
  return $response[1];
72
  }
@@ -124,9 +132,7 @@ class Akismet {
124
 
125
  do_action( 'akismet_comment_check_response', $response );
126
 
127
- self::update_alert( $response );
128
-
129
- $commentdata['comment_as_submitted'] = array_intersect_key( $comment, array( 'blog' => '', 'blog_charset' => '', 'blog_lang' => '', 'blog_ua' => '', 'comment_agent' => '', 'comment_author' => '', 'comment_author_IP' => '', 'comment_author_email' => '', 'comment_author_url' => '', 'comment_content' => '', 'comment_date_gmt' => '', 'comment_tags' => '', 'comment_type' => '', 'guid' => '', 'is_test' => '', 'permalink' => '', 'reporter' => '', 'site_domain' => '', 'submit_referer' => '', 'submit_uri' => '', 'user_ID' => '', 'user_agent' => '', 'user_id' => '', 'user_ip' => '' ) );
130
  $commentdata['akismet_result'] = $response[1];
131
 
132
  if ( isset( $response[0]['x-akismet-pro-tip'] ) )
@@ -228,23 +234,32 @@ class Akismet {
228
  // normal result: true or false
229
  if ( self::$last_comment['akismet_result'] == 'true' ) {
230
  update_comment_meta( $comment->comment_ID, 'akismet_result', 'true' );
231
- self::update_comment_history( $comment->comment_ID, __('Akismet caught this comment as spam', 'akismet'), 'check-spam' );
232
  if ( $comment->comment_approved != 'spam' )
233
- self::update_comment_history( $comment->comment_ID, sprintf( __('Comment status was changed to %s', 'akismet'), $comment->comment_approved), 'status-changed'.$comment->comment_approved );
 
 
 
 
234
  }
235
  elseif ( self::$last_comment['akismet_result'] == 'false' ) {
236
  update_comment_meta( $comment->comment_ID, 'akismet_result', 'false' );
237
- self::update_comment_history( $comment->comment_ID, __('Akismet cleared this comment', 'akismet'), 'check-ham' );
238
  if ( $comment->comment_approved == 'spam' ) {
239
  if ( wp_blacklist_check($comment->comment_author, $comment->comment_author_email, $comment->comment_author_url, $comment->comment_content, $comment->comment_author_IP, $comment->comment_agent) )
240
- self::update_comment_history( $comment->comment_ID, __('Comment was caught by wp_blacklist_check', 'akismet'), 'wp-blacklisted' );
241
  else
242
- self::update_comment_history( $comment->comment_ID, sprintf( __('Comment status was changed to %s', 'akismet'), $comment->comment_approved), 'status-changed-'.$comment->comment_approved );
243
  }
244
  } // abnormal result: error
245
  else {
246
  update_comment_meta( $comment->comment_ID, 'akismet_error', time() );
247
- self::update_comment_history( $comment->comment_ID, sprintf( __('Akismet was unable to check this comment (response: %s), will automatically retry again later.', 'akismet'), substr(self::$last_comment['akismet_result'], 0, 50)), 'check-error' );
 
 
 
 
 
248
  }
249
 
250
  // record the complete original data as submitted for checking
@@ -350,8 +365,15 @@ class Akismet {
350
  return $history;
351
  }
352
 
353
- // log an event for a given comment, storing it in comment_meta
354
- public static function update_comment_history( $comment_id, $message, $event=null ) {
 
 
 
 
 
 
 
355
  global $current_user;
356
 
357
  // failsafe for old WP versions
@@ -359,15 +381,19 @@ class Akismet {
359
  return false;
360
 
361
  $user = '';
362
- if ( is_object( $current_user ) && isset( $current_user->user_login ) )
363
- $user = $current_user->user_login;
364
 
365
  $event = array(
366
  'time' => self::_get_microtime(),
367
- 'message' => $message,
368
  'event' => $event,
369
- 'user' => $user,
370
  );
 
 
 
 
 
 
 
 
371
 
372
  // $unique = false so as to allow multiple values per comment
373
  $r = add_comment_meta( $comment_id, 'akismet_history', $event, false );
@@ -443,7 +469,7 @@ class Akismet {
443
  }
444
  }
445
 
446
- self::update_comment_history( $comment->comment_ID, sprintf( __('%1$s changed the comment status to %2$s', 'akismet'), $reporter, $new_status ), 'status-' . $new_status );
447
  }
448
 
449
  public static function submit_spam_comment( $comment_id ) {
@@ -460,7 +486,7 @@ class Akismet {
460
  return;
461
 
462
  // use the original version stored in comment_meta if available
463
- $as_submitted = get_comment_meta( $comment_id, 'akismet_as_submitted', true);
464
 
465
  if ( $as_submitted && is_array( $as_submitted ) && isset( $as_submitted['comment_content'] ) )
466
  $comment = (object) array_merge( (array)$comment, $as_submitted );
@@ -488,7 +514,7 @@ class Akismet {
488
 
489
  $response = Akismet::http_post( Akismet::build_query( $comment ), 'submit-spam' );
490
  if ( $comment->reporter ) {
491
- self::update_comment_history( $comment_id, sprintf( __('%s reported this comment as spam', 'akismet'), $comment->reporter ), 'report-spam' );
492
  update_comment_meta( $comment_id, 'akismet_user_result', 'true' );
493
  update_comment_meta( $comment_id, 'akismet_user', $comment->reporter );
494
  }
@@ -506,7 +532,7 @@ class Akismet {
506
  return;
507
 
508
  // use the original version stored in comment_meta if available
509
- $as_submitted = get_comment_meta( $comment_id, 'akismet_as_submitted', true);
510
 
511
  if ( $as_submitted && is_array($as_submitted) && isset($as_submitted['comment_content']) )
512
  $comment = (object) array_merge( (array)$comment, $as_submitted );
@@ -534,7 +560,7 @@ class Akismet {
534
 
535
  $response = self::http_post( Akismet::build_query( $comment ), 'submit-ham' );
536
  if ( $comment->reporter ) {
537
- self::update_comment_history( $comment_id, sprintf( __('%s reported this comment as not spam', 'akismet'), $comment->reporter ), 'report-ham' );
538
  update_comment_meta( $comment_id, 'akismet_user_result', 'false' );
539
  update_comment_meta( $comment_id, 'akismet_user', $comment->reporter );
540
  }
@@ -573,19 +599,19 @@ class Akismet {
573
  add_comment_meta( $comment_id, 'akismet_rechecking', true );
574
  $status = self::check_db_comment( $comment_id, 'retry' );
575
 
576
- $msg = '';
577
  if ( $status == 'true' ) {
578
- $msg = __( 'Akismet caught this comment as spam during an automatic retry.' , 'akismet');
579
  } elseif ( $status == 'false' ) {
580
- $msg = __( 'Akismet cleared this comment during an automatic retry.' , 'akismet');
581
  }
582
 
583
  // If we got back a legit response then update the comment history
584
  // other wise just bail now and try again later. No point in
585
  // re-trying all the comments once we hit one failure.
586
- if ( !empty( $msg ) ) {
587
  delete_comment_meta( $comment_id, 'akismet_error' );
588
- self::update_comment_history( $comment_id, $msg, 'cron-retry' );
589
  update_comment_meta( $comment_id, 'akismet_result', $status );
590
  // make sure the comment status is still pending. if it isn't, that means the user has already moved it elsewhere.
591
  $comment = get_comment( $comment_id );
@@ -681,8 +707,16 @@ class Akismet {
681
  return (
682
  isset( $comment1['comment_post_ID'], $comment2['comment_post_ID'] )
683
  && intval( $comment1['comment_post_ID'] ) == intval( $comment2['comment_post_ID'] )
684
- && $comment1['comment_author'] == $comment2['comment_author']
685
- && $comment1['comment_author_email'] == $comment2['comment_author_email']
 
 
 
 
 
 
 
 
686
  );
687
  }
688
 
@@ -882,8 +916,12 @@ class Akismet {
882
 
883
  do_action( 'akismet_https_disabled' );
884
  }
 
 
 
 
885
 
886
- return array( $response['headers'], $response['body'] );
887
  }
888
 
889
  // given a response from an API call like check_key_status(), update the alert code options if an alert is present.
@@ -999,7 +1037,7 @@ p {
999
  * @static
1000
  */
1001
  public static function plugin_deactivation( ) {
1002
- //tidy up
1003
  }
1004
 
1005
  /**
@@ -1085,4 +1123,26 @@ p {
1085
 
1086
  return $r;
1087
  }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1088
  }
9
  private static $initiated = false;
10
  private static $prevent_moderation_email_for_these_comments = array();
11
  private static $last_comment_result = null;
12
+ private static $comment_as_submitted_allowed_keys = array( 'blog' => '', 'blog_charset' => '', 'blog_lang' => '', 'blog_ua' => '', 'comment_agent' => '', 'comment_author' => '', 'comment_author_IP' => '', 'comment_author_email' => '', 'comment_author_url' => '', 'comment_content' => '', 'comment_date_gmt' => '', 'comment_tags' => '', 'comment_type' => '', 'guid' => '', 'is_test' => '', 'permalink' => '', 'reporter' => '', 'site_domain' => '', 'submit_referer' => '', 'submit_uri' => '', 'user_ID' => '', 'user_agent' => '', 'user_id' => '', 'user_ip' => '' );
13
+
14
  public static function init() {
15
  if ( ! self::$initiated ) {
16
  self::init_hooks();
67
  if ( $response[1] != 'valid' && $response[1] != 'invalid' )
68
  return 'failed';
69
 
70
+ return $response[1];
71
+ }
72
+
73
+ public static function deactivate_key( $key ) {
74
+ $response = self::http_post( Akismet::build_query( array( 'key' => $key, 'blog' => get_option('home') ) ), 'deactivate' );
75
+
76
+ if ( $response[1] != 'deactivated' )
77
+ return 'failed';
78
 
79
  return $response[1];
80
  }
132
 
133
  do_action( 'akismet_comment_check_response', $response );
134
 
135
+ $commentdata['comment_as_submitted'] = array_intersect_key( $comment, self::$comment_as_submitted_allowed_keys );
 
 
136
  $commentdata['akismet_result'] = $response[1];
137
 
138
  if ( isset( $response[0]['x-akismet-pro-tip'] ) )
234
  // normal result: true or false
235
  if ( self::$last_comment['akismet_result'] == 'true' ) {
236
  update_comment_meta( $comment->comment_ID, 'akismet_result', 'true' );
237
+ self::update_comment_history( $comment->comment_ID, '', 'check-spam' );
238
  if ( $comment->comment_approved != 'spam' )
239
+ self::update_comment_history(
240
+ $comment->comment_ID,
241
+ '',
242
+ 'status-changed-'.$comment->comment_approved
243
+ );
244
  }
245
  elseif ( self::$last_comment['akismet_result'] == 'false' ) {
246
  update_comment_meta( $comment->comment_ID, 'akismet_result', 'false' );
247
+ self::update_comment_history( $comment->comment_ID, '', 'check-ham' );
248
  if ( $comment->comment_approved == 'spam' ) {
249
  if ( wp_blacklist_check($comment->comment_author, $comment->comment_author_email, $comment->comment_author_url, $comment->comment_content, $comment->comment_author_IP, $comment->comment_agent) )
250
+ self::update_comment_history( $comment->comment_ID, '', 'wp-blacklisted' );
251
  else
252
+ self::update_comment_history( $comment->comment_ID, '', 'status-changed-'.$comment->comment_approved );
253
  }
254
  } // abnormal result: error
255
  else {
256
  update_comment_meta( $comment->comment_ID, 'akismet_error', time() );
257
+ self::update_comment_history(
258
+ $comment->comment_ID,
259
+ '',
260
+ 'check-error',
261
+ array( 'response' => substr( self::$last_comment['akismet_result'], 0, 50 ) )
262
+ );
263
  }
264
 
265
  // record the complete original data as submitted for checking
365
  return $history;
366
  }
367
 
368
+ /**
369
+ * Log an event for a given comment, storing it in comment_meta.
370
+ *
371
+ * @param int $comment_id The ID of the relevant comment.
372
+ * @param string $message The string description of the event. No longer used.
373
+ * @param string $event The event code.
374
+ * @param array $meta Metadata about the history entry. e.g., the user that reported or changed the status of a given comment.
375
+ */
376
+ public static function update_comment_history( $comment_id, $message, $event=null, $meta=null ) {
377
  global $current_user;
378
 
379
  // failsafe for old WP versions
381
  return false;
382
 
383
  $user = '';
 
 
384
 
385
  $event = array(
386
  'time' => self::_get_microtime(),
 
387
  'event' => $event,
 
388
  );
389
+
390
+ if ( is_object( $current_user ) && isset( $current_user->user_login ) ) {
391
+ $event['user'] = $current_user->user_login;
392
+ }
393
+
394
+ if ( ! empty( $meta ) ) {
395
+ $event['meta'] = $meta;
396
+ }
397
 
398
  // $unique = false so as to allow multiple values per comment
399
  $r = add_comment_meta( $comment_id, 'akismet_history', $event, false );
469
  }
470
  }
471
 
472
+ self::update_comment_history( $comment->comment_ID, '', 'status-' . $new_status );
473
  }
474
 
475
  public static function submit_spam_comment( $comment_id ) {
486
  return;
487
 
488
  // use the original version stored in comment_meta if available
489
+ $as_submitted = self::sanitize_comment_as_submitted( get_comment_meta( $comment_id, 'akismet_as_submitted', true ) );
490
 
491
  if ( $as_submitted && is_array( $as_submitted ) && isset( $as_submitted['comment_content'] ) )
492
  $comment = (object) array_merge( (array)$comment, $as_submitted );
514
 
515
  $response = Akismet::http_post( Akismet::build_query( $comment ), 'submit-spam' );
516
  if ( $comment->reporter ) {
517
+ self::update_comment_history( $comment_id, '', 'report-spam' );
518
  update_comment_meta( $comment_id, 'akismet_user_result', 'true' );
519
  update_comment_meta( $comment_id, 'akismet_user', $comment->reporter );
520
  }
532
  return;
533
 
534
  // use the original version stored in comment_meta if available
535
+ $as_submitted = self::sanitize_comment_as_submitted( get_comment_meta( $comment_id, 'akismet_as_submitted', true ) );
536
 
537
  if ( $as_submitted && is_array($as_submitted) && isset($as_submitted['comment_content']) )
538
  $comment = (object) array_merge( (array)$comment, $as_submitted );
560
 
561
  $response = self::http_post( Akismet::build_query( $comment ), 'submit-ham' );
562
  if ( $comment->reporter ) {
563
+ self::update_comment_history( $comment_id, '', 'report-ham' );
564
  update_comment_meta( $comment_id, 'akismet_user_result', 'false' );
565
  update_comment_meta( $comment_id, 'akismet_user', $comment->reporter );
566
  }
599
  add_comment_meta( $comment_id, 'akismet_rechecking', true );
600
  $status = self::check_db_comment( $comment_id, 'retry' );
601
 
602
+ $event = '';
603
  if ( $status == 'true' ) {
604
+ $event = 'cron-retry-spam';
605
  } elseif ( $status == 'false' ) {
606
+ $event = 'cron-retry-ham';
607
  }
608
 
609
  // If we got back a legit response then update the comment history
610
  // other wise just bail now and try again later. No point in
611
  // re-trying all the comments once we hit one failure.
612
+ if ( !empty( $event ) ) {
613
  delete_comment_meta( $comment_id, 'akismet_error' );
614
+ self::update_comment_history( $comment_id, '', $event );
615
  update_comment_meta( $comment_id, 'akismet_result', $status );
616
  // make sure the comment status is still pending. if it isn't, that means the user has already moved it elsewhere.
617
  $comment = get_comment( $comment_id );
707
  return (
708
  isset( $comment1['comment_post_ID'], $comment2['comment_post_ID'] )
709
  && intval( $comment1['comment_post_ID'] ) == intval( $comment2['comment_post_ID'] )
710
+ && (
711
+ $comment1['comment_author'] == $comment2['comment_author']
712
+ || stripslashes( $comment1['comment_author'] ) == $comment2['comment_author']
713
+ || $comment1['comment_author'] == stripslashes( $comment2['comment_author'] )
714
+ )
715
+ && (
716
+ $comment1['comment_author_email'] == $comment2['comment_author_email']
717
+ || stripslashes( $comment1['comment_author_email'] ) == $comment2['comment_author_email']
718
+ || $comment1['comment_author_email'] == stripslashes( $comment2['comment_author_email'] )
719
+ )
720
  );
721
  }
722
 
916
 
917
  do_action( 'akismet_https_disabled' );
918
  }
919
+
920
+ $simplified_response = array( $response['headers'], $response['body'] );
921
+
922
+ self::update_alert( $simplified_response );
923
 
924
+ return $simplified_response;
925
  }
926
 
927
  // given a response from an API call like check_key_status(), update the alert code options if an alert is present.
1037
  * @static
1038
  */
1039
  public static function plugin_deactivation( ) {
1040
+ return self::deactivate_key( self::get_api_key() );
1041
  }
1042
 
1043
  /**
1123
 
1124
  return $r;
1125
  }
1126
+
1127
+ /**
1128
+ * Ensure that we are loading expected scalar values from akismet_as_submitted commentmeta.
1129
+ *
1130
+ * @param mixed $meta_value
1131
+ * @return mixed
1132
+ */
1133
+ private static function sanitize_comment_as_submitted( $meta_value ) {
1134
+ if ( empty( $meta_value ) ) {
1135
+ return $meta_value;
1136
+ }
1137
+
1138
+ $meta_value = (array) $meta_value;
1139
+
1140
+ foreach ( $meta_value as $key => $value ) {
1141
+ if ( ! isset( self::$comment_as_submitted_allowed_keys[$key] ) || ! is_scalar( $value ) ) {
1142
+ unset( $meta_value[$key] );
1143
+ }
1144
+ }
1145
+
1146
+ return $meta_value;
1147
+ }
1148
  }
readme.txt CHANGED
@@ -1,9 +1,9 @@
1
  === Akismet ===
2
  Contributors: matt, ryan, andy, mdawaffe, tellyworth, josephscott, lessbloat, eoigal, cfinke, automattic, jgs
3
- Tags: akismet, comments, spam
4
  Requires at least: 3.2
5
- Tested up to: 4.2.1
6
- Stable tag: 3.1.1
7
  License: GPLv2 or later
8
 
9
  Akismet checks your comments against the Akismet Web service to see if they look like spam or not.
@@ -30,6 +30,16 @@ Upload the Akismet plugin to your blog, Activate it, then enter your [Akismet.co
30
 
31
  == Changelog ==
32
 
 
 
 
 
 
 
 
 
 
 
33
  = 3.1.1 =
34
  *Release Date - 17th March, 2015*
35
 
1
  === Akismet ===
2
  Contributors: matt, ryan, andy, mdawaffe, tellyworth, josephscott, lessbloat, eoigal, cfinke, automattic, jgs
3
+ Tags: akismet, comments, spam, antispam, anti-spam, anti spam, comment moderation, comment spam, contact form spam, spam comments
4
  Requires at least: 3.2
5
+ Tested up to: 4.2.2
6
+ Stable tag: 3.1.2
7
  License: GPLv2 or later
8
 
9
  Akismet checks your comments against the Akismet Web service to see if they look like spam or not.
30
 
31
  == Changelog ==
32
 
33
+ = 3.1.2 =
34
+ *Release Date - 7 June 2015*
35
+
36
+ * Reduced the amount of space Akismet uses in the commentmeta table.
37
+ * Fixed a bug where some comments with quotes in the author name weren't getting history entries
38
+ * Pre-emptive security improvements to ensure that the Akismet plugin can't be used by attackers to compromise a WordPress installation.
39
+ * Better UI for the key entry field: allow whitespace to be included at the beginning or end of the key and strip it out automatically when the form is submitted.
40
+ * When deactivating the plugin, notify the Akismet API so the site can be marked as inactive.
41
+ * Clearer error messages.
42
+
43
  = 3.1.1 =
44
  *Release Date - 17th March, 2015*
45
 
views/config.php CHANGED
@@ -67,7 +67,7 @@
67
  <th class="akismet-api-key" width="10%" align="left" scope="row"><?php esc_html_e('API Key', 'akismet');?></th>
68
  <td width="5%"/>
69
  <td align="left">
70
- <span class="api-key"><input id="key" name="key" type="text" size="15" maxlength="12" value="<?php echo esc_attr( get_option('wordpress_api_key') ); ?>" class="regular-text code <?php echo $akismet_user->status;?>"></span>
71
  </td>
72
  </tr>
73
  <?php endif; ?>
67
  <th class="akismet-api-key" width="10%" align="left" scope="row"><?php esc_html_e('API Key', 'akismet');?></th>
68
  <td width="5%"/>
69
  <td align="left">
70
+ <span class="api-key"><input id="key" name="key" type="text" size="15" value="<?php echo esc_attr( get_option('wordpress_api_key') ); ?>" class="regular-text code <?php echo $akismet_user->status;?>"></span>
71
  </td>
72
  </tr>
73
  <?php endif; ?>
views/notice.php CHANGED
@@ -75,7 +75,11 @@
75
  <?php elseif ( $type == 'no-sub' ) :?>
76
  <div class="wrap alert critical">
77
  <h3 class="key-status failed"><?php esc_html_e( 'Your subscription is missing.', 'akismet'); ?></h3>
78
- <p class="description"><?php printf( __('Since 2012, Akismet began using subscriptions for all accounts (even free ones). It looks like a subscription has not been assigned to your account, and we’d appreciate it if you’d <a href="%s" target="_blank">sign into your account</a> and choose one. Please <a href="%s" target="_blank">contact our support team</a> with any questions.', 'akismet'), 'https://akismet.com/account/upgrade/', 'https://akismet.com/contact/' ); ?></p>
 
 
 
 
79
  </div>
80
  <?php elseif ( $type == 'new-key-valid' ) :?>
81
  <div class="wrap alert active">
@@ -87,16 +91,25 @@
87
  </div>
88
  <?php elseif ( $type == 'new-key-failed' ) :?>
89
  <div class="wrap alert critical">
90
- <h3 class="key-status"><?php esc_html_e( 'The key you entered could not be verified because a connection to akismet.com could not be established. Please check your server configuration.' , 'akismet'); ?></h3>
 
91
  </div>
92
  <?php elseif ( $type == 'limit-reached' && in_array( $level, array( 'yellow', 'red' ) ) ) :?>
93
  <div class="wrap alert critical">
94
  <?php if ( $level == 'yellow' ): ?>
95
- <h3 class="key-status failed"><?php esc_html_e("You're using your Akismet key on more sites than your Pro subscription allows.", 'akismet'); ?></h3>
96
- <p class="description"><?php printf( __('Your Pro subscription allows the use of Akismet on only one site. Please <a href="http://docs.akismet.com/billing/add-more-sites/">purchase additional Pro subscriptions</a> or upgrade to an Enterprise subscription that allows the use of Akismet on unlimited sites.<br /><br />If you have any questions, please get in touch with our support team.', 'akismet'), 'https://akismet.com/account/upgrade/', 'https://akismet.com/contact/'); ?></p>
 
 
 
 
97
  <?php elseif ( $level == 'red' ): ?>
98
- <h3 class="key-status failed"><?php esc_html_e("You're using Akismet on far too many sites for your Pro subscription.", 'akismet'); ?></h3>
99
- <p class="description"><?php printf( __('To continue your service, <a href="%s" target="_blank">upgrade to an Enterprise subscription</a>, which covers an unlimited number of sites. Please <a href="%s" target="_blank">contact our support team</a> with any questions.', 'akismet'), 'https://akismet.com/account/upgrade/', 'https://akismet.com/contact/'); ?></p>
 
 
 
 
100
  <?php endif; ?>
101
  </div>
102
- <?php endif;?>
75
  <?php elseif ( $type == 'no-sub' ) :?>
76
  <div class="wrap alert critical">
77
  <h3 class="key-status failed"><?php esc_html_e( 'Your subscription is missing.', 'akismet'); ?></h3>
78
+ <p class="description">
79
+ <?php printf( __( 'Since 2012, Akismet began using subscriptions for all accounts (even free ones). It looks like a subscription has not been assigned to your account, and we’d appreciate it if you’d <a href="%s" target="_blank">sign into your account</a> and choose one.', 'akismet'), 'https://akismet.com/account/upgrade/' ); ?>
80
+ <br /><br />
81
+ <?php printf( __( 'Please <a href="%s" target="_blank">contact our support team</a> with any questions.', 'akismet' ), 'https://akismet.com/contact/' ); ?>
82
+ </p>
83
  </div>
84
  <?php elseif ( $type == 'new-key-valid' ) :?>
85
  <div class="wrap alert active">
91
  </div>
92
  <?php elseif ( $type == 'new-key-failed' ) :?>
93
  <div class="wrap alert critical">
94
+ <h3 class="key-status"><?php esc_html_e( 'The key you entered could not be verified.' , 'akismet'); ?></h3>
95
+ <p class="description"><?php printf( __('The connection to akismet.com cannot be established. Please refer to <a href="%s" target="_blank">our guide about firewalls</a> and check your server configuration.', 'akismet'), 'http://blog.akismet.com/akismet-hosting-faq/'); ?></p>
96
  </div>
97
  <?php elseif ( $type == 'limit-reached' && in_array( $level, array( 'yellow', 'red' ) ) ) :?>
98
  <div class="wrap alert critical">
99
  <?php if ( $level == 'yellow' ): ?>
100
+ <h3 class="key-status failed"><?php esc_html_e( 'You&#8217;re using your Akismet key on more sites than your Pro subscription allows.', 'akismet' ); ?></h3>
101
+ <p class="description">
102
+ <?php printf( __( 'Your Pro subscription allows the use of Akismet on only one site. Please <a href="%s" target="_blank">purchase additional Pro subscriptions</a> or upgrade to an Enterprise subscription that allows the use of Akismet on unlimited sites.', 'akismet' ), 'http://docs.akismet.com/billing/add-more-sites/' ); ?>
103
+ <br /><br />
104
+ <?php printf( __( 'Please <a href="%s" target="_blank">contact our support team</a> with any questions.', 'akismet' ), 'https://akismet.com/contact/'); ?>
105
+ </p>
106
  <?php elseif ( $level == 'red' ): ?>
107
+ <h3 class="key-status failed"><?php esc_html_e( 'You&#8217;re using Akismet on far too many sites for your Pro subscription.', 'akismet' ); ?></h3>
108
+ <p class="description">
109
+ <?php printf( __( 'To continue your service, <a href="%s" target="_blank">upgrade to an Enterprise subscription</a>, which covers an unlimited number of sites.', 'akismet'), 'https://akismet.com/account/upgrade/' ); ?></p>
110
+ <br /><br />
111
+ <?php printf( __( 'Please <a href="%s" target="_blank">contact our support team</a> with any questions.', 'akismet' ), 'https://akismet.com/contact/'); ?></p>
112
+ </p>
113
  <?php endif; ?>
114
  </div>
115
+ <?php endif;?>
views/start.php CHANGED
@@ -8,7 +8,7 @@
8
  <?php echo esc_attr( $akismet_user->user_email ); ?>
9
  </div>
10
  <form name="akismet_activate" id="akismet_activate" action="https://akismet.com/get/" method="post" class="right" target="_blank">
11
- <input type="hidden" name="passback_url" value="<?php echo esc_attr( Akismet_Admin::get_page_url() ); ?>"/>
12
  <input type="hidden" name="auto-connect" value="<?php echo $akismet_user->ID;?>"/>
13
  <input type="hidden" name="redirect" value="plugin-signup"/>
14
  <input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Register Akismet' , 'akismet'); ?>"/>
@@ -22,7 +22,7 @@
22
  <?php printf( esc_html__( 'Your subscription for %s is cancelled' , 'akismet'), $akismet_user->user_email ); ?>
23
  </div>
24
  <form name="akismet_activate" id="akismet_activate" action="https://akismet.com/get/" method="post" class="right" target="_blank">
25
- <input type="hidden" name="passback_url" value="<?php echo esc_attr( Akismet_Admin::get_page_url() ); ?>"/>
26
  <input type="hidden" name="user_id" value="<?php echo $akismet_user->ID;?>"/>
27
  <input type="hidden" name="redirect" value="upgrade"/>
28
  <input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Reactivate Akismet' , 'akismet'); ?>"/>
@@ -64,7 +64,7 @@
64
  <p><?php esc_html_e('If you already know your API key.', 'akismet'); ?></p>
65
  </div>
66
  <form action="<?php echo esc_url( Akismet_Admin::get_page_url() ); ?>" method="post" id="akismet-enter-api-key" class="right">
67
- <input id="key" name="key" type="text" size="15" maxlength="12" value="" class="regular-text code">
68
  <input type="hidden" name="action" value="enter-key">
69
  <?php wp_nonce_field( Akismet_Admin::NONCE ) ?>
70
  <input type="submit" name="submit" id="submit" class="button button-secondary" value="<?php esc_attr_e('Use this key', 'akismet');?>">
@@ -85,7 +85,7 @@
85
  <p><?php esc_html_e('If you already know your API key.', 'akismet'); ?></p>
86
  </div>
87
  <form action="<?php echo esc_url( Akismet_Admin::get_page_url() ); ?>" method="post" id="akismet-enter-api-key" class="right">
88
- <input id="key" name="key" type="text" size="15" maxlength="12" value="" class="regular-text code">
89
  <input type="hidden" name="action" value="enter-key">
90
  <?php wp_nonce_field( Akismet_Admin::NONCE ); ?>
91
  <input type="submit" name="submit" id="submit" class="button button-secondary" value="<?php esc_attr_e('Use this key', 'akismet');?>">
8
  <?php echo esc_attr( $akismet_user->user_email ); ?>
9
  </div>
10
  <form name="akismet_activate" id="akismet_activate" action="https://akismet.com/get/" method="post" class="right" target="_blank">
11
+ <input type="hidden" name="passback_url" value="<?php echo esc_url( Akismet_Admin::get_page_url() ); ?>"/>
12
  <input type="hidden" name="auto-connect" value="<?php echo $akismet_user->ID;?>"/>
13
  <input type="hidden" name="redirect" value="plugin-signup"/>
14
  <input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Register Akismet' , 'akismet'); ?>"/>
22
  <?php printf( esc_html__( 'Your subscription for %s is cancelled' , 'akismet'), $akismet_user->user_email ); ?>
23
  </div>
24
  <form name="akismet_activate" id="akismet_activate" action="https://akismet.com/get/" method="post" class="right" target="_blank">
25
+ <input type="hidden" name="passback_url" value="<?php echo esc_url( Akismet_Admin::get_page_url() ); ?>"/>
26
  <input type="hidden" name="user_id" value="<?php echo $akismet_user->ID;?>"/>
27
  <input type="hidden" name="redirect" value="upgrade"/>
28
  <input type="submit" class="button button-primary" value="<?php esc_attr_e( 'Reactivate Akismet' , 'akismet'); ?>"/>
64
  <p><?php esc_html_e('If you already know your API key.', 'akismet'); ?></p>
65
  </div>
66
  <form action="<?php echo esc_url( Akismet_Admin::get_page_url() ); ?>" method="post" id="akismet-enter-api-key" class="right">
67
+ <input id="key" name="key" type="text" size="15" value="" class="regular-text code">
68
  <input type="hidden" name="action" value="enter-key">
69
  <?php wp_nonce_field( Akismet_Admin::NONCE ) ?>
70
  <input type="submit" name="submit" id="submit" class="button button-secondary" value="<?php esc_attr_e('Use this key', 'akismet');?>">
85
  <p><?php esc_html_e('If you already know your API key.', 'akismet'); ?></p>
86
  </div>
87
  <form action="<?php echo esc_url( Akismet_Admin::get_page_url() ); ?>" method="post" id="akismet-enter-api-key" class="right">
88
+ <input id="key" name="key" type="text" size="15" value="" class="regular-text code">
89
  <input type="hidden" name="action" value="enter-key">
90
  <?php wp_nonce_field( Akismet_Admin::NONCE ); ?>
91
  <input type="submit" name="submit" id="submit" class="button button-secondary" value="<?php esc_attr_e('Use this key', 'akismet');?>">