PHP user log-in and log-out
In this section, we'll go over how to create a user log-in system. We recommend checking out our lesson about a user registration system if you aren't sure how to start.
The code for this version will be written in a procedural method.
Requirements
Refer to the Get Started section to know what you need to use this tutorial. You must also have an understanding of HTML and how a web page is constructed.
We'll go through this assuming you know how to make an HTML form and use a MySQL database.
Prerequisites
To use this tutorial, we recommend that you use our other lesson, User registration, or something similar.
Contents
The MySQL database
To create this user registration app, we'll need a database. We will be using a MySQL database. Feel free to use any kind with which you are familiar as long as you can adapt our code to fit correctly.
We'll use the database created in our other lesson about user registration. This is the table we will be using to log in a user.
Table: users
Column | Type | Description |
---|---|---|
userID | INT (11) | This will be the primary key. It is a unique ID number assigned to each individual user. It should be set to increment automatically. |
Varchar (250) | This will hold the user's email address. They'll use this to log into your site. | |
password | Text | The user's password will be encrypted. |
salt | Int (11) | "salt" will be used to encrypt they user's password. |
isDeleted | Bool | A TRUE/FALSE value that will be used to tell if a user has canceld there account or has been blocked. |
timestamp | Timestamp | A time stamp, provided by the database, about time the account was created or last updated. |
If you've successfully done our other lesson, User registration, you should have rows in your table that look similar to this:
userID | Password | Salt | isDeleted | timestamp | |
---|---|---|---|---|---|
1 | user@website.com | alksjd98f7a3lkj23kjlafg135ge | 1611077481 | 0 | 2021-01-19 12:31:21 |
2 | user2@website.com | iooqiqur798gn3l523nkavf98u | 1611077783 | 0 | 2021-01-19 12:36:33 |
3 | user3@website.com | vx63iv73oulvkj456209v8vj34 | 1611078085 | 0 | 2021-01-19 12:41:45 |
We will create a log-in form, then compare the data submitted by the user against the rows in the database.
The HTML form
Create a PHP web page file with a form for your users to log in.
<html> <head> <title>Log in</title> </head> <body> <h1>Log in</h1> <form action="" method="post"> <p> <label for="email">Your email address</label> <br/> <input type="text" name="email" id="email" /> </p> <p> <label for="password">Your password</label> <br/> <input type="password" name="password" id="password" /> </p> <p> <button type="submit">Log in</button> </p> </form> </body> </html>
With that form, we'll be able to gather the user's email address and password. Leave the method="post"
so the user's submitted data won't be displayed in the URL. We're leaving the action=""
blank so the PHP can remain on just this page.

