Jetpack_ReCaptcha

Class that handles reCAPTCHA.

Defined (1)

The class is defined in the following location(s).

/modules/sharedaddy/recaptcha.php  
  1. class Jetpack_ReCaptcha { 
  2.  
  3. /** 
  4. * URL to which requests are POSTed. 
  5. * @const string 
  6. */ 
  7. const VERIFY_URL = 'https://www.google.com/recaptcha/api/siteverify'; 
  8.  
  9. /** 
  10. * Site key to use in HTML code. 
  11. * @var string 
  12. */ 
  13. private $site_key; 
  14.  
  15. /** 
  16. * Shared secret for the site. 
  17. * @var string 
  18. */ 
  19. private $secret_key; 
  20.  
  21. /** 
  22. * Config for reCAPTCHA instance. 
  23. * @var array 
  24. */ 
  25. private $config; 
  26.  
  27. /** 
  28. * Error codes returned from reCAPTCHA API. 
  29. * @see https://developers.google.com/recaptcha/docs/verify 
  30. * @var array 
  31. */ 
  32. private $error_codes; 
  33.  
  34. /** 
  35. * Create a configured instance to use the reCAPTCHA service. 
  36. * @param string $site_key Site key to use in HTML code. 
  37. * @param string $secret_key Shared secret between site and reCAPTCHA server. 
  38. * @param array $config Config array to optionally configure reCAPTCHA instance. 
  39. */ 
  40. public function __construct( $site_key, $secret_key, $config = array() ) { 
  41. $this->site_key = $site_key; 
  42. $this->secret_key = $secret_key; 
  43. $this->config = wp_parse_args( $config, $this->get_default_config() ); 
  44.  
  45. $this->error_codes = array( 
  46. 'missing-input-secret' => __( 'The secret parameter is missing', 'jetpack' ),  
  47. 'invalid-input-secret' => __( 'The secret parameter is invalid or malformed', 'jetpack' ),  
  48. 'missing-input-response' => __( 'The response parameter is missing', 'jetpack' ),  
  49. 'invalid-input-response' => __( 'The response parameter is invalid or malformed', 'jetpack' ),  
  50. 'invalid-json' => __( 'Invalid JSON', 'jetpack' ),  
  51. 'unexpected-response' => __( 'Unexpected response', 'jetpack' ),  
  52. ); 
  53.  
  54. /** 
  55. * Get default config for this reCAPTCHA instance. 
  56. * @return array Default config 
  57. */ 
  58. public function get_default_config() { 
  59. return array( 
  60. 'language' => get_locale(),  
  61. 'script_async' => true,  
  62. 'tag_class' => 'g-recaptcha',  
  63. 'tag_attributes' => array( 
  64. 'theme' => 'light',  
  65. 'type' => 'image',  
  66. 'tabindex' => 0,  
  67. ),  
  68. ); 
  69.  
  70. /** 
  71. * Calls the reCAPTCHA siteverify API to verify whether the user passes 
  72. * CAPTCHA test. 
  73. * @param string $response The value of 'g-recaptcha-response' in the submitted 
  74. * form. 
  75. * @param string $remote_ip The end user's IP address. 
  76. * @return bool|WP_Error Returns true if verified. Otherwise WP_Error is returned. 
  77. */ 
  78. public function verify( $response, $remote_ip ) { 
  79. // No need make a request if response is empty. 
  80. if ( empty( $response ) ) { 
  81. return new WP_Error( 'missing-input-response', $this->error_codes['missing-input-response'], 400 ); 
  82.  
  83. $resp = wp_remote_post( self::VERIFY_URL, $this->get_verify_request_params( $response, $remote_ip ) ); 
  84. if ( is_wp_error( $resp ) ) { 
  85. return $resp; 
  86.  
  87. $resp_decoded = json_decode( wp_remote_retrieve_body( $resp ), true ); 
  88. if ( ! $resp_decoded ) { 
  89. return new WP_Error( 'invalid-json', $this->error_codes['invalid-json'], 400 ); 
  90.  
  91. // Default error code and message. 
  92. $error_code = 'unexpected-response'; 
  93. $error_message = $this->error_codes['unexpected-response']; 
  94.  
  95. // Use the first error code if exists. 
  96. if ( isset( $resp_decoded['error-codes'] ) && is_array( $resp_decoded['error-codes'] ) ) { 
  97. if ( isset( $resp_decoded['error-codes'][0] ) && isset( $this->error_codes[ $resp_decoded['error-codes'][0] ] ) ) { 
  98. $error_message = $this->error_codes[ $resp_decoded['error-codes'][0] ]; 
  99. $error_code = $resp_decoded['error-codes'][0]; 
  100.  
  101. if ( ! isset( $resp_decoded['success'] ) ) { 
  102. return new WP_Error( $error_code, $error_message ); 
  103.  
  104. if ( true !== $resp_decoded['success'] ) { 
  105. return new WP_Error( $error_code, $error_message ); 
  106.  
  107. return true; 
  108.  
  109. /** 
  110. * Get siteverify request parameters. 
  111. * @param string $response The value of 'g-recaptcha-response' in the submitted 
  112. * form. 
  113. * @param string $remote_ip The end user's IP address. 
  114. * @return array 
  115. */ 
  116. public function get_verify_request_params( $response, $remote_ip ) { 
  117. return array( 
  118. 'body' => array( 
  119. 'secret' => $this->secret_key,  
  120. 'response' => $response,  
  121. 'remoteip' => $remote_ip,  
  122. ),  
  123. 'sslverify' => true,  
  124. ); 
  125.  
  126. /** 
  127. * Get reCAPTCHA HTML to render. 
  128. * @return string 
  129. */ 
  130. public function get_recaptcha_html() { 
  131. return sprintf( 
  132. <div 
  133. class="%s" 
  134. data-sitekey="%s" 
  135. data-theme="%s" 
  136. data-type="%s" 
  137. data-tabindex="%s"></div> 
  138. <script type="text/javascript" src="https://www.google.com/recaptcha/api.js?hl=%s"%s></script> 
  139. ',  
  140. esc_attr( $this->config['tag_class'] ),  
  141. esc_attr( $this->site_key ),  
  142. esc_attr( $this->config['tag_attributes']['theme'] ),  
  143. esc_attr( $this->config['tag_attributes']['type'] ),  
  144. esc_attr( $this->config['tag_attributes']['tabindex'] ),  
  145. rawurlencode( $this->config['language'] ),  
  146. $this->config['script_async'] ? ' async' : '' 
  147. );