/    Sign up×
Community /Pin to ProfileBookmark

Why password_verify Not Passing The Verification ?

Php Programmers,

Why does the password_verify keep failing ? I checked the myql tbl column name (passwords) and there is no typo.
The $query is able to get the $result querying the db ($result = true).
The password_verify is in this format:

password_verify(User Input Password, Password found in D?.

[code]
if (password_verify($password, (string)$row[‘passwords’]))
[/code]

I type casted the 2nd param of password_verify because it was giving error before:

Fatal error: Uncaught TypeError: password_verify() expects parameter 2 to be string, null given in /home/user/public_html/php/login.php:64 Stack trace: #0 /home/user/public_html/php/login.php(64): password_verify(‘password’, NULL) #1 {main} thrown in /home/luser/public_html/php/login.php on line 64

After type casting the error is gone. But new problem. I get echoed that, the password_verify failed. I created a condition ith the echo to echo that if the password_verify fails:

[code]
if (password_verify($password, $row[‘passwords’]))
{
$_SESSION[“user”] = $username;
header(“location:home.php?user=$username”);
}
else
{
echo “‘password_verify’ function failed!”;
exit();
[/code]

}

Here, the full code:

[code]
<?php

/*
ERROR HANDLING
*/
declare(strict_types=1);
ini_set(‘display_errors’, ‘1’);
ini_set(‘display_startup_errors’, ‘1’);
error_reporting(E_ALL);
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);

include ‘config.php’;

// check if user is already logged in
if (is_logged() === true)
{
//Redirect user to homepage page after 5 seconds.
header(“refresh:5;url=home.php”);
exit; //
}

if ($_SERVER[‘REQUEST_METHOD’] == “POST”)
{
if (isset($_POST[“login_username”]) && isset($_POST[“login_password”]))
{
$username = trim($_POST[“login_username”]); //
$password = trim($_POST[“login_password”]); //
$hashed_password = password_hash($_POST[“login_password”], PASSWORD_DEFAULT);

//Select Username or Email to check against Mysql DB if they are already registered or not.

$stmt = mysqli_stmt_init($conn);

$stmt = mysqli_prepare($conn, “SELECT ids, usernames, passwords, emails, accounts_activations_statuses FROM users WHERE usernames = ?”);
mysqli_stmt_bind_param($stmt, ‘s’, $email);
mysqli_stmt_execute($stmt);
$result = mysqli_stmt_bind_result($stmt, $db_id, $db_username, $db_password, $db_email, $db_account_activation_status); // … this line. But not both.
$row = mysqli_stmt_fetch($stmt);

printf(“%s (%s)n”,$row[“usernames”],$row[“passwords”]);
echo “var_dump(result)”;var_dump($result)?><br><?php //On experiment, this showing as: () bool(true);

if ($result == false)
{
echo “Incorrect Login Details!”;
echo “$result == false”;
exit();
}
elseif ($row[‘accounts_activations_statuses’] == ‘0’)
{
{
echo “You have not activated your account! Check your email for instructions.”;
exit();
}
}
else
{
echo ‘$result == True’; //for debugging purpose
echo “‘Hashed Password from Data Base:’ $db_password<br>”; //for debugging purpose
}

if (password_verify($password, $row[‘passwords’]))
{
$_SESSION[“user”] = $username;
header(“location:home.php?user=$username”);
}
else
{
echo “‘password_verify’ function failed!”;
exit();
}
}
}

?>

<!DOCTYPE html>
<html>
<head>
<title><?php $site_name?> Login Page</title>
<meta charset=”utf-8″>
</head>
<body>
<div class = “container”>
<form method=”post” action=””>
<center><h3><?php $site_name ?> Login Form</h3></center>
<div class=”text-danger”>
<div class=”form-group”>
<center><label>Username:</label>
<input type=”text” placeholder=”Enter Username” name=”login_username” value=””</center>
</div>
<div class=”form-group”>
<center><label>Password:</label>
<input type=”password” placeholder=”Enter password” name=”login_password” value=””></center>
</div>
<div class=”form-group”>
<center><input type=”submit” name=”login_submit” value=”Login” class=”button button-success” /></center>
</div>
</form>
</div>
</body>
</html>

[/code]

What is causing the password_verify to fail the verification ?

to post a comment
PHP

24 Comments(s)