Beginning the PHP
The array $_POST
will hold the user's submitted information. It is a global variable and is available on the page whether the user has submitted the form or not. To prevent this from processing an empty $_POST
, we'll set up a simple if()
conditional about the HTML.
<?php // Did the user submit the form? if(!empty($_POST)){ // Process the form } ?> <html> [...]
The $_POST
is empty and/or NULL by default. That conditional will prevent anything from happening unless the form is submitted. Next, we'll take the variables out of the $_POST
array for use.
Getting the $_POST variables
Once the form is submitted, the $_POST
array will be holding the variables from it. The form we have will carry two variables, $_POST['email']
and $_POST['password']
.
<?php // Did the user submit the form? if(!empty($_POST)){ // Process the form $email = $_POST['email']; $password = $_POST['password']; } ?> <html> [...]
Now we have the variables from the $_POST
array in separte variables. We could work through the whole process with them in the $_POST
array, but htis simplifies it. Next, let's make sure both fields are valid.
Validating the form fields
We want to avoid bad data as often as possible. So, let's make sure the user has submitted real, valid data.
PHP has two functions that we will be using. We'll use the function trim()
to see if the password was left blank or with only spaces. We'll use function filter_var()
to make sure the email address is formatted like an email address. We'll use a conditional if()
to judge whether or not the process should continue.
<?php // Did the user submit the form? if(!empty($_POST)){ // Process the form $email = $_POST['email']; $password = $_POST['password']; $check_password = trim($password); $check_email = filter_var($email, FILTER_VALIDATE_EMAIL); if($check_password != '' && $check_email !== FALSE){ // Continue the process } else { $error = 'Please provide a valid email address and password.'; } } ?> <html> [...]
The function trim()
removes any spaces at the start and end of the string in $password
. The function filter_var
, when told to FILTER_VALIDATE_EMAIL
, makes sure the string $email
looks like an email address. Note: different server settings might handle filter_var
differently. Some settings consider user@website
to be a valid address, while others consider user@website.com
to be valid.
Notice the variable, $error
. We'll use that later on to tell the user something went wrong. If everything went well, we'll get started with a connection to the database.
Connecting with the database
If the user's email address and password checked out, let's connect to the database and prepare to log in the user. We'll use the PHP built-in class MySQLi
to do it. Let's take a look into the if()
conditional that approved the email address and password.
if($check_password != '' && $check_email !== FALSE){ // Continue the process // What's the address of your database? $database_host = 'localhost'; // What's the username to connect? $database_user = 'root'; // What's the password for that user? $database_password = 'password'; // What's the name of the database? $database = 'social'; // User the MySQLi class to connect to database $mysqli = new mysqli($database_host, $database_user, $database_password, $database); $email = $mysqli->real_escape_string($email); $password = $mysqli->real_escape_string($password); // Always close the database connection $mysqli->close(); }
Once we had a connection to the database, we were able to use a function built into the class MySQLi
, real_escape_string()
. That function analyzed the strings and cleaned them up, if necessary, to protect the database from queries a user might be sending. Even though we validated the username and password, We should still sanitize them.
Getting the user information
Now that we know the user has submitted valid data, we want to compare it against the info in the database. We'll query for information about the user depending on the email address they submitted.
if($check_password != '' && $check_email !== FALSE){ /* Database connection stuff */ $sql = "SELECT * FROM users WHERE email='" . $email . "' AND isDeleted!=1"; $query = $mysqli->query($sql); $user = $query->fetch_assoc(); if(isset($user['userID'])){ // Continue logging in the user } else { $error = 'Incorrect log-in information.'; } // Always close the database connection $mysqli->close(); }
The query is asking for all information about a user with an email address matching the one submitted that has not beed deleted. Then, we're using the MySQLi
class function, fetch_assoc()
, to get that information into an array.
The variable, $user
, is now an array containing all the information about the user, such as their password, timestamp, etc. If you want to see what is in $user
, enter print_r($user);
under the variable. The array looks similar to this:
Array ( [userID] => 1 [email] => user@website.com [password] => alksjd98f7a3lkj23kjlafg135ge [salt] => 1408705391 [isDeleted] => [timestamp] => 2014-08-22 07:03:11 )
The conditional statement that follows the fetch_assoc()
function helps determine if a user has been found. If no user has been found, we've prepared an error message to be displayed on the user's screen.
If the query found a user, we'll need to compare the password they submitted again the one stored in the database.
Comparing the passwords
In a different lesson, User registration, we went over a way to encrypt the user's password by salting it with another variable. We stored the salt
in the database next to the encrypted password. Let's attach the salt
to the password the user submitted, encrypt it, and then compare it against the encrypted password in the database.
To get to the stored salt
, we need to use $user['salt']
. To get to the stored password, we need to use $user['password']
.
if($check_password != '' && $check_email !== FALSE){ /* Database connection stuff Table query */ $user = $query->fetch_assoc(); if(isset($user['userID'])){ // Continue logging in the user $salt = $user['salt']; $encrypt_password = sha1($password . $salt); if($encrypt_password == $user['password']){ // Password matches. Continue loggin in. } else { $error = 'Incorrect log-in information.'; } } else { $error = 'Incorrect log-in information.'; } // Always close the database connection $mysqli->close(); }
Just as we did in a different lesson, User registration, encrypted the password the user submitted by salting it with another variable, the one provided by the database, and compared the encrypted version.
If the encrypted versions match, the user is valid and we should allow them in to do whatever it is we have been protecting.
Logging in the user
To keep a user logged-in, we'll use PHP's built-in array, $_SESSION
. The array $_SESSION
can hold anything; numbers; letters; arrays; boolean values. Since we need the $_SESSION
at the moment for keeping a user logged in, we'll use their userID
and their email
variables. Their userID
is available thanks to the query we operated.
if($encrypt_password == $user['password']){ // Password matches. Continue loggin in. // Start a session to recognize the user session_start(); $_SESSION['userID'] = $user['userID']; $_SESSION['email'] = $email; // Send the new user somewhere header('Location: /some-other-page.php'); } else { $error = 'Incorrect log-in information.'; }
Notice the header()
function. This function will send the user to another website or another page. Since this is a registration tool, it would send the user to their profile, an account management page, anywhere. Note: always have a space between Location: /some-other-page.php'
. If you don't, it causes an error in some versions of IE.
What if there were errors?
The user may have submitted invalid data, or their password may not have matched that in the database. Let's use the $error
variable we created to deliver the message on the web page.
<html> <head> <title>Log in</title> </head> <body> <h1>Log in</h1> <?php if(isset($error)): ?><?php echo $error; ?>
<?php endif; ?> <form action="" method="post"> <p> <label for="email">Your email address</label> <br/> <input type="text" name="email" id="email" /> </p> <p> <label for="password">Your password</label> <br/> <input type="password" name="password" id="password" /> </p> <p> <button type="submit">Log in</button> </p> </form> </body> </html>

How to keep a user logged in
In our demonstration about when a user logs in successfully, a pair of $_SESSION
variables are created to recognize them: userID
and email
. To keep them logged in, we must declare session_start()
on every page that we want to involve their user values.
For example, if you have a profile page or a message inbox page, we'll want to allow only logged-in users to see those pages. So, we need to make sure their $_SESSION
variables exist.
In the files you want to include the $_SESSION
array, or in files included within them at the very top, use this code:
<?php session_start(); if(!isset($_SESSION['userID']) || !isset($_SESSION['email'])){ header('Location: /login.php'); } ?>
With the code above, we are verifying whether or not the user has logged in. If either of the $_SESSION
variables does not exist, the user must not be logged in. So, we'll use header()
to send them to our log-in page. In this example, our log-in page is in the root of our website. It's address would be website.com/login.php
. Make sure you are aiming the Location
address correctly.
Logging out a user
You may want to provide a way for your users to log out. To do so, we need to get rid of the $_SESSION
variables that were allowing them to stay logged in. Create a file called logout.php
. This code is all you will need to log a user out:
<?php session_start(); $_SESSION['userID'] = NULL; $_SESSION['email'] = NULL; unset($_SESSION); session_destroy(); header('Location: /index.php'); ?>
Even though we are trying to log a user out, we must first continue the session with session_start()
to make the variable available. Then, we want to change the variables from their normal values to NULL
. We'll use the PHP function unset()
to get rid of the $_SESSION
variables and session_destroy()
to eliminate the $_SESSION
entirely. Lastly, we'll use header()
to redirect the user elsewhere.
All the log-in code
<?php // Did the user submit the form? if(!empty($_POST)){ // Process the form $email = $_POST['email']; $password = $_POST['password']; $check_password = trim($password); $check_email = filter_var($email, FILTER_VALIDATE_EMAIL); if($check_password != '' && $check_email !== FALSE){ // Continue the process // What's the address of your database? $database_host = 'localhost'; // What's the username to connect? $database_user = 'root'; // What's the password for that user? $database_password = 'password'; // What's the name of the database? $database = 'social'; // User the MySQLi class to connect to database $mysqli = new mysqli($database_host, $database_user, $database_password, $database); $email = $mysqli->real_escape_string($email); $password = $mysqli->real_escape_string($password); $sql = "SELECT * FROM users WHERE email='" . $email . "' AND isDeleted!=1"; $query = $mysqli->query($sql); $user = $query->fetch_assoc(); if(isset($user['userID'])){ // Continue logging in the user $salt = $user['salt']; $encrypt_password = sha1($password . $salt); if($encrypt_password == $user['password']){ // Password matches. Continue loggin in. // Start a session to recognize the user session_start(); $_SESSION['userID'] = $user['userID']; $_SESSION['email'] = $email; // Send the new user somewhere header('Location: /some-other-page.php'); } else { $error = 'Incorrect log-in information.'; } } else { $error = 'Incorrect log-in information.'; } // Always close the database connection $mysqli->close(); } else { $error = 'Please provide a valid email address and password.'; } } ?> <html> <head> <title>Log in</title> </head> <body> <h1>Log in</h1> <?php if(isset($error)): ?><?php echo $error; ?>
<?php endif; ?> <form action="" method="post"> <p> <label for="email">Your email address</label> <br/> <input type="text" name="email" id="email" /> </p> <p> <label for="password">Your password</label> <br/> <input type="password" name="password" id="password" /> </p> <p> <button type="submit">Log in</button> </p> </form> </body> </html>
Contact us
Questions or problems? Want to contribute to this tutorial or others?