从头开始创建一个php验证码

时间:2012-12-27 15:00:09

标签: php

我需要在注册表单中添加一个简单的验证码,如单词验证码或数学验证码。但是代码不起作用。以下是代码:(请帮我修复代码)

<?php
session_start();
//random string generator function
function random($length){
//create a or array string called chars
        $chars ="abcdefghijklmnopqrstuvwxyz23456789";
         $str = "";
        //is the variable which is equal to the length of the string called chars
        $size = strlen($chars);
        for($i=0; $i<$length; $i++){
             $str .= $chars[rand(0, $size-1)];

    }
    return $str;
}
//the gd image adaptor in xampp
$cap = random(7);
$_SESSION['real'] = $cap;
$image = imagecreate(100, 20);
$background = imagecolorallocate($image, 0, 0, 0);
$foreground = imagecolorallocate($image, 255, 255, 255);
//this is going to write our string in the image
imagestring($image, 5,5,1,$cap,$foreground);
header("Content-type: image/jpeg");
imagejpeg($image);
?>

注册页码

   <?php
//This function will display the registration form
function register_form(){

$date = date('D, M, Y');
echo "<form action='?act=register' method='post'>"
    ."Username: <input type='text' name='username' size='30'><br>"
    ."Password: <input type='password' name='password' size='30'><br>"
    ."Confirm your password: <input type='password' name='password_conf' size='30'><br>"
    ."Email: <input type='text' name='email' size='30'><br>"
    ."<img src= 'captcha.php'>  <input type='text' name='captcha'<br>"
    ."<input type='hidden' name='date' value='$date'>"
    ."<input type='submit' value='Register'>"
    ."</form>";

}

//This function will register users data
function register(){

//Connecting to database
$connect = mysql_connect("localhost", "root", "nokiae71");
if(!$connect){
die(mysql_error());
}

//Selecting database
$select_db = mysql_select_db("forumStructure", $connect);
if(!$select_db){
die(mysql_error());
}

//Collecting info
$username = $_REQUEST['username'];
$password = $_REQUEST['password'];
$pass_conf = $_REQUEST['password_conf'];
$email = $_REQUEST['email'];
$date = $_REQUEST['date'];
$guess = $_POST['captcha'];

//Here we will check do we have all inputs filled

if(empty($username)){
die("Please enter your username!<br>");
}

if(empty($password)){
die("Please enter your password!<br>");
}

if(empty($pass_conf)){
die("Please confirm your password!<br>");
}

if(empty($email)){
die("Please enter your email!");
}


$real = (isset($_SESSION['real'])) ? $_SESSION['real'] : "";


if (empty($guess))
{ 
    die("Please enter the correct CAPTCHA.<br>");
} 
/*if ($real != $guess){
    die("things are bad");
}*/
if (!empty($guess) && $guess !== $real)
{
    die("Please enter the correct CAPTCHA.<br>");
}

//Let's check if this username is already in use

$user_check = mysql_query("SELECT username FROM users WHERE username='$username'");
$do_user_check = mysql_num_rows($user_check);

//Now if email is already in use

$email_check = mysql_query("SELECT email FROM users WHERE email='$email'");
$do_email_check = mysql_num_rows($email_check);

//Now display errors

if($do_user_check > 0){
die("Username is already in use!<br>");
}

if($do_email_check > 0){
die("Email is already in use!");
}

//Now let's check does passwords match

if($password != $pass_conf){
die("Passwords don't match!");
}


//If everything is okay let's register this user

$insert = mysql_query("INSERT INTO users (username, password, email) VALUES ('$username', '$password', '$email')");
if(!$insert){
die("There's little problem: ".mysql_error());
}

echo $username.", you are now registered. Thank you!<br><a href=login.php>Login</a> | <a href=index.php>Index</a>";

}
$act = isset($_GET['act']) ? $_GET['act'] : '';
switch($act){

default;
register_form();
break;

case "register";
register();
break;

}

?> 

谢谢我只是php的新手,我想学习如何做到这一点。我在stackoverflow上获得了注册码仅用于学习目的...我们将非常感谢您的帮助或建议。

2 个答案:

答案 0 :(得分:1)

你缺少session_start();在顶部和&gt;在...上 <img src= 'captcha.php'> <input type='text' name='captcha'><br>"

答案 1 :(得分:0)

您可以使用此代码 -

<?php
 //