Copy linkTweet thisAlerts:
@ginerjmSep 20.2017 — What type is your password column? You definitely don't need the typecast so remove that. AND - how did you create the table's password value? Did you use the password_hash function?
Copy linkTweet thisAlerts:
@NogDogSep 20.2017 — Firstly, checking if $result is true/false is meaningless, as it will always be true if your code is bug-free, and likely always false if not. Similarly, mysqli_stmt_fetch() will return true if it found a result row, otherwise false. You instead need to check the value bound to $db_password to see if it's correct. So it might be something like:
[code=php]
if($row && password_verify($password, $db_password)) {
// good to go...
}
[/code]
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 20.2017 — Firstly, checking if $result is true/false is meaningless, as it will always be true if your code is bug-free, and likely always false if not. Similarly, mysqli_stmt_fetch() will return true if it found a result row, otherwise false. You instead need to check the value bound to $db_password to see if it's correct. So it might be something like:
[code=php]
if($row && password_verify($password, $db_password)) {
// good to go...
}
[/code]
[/QUOTE]


Ok, I did like you suggested. Tried these but same result. No luck.

<i>
</i> if($row &amp;&amp; password_verify($password, $db_password))
{
$_SESSION["user"] = $username;
header("location:home.php?user=$username");
}
else
{
echo "'password_verify' function failed!";
exit();
}


<i>
</i>if($row &amp;&amp; password_verify($password, $row['passwords']))
{
$_SESSION["user"] = $username;
header("location:home.php?user=$username");
}
else
{
echo "'password_verify' function failed!";
exit();
}
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 20.2017 — What type is your password column? You definitely don't need the typecast so remove that. AND - how did you create the table's password value? Did you use the password_hash function?[/QUOTE]

[ATTACH]17573[/ATTACH]

[ATTACH]17575[/ATTACH]

Look at the imgs above to see my "passwords" column type and the hash.

Yes, I used hash to create the password via the registration.php.

I am including the registration.php below so you can see ho the hash was created.

[canned-message]attachments-removed-during-migration[/canned-message]
Copy linkTweet thisAlerts:
@NogDogSep 20.2017 — Wait a second, you define $username from the form input, but then you search the DB for $email. Where does that come from?

Make sure you have all error-reporting turned on and are catching things like unset variables.
[code=php]
<?php
ini_set('display_errors', true); // set to false in production
error_reporting(E_ALL);

// rest of script
[/code]
Copy linkTweet thisAlerts:
@NogDogSep 20.2017 — totally untested, but it should be possible to trim it down quite a bit to something like this:
[code=php]
if ($_SERVER['REQUEST_METHOD'] == "POST") // not really needed since you're checking $_POST
{
if (isset($_POST["login_username"]) && isset($_POST["login_password"])) {
$username = trim($_POST["login_username"]); //
$password = trim($_POST["login_password"]); //
$hashed_password = password_hash($_POST["login_password"], PASSWORD_DEFAULT);
$sql = "
SELECT
ids,
usernames,
passwords,
emails,
accounts_activations_statuses
FROM users
WHERE usernames = ?
AND passwords = ?
";
$stmt = mysqli_prepare($conn, $sql);
mysqli_stmt_bind_param($stmt, 'ss', $username, $hashed_password);
mysqli_stmt_execute($stmt);
if (mysqli_stmt_num_rows($stmt)) {
// found a match, we're good to go...
} else {
// whatever you do when user/password not found...
}
}
}
[/code]
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 21.2017 — totally untested, but it should be possible to trim it down quite a bit to something like this:
[code=php]
if ($_SERVER['REQUEST_METHOD'] == "POST") // not really needed since you're checking $_POST
{
if (isset($_POST["login_username"]) && isset($_POST["login_password"])) {
$username = trim($_POST["login_username"]); //
$password = trim($_POST["login_password"]); //
$hashed_password = password_hash($_POST["login_password"], PASSWORD_DEFAULT);
$sql = "
SELECT
ids,
usernames,
passwords,
emails,
accounts_activations_statuses
FROM users
WHERE usernames = ?
AND passwords = ?
";
$stmt = mysqli_prepare($conn, $sql);
mysqli_stmt_bind_param($stmt, 'ss', $username, $hashed_password);
mysqli_stmt_execute($stmt);
if (mysqli_stmt_num_rows($stmt)) {
// found a match, we're good to go...
} else {
// whatever you do when user/password not found...
}
}
}
[/code]
[/QUOTE]



Thank you for your input NogDog! I shall try testing your provided solution soon.

As for why I did not query for the Password at the beginning alongside the Username and why I am querying for the Username/Email on the 1st attempt and Password on the 2nd attempt. Well if you read posts 13 & 17 (by Psycho) then you might understand why.

https://forums.phpfreaks.com/topic/304950-fatal-error-uncaught-mysqli-sql-exception/

Infact, read the original post there first or you won't understand the full context of the discussion. Let me know if you agree or disagree with Psycho there. I've got feed-back now that it is bad advice and internet is full of it. But, I want your opinion here too.

