jh95 jh95 - 1 month ago 6
MySQL Question

Where in my code do I use $_GET['token']?

I am new to PHP, and I have been working on setting up a reset password script. The biggest problem I am having is storing the last part of the URL into the variable $token.

What exactly do I need to have to ensure that the $token variable gets set after the user clicks the 'Reset Password' button? As of now, after the button is clicked, $token is not set to anything and the url turns into "www.website.com/resetpassword.php" without the token at the end. Thanks for your help!

Here is my form code:

<form method="post" action="<?php echo htmlspecialchars($_SERVER['PHP_SELF']); ?>">
<div class="login_form">
<h2 style="font-family: Helvetica, sans-serif; font-size: 28pt; padding-top: 50px;">Forgot Password</h2>
<input type="email" name="email" placeholder="Your Email" maxlength="60"/>
<?php
if ( isset($sucMSG) ) {
echo '<span class="successful_registration">'.$sucMSG.'</span>';
}

if ( isset($matchError) ) {
echo '<span class="text-danger">'.$matchError.'</span>';
}

if ( isset($keyError) ) {
echo '<span class="text-danger">'.$keyError.'</span>';
}
?>

<br>
<input type="password" name="pass" placeholder="New Password" maxlength="255" />

<br>
<input type="password" name="cpass" placeholder="Confirm Password" maxlength="255" />

<input type="hidden" name="token" value= "random" />
<br>

<button type="submit" name="btn-reset">Reset Password</button>
<br><br><br>
<br><br><br><br><br><br>
</div>
</form>


Here is the PHP code:

if (isset($_POST['btn-reset'])){
// Gather the post data
$email = trim($_POST['email']);
$email = strip_tags($email);

$pass = trim($_POST['pass']);
$pass = strip_tags($pass);

$cpass = trim($_POST['cpass']);
$cpass = strip_tags($cpass);

$token = $_GET ['token'];

// Retrieve token from database
$stmt = $conn->prepare('SELECT token FROM token WHERE userEmail=? and NOW() < expire_date');
$stmt->bind_param('s', $email);
$stmt->execute();
$result = $stmt->get_result();
while ($row = $result->fetch_assoc()) {
$resetKey = $row['token'];
}

// Does the new reset key match the old one?
if ($resetKey == $token && isset($token)){
if ($pass == $cpass){
//hash and secure the password
$password = password_hash($pass, PASSWORD_DEFAULT);

// Update the user's password
$stmt = $conn->prepare('UPDATE user SET userPass = ? WHERE userEmail = ?');
$stmt->bind_param('s', $password);
$stmt->bind_param('s', $email);
$stmt->execute();
$conn = null;
$sucMSG = "Your password has been successfully reset.";
unset($email);
unset($pass);
unset($cpass);
unset($token);
unset($resetKey);
}
else
$matchError = "Your password's do not match.";
}
else
$keyError = "Your password reset key is invalid.";
}


Here is the PHP code from the previous step (forgotpassword.php):

if (isset($_POST['email'])){
$email = trim($_POST['email']);
$email = strip_tags($email);
$email = htmlspecialchars($email);

$stmt = $conn->prepare('SELECT * FROM user WHERE userEmail = ?');
$stmt->bind_param('s', $email);
$stmt->execute();
$result = $stmt->get_result();
$count=mysqli_num_rows($result);
// If the count is equal to one, we will send message other wise display an error message.
if($count==1){
$rows=mysqli_fetch_array($result);
$length = 55;
$token = bin2hex(random_bytes($length));//Creating Token
$create_date = date('Y-m-d H:i:s',strtotime("now"));
$expire_date = date('Y-m-d H:i:s',strtotime("+3 hours"));
//Using prepared statements to prevent SQL Injection
$stmt = $conn->prepare('INSERT INTO token (token, userEmail, create_date, expire_date) VALUES (?, ?, ?, ?)');
$stmt->bind_param('ssss', $token, $email, $create_date, $expire_date);
$stmt->execute();

// Create a url which we will direct them to reset their password
$pwrurl = 'https://www.domain.com/resetpassword.php?token='.$token;

$to = $rows['userEmail'];
//Details for sending E-mail
$from = "Company";
$body = "Company password recovery<br>
-----------------------------------------------<br><br>
Welcome to Company password recovery.
You can reset your password by clicking the following link: $pwrurl.<br><br>
Sincerely,<br><br>
Company";
$from = "support@company.com";
$subject = "Company Password recovered";
$headers1 = "From: $from\n";
$headers1 .= "Content-type: text/html;charset=iso-8859-1\r\n";
$headers1 .= "X-Priority: 1\r\n";
$headers1 .= "X-MSMail-Priority: High\r\n";
$headers1 .= "X-Mailer: Just My Server\r\n";
$sentmail = mail ( $to, $subject, $body, $headers1 );
}
elseif ($_POST['email'] == ""){
$fMSG = "Please enter an email address.";
} /*else {
if ($_POST['email'] != "")
$wMSG = "Cannot send password to your email address. Problem with sending mail.";
}*/
//If the message is sent successfully, display sucess message otherwise display an error message.
if($sentmail==1){
$sMSG = "Your Password Has Been Sent To Your Email Address.";
}
else{
if($_POST['email']!="")
$nMSG = "Cannot send password to your email address. Problem with sending mail.";
}
}

Answer

Note: I am posting as a community wiki, since no rep gain should come of this.

"Why don't you use the token as a hidden field rather than in query string, just a suggestion. – HSharma"

...

@Fred-ii- I don't know how to ping people, but the comment above this one has what ended up solving my problem. Thanks for your help! – jh95"

"@HSharma suggestion was what ultimately solved my problem. I added this to my html form <?php echo' <input type="hidden" name="token" value="'; if (isset($_GET['token'])) { echo $_GET['token']; } echo '" />' ?> and in my PHP script I added $token = $_POST ['token']; and now the token sets properly. Thanks everyone for your help!"

However and as I stated in comments:

"Since the length for it most probably surpasses the column's length, you need to increase it by ALTERing the column to be of a higher value in length, one big enough. You then need to clear the values from it and start over; you have no choice."

Comments