// PHP module for easy utilization of the free captchas.net CAPTCHA service
//
// For documentation look at http://captchas.net/sample/php/
//
// Written by
//   Sebastian Wilhelmi <seppi@seppi.de> and
//   Felix Holderied <felix@holderied.de>
// This file is in the public domain.
//
// ChangeLog:
//
// 2014-04-27: Fixed missing initialization 
//
// 2011-04-25: Added function captchas_image_reload
//
// 2011-03-08: Added color option (Alfred Vink)
//
// 2006-08-16: New optional features integrated
//
// 2006-03-01: Only delete the random string from the repository in
//             case of a successful verification.
 //
 // 2006-02-14: Add new image() method returning an HTML/JavaScript
//             snippet providing a fault tolerant service.
//
// 2005-06-02: Initial version.
 //

 class CaptchasDotNet
  {
 function CaptchasDotNet ($client, $secret,
                       $random_repository = '/tmp/captchasnet-random-strings',
                       $cleanup_time      = 3600,
                       $alphabet          = 'abcdefghijklmnopqrstuvwxyz',
                       $letters           = 6,
                       $width             = 240,
                       $height            = 80,
                       $color             = '000000'
                       )
   {
   $this->__client = $client;
  $this->__secret = $secret;
     $this->__random_repository = $random_repository;
     $this->__cleanup_time      = $cleanup_time;
     $this->__time_stamp_file   = $random_repository . '/__time_stamp__';
     $this->__alphabet          = $alphabet;
     $this->__letters           = $letters;
     $this->__width             = $width;
     $this->__height            = $height;
     $this->__color             = $color; 
     $this->__random_file       = ""; 
   }

   function __random_string ()
    {
      // The random string shall consist of small letters, big letters
      // and digits.
      $letters = "abcdefghijklmnopqrstuvwxyz";
      $letters .= strtoupper ($letters) + "0123456789";

      // The random starts out empty, then 40 random possible characters
      // are appended.
      $random_string = '';
      for ($i = 0; $i < 40; $i++)
      {
        $random_string .= $letters{rand (0, strlen ($letters) - 1)};
      }

      // Return the random string.
      return $random_string;
    }

    // Create a new random string and register it.
    function random ()
    {
      // If the repository directory is does not yet exist, create it.
      if (!is_dir ($this->__random_repository))
      {
        mkdir ($this->__random_repository);
      }

      // If the time stamp file does not yet exist, create it.
      if (!is_file ($this->__time_stamp_file))
      {
        touch ($this->__time_stamp_file);
      }

      // Get the current time.
      $now = time ();

      // Determine the time, before which to remove random strings.
      $cleanup_time = $now - $this->__cleanup_time;

      // If the last cleanup is older than specified, cleanup the
      // directory.
      if (filemtime ($this->__time_stamp_file) < $cleanup_time)
      {
        $handle = opendir ($this->__random_repository);
  while (true)
  {
    $filename = readdir ($handle);
    if (!$filename)
    {
      break;
    }
    if ($filename != '.' && $filename != '..')
    {
      $filename = $this->__random_repository . '/' . $filename;
      if (filemtime ($filename) <  $cleanup_time)
      {
        unlink ($filename);
      }
          }
        }
        closedir ($handle);

        touch ($this->__time_stamp_file);
      }

      // loop until a valid random string has been found and registered,
      // but at most 20 times. If no valid random has been found during
      // that time, there is something really wrong. Also show the error
      // in the last run.
      for ($remaining = 20; $remaining > 0; $remaining--)
      {
        // generate a new random string.
        $random = $this->__random_string ();

        // open a file with the corresponding name in the repository
        // directory in such a way, that the creation fails, when the
        // file already exists. That should be near to impossible with
        // good seeding of the random number generator, but it's better
        // to play safe. If this is the last run, show the possible
        // error message.
        $filename = $this->__random_repository . '/' . $random;

        if ($remaining == 1)
        {
          $file = fopen ($filename, 'x');
        }
        else
        {
          $file = @fopen ($filename, 'x');
        }

        if ($file)
        {
          fclose ($file);
          break;
        }

        // if the file already existed, rerun the loop to try the next
        // string.
      }

      // return the successfully registered random string.
      $this->__random = $random;
      return $random;
    }

    //
    // Generates image-URL Parameters are only atached if different from default
    //
    function image_url ($random = False, $base = 'http://image.captchas.net/')
    {
      if (!$random)
      {
        $random = $this->__random;
      }
      $image_url  = $base;
      $image_url .= '?client='   . $this->__client;
      $image_url .= '&amp;random='   . $random;
      if ($this->__alphabet!='abcdefghijklmnopqrstuvwxyz') {$image_url .= '&amp;alphabet=' . $this->__alphabet;};
      if ($this->__letters!=6) {$image_url .= '&amp;letters='  . $this->__letters;};
      if ($this->__width!=240) {$image_url .= '&amp;width='    . $this->__width;};
      if ($this->__height!=80) {$image_url .= '&amp;height='   . $this->__height;};
      if ($this->__color!='000000') {$image_url .= '&amp;color='   . $this->__color;};
      return $image_url;
    }

    //
    // Same as image_url but without width and height
    //
    function audio_url ($random = False, $base = 'http://audio.captchas.net/')
    {
      if (!$random)
      {
        $random = $this->__random;
      }
      $audio_url  = $base;
            $audio_url .= '?client='   . $this->__client;
      $audio_url .= '&amp;random='   . $random;
      if ($this->__alphabet!='abcdefghijklmnopqrstuvwxyz') {$audio_url .= '&amp;alphabet=' . $this->__alphabet;};
      if ($this->__letters!=6) {$audio_url .= '&amp;letters='  . $this->__letters;};
      return $audio_url;
    }

    //
    // Generates complete html-sample with javascript to reload image from
    // backup server
    //
    function image ($random = False, $id = 'captchas.net')
    {
      $image = <<<EOT
    <a href="http://captchas.net"><img
        style="border: none; vertical-align: bottom"
        id="@ID@" src="@URL@" width="@WIDTH@" height="@HEIGHT@"
        alt="The Captcha image" /></a>
    <script type="text/javascript">
      <!--
      function captchas_image_reload (imgId) 
      {
        var image_url = document.getElementById(imgId).src;
        image_url+= "&";
        document.getElementById(imgId).src = image_url;
      }

      function captchas_image_error (image)
      {
        if (!image.timeout) return true;
        image.src = image.src.replace (/^http:\/\/image\.captchas\.net/,
                                       'http://image.backup.captchas.net');
        return captchas_image_loaded (image);
      }

      function captchas_image_loaded (image)
      {
        if (!image.timeout) return true;
        window.clearTimeout (image.timeout);
        image.timeout = false;
        return true;
      }

      var image = document.getElementById ('@ID@');
      image.onerror = function() {return captchas_image_error (image);};
      image.onload = function() {return captchas_image_loaded (image);};
      image.timeout
        = window.setTimeout(
           "captchas_image_error (document.getElementById ('@ID@'))",
           10000);
      image.src = image.src;
      //-->
    </script>
  EOT;
      $image = str_replace ('@HEIGHT@', $this->__height, $image);
      $image = str_replace ('@WIDTH@', $this->__width, $image);
      $image = str_replace ('@ID@', $id, $image);
      $image = str_replace ('@URL@', $this->image_url (), $image);
      return $image;
    }

    function validate ($random)
    {
      $this->__random = $random;

      $file_name = $this->__random_repository . '/' . $random;

      // Find out, whether the file exists
      $result = is_file ($file_name);

      // if the file exists, remember it.
      if ($result)
      {
        $this->__random_file = $file_name;
      }

      // the random string was valid, if and only if the corresponding
      // file existed.
      return $result;
    }

    function verify ($input, $random = False)
    {
      if (!$random)
      {
        $random = $this->__random;
      }
      $password_letters = $this->__alphabet;
      $password_length  = $this->__letters;

      // If the user input has the wrong lenght, it can't be correct.
      if (strlen ($input) != $password_length)
      {
        return False;
      }

      // Calculate the MD5 digest of the concatenation of secret key and
      // random string. The digest is a hex string.
      $encryption_base = $this->__secret . $random;
      // This extension is needed for secure use of optional parameters
      // In case of standard use we do not append the values, to be
      // compatible to existing implementations
      if(($password_letters  != 'abcdefghijklmnopqrstuvwxyz') || ($password_length != '6'))
      {
        $encryption_base = $encryption_base . ':' . $password_letters  . ':' . $password_length;
      }
      $digest = md5 ($encryption_base);

      // Check the password according to the rules from the first
      // positions of the digest.
      for ($pos = 0; $pos < $password_length; $pos++)
{
  $letter_num
    = hexdec (substr ($digest, 2 * $pos, 2)) % strlen ($password_letters);

  // If the letter at the current position is wrong, the user
  // input isn't correct.
  if ($input[$pos] != $password_letters[$letter_num])
  {
    return False;
  }
}

// if the file exists, remove it.
if ($this->__random_file)
{
  unlink ($this->__random_file);
  unset ($this->__random_file);
}

      // The user input was correct.
      return True;
    }

  }

  ?>

