PageRenderTime 45ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 0ms

/inc/captcha.php

https://bitbucket.org/yoander/mtrack
PHP | 114 lines | 94 code | 13 blank | 7 comment | 7 complexity | 068fadef054192afdcc18a9c7267b6b5 MD5 | raw file
Possible License(s): BSD-3-Clause, Apache-2.0
  1. <?php # vim:ts=2:sw=2:et:
  2. /* For licensing and copyright terms, see the file named LICENSE */
  3. interface IMTrackCaptchImplementation {
  4. /** return the captcha content */
  5. function emit($form);
  6. /** check that the captcha is good
  7. * Returns true/false */
  8. function check($form);
  9. }
  10. class MTrackCaptcha {
  11. static $impl = null;
  12. static function register(IMTrackCaptchImplementation $impl)
  13. {
  14. self::$impl = $impl;
  15. }
  16. static function emit($form)
  17. {
  18. if (self::$impl !== null) {
  19. return self::$impl->emit($form);
  20. }
  21. return '';
  22. }
  23. static function check($form)
  24. {
  25. if (self::$impl !== null) {
  26. return self::$impl->check($form);
  27. }
  28. return true;
  29. }
  30. }
  31. class MTrackCaptcha_Recaptcha implements IMTrackCaptchImplementation {
  32. public $errcode = null;
  33. public $pub;
  34. public $priv;
  35. public $userclass;
  36. function __construct($pub, $priv, $userclass = 'anonymous|authenticated') {
  37. $this->pub = $pub;
  38. $this->priv = $priv;
  39. $this->userclass = explode("|", $userclass);
  40. MTrackCaptcha::register($this);
  41. }
  42. function emit($form)
  43. {
  44. $class = MTrackAuth::getUserClass();
  45. if (!in_array($class, $this->userclass)) {
  46. return '';
  47. }
  48. $pub = $this->pub;
  49. $err = $this->errcode === null ? '' : "&error=$this->errcode";
  50. $http = $_SERVER['HTTPS'] ? 'https' : 'http';
  51. return <<<HTML
  52. <script type='text/javascript'
  53. src="$http://www.google.com/recaptcha/api/challenge?k=$pub$err">
  54. </script>
  55. <noscript>
  56. <iframe src="$http://www.google.com/recaptcha/api/noscript?k=$pub$err"
  57. height="300" width="500" frameborder="0"></iframe>
  58. <br/>
  59. <textarea name="recaptcha_challenge_field" rows="3" cols="40"></textarea>
  60. <input type="hidden" name="recaptcha_response_field"
  61. value="manual_challenge"/>
  62. </noscript>
  63. HTML;
  64. }
  65. function check($form)
  66. {
  67. $class = MTrackAuth::getUserClass();
  68. if (!in_array($class, $this->userclass)) {
  69. return true;
  70. }
  71. if (empty($_POST['recaptcha_challenge_field']) or
  72. empty($_POST['recaptcha_response_field'])) {
  73. return array('false', 'incorrect-captcha-sol');
  74. }
  75. $data = http_build_query(array(
  76. 'privatekey' => $this->priv,
  77. 'remoteip' => $_SERVER['REMOTE_ADDR'],
  78. 'challenge' => $_POST['recaptcha_challenge_field'],
  79. 'response' => $_POST['recaptcha_response_field'],
  80. ));
  81. $params = array(
  82. 'http' => array(
  83. 'method' => 'POST',
  84. 'content' => $data,
  85. ),
  86. );
  87. $ctx = stream_context_create($params);
  88. /* first line: true/false
  89. * second line: error code
  90. */
  91. $res = array();
  92. foreach (file('http://www.google.com/recaptcha/api/verify', 0, $ctx) as $line) {
  93. $res[] = trim($line);
  94. }
  95. if ($res[0] == 'true') {
  96. return true;
  97. }
  98. $this->errcode = $res[1];
  99. return array(false, $this->errcode);
  100. }
  101. }