I'm hashing a password using sha1 and it is successfully storing it in the database, however i cannot seem to properly check to see if the sha1 matches one that is in the database. I've tried numerous different iterations of the below code, but nothing seems to work - what am i missing?
Registration
<?php
$username = $_POST['username'];
$password = $_POST['password'];
$passwordEncrypted = sha1($password);
try {
$result = $db->prepare("INSERT INTO
user_info
SET
username = :user,
pass = :pass
");
$result->bindParam(':user', $username);
$result->bindParam(':pass', $passwordEncrypted);
$result->execute();
}
catch (Exception $e) {
echo "Could not create username";
}
if (isset($_POST['submit'])) {
foreach ($_POST as $field) {
if (empty($field)) {
$fail = true;
}
else {
$continue = false;
}
}
if ($field == $fail) {
echo "You must enter a username and/or password";
}
else {
echo "Your account has been successfully created.";
}
}
?>
Logging in
<?php
$username = $_POST['username'];
$password = $_POST['password'];
$encryptedPassword = sha1($password);
try {
$result = $db->prepare("SELECT username, pass FROM user_info WHERE username = :user AND BINARY pass = :pass");
$result->bindParam(':user', $username);
$result->bindParam(':pass', $password);
$result->execute();
$rows = $result->fetch(PDO::FETCH_NUM);
}
catch (Exception $e) {
echo "Could not retrieve data from database";
exit();
}
if ($rows) {
session_start();
$_SESSION['username'] = $_POST['username'];
$_SESSION['loggedin'] = true;
include("inc/redirect.php");
} else {
if (isset($_POST['login'])) {
echo "Username or password incorrect (passwords are case sensitive)";
}
}
?>
You need to hash the password before querying the table, not afterwards:
<?php
$username = $_POST['username'];
$password = $_POST['password'];
$passwordEncrypted = sha1($password);
try {
$result = $db->prepare("SELECT username, pass FROM user_info WHERE username = :user AND BINARY pass = :pass");
$result->bindParam(':user', $username);
$result->bindParam(':pass', $passwordEncrypted);
$result->execute();
if ($result->fetch(PDO::FETCH_NUM)) {
session_start();
$_SESSION['username'] = $_POST['username'];
$_SESSION['loggedin'] = true;
include("inc/redirect.php");
} else {
if (isset($_POST['login'])) {
echo "Username or password incorrect (passwords are case sensitive)";
}
}
}
catch (Exception $e) {
echo "Could not retrieve data from database";
exit();
}
?>
Related
Password_verfiy is not working at all even if i hardcode the values of the password and the hash itself. It is working in a similar program but that program is without prameterized queries
<?php
include 'db.php';
session_start();
$numrows=null;
$hpass=null;
if ($_SERVER['REQUEST_METHOD']=='POST') {
if (!empty($_POST['user']) && !empty($_POST['pass'])) {
$username = $_POST['user'];
$password = $_POST['pass'];
$query = $connection->prepare('Select password from users where username=?');
$query->bind_param("s", $username);
$query->execute();
$query->bind_result($hpass);
while ($query->fetch()) {
$numrows++;
}
$query->close();
//$query->fetch();
//$numofrows=$query->num_rows;
if ($numrows == 1) {
if (password_verify($password, $hpass)) {
$_SESSION['login_user'] = $username;
header("location:todo.php");
} else {
header("location:1.php");
}
} else {
header("location:2.php");
}
}
else {
header("location:not.php");
}
}
$password = $_GET['pass'];
$hpass = password_hash($password, PASSWORD_DEFAULT);
$query=$connection->prepare("insert into users (username,password) values (?,?)");
$query->bind_param('ss',$name,$hpass);
if ($query->execute()) {
$query->close();
header('location:index.php');
} else {
header('location:not.php');
}
As recommended, I've been trying to secure my DB by using prepared statements. I have the following login that works perfectly that I'm trying to convert to prepared statement.
if(isset($_POST["Submit"])) {
$Username = mysqli_real_escape_string($con, $_POST["Username"]);
$get_hash_db = mysqli_query($con, "SELECT password FROM admin_registration WHERE username='$Username'");
$hash_db_data = mysqli_fetch_array($get_hash_db);
$hash = $hash_db_data['password'];
echo $hash;
if(password_verify($_POST['Password'], $hash)){
$Password = $hash;
}else {
$_SESSION["ErrorMessage"] = "Username or Password was incorrect";
Redirect_to("admin_login.php");
}
else {
$Found_Account = Login_Attempt($Username, $Password);
$_SESSION["User_Id"] = $Found_Account["id"];
$_SESSION["Username"] = $Found_Account["username"];
if($Found_Account) {
$_SESSION["SuccessMessage"] = "Login Successful! Welcome {$_SESSION["Username"]}";
Redirect_to("blog_admin/dashboard.php");
}else {
$_SESSION["ErrorMessage"] = "Invalid Username / Password";
Redirect_to("admin_login.php");
}
}
}
Below this it takes you into a Login_Attempt() function that look like this:
function Login_Attempt($Username, $Password) {
global $con;
$sql = "SELECT * FROM admin_registration WHERE username='$Username' AND password='$Password'";
$result = mysqli_query($con, $sql);
if($admin = mysqli_fetch_assoc($result)) {
return $admin;
}
else {
return null;
}
}
With my new prepared statements I never get past $_SESSION["ErrorMessage"] = "Invalid Username / Password"; Which tells me that I'm at least satisfying the condition $Password = $hash; Here is what I have.
if(isset($_POST["Submit"])) {
$Username = mysqli_real_escape_string($con, $_POST["Username"]);
$get_hash_db = mysqli_prepare($con, "SELECT password FROM admin_registration WHERE username = ? ");
mysqli_stmt_bind_param($get_hash_db, "s", $Username);
mysqli_stmt_execute($get_hash_db);
mysqli_stmt_bind_result($get_hash_db, $hash);
mysqli_stmt_fetch($get_hash_db);
echo $hash;
if(password_verify($_POST['Password'], $hash)){
$Password = $hash;
}else {
$_SESSION["ErrorMessage"] = "Username or Password was incorrect";
Redirect_to("admin_login.php");
}
Once I get passed this, I'm going through this:
else {
$Found_Account = Login_Attempt($Username, $Password);
$_SESSION["User_Id"] = $Found_Account["id"];
$_SESSION["Username"] = $Found_Account["username"];
if($Found_Account) {
$_SESSION["SuccessMessage"] = "Login Successful! Welcome {$_SESSION["Username"]}";
Redirect_to("blog_admin/dashboard.php");
}else {
$_SESSION["ErrorMessage"] = "Invalid Username / Password";
Redirect_to("admin_login.php");
}
}
}
but it always returns to $_SESSION["ErrorMessage"] = "Invalid Username / Password"; I'm not sure I understand why? Is it because I'm binding the param $Username, so function Login_Attempt($Username, $Password) does not handle correctly? Sorry, this is my first go at prepared statements so really struggling to understand.
ok so ive got password_hash working on one of my pages.
I'm wondering how would i apply password_verify to the following code:
function selectUser($conn, $username, $password)
{
$query = "SELECT username, password FROM login WHERE password = :password AND username = :username";
$stmt = $conn->prepare($query);
$stmt->bindValue(':username', $username);
$stmt->bindValue(':password', $password);
$stmt->execute();
if ($row = $stmt->fetch()) {
$_SESSION['username'] = $username;
$_SESSION['password'] = $password;
echo "Welcome, you are now logged in as " . $username;
return true;
}
else {
//echo "Your details were not found";
return false;
}
tried it myself and its been very confusing to me.
thank you
also got this:
if(!isset($_POST["Login"]))
{
header("Location:new-user.php");
}
$username=trim($_POST['username']);
$password=$_POST['password'];
$username= htmlspecialchars($username);
$validForm = true;
if (empty($_POST["username"]))
{
$validForm=false;
}
if (empty($_POST["password"]))
{
$validForm=false;
}
if (!$validForm) {
$error = "please ensure all fields are filled in";
include("add.php");
return false;
}
$conn=getConn();
$successLogin=selectUser($conn,$username,$password);
if($successLogin)
{
header( "Location: search.php" );
}else{
$error = "The details you have entered are incorrect";
include("add.php");
}
$conn=NULL; //close the connection
Update
also tried this: Knowing this doesnt work, tested with echo statements but still no luck
function hash_input() {
$password = "sfafgsd";
return $password = password_hash($_POST['password'], PASSWORD_BCRYPT);
}
function selectUser($conn, $username, $password)
{
$query = "SELECT password FROM login WHERE username = :username";
$stmt = $conn->prepare($query);
$stmt->bindValue(':username', $username);
$stmt->execute();
echo $username . " " . $password;
if ($row = $stmt->fetch(PDO::FETCH_ASSOC))
{
echo "WE MADE IT";
if(password_verify(hash_input($password), $row['password'])){
$_SESSION['username'] = $username;
echo "Welcome, you are now logged in as " . $username;
return true;
}
//echo "Your details were not found";
sleep(1);
return false;
}
else
{
//echo "Your details were not found";
return false;
}
}
The comments given by Mark cover the below exactly.
Order of events:
Send username to database and collect the hashed password from the row found.
run the password string given through password_verify to compare with the hashed value
return this result (true/false).
Celebrate. Have a coffeee or a tea.
There is no need to $_SESSION password data and this is a bad idea. Password data (hash or plaintext) should not be retained beyond this function call. If you do for some reason need to have a nonce value associated with this account/membership/login then this should be setup using a random string in its own column in the database.
Improved Function Code
function selectUser($conn, $username, $password)
{
$query = "SELECT password FROM login WHERE username = :username LIMIT 1";
$stmt = $conn->prepare($query);
$stmt->bindValue(':username', $username);
// $stmt->bindValue(':password', $password); NO Don't do this.
$stmt->execute();
if ($row = $stmt->fetch(PDO::FETCH_ASSOC))
{
if(password_verify($password,$row['password'])){
$_SESSION['username'] = $username;
// $_SESSION['password'] = $password; DO NOT DO THIS
echo "Welcome, you are now logged in as " . $username;
return true;
}
//bad password
//echo "Your details were not found";
sleep(1); // it can be a good idea to add a forced pause on
// password fail to discourage brute force cracking.
return false;
}
//echo "Your details were not found";
return false;
}
I'm creating a back end to my website and running into issues with the login user part.
The user registration into the database is made with the password_hash function using the code below:
UserReg.php :
<?php
require_once 'db.php';
$mysqli = new mysqli($host, $user, $password, $dbname);
if($mysqli -> connect_error) {
die($mysqli -> connect_erro);
}
$username = "userF";
$password = "somePass";
$token = password_hash("$password", PASSWORD_DEFAULT);
add_user($mysqli,$username, $token);
function add_user($mysqli,$username, $token) {
$query = $mysqli->prepare("INSERT INTO users(username, password) VALUES
(?,?)");
$query->bind_param('ss',$username, $token);
$query->execute();
$result = $query->get_result();
if(!$result) {
die($mysqli->error);
}
$query->close();
}
My login form skips to a blank page even when i insert my username and password. Doesn't even go to the login error message.
Login.php
<?php
include 'db.php';
$username = $_POST['user'];
$pwd = $_POST['password'];
$sql = "SELECT password FROM users WHERE username = ?";
$stmt = $mysqli->prepare($sql);
$stmt->execute();
$stmt->bind_result($pass);
while ($result = $stmt->num_rows()) {
if($stmt->password_verify($pwd, $result)) {
echo "Your username or password is incorrect";
} else {
header("Location: Menu.php");
}
}
What am i missing?
Appreciate your help.
I think you need to take a look at password_verify how it works.
$username = $_POST['user'];
$pwd = $_POST['password'];
$sql = "SELECT username, password FROM users WHERE username = ?";
$stmt = $mysqli->prepare($sql);
$stmt->bind_param('s', $username);
$stmt->execute();
$stmt->bind_result($username, $password);
$stmt->store_result();
if ($stmt->num_rows == 1) { //To check if the row exists
if ($stmt->fetch()) { //fetching the contents of the row
if (password_verify($pwd, $password)) {
$_SESSION['username'] = $username;
echo 'Success!';
exit();
} else {
echo "INVALID PASSWORD!";
}
}
} else {
echo "INVALID USERNAME";
}
$stmt->close();
My code works perfectly until the validation, When i enter wrong username it doesn't show Invaild Username or Password! but if i entered correct username but wrong password the message appears, How do i fix that?
if(isset($_POST['login'])){
$username = $_POST['username'];
$password = $_POST['password'];
try {
$sql = "SELECT * FROM users WHERE username=:username";
$stmt = $db->prepare($sql);
$stmt->execute(array(':username' => $username));
while($row = $stmt->fetch()){
$user_id = $row['user_id'];
$username = $row['username'];
$hash_password = $row['password'];
if(password_verify($password, $hash_password)){
$_SESSION['user_id'] = $user_id;
$_SESSION['username'] = $username;
} else {
die("Invaild Username or Password!");
}
}
}
catch(PDOException $e)
{
echo "An error occurred " . $e->getMessage();
}
}
if(isset($_POST['login'])){
$username = $_POST['username'];
$password = $_POST['password'];
try {
$sql = "SELECT * FROM users WHERE username=:username";
$stmt = $db->prepare($sql);
$res = $stmt->execute(array(':username' => $username));
if (!$res){
die("Invaild Username!");
}
while($row = $stmt->fetch()){
$user_id = $row['user_id'];
$username = $row['username'];
$hash_password = $row['password'];
if(password_verify($password, $hash_password)){
$_SESSION['user_id'] = $user_id;
$_SESSION['username'] = $username;
} else {
die("Invaild Username or Password!");
}
}
} catch(PDOException $e)
{
echo "An error occurred " . $e->getMessage();
}
}