这是图书馆。

现在是HTML代码 -

<?php

  require 'CaptchasDotNet.php';

  // Required Parameters
  // Replace the values you receive upon registration at http://captchas.net.
  //
  //   client: 'demo'
  //
  //   secret: 'secret'
  //
  // Optional Parameters and defaults
  //
  //   repository_prefix: '/tmp/captchasnet-random-strings' path to repository
  //   ATTENTION SAFE-MODE, YOU HAVE TO CHOOSE SOMETHING LIKE
  //   '/writable/path/captchasnet-random-strings'
        //
  //   cleanup_time: '3600' (means max 1 hour between query and check)
  //
  //   alphabet: 'abcdefghijklmnopqrstuvwxyz' (Used characters in captcha)
  //   We recommend alphabet without ijl: 'abcdefghkmnopqrstuvwxyz'
  //
  //   letters: '6' (Number of characters in captcha)
  //
  //   width: '240' (image width)
  //
  //   height: '80' (image height)
  //
  //   color: '000000' (image color in rgb)
  //
  //   language: 'en' (audio language, append &language=fr/de/it/nl to audio-url)
  //
  //   Usage
  //   $captchas = new CaptchasDotNet (<client>, <secret>,
  //                                   <repository_prefix>, <cleanup_time>,
  //                                   <alphabet>,<letters>,
  //                                   <height>,<width>,<color>);
  //
  // Don't forget same settings in check.php

  // Construct the captchas object.

  $captchas = new CaptchasDotNet ('demo', 'secret',
                            '/tmp/captchasnet-random-strings','3600',
                            'abcdefghkmnopqrstuvwxyz','6',
                            '240','80','000088');
  ?>

  <html>
    <head>
      <title>Sample PHP CAPTCHA Query</title>
    </head>
    <h1>Sample PHP CAPTCHA Query</h1>
    <form method="get" action="check.php">
      <table>
  <tr>
    <td>
      <input type="hidden" name="random" value="<?= $captchas->random () ?>" />
        Your message:</td><td><input name="message" size="60" />
    </td>
  </tr>
  <tr>
    <td>
      The CAPTCHA password:
    </td>
    <td>
      <input name="password" size="6" />
    </td>
  </tr>
  <tr>
    <td>
    </td>
    <td>
      <?= $captchas->image () ?> <a href="javascript:captchas_image_reload('captchas.net')">Reload Image</a>
      <br> <a href="<?= $captchas->audio_url () ?>">Phonetic spelling (mp3)</a>
      <br> <a href="<?= $captchas->audio_url () ?>&language=de">Buchstabieren (mp3)</a>
      <br> <a href="<?= $captchas->audio_url () ?>&language=it">Compitare (mp3)</a>
      <br> <a href="<?= $captchas->audio_url () ?>&language=nl">Spellen (mp3)</a>
      <br> <a href="<?= $captchas->audio_url () ?>&language=fr">Epeler (mp3)</a>
    </td>
  </tr>
  <tr>
    <td>
    </td>
    <td>
      <input type="submit" value="Submit" />
    </td>
  </tr>