I agree not all advice found on the internet is sound. I have found this true when Users at phpfreaks.com and maybe codingforums started pointing out that the sample codes from stackoverflow.com are buggy.

Buggy codes found here:

https://stackoverflow.com/questions/32522192/check-if-an-array-element-is-in-a-string

Anyway, I started believing Psycho in phpfreaks.com (not sure if he is right or wrong but let's see what pros (you included) say in both this forum and others) and that is why my current code is structured to query the Username/Email & Password in 2 separate attempts after I failed to get it to query it in a single attempt after adding PREP STMTS.

I did manage it in a single attempt on the NON-PREP STMT once upon a time. But, when I started adding the PREP STMT the trouble started.

If you check the 1st post there then you will see an attempt was made to check for Username/Email & Password on 1st attempt but it failed. And so, my current code took the turn towards Pycho's advice to make the query in 2 separate attempts instead.

Finally, don't forget to give your professional opinion on how the code should be where on the 1st attempt the query checks if there is a Username/Email & Password match or not..

Anyone else are welcome too!

AIM:

I am trying to create a Login system where the user can login to his account by either typing his Username or Email and Password. Like you do with your Youtube account.

Remember this showed error:

<i>
</i>if (password_verify($password, $row['passwords']))


Fatal error: Uncaught TypeError: password_verify() expects parameter 2 to be string, null given in C:xampphtdocse_idlogin.php:77 Stack trace: #0 C:xampphtdocse_idlogin.php(77): password_verify('password', NULL) #1 {main} thrown in C:xampphtdocse_idlogin.php on line 77

Therefore, I switched this:

password_verify($password, $row['passwords']);

To this:

password_verify($password, (string)$row['passwords']);

And this error is gone:

"Fatal error: Uncaught TypeError: password_verify() expects parameter 2 to be string, null given in C:xampphtdocse_idlogin.php:77

Stack trace:

#0 C:xampphtdocse_idlogin.php(77): password_verify('password', NULL)

#1 {main} thrown in C:xampphtdocse_idlogin.php on line 77".

But should the code really be like that by Type Casting the password_verify 2nd param ? Others reply: No!

However, no-one has managed to provide a proper solution yet which I have tested and found positive. I have been given 2 samples to test and so I will keep you guys updated. Saying all this, I do not want to simply rely on the 2 samples as they may not work. And so, do give your on professional inputs on this issue too.

AIM:

I am trying to create a Login system where the user can login to his account by either typing his Username or Email and Password. Like you do with your Youtube account.

Once again, thanks!
Copy linkTweet thisAlerts:
@rootSep 22.2017 — This isn't a case of someone coming up with a solution, what you should be finding out what the [B]$row['passwords'][/B] contains, are you even sure that the return value is returning a string?
Copy linkTweet thisAlerts:
@cluelessPHPSep 23.2017 — Fifty characters seems a little small for a password field, I'll admit I only skimmed the thread but did you try increasing your password column from 50 to say 100?
Copy linkTweet thisAlerts:
@NogDogSep 23.2017 — Fifty characters seems a little small for a password field, I'll admit I only skimmed the thread but did you try increasing your password column from 50 to say 100?[/QUOTE]

Nice call:
<i>
</i>$ php -a
Interactive shell

php &gt; $hashed = password_hash("rasmuslerdorf", PASSWORD_DEFAULT);
php &gt; $size = strlen($hashed);
php &gt; echo $size.PHP_EOL;
60
php &gt;
Copy linkTweet thisAlerts:
@cluelessPHPSep 23.2017 — More a combination of past traumatic experiences and some good teachers ?
Copy linkTweet thisAlerts:
@rootSep 24.2017 — I would say that your hash field should be larger, like big enough to take the largest producible hash string from a hashing function.

That way you can change a hashing system without too much consequence (as long as existing hashes are updated as and when needed of course) you will ensure that the hash can be held safely.
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 24.2017 — I would say that your hash field should be larger, like big enough to take the largest producible hash string from a hashing function.

That way you can change a hashing system without too much consequence (as long as existing hashes are updated as and when needed of course) you will ensure that the hash can be held safely.[/QUOTE]


How many digits would you suggest to be precise ?
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 24.2017 — Fifty characters seems a little small for a password field, I'll admit I only skimmed the thread but did you try increasing your password column from 50 to say 100?[/QUOTE]

I think you maybe right! Wisest thing I have heard about this case in a week out of all the forums I have been asking for help (21). And so far, only YOU mentioned about the size!!! Maybe the tbl column restriction to 50 digits is the problem. How many digits would you suggest to be precise ? I have tried many suggestions from many forums but none worked. Only got 2 suggested codes to test but I reckon you're spot on on the diagnosis!
Copy linkTweet thisAlerts:
@rootSep 24.2017 — How many digits would you suggest to be precise ?[/QUOTE]

If you google the question [B]Sting Hash Lengths[/B] you will get a typical result like... As the name implies, it's 512 bits, that is 64 bytes. But that's the hash, maybe you're wondering about a specific representation of that hash in string, as is commonly used, then it depends of the given representation. If you write the hash in hexa, then it will be 128 characters.[/quote]

So it is best to set the length of the field to a length that is going to be the longest length of the hashing system you are using, clearly it has been demonstrated that your current 50 chars worth is not enough as the system you are using is 60 chars, if you want to build in future proofing, then you can have a longer field length and consider 128 chars as the maximum length.
Copy linkTweet thisAlerts:
@NogDogSep 24.2017 — Note that there is no harm in setting the database column to a larger size than currently needed, just to be safe. If you make it a "varchar" or "character varying" type of column, it won't use any more actual disk/memory space than needed (plus a byte or three it needs to keep track of things).
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 25.2017 — Actually switching the column size to 255 did not work, either.
Copy linkTweet thisAlerts:
@NogDogSep 25.2017 — Did you repopulate the passwords in it after you resized it? (If not, then they're still truncated to 50 characters.)
Copy linkTweet thisAlerts:
@cluelessPHPSep 25.2017 — I think you maybe right! Wisest thing I have heard about this case in a week out of all the forums I have been asking for help (21). And so far, only YOU mentioned about the size!!! Maybe the tbl column restriction to 50 digits is the problem. How many digits would you suggest to be precise ? I have tried many suggestions from many forums but none worked. Only got 2 suggested codes to test but I reckon you're spot on on the diagnosis![/QUOTE]

255, although as Nogdog pointed out, don't forget to register a new account in your system the old passwords won't be stored correctly so it'll still show as being "wrong"
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 25.2017 — Did you repopulate the passwords in it after you resized it? (If not, then they're still truncated to 50 characters.)[/QUOTE]

255, although as Nogdog pointed out, don't forget to register a new account in your system the old passwords won't be stored correctly so it'll still show as being "wrong"[/QUOTE]


Thank you NogDog and thank you cluelessPhp!

Yes, repopulating the column now logs the user in. No more password_verify a fail.

Did you know, I posted this issue on 10-21 forums and so far no-one managed to figure-out that the size of the column was the issue. Not their fault as I never mentioned the size is 50 chars only. But someone here suspected I got the size wrong! Now, that is what I call "experience helps"!

Pitty, this forum does not allow us to vote or give thanks through icon clicks or give reps, etc. like other forums. ?
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 25.2017 — Firstly, checking if $result is true/false is meaningless, as it will always be true if your code is bug-free, and likely always false if not. Similarly, mysqli_stmt_fetch() will return true if it found a result row, otherwise false. You instead need to check the value bound to $db_password to see if it's correct. So it might be something like:
[code=php]
if($row && password_verify($password, $db_password)) {
// good to go...
}
[/code]
[/QUOTE]


After solving this issue I started to get $result == $true with the wrong password and was getting puzzled. Going through my code I could not find any errors. But then I remembered this post and looking back at it I have now recalled what you said.
Copy linkTweet thisAlerts:
@cluelessPHPSep 26.2017 — So if everything is ok, mark the thread resolved ?

Most of what I know comes from Noggdog and a few others over on phpbuilder, I'm the filthy spammer who lives in echo lounge :p
Copy linkTweet thisAlerts:
@uniqueideamanauthorSep 29.2017 — Thanks Guys! Continuing this project on a new thread.

How do I mark this thread as resolved ?
Copy linkTweet thisAlerts:
@TrainSep 29.2017 — Above you first post is Thread tools, in there you can mark it Resolved.
×

Success!

Help @uniqueideaman spread the word by sharing this article on Twitter...

Tweet This
Sign in
Forgot password?
Sign in with TwitchSign in with GithubCreate Account
about: ({
version: 0.1.9 BETA 5.12,
whats_new: community page,
up_next: more Davinci•003 tasks,
coming_soon: events calendar,
social: @webDeveloperHQ
});

legal: ({
terms: of use,
privacy: policy
});
changelog: (
version: 0.1.9,
notes: added community page

version: 0.1.8,
notes: added Davinci•003

version: 0.1.7,
notes: upvote answers to bounties

version: 0.1.6,
notes: article editor refresh
)...
recent_tips: (
tipper: @AriseFacilitySolutions09,
tipped: article
amount: 1000 SATS,

tipper: @Yussuf4331,
tipped: article
amount: 1000 SATS,

tipper: @darkwebsites540,
tipped: article
amount: 10 SATS,
)...