3

So I have a Registration page and a Login page, the registration page works perfectly fine but the Login page doesnt seem to work and I cant seem to figure it out.

My database seems to be working as I am able to echo out the hashed password onto the page of the login, it seems to have something to do with password_verify()

Registration Page (Working)

<?php 
include("assets/includes/conn.php");

$user = $_POST['username'];
$pass = $_POST['pass'];
$cPass = $_POST['c-pass'];
$email = $_POST['email'];

$options = [
    'cost' => 11
];

if($pass == $cPass){

    $stmt = $conn->prepare("INSERT INTO users (username, pass, email) VALUES (?, ?, ?)");
    $stmt->bind_param("sss", $user, $h_p, $email);

    $user = $_POST['username'];
    $h_p = password_hash($pass, PASSWORD_DEFAULT, $options)."\n";
    $email = $_POST['email'];
    $stmt->execute();

    echo "Created";
    echo $h_p;
    $stmt->close();
    $conn->close();

}

Login Page (Not working)

<?php 
include("assets/includes/conn.php");

$username = $_POST['username'];
$password = $_POST['pass'];

$sql = "SELECT * FROM users WHERE username = '$username'";
$result = $conn->query($sql);

if ($result->num_rows == 1){
    $row = $result->fetch_assoc();
    $hash = $row['pass'];

    if(password_verify($password, $hash)){
        echo "Yes";
    } else {
        echo "No<br/>";
        echo "" . $hash . "<br/>";
        echo $password;

    }
}
Your Common Sense
  • 152,517
  • 33
  • 193
  • 313
  • I have a few thoughts as to why it's failing, but you can see the answer below. – Funk Forty Niner Feb 19 '17 at 04:21
  • Make sure you are [displaying errors](http://stackoverflow.com/questions/1053424/how-do-i-get-php-errors-to-display) in case you have a problem with variables not being properly sent to the script, etc. – Mike Feb 19 '17 at 04:26
  • @Mike The issue is I dont think it is an error, it is simply telling me that the password isnt correct even though it is, which might have something to do with it being hashed – Tristan Schlarman Feb 19 '17 at 04:29
  • @TristanSchlarman Don't assume anything. Maybe you're not correctly passing the values to the script. – Mike Feb 19 '17 at 04:32
  • Is there a unique index on `username` in your DB? – Mike Feb 19 '17 at 04:34
  • @Mike I even checked the hash when it was first created before it was put in the db and then compared it to the one that I got from `$hash = $row['pass']` and they are the same thing, and I made sure that my password was the same one that I registered with, I even made more than 1 account to make sure yet they all claim that the password is incorrect. – Tristan Schlarman Feb 19 '17 at 04:35
  • What is the column type of the password in your DB? – Mike Feb 19 '17 at 04:36
  • @Mike [link](http://imgur.com/a/gXGX1) That is what the table looks like might answer that – Tristan Schlarman Feb 19 '17 at 04:39
  • In both cases, do `var_dump($_POST);` to make sure the values are what you think they are. Also check for white space before and after the values. – Mike Feb 19 '17 at 04:44
  • @Mike Just checked, made a new account and saved the data and then logged in and compared them, same thing. Still not letting me in – Tristan Schlarman Feb 19 '17 at 04:52
  • Just checked *what* exactly? Did you do `var_dump`? – Mike Feb 19 '17 at 04:55
  • @Mike, yes sorry. I added `var_dump($_POST)` on both the registration and login pages – Tristan Schlarman Feb 19 '17 at 05:07
  • @TristanSchlarman No idea then. I don't see anything in the code itself that looks wrong. – Mike Feb 19 '17 at 06:52
  • What's the size of your password column? maybe it's too short and it's being truncated. from the php.net site, *Therefore, it is recommended to store the result in a database column that can expand beyond 60 characters (255 characters would be a good choice).* – Augwa Feb 19 '17 at 09:13
  • @Augwa It is set to Varchar(255) – Tristan Schlarman Feb 19 '17 at 15:43
  • 1
    *Welcome to Stack* @TristanSchlarman *cheers* – Funk Forty Niner Feb 19 '17 at 16:22

1 Answers1

7

The problem here is that the \n in:

$h_p = password_hash($pass, PASSWORD_DEFAULT, $options)."\n";
                                                         ^^

is (invisibly) adding a carriage return/linefeed at the end of your password/hash.

You can either remove it.

$h_p = password_hash($pass, PASSWORD_DEFAULT, $options);

or trim() it:

$h_p = password_hash($pass, PASSWORD_DEFAULT, $options)."\n";
$h_p = trim($h_p);

I honestly don't know why the manual on password_hash() doesn't make a mention about it and the usage of it for storing it in a database (or a file).

NOTE: What the docs haven't used here, was to assign a variable to the example, which is what was done in the question here. Some may think that using the example and assigning a variable to it will work; it won't; not for storing the hash and then verifying it after.

The example from the manual reads as:

echo password_hash("rasmuslerdorf", PASSWORD_DEFAULT)."\n";

But doing:

$var = password_hash("rasmuslerdorf", PASSWORD_DEFAULT)."\n";

will in fact (theoretically) contain a 61-length string (because of the concated linefeed character), instead of the intended 60 without the linefeed character.

  • So now you need to clear out your present hashes and start over with a new set of hashes.

Have a look at this sandbox code example

When run, it will output something like this:

$2y$10$494GPYzaynEkfYxE3wcAj.OtwBU3CCwTMXOHKbdJmOqwMXRmq6v1u
61

Just in case the URL's a 404 later on, here's the code for the above:

<?php
$foo = password_hash('mypass',  PASSWORD_DEFAULT)."\n";
echo $foo;
echo strlen($foo);

On an added note; you should also use a prepared statement for your SELECT just as you did for the INSERT; it's much safer.

Funk Forty Niner
  • 73,764
  • 15
  • 63
  • 131
  • @TristanSchlarman You're welcome. I was in the question last night but had to go to bed. I then revisited the question today to add my answer. It can now be marked as solved. – Funk Forty Niner Feb 19 '17 at 16:17
  • @TristanSchlarman just give that gray tick under the up/down arrows a click till it turns green; that's how the question is marked as solved/closed. – Funk Forty Niner Feb 19 '17 at 16:18
  • Interesting point there, I've done that before and never figured out why it messed up – Darren Feb 20 '17 at 07:15
  • @Darren I take it that the code you were using has now been changed; or did you end up using something else since that didn't contain the `\n`? – Funk Forty Niner Feb 20 '17 at 14:57