</table>

现在检查 -

<?php

  require 'CaptchasDotNet.php';

  // See query.php for documentation

  $captchas = new CaptchasDotNet ('demo', 'secret',
                            '/tmp/captchasnet-random-strings','3600',
                            'abcdefghkmnopqrstuvwxyz','6',
                            '240','80','000088');

  // Read the form values
  $message       = $_REQUEST['message'];
  $password      = $_REQUEST['password'];
  $random_string = $_REQUEST['random'];
  ?>

  <html>
    <head>
      <title>Sample PHP CAPTCHA Query</title>
    </head>
    <h1>Sample PHP CAPTCHA Query</h1>

  <?php
    // Check the random string to be valid and return an error message
    // otherwise.
    if (!$captchas->validate ($random_string))
    {
      echo 'The session key (random) does not exist, please go back and reload form.<br/>';
      echo 'In case you are the administrator of this page, ';
      echo 'please check if random keys are stored correct.<br/>';
      echo 'See http://captchas.net/sample/php/ "Problems with save mode"';
    }
    // Check, that the right CAPTCHA password has been entered and
    // return an error message otherwise.
    elseif (!$captchas->verify ($password))
    {
      echo 'You entered the wrong password. Aren\'t you human? Please use back button and reload.';
    }
    // Return a success message
    else
    {
      echo 'Your message was verified to be entered by a human and is "' . $message . '"';
    }
  ?>

  </html>

想想,它会对你有所帮助