Hi coders, In this tutorial post we have a simple login and registration script with email verification along with forgot password recovery feature using PHP and MySQL, Well advanced PHP Programming must follow proper Object Oriented(OOP) approach so i have used here OOP with PDO(PHP Data Object),
and PDO is recommended to use since mysql extension is deprecated, ok
let's come to the post. Well to avoid fake registrations we need to
verify a newly registered user with their email id, So to send
verification email i have used here PHPMailer library which is awesome
mailer library, i have already posted a tutorial about sending plain
& HTML format
emails using PHPMailer you can check them out. so set your domain smtp
credentials, if you don't have domain smtp you can also use your Gmail
credentials as well using gmail smtp(smtp.gmail.com) so lets have a look
at this tutorial and see php code to send email while registration you
can also try this in your localhost also. let's code.
Note I have used here Bootstrap to make better user Interface of this script so scripts looks little lengthy.
read also : jQuery Ajax Registration Form with PHP MySQL
after database creation we have to create following files which are :
- runQuery() : executes a Query.
- lastID() : return a last insert id.
- register() : register new user.
- login() : to login user.
- is_logged_in() : return users session is active or not.
- logout() : to destroy users session.
- send_mail() : to send mail at user registration and send forgot password reset link.
i have used here PHPMailer to send emails using gmail smtp so you can use in your localhost server.
NOTE : I have Skip validation part over here and used only HTML5 validation attributes and used MD5() Password Encryption Function, if you use PHP5.5 then you must use New Password Hashing Functions Here.
after registration a user will get mailed to his mail account to activate and verify his/her account and redirects to the "verify.php" file.
send_mail() function send a confirmation link to the user registered email.
That's it
we have created here login & registration script with email verification along with forgot password recovery feature, we already have a login and registrations tutorials but i have to decide to post email verification and forgot password tutorial after getting email requests from my readers so enjoy...
Note I have used here Bootstrap to make better user Interface of this script so scripts looks little lengthy.
read also : jQuery Ajax Registration Form with PHP MySQL
Database and Table
import and run this sql code to create database and tableCREATE TABLE IF NOT EXISTS `tbl_users` (
`userID` int(11) NOT NULL AUTO_INCREMENT,
`userName` varchar(100) NOT NULL,
`userEmail` varchar(100) NOT NULL UNIQUE,
`userPass` varchar(100) NOT NULL,
`userStatus` enum('Y','N') NOT NULL DEFAULT 'N',
`tokenCode` varchar(100) NOT NULL,
PRIMARY KEY (`userID`)
)
after database creation we have to create following files which are :
- dbconfig.php
- class.user.php
- index.php
- signup.php
- verify.php
- home.php
- fpass.php
- resetpass.php
- logout.php
dbconfig.php
In this file we have a simple database connection code using Database class, and one dbConnection function which connects database<?php
class Database
{
private $host = "localhost";
private $db_name = "dbtest";
private $username = "root";
private $password = "";
public $conn;
public function dbConnection()
{
$this->conn = null;
try
{
$this->conn = new PDO("mysql:host=" . $this->host . ";dbname=" . $this->db_name, $this->username, $this->password);
$this->conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
}
catch(PDOException $exception)
{
echo "Connection error: " . $exception->getMessage();
}
return $this->conn;
}
}
?>
class.user.php
include "dbconfig.php" file at the beginning of this class file to make use of database and within "__construct()" function create new object of "Database()" class as "$db" as shown in this file- runQuery() : executes a Query.
- lastID() : return a last insert id.
- register() : register new user.
- login() : to login user.
- is_logged_in() : return users session is active or not.
- logout() : to destroy users session.
- send_mail() : to send mail at user registration and send forgot password reset link.
i have used here PHPMailer to send emails using gmail smtp so you can use in your localhost server.
<?php
require_once 'dbconfig.php';
class USER
{
private $conn;
public function __construct()
{
$database = new Database();
$db = $database->dbConnection();
$this->conn = $db;
}
public function runQuery($sql)
{
$stmt = $this->conn->prepare($sql);
return $stmt;
}
public function lasdID()
{
$stmt = $this->conn->lastInsertId();
return $stmt;
}
public function register($uname,$email,$upass,$code)
{
try
{
$password = md5($upass);
$stmt = $this->conn->prepare("INSERT INTO tbl_users(userName,userEmail,userPass,tokenCode)
VALUES(:user_name, :user_mail, :user_pass, :active_code)");
$stmt->bindparam(":user_name",$uname);
$stmt->bindparam(":user_mail",$email);
$stmt->bindparam(":user_pass",$password);
$stmt->bindparam(":active_code",$code);
$stmt->execute();
return $stmt;
}
catch(PDOException $ex)
{
echo $ex->getMessage();
}
}
public function login($email,$upass)
{
try
{
$stmt = $this->conn->prepare("SELECT * FROM tbl_users WHERE userEmail=:email_id");
$stmt->execute(array(":email_id"=>$email));
$userRow=$stmt->fetch(PDO::FETCH_ASSOC);
if($stmt->rowCount() == 1)
{
if($userRow['userStatus']=="Y")
{
if($userRow['userPass']==md5($upass))
{
$_SESSION['userSession'] = $userRow['userID'];
return true;
}
else
{
header("Location: index.php?error");
exit;
}
}
else
{
header("Location: index.php?inactive");
exit;
}
}
else
{
header("Location: index.php?error");
exit;
}
}
catch(PDOException $ex)
{
echo $ex->getMessage();
}
}
public function is_logged_in()
{
if(isset($_SESSION['userSession']))
{
return true;
}
}
public function redirect($url)
{
header("Location: $url");
}
public function logout()
{
session_destroy();
$_SESSION['userSession'] = false;
}
function send_mail($email,$message,$subject)
{
require_once('mailer/class.phpmailer.php');
$mail = new PHPMailer();
$mail->IsSMTP();
$mail->SMTPDebug = 0;
$mail->SMTPAuth = true;
$mail->SMTPSecure = "ssl";
$mail->Host = "smtp.gmail.com";
$mail->Port = 465;
$mail->AddAddress($email);
$mail->Username="yourgmailid@gmail.com";
$mail->Password="yourgmailpassword";
$mail->SetFrom('you@yourdomain.com','Coding Cage');
$mail->AddReplyTo("you@yourdomain.com","Coding Cage");
$mail->Subject = $subject;
$mail->MsgHTML($message);
$mail->Send();
}
}
signup.php | Email Verification
create "signup.php" file and paste following code inside file and include "class.user.php" file at the beginning of this file and create new object to access class files function as shown in the file.NOTE : I have Skip validation part over here and used only HTML5 validation attributes and used MD5() Password Encryption Function, if you use PHP5.5 then you must use New Password Hashing Functions Here.
after registration a user will get mailed to his mail account to activate and verify his/her account and redirects to the "verify.php" file.
send_mail() function send a confirmation link to the user registered email.
<?php
session_start();
require_once 'class.user.php';
$reg_user = new USER();
if($reg_user->is_logged_in()!="")
{
$reg_user->redirect('home.php');
}
if(isset($_POST['btn-signup']))
{
$uname = trim($_POST['txtuname']);
$email = trim($_POST['txtemail']);
$upass = trim($_POST['txtpass']);
$code = md5(uniqid(rand()));
$stmt = $reg_user->runQuery("SELECT * FROM tbl_users WHERE userEmail=:email_id");
$stmt->execute(array(":email_id"=>$email));
$row = $stmt->fetch(PDO::FETCH_ASSOC);
if($stmt->rowCount() > 0)
{
$msg = "
<div class='alert alert-error'>
<button class='close' data-dismiss='alert'>×</button>
<strong>Sorry !</strong> email allready exists , Please Try another one
</div>
";
}
else
{
if($reg_user->register($uname,$email,$upass,$code))
{
$id = $reg_user->lasdID();
$key = base64_encode($id);
$id = $key;
$message = "
Hello $uname,
<br /><br />
Welcome to Coding Cage!<br/>
To complete your registration please , just click following link<br/>
<br /><br />
<a href='http://www.SITE_URL.com/verify.php?id=$id&code=$code'>Click HERE to Activate :)</a>
<br /><br />
Thanks,";
$subject = "Confirm Registration";
$reg_user->send_mail($email,$message,$subject);
$msg = "
<div class='alert alert-success'>
<button class='close' data-dismiss='alert'>×</button>
<strong>Success!</strong> We've sent an email to $email.
Please click on the confirmation link in the email to create your account.
</div>
";
}
else
{
echo "sorry , Query could no execute...";
}
}
}
?>
<!DOCTYPE html>
<html>
<head>
<title>Signup | Coding Cage</title>
<!-- Bootstrap -->
<link href="bootstrap/css/bootstrap.min.css" rel="stylesheet" media="screen">
<link href="bootstrap/css/bootstrap-responsive.min.css" rel="stylesheet" media="screen">
<link href="assets/styles.css" rel="stylesheet" media="screen">
<!-- HTML5 shim, for IE6-8 support of HTML5 elements -->
<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
<script src="js/vendor/modernizr-2.6.2-respond-1.1.0.min.js"></script>
</head>
<body id="login">
<div class="container">
<?php if(isset($msg)) echo $msg; ?>
<form class="form-signin" method="post">
<h2 class="form-signin-heading">Sign Up</h2><hr />
<input type="text" class="input-block-level" placeholder="Username" name="txtuname" required />
<input type="email" class="input-block-level" placeholder="Email address" name="txtemail" required />
<input type="password" class="input-block-level" placeholder="Password" name="txtpass" required />
<hr />
<button class="btn btn-large btn-primary" type="submit" name="btn-signup">Sign Up</button>
<a href="index.php" style="float:right;" class="btn btn-large">Sign In</a>
</form>
</div> <!-- /container -->
<script src="vendors/jquery-1.9.1.min.js"></script>
<script src="bootstrap/js/bootstrap.min.js"></script>
</body>
</html>
verify.php
create new file as "verify.php" and paste following code inside this file, after redirecting from email this file will generate a QueryString as "id=something&code=something" and based on activation code the userStatus will update from "N" to "Y" means "inactive" to "active"<?php
require_once 'class.user.php';
$user = new USER();
if(empty($_GET['id']) && empty($_GET['code']))
{
$user->redirect('index.php');
}
if(isset($_GET['id']) && isset($_GET['code']))
{
$id = base64_decode($_GET['id']);
$code = $_GET['code'];
$statusY = "Y";
$statusN = "N";
$stmt = $user->runQuery("SELECT userID,userStatus FROM tbl_users WHERE userID=:uID AND tokenCode=:code LIMIT 1");
$stmt->execute(array(":uID"=>$id,":code"=>$code));
$row=$stmt->fetch(PDO::FETCH_ASSOC);
if($stmt->rowCount() > 0)
{
if($row['userStatus']==$statusN)
{
$stmt = $user->runQuery("UPDATE tbl_users SET userStatus=:status WHERE userID=:uID");
$stmt->bindparam(":status",$statusY);
$stmt->bindparam(":uID",$id);
$stmt->execute();
$msg = "
<div class='alert alert-success'>
<button class='close' data-dismiss='alert'>×</button>
<strong>WoW !</strong> Your Account is Now Activated : <a href='index.php'>Login here</a>
</div>
";
}
else
{
$msg = "
<div class='alert alert-error'>
<button class='close' data-dismiss='alert'>×</button>
<strong>sorry !</strong> Your Account is allready Activated : <a href='index.php'>Login here</a>
</div>
";
}
}
else
{
$msg = "
<div class='alert alert-error'>
<button class='close' data-dismiss='alert'>×</button>
<strong>sorry !</strong> No Account Found : <a href='signup.php'>Signup here</a>
</div>
";
}
}
?>
<!DOCTYPE html>
<html>
<head>
<title>Confirm Registration</title>
<!-- Bootstrap -->
<link href="bootstrap/css/bootstrap.min.css" rel="stylesheet" media="screen">
<link href="bootstrap/css/bootstrap-responsive.min.css" rel="stylesheet" media="screen">
<link href="assets/styles.css" rel="stylesheet" media="screen">
<!-- HTML5 shim, for IE6-8 support of HTML5 elements -->
<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
<script src="js/vendor/modernizr-2.6.2-respond-1.1.0.min.js"></script>
</head>
<body id="login">
<div class="container">
<?php if(isset($msg)) { echo $msg; } ?>
</div> <!-- /container -->
<script src="vendors/jquery-1.9.1.min.js"></script>
<script src="bootstrap/js/bootstrap.min.js"></script>
</body>
</html>
index.php / Login Page
index.php as login page which will take email id and password to access users home page if the details are wrong it will show appropriate message, with forgot password link. only email verified user can log in and access member page.<?php
session_start();
require_once 'class.user.php';
$user_login = new USER();
if($user_login->is_logged_in()!="")
{
$user_login->redirect('home.php');
}
if(isset($_POST['btn-login']))
{
$email = trim($_POST['txtemail']);
$upass = trim($_POST['txtupass']);
if($user_login->login($email,$upass))
{
$user_login->redirect('home.php');
}
}
?>
<!DOCTYPE html>
<html>
<head>
<title>Login | Coding Cage</title>
<!-- Bootstrap -->
<link href="bootstrap/css/bootstrap.min.css" rel="stylesheet" media="screen">
<link href="bootstrap/css/bootstrap-responsive.min.css" rel="stylesheet" media="screen">
<link href="assets/styles.css" rel="stylesheet" media="screen">
<!-- HTML5 shim, for IE6-8 support of HTML5 elements -->
<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
<script src="js/vendor/modernizr-2.6.2-respond-1.1.0.min.js"></script>
</head>
<body id="login">
<div class="container">
<?php
if(isset($_GET['inactive']))
{
?>
<div class='alert alert-error'>
<button class='close' data-dismiss='alert'>×</button>
<strong>Sorry!</strong> This Account is not Activated Go to your Inbox and Activate it.
</div>
<?php
}
?>
<form class="form-signin" method="post">
<?php
if(isset($_GET['error']))
{
?>
<div class='alert alert-success'>
<button class='close' data-dismiss='alert'>×</button>
<strong>Wrong Details!</strong>
</div>
<?php
}
?>
<h2 class="form-signin-heading">Sign In.</h2><hr />
<input type="email" class="input-block-level" placeholder="Email address" name="txtemail" required />
<input type="password" class="input-block-level" placeholder="Password" name="txtupass" required />
<hr />
<button class="btn btn-large btn-primary" type="submit" name="btn-login">Sign in</button>
<a href="signup.php" style="float:right;" class="btn btn-large">Sign Up</a><hr />
<a href="fpass.php">Lost your Password ? </a>
</form>
</div> <!-- /container -->
<script src="bootstrap/js/jquery-1.9.1.min.js"></script>
<script src="bootstrap/js/bootstrap.min.js"></script>
</body>
</html>
Home.php / Member Page
after verifying and email confirmation finally user will become verified user of site and can access this member page. this page is for registered members.<?php
session_start();
require_once 'class.user.php';
$user_home = new USER();
if(!$user_home->is_logged_in())
{
$user_home->redirect('index.php');
}
$stmt = $user_home->runQuery("SELECT * FROM tbl_users WHERE userID=:uid");
$stmt->execute(array(":uid"=>$_SESSION['userSession']));
$row = $stmt->fetch(PDO::FETCH_ASSOC);
?>
<!DOCTYPE html>
<html class="no-js">
<head>
<title><?php echo $row['userEmail']; ?></title>
<!-- Bootstrap -->
<link href="bootstrap/css/bootstrap.min.css" rel="stylesheet" media="screen">
<link href="bootstrap/css/bootstrap-responsive.min.css" rel="stylesheet" media="screen">
<link href="assets/styles.css" rel="stylesheet" media="screen">
<!-- HTML5 shim, for IE6-8 support of HTML5 elements -->
<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
</head>
<body>
<div class="navbar navbar-fixed-top">
<div class="navbar-inner">
<div class="container-fluid">
<a class="btn btn-navbar" data-toggle="collapse" data-target=".nav-collapse"> <span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</a>
<a class="brand" href="#">Member Home</a>
<div class="nav-collapse collapse">
<ul class="nav pull-right">
<li class="dropdown">
<a href="#" role="button" class="dropdown-toggle" data-toggle="dropdown"> <i class="icon-user"></i>
<?php echo $row['userEmail']; ?> <i class="caret"></i>
</a>
<ul class="dropdown-menu">
<li>
<a tabindex="-1" href="logout.php">Logout</a>
</li>
</ul>
</li>
</ul>
<ul class="nav">
<li class="active">
<a href="http://www.codingcage.com/">Coding Cage</a>
</li>
<li class="dropdown">
<a href="#" data-toggle="dropdown" class="dropdown-toggle">Tutorials <b class="caret"></b>
</a>
<ul class="dropdown-menu" id="menu1">
<li><a href="http://www.codingcage.com/search/label/PHP OOP">PHP OOP</a></li>
<li><a href="http://www.codingcage.com/search/label/PDO">PHP PDO</a></li>
<li><a href="http://www.codingcage.com/search/label/jQuery">jQuery</a></li>
<li><a href="http://www.codingcage.com/search/label/Bootstrap">Bootstrap</a></li>
<li><a href="http://www.codingcage.com/search/label/CRUD">CRUD</a></li>
</ul>
</li>
</ul>
</div>
<!--/.nav-collapse -->
</div>
</div>
</div>
<!--/.fluid-container-->
<script src="bootstrap/js/jquery-1.9.1.min.js"></script>
<script src="bootstrap/js/bootstrap.min.js"></script>
<script src="assets/scripts.js"></script>
</body>
</html>
logout.php
simple script and code to logout current logged in user and redirects user to "index.php" login page.<?php
session_start();
require_once 'class.user.php';
$user = new USER();
if(!$user->is_logged_in())
{
$user->redirect('index.php');
}
if($user->is_logged_in()!="")
{
$user->logout();
$user->redirect('index.php');
}
?>
fpass.php | Forgot Password
if user forgets password then this page will ask verified users email and send password reset link to his email account to reset his password and redirects to "resetpass.php" with QueryString id="something&code=something", this will update tokenCode field in database table and in "resetpass.php" it will match the code then user finally can reset password.<?php
session_start();
require_once 'class.user.php';
$user = new USER();
if($user->is_logged_in()!="")
{
$user->redirect('home.php');
}
if(isset($_POST['btn-submit']))
{
$email = $_POST['txtemail'];
$stmt = $user->runQuery("SELECT userID FROM tbl_users WHERE userEmail=:email LIMIT 1");
$stmt->execute(array(":email"=>$email));
$row = $stmt->fetch(PDO::FETCH_ASSOC);
if($stmt->rowCount() == 1)
{
$id = base64_encode($row['userID']);
$code = md5(uniqid(rand()));
$stmt = $user->runQuery("UPDATE tbl_users SET tokenCode=:token WHERE userEmail=:email");
$stmt->execute(array(":token"=>$code,"email"=>$email));
$message= "
Hello , $email
<br /><br />
We got requested to reset your password, if you do this then just click the following link to reset your password, if not just ignore this email,
<br /><br />
Click Following Link To Reset Your Password
<br /><br />
<a href='http://www.SITEURL.com/resetpass.php?id=$id&code=$code'>click here to reset your password</a>
<br /><br />
thank you :)
";
$subject = "Password Reset";
$user->send_mail($email,$message,$subject);
$msg = "<div class='alert alert-success'>
<button class='close' data-dismiss='alert'>×</button>
We've sent an email to $email.
Please click on the password reset link in the email to generate new password.
</div>";
}
else
{
$msg = "<div class='alert alert-danger'>
<button class='close' data-dismiss='alert'>×</button>
<strong>Sorry!</strong> this email not found.
</div>";
}
}
?>
<!DOCTYPE html>
<html>
<head>
<title>Forgot Password</title>
<!-- Bootstrap -->
<link href="bootstrap/css/bootstrap.min.css" rel="stylesheet" media="screen">
<link href="bootstrap/css/bootstrap-responsive.min.css" rel="stylesheet" media="screen">
<link href="assets/styles.css" rel="stylesheet" media="screen">
<!-- HTML5 shim, for IE6-8 support of HTML5 elements -->
<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
</head>
<body id="login">
<div class="container">
<form class="form-signin" method="post">
<h2 class="form-signin-heading">Forgot Password</h2><hr />
<?php
if(isset($msg))
{
echo $msg;
}
else
{
?>
<div class='alert alert-info'>
Please enter your email address. You will receive a link to create a new password via email.!
</div>
<?php
}
?>
<input type="email" class="input-block-level" placeholder="Email address" name="txtemail" required />
<hr />
<button class="btn btn-danger btn-primary" type="submit" name="btn-submit">Generate new Password</button>
</form>
</div> <!-- /container -->
<script src="bootstrap/js/jquery-1.9.1.min.js"></script>
<script src="bootstrap/js/bootstrap.min.js"></script>
</body>
</html>
resetpass.php
this page will be redirected from user email account to reset password, as in the QueryString there is id and code and based on code a user can reset his forgotten password, if a QueryString is set then this page can be opened. after resetting password user will be redirected to the login page.<?php
require_once 'class.user.php';
$user = new USER();
if(empty($_GET['id']) && empty($_GET['code']))
{
$user->redirect('index.php');
}
if(isset($_GET['id']) && isset($_GET['code']))
{
$id = base64_decode($_GET['id']);
$code = $_GET['code'];
$stmt = $user->runQuery("SELECT * FROM tbl_users WHERE userID=:uid AND tokenCode=:token");
$stmt->execute(array(":uid"=>$id,":token"=>$code));
$rows = $stmt->fetch(PDO::FETCH_ASSOC);
if($stmt->rowCount() == 1)
{
if(isset($_POST['btn-reset-pass']))
{
$pass = $_POST['pass'];
$cpass = $_POST['confirm-pass'];
if($cpass!==$pass)
{
$msg = "<div class='alert alert-block'>
<button class='close' data-dismiss='alert'>×</button>
<strong>Sorry!</strong> Password Doesn't match.
</div>";
}
else
{
$stmt = $user->runQuery("UPDATE tbl_users SET userPass=:upass WHERE userID=:uid");
$stmt->execute(array(":upass"=>$cpass,":uid"=>$rows['userID']));
$msg = "<div class='alert alert-success'>
<button class='close' data-dismiss='alert'>×</button>
Password Changed.
</div>";
header("refresh:5;index.php");
}
}
}
else
{
exit;
}
}
?>
<!DOCTYPE html>
<html>
<head>
<title>Password Reset</title>
<!-- Bootstrap -->
<link href="bootstrap/css/bootstrap.min.css" rel="stylesheet" media="screen">
<link href="bootstrap/css/bootstrap-responsive.min.css" rel="stylesheet" media="screen">
<link href="assets/styles.css" rel="stylesheet" media="screen">
<!-- HTML5 shim, for IE6-8 support of HTML5 elements -->
<!--[if lt IE 9]>
<script src="http://html5shim.googlecode.com/svn/trunk/html5.js"></script>
<![endif]-->
</head>
<body id="login">
<div class="container">
<div class='alert alert-success'>
<strong>Hello !</strong> <?php echo $rows['userName'] ?> you are here to reset your forgetton password.
</div>
<form class="form-signin" method="post">
<h3 class="form-signin-heading">Password Reset.</h3><hr />
<?php
if(isset($msg))
{
echo $msg;
}
?>
<input type="password" class="input-block-level" placeholder="New Password" name="pass" required />
<input type="password" class="input-block-level" placeholder="Confirm New Password" name="confirm-pass" required />
<hr />
<button class="btn btn-large btn-primary" type="submit" name="btn-reset-pass">Reset Your Password</button>
</form>
</div> <!-- /container -->
<script src="bootstrap/js/jquery-1.9.1.min.js"></script>
<script src="bootstrap/js/bootstrap.min.js"></script>
</body>
</html>
That's it
we have created here login & registration script with email verification along with forgot password recovery feature, we already have a login and registrations tutorials but i have to decide to post email verification and forgot password tutorial after getting email requests from my readers so enjoy...
No comments:
Post a Comment