Header Location not working - php

I am creating a basic login and registration page and on completion of the change password form I want to redirect to changepassword.php?success. The redirected page works fine if entered into a browser, however when submitting the form it reloads the changepassword.php page instead of ?success and everything from the php code block down doesn't display (i.e. the form, column right and footer). Below is my changepassword.php code:
<!DOCTYPE html>
<html>
<?php
include ("storescripts/init.php");
protect_page();
include ("includes/overall/head.php");
if (empty($_POST) === false){
$required_fields = array('current_password','password','password_again');
foreach ($_POST as $key=>$value) {
if (empty($value) && in_array($key, $required_fields) == true) {
$errors[] = 'Fields marked with an asterisk are required';
break 1;
}
}
if ($_POST['current_password'] === $member_data['mem_password']) {
if(trim($_POST['password']) !== trim($_POST['password_again'])){
$errors[] = 'Your new passwords do not match';
} else if (strlen($_POST['password']) <6) {
$errors[] = 'Your password must be at least 6 characters';
}
} else {
$errors[] = 'Your current password is incorrect';
}
}
?>
<body>
<?php include ("includes/overall/template_header.php");?>
<div id="mainDivShort">
<h1>Change Password</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php"); ?>
<div id="middleContent">
<?php
if (isset($_GET['success']) && empty($_GET['success'])) {
echo 'You have been registered successfully';
} else {
if (empty($_POST) === false && empty($errors) === true) {
//echo "**********************";
change_password($session_mem_id, $_POST['password']);
header('Location: changepassword.php?success');
exit();
} else if (empty($errors) === false) {
echo output_errors($errors);
}
?>
<form action="" method="post">
<ul>
<li>Current Password*: <br> <input type="password"
name="current_password">
</li>
<li>New Password*: <br> <input type="password" name="password">
</li>
<li>Repeat New Password*: <br> <input type="password"
name="password_again">
</li>
<li><input type="submit" value="Change">
</li>
</ul>
</form>
<?php }?>
</div>
<?php include ("includes/overall/column_right.php"); ?>
</div>
<?php include ("includes/overall/template_footer.php");?>
</body>
</html>
And just incase you need to look at the change password function:
function change_password($mem_id, $password) {
$mem_id = (int)$mem_id;
mysql_query("UPDATE `members` SET `mem_password` = '$password' WHERE `mem_id` = $mem_id");
}
The password updates fine on the database, it just purely doesn't redirect to the success page.
Thanks in advance

Header directives must come before content, any content, incuding line breaks, spaces, html, etc... otherwise it's too late to send headers. As soon as 1 bit of content is sent, the headers have already gone.

You cannot put header('Location: changepassword.php?success'); after outputting any content. Also header redirects should contain absolute path.

Related

PHP Login Validation Issue

This is my PHP validation code
include 'core/init.php';
if (empty($_POST) === false) {
$username = $_POST['username'];
$password = $_POST['password'];
if (empty($username) === true || empty($password) === true) {
$errors[] = 'Enter a valid username or password.';
}
elseif (user_exists($username) === false) {
$errors[] = 'User does not exist.';
}
elseif (user_active($username) === false) {
$errors[] = 'Please activate your account first.';
}
else {
if (strlen($password) > 32) {
$errors[] = 'Password too long. <br>';
}
$login = login($username, $password);
if ($login === false) {
$errors[] = 'Incorrect username or password.';
}
else {
$_SESSION['user_id'] = $login; //login returns user_id
header('Location: hashtagphotowall.php');
exit();
}
}
//visual representation of error arrays
//print_r($errors);
}
else {
if (empty($errors) === false) {
$_SESSION['validation_errors'] = $errors;
header('Location: login.php');
}
}
This is my login form inside a modal
<div class="row">
<div class="large-12 large-centered columns">
<!--first modal form for login window-->
<div id="firstModal" class="reveal-modal" data-reveal aria-hidden="true" role="dialog">
<?php if(isset($_SESSION['validation_errors'])): ?>
<div class="validation_error_box">
<?php output_errors($_SESSION['validation_errors']); ?>
</div>
<?php endif; ?>
<p class="modal-row"><em>Sign In.</em><hr></p>
Connect with Facebook
<p class="hr-enclosed">or login with email</p>
<form action="login.php" method="post">
<div class="field-box">
<input type="text" name="username" placeholder="Username:" />
<input type="password" name="password" placeholder="Password:" />
<input type="submit" name="loginbutton" class="button small" value="LOGIN" />
<?php
function output_errors($errors) {
echo '<ul><li>' . implode('</li><li>', $errors) . '</li></ul>';
}
?>
</div>
</form>
<p class="modal-row-sub">forgot your password? get help here.<br>
new user? sign up here.</p>
<a class="close-reveal-modal" aria-label="Close">×</a>
</div>
I cannot achieve my goal which is "to display validation errors in the same place where my login form is located. For example, under the submit button." Before I arrived with this code, my first code outputs an error but not inline with the login form. It displays errors on another web page. So I revised it so that I can show errors under input tags or under the field box itself. But what's happening now with my code was when I hit the login button, it redirects to another web page with no results. Just plain white page. I used the header('Location: login.php'); which is the place where my php validation is located. When I changed it to where my login form is which is login-modal.php (take note that I used proper calling of dir, whatever you call it), it redirects to another page with NO foundation framework and CSS. Just plain login form. And also NO VALIDATION ERRORS DISPLAYED.
I am just a newbie with back-end web development so please bear with me. And also please help me. I have been stuck with this problem for long. Thank you. I highly appreciate your help.
Use jquery for same page updation 'AJAX'. Simple PHP codeing will not be effective.
When you use simple PHP it will work for reload purpose while if you use jquery it will work for refresh.

Add points to user shows no errors but doesn't add

I need to add a option in the Admin page where a admin can Select a user and add points to them, however I write the name and how many points to add, enter it and it shows up with no errors but saying it has been successfully added, but the points have not been added to that user...
Here's my code for the page with the form:
if (empty($_POST) === false) {
$required_fields = array('username', 'add');
foreach($_POST as $key=>$value) {
if (empty($value) && in_array($key, $required_fields) === true) {
$errors[] = 'Fields marked with an asterisk are required';
break 1;
}
}
}
if (empty($errors) === false) {
if (user_exists($_POST['username']) === true) {
$errors[] = 'Sorry, the username \'' . $_POST['username'] . '\' doesn\'t exist';
}
}
?>
<?php
if (isset($_GET['success']) === true && empty($_GET['success']) === true) {
echo 'The points have succesfully been added to the user!';
} else {
if (empty($_POST) === false && empty($errors) === true) {
$addpoints = array(
'username' => $_POST['username'],
'add' => $_POST['add']
);
addpoints($addpoints);
header('Location: addthepoints352346.php?success');
exit();
} else if (empty($errors) === false) {
echo output_errors($errors);
}
?>
<h1>Admin Access Only</h1>
<p>Add points to a user</p>
<form action="" method="post">
<ul>
<li>
Username*:<br>
<input type="text" name="username">
</li>
<li>
How many points to add*:<br>
<input type="text" name="add">
</li>
<li>
<input type="submit" value="Add">
</li>
</ul>
</form>
<?php
}
include 'includes/overall/footer.php';
?>
And also another page with the function where it actually sends it to the mysql database:
function addpoints($addpoints) {
mysql_query("UPDATE `users` SET `points` = `points` + '$add' WHERE `username` = '$username'");
}
I literally have no idea what it is, to help I have added a couple of photos
update your function as follows.
function addpoints($addpoints) {
mysql_query("UPDATE users SET points = points +".$addpoints['add']." WHERE username = ".$addpoints['$username'].")";
}

Rearrange my password recovery file so HTML output is below Header

I am slowly getting to grips with PHP, however struggle with breaking up a my if statements so my header functions work. I have done a few but they didn't involve as many conditions as my password recovery file does. Could somebody show me how I can go about doing this?
<?php
include ("storescripts/init.php");
logged_in_redirect();
include ("includes/overall/head.php");?>
<?php include ("includes/overall/template_header.php");?>
<div id="mainDivShort">
<h1>Recover</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php");?>
<div id="middleContent">
<?php
if(isset($_GET['success']) === true && empty($_GET['success']) === true){
?>
<p>Thanks, we've emailed you.</p>
<?php
} else {
$mode_allowed = array('mem_password');
if (isset($_GET['mode']) === true && in_array($_GET['mode'], $mode_allowed) === true) {
if(isset($_POST['mem_email']) === true && empty($_POST['mem_email']) === false) {
if (email_exists($_POST['mem_email']) === true) {
recover($_GET['mode'], $_POST['mem_email']);
header('Location: recover.php?success');
exit();
} else {
echo '<p>Oops, we couldn\'t find that email in the system</p>';
}
}
?>
<form action="" method="post">
<ul>
<li>Please enter your email address:<br> <input type="text"
name="mem_email">
</li>
<li><input type="submit" value="Recover"></li>
</ul>
</form>
<?php
} else {
header('Location: index.php');
exit();
}
}
?>
</div>
<?php include ("includes/overall/column_right.php");?>
</div>
<?php include ("includes/overall/template_footer.php");?>
The header statements need to be above my includes head.php as this includes HTML output. I have tried the buffering however this didn't work for me! Thank you!
<?php
ob_start(); // We start the buffer
include ("storescripts/init.php");
logged_in_redirect();
include ("includes/overall/head.php");?>
<?php include ("includes/overall/template_header.php");?>
<div id="mainDivShort">
<h1>Recover</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php");?>
<div id="middleContent">
<?php
if(isset($_GET['success']) === true && empty($_GET['success']) === true){
?>
<p>Thanks, we've emailed you.</p>
<?php
} else {
$mode_allowed = array('mem_password');
if (isset($_GET['mode']) === true && in_array($_GET['mode'], $mode_allowed) === true) {
if(isset($_POST['mem_email']) === true && empty($_POST['mem_email']) === false) {
if (email_exists($_POST['mem_email']) === true) {
ob_clean(); // Clean the buffer and make the redirect
recover($_GET['mode'], $_POST['mem_email']);
header('Location: recover.php?success');
exit();
} else {
echo '<p>Oops, we couldn\'t find that email in the system</p>';
}
}
?>
<form action="" method="post">
<ul>
<li>Please enter your email address:<br> <input type="text"
name="mem_email">
</li>
<li><input type="submit" value="Recover"></li>
</ul>
</form>
<?php
} else {
ob_clean();// Clean the buffer and make the redirect
header('Location: index.php');
exit();
}
}
?>
</div>
<?php include ("includes/overall/column_right.php");?>
</div>
<?php include ("includes/overall/template_footer.php");?>
What you may not be aware of is that php sends a header as soon as the first character is echoed out... That first character can even be white space like a lf or tab or cr. etc.
Once that first header goes out, your other headers that you are planning to send will no longer count... So your mixing of text html and use of tags is probably going to hurt you. as the first bit of white space outside of a php tag will generate a header and your planned headers will no longer count.
I could go further and recommend that you start using a templating system to separate code from content.
<?php
$msg = "";
if (!empty($_GET)) //check if form has been submitted
{
if(isset($_GET['success']) === true && empty($_GET['success']) === true)
{
$msg = "Thanks, we've emailed you.";
}
else
{
$mode_allowed = array('mem_password');
if (isset($_GET['mode']) === true && in_array($_GET['mode'], $mode_allowed) === true)
{
if(isset($_POST['mem_email']) === true && empty($_POST['mem_email']) === false)
{
if (email_exists($_POST['mem_email']) === true)
{
recover($_GET['mode'], $_POST['mem_email']);
header('Location: recover.php?success');
exit();
}
else
{
$msg = "<p>Oops, we couldn\'t find that email in the system</p>";
}
}
}
else
{
header('Location: index.php');
exit();
}
}
}
include 'storescripts/init.php';
logged_in_redirect();
include 'includes/overall/head.php';
include 'includes/overall/template_header.php';
?>
<div id="mainDivShort">
<h1>Recover</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php");?>
<div id="middleContent">
<?php echo $msg; ?>
<form action="" method="post">
<ul>
<li>Please enter your email address:<br> <input type="text"
name="mem_email">
</li>
<li><input type="submit" value="Recover"></li>
</ul>
</form>
</div>
<?php include ("includes/overall/column_right.php");?>
</div>
<?php include ("includes/overall/template_footer.php");?>
Didn't you solve this already here? Rearranging PHP page so header is before HTML

Rearranging PHP page so header is before HTML

My header is not redirecting to the correct page because I believe I have HTML elements before it. I am new to PHP and need help rearranging my page so this isn't the case. If I replace the header line with
print_r("<script>location.href='changepassword.php?success'</script>");
it works perfectly, however I know this is not good practise to use JS. Once have been shown the one, I can so the rest as none of them on my website work! Below is my changepassword.php page:
<!DOCTYPE html>
<html>
<?php
include ("storescripts/init.php");
protect_page();
include ("includes/overall/head.php");
if (empty($_POST) === false){
$required_fields = array('current_password','password','password_again');
foreach ($_POST as $key=>$value) {
if (empty($value) && in_array($key, $required_fields) == true) {
$errors[] = 'Fields marked with an asterisk are required';
break 1;
}
}
if ($_POST['current_password'] === $member_data['mem_password']) {
if(trim($_POST['password']) !== trim($_POST['password_again'])){
$errors[] = 'Your new passwords do not match';
} else if (strlen($_POST['password']) <6) {
$errors[] = 'Your password must be at least 6 characters';
}
} else {
$errors[] = 'Your current password is incorrect';
}
}?>
<body>
<?php include ("includes/overall/template_header.php");?>
<div id="mainDivShort">
<h1>Change Password</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php");?>
<div id="middleContent">
<?php if (isset($_GET['success']) && isset($_GET['success'])) {
echo 'You have been registered successfully';
} else {
if(empty($_POST) === false && empty($errors) === true) {
change_password($session_mem_id, $_POST['password']);
header('Location: changepassword.php?success');
} else if (empty($errors) === false) {
echo output_errors($errors);
}?>
<form action="" method="post">
<ul>
<li>Current Password*: <br> <input type="password"
name="current_password">
</li>
<li>New Password*: <br> <input type="password" name="password">
</li>
<li>Repeat New Password*: <br> <input type="password"
name="password_again">
</li>
<li><input type="submit" value="Change">
</li>
</ul>
</form>
<?php }?>
</div>
<?php include ("includes/overall/column_right.php");?>
</div>
<?php include ("includes/overall/template_footer.php");?>
</body>
</html>
Your header needs to go before any output. That includes your includes. include ("storescripts/init.php");, include ("includes/overall/head.php");,include ("includes/overall/template_header.php"); any output will stop the header.
This arrangement ought to work. We just move the change password if() above any of your document. Note the die() command which tells PHP to stop processing. No need to execute the rest of the script when we've instructed the browser to carry on someplace else.
As Dan points out below, you'll want to make sure your include()d files do not contain any output.
<?php
include ("storescripts/init.php");
protect_page();
include ("includes/overall/head.php");
if (empty($_POST) === false){
$required_fields = array('current_password','password','password_again');
foreach ($_POST as $key=>$value) {
if (empty($value) && in_array($key, $required_fields) == true) {
$errors[] = 'Fields marked with an asterisk are required';
break 1;
}
}
if ($_POST['current_password'] === $member_data['mem_password']) {
if(trim($_POST['password']) !== trim($_POST['password_again'])){
$errors[] = 'Your new passwords do not match';
} else if (strlen($_POST['password']) <6) {
$errors[] = 'Your password must be at least 6 characters';
}
} else {
$errors[] = 'Your current password is incorrect';
}
}
if(empty($_POST) === false && empty($errors) === true) {
change_password($session_mem_id, $_POST['password']);
header('Location: changepassword.php?success=1');
die();
}
?><!DOCTYPE html>
<html>
<body>
<?php include ("includes/overall/template_header.php");?>
<div id="mainDivShort">
<h1>Change Password</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php");?>
<div id="middleContent">
<?php if (isset($_GET['success']) && isset($_GET['success'])) {
echo 'You have been registered successfully';
} else {
if (empty($errors) === false) {
echo output_errors($errors);
}?>
<form action="" method="post">
<ul>
<li>Current Password*: <br> <input type="password"
name="current_password">
</li>
<li>New Password*: <br> <input type="password" name="password">
</li>
<li>Repeat New Password*: <br> <input type="password"
name="password_again">
</li>
<li><input type="submit" value="Change">
</li>
</ul>
</form>
<?php }?>
</div>
<?php include ("includes/overall/column_right.php");?>
</div>
<?php include ("includes/overall/template_footer.php");?>
</body>
</html>
This is not an answer, maybe useful informations if you dont know this.
To make use header() function - you have to execute it before any echo, print_r etc.
Other words - "product of" header(); function must be first data sent to browser.
You could use output buffering.
In PHP, headers must be sent before the content. So once you output anything (includes echo, print, etc, and anything outside the <?php ?> blocks including whitespace), then the headers cannot be modified.
However: What you can do is turn on output buffering, which will sent all output into a temporary buffer. That buffer will not be output until you tell it to.
The basic pattern is:
ob_start(); //Turn on output buffering at the
// beginning of your script
echo "Hello world!"; //Here would be your HTML document
if ($redirect) //This would be your condition for redirection
header('Location: otherpage.php');
else
ob_flush(); //At the very end, send the buffer to the browser
There are a number of options for ending the buffering. In this case I simply flushed the output by using ob_flush(), but you can check out the PHP documentation for various other options.

Conditions not being met in my IF statement

I have the below code, which allows a member to recover their password. However I cannot spot the mistake that is made and my conditions aren't being met. When you visit recover.php you are redirected to index.php, so the last else statement is being executed (this should only happen when a user is logged in - meaning they can't recover a password if they are logged in).
<?php
include 'storescripts/init.php';
$msg = "";
if(isset($_GET['success']) === true && empty($_GET['success']) === true)
{
$msg = "Thanks, we've emailed you.";
}
else
{
$mode_allowed = array('mem_password');
if (isset($_GET['mode']) === true && in_array($_GET['mode'], $mode_allowed) === true)
{
if(isset($_POST['mem_email']) === true && empty($_POST['mem_email']) === false)
{
if (email_exists($_POST['mem_email']) === true)
{
recover($_GET['mode'], $_POST['mem_email']);
header('Location: recover.php?success');
exit();
}
else
{
$msg = "<p>Oops, we couldn\'t find that email in the system</p>";
}
}
}
else
{
header('Location: index.php');
exit();
}
}
logged_in_redirect();
include 'includes/overall/head.php';
include 'includes/overall/template_header.php';
?>
<div id="mainDivShort">
<h1>Recover</h1>
<div id="divBreak"></div>
<?php include ("includes/overall/column_left.php");?>
<div id="middleContent">
<?php echo $msg; ?>
<form action="" method="post">
<ul>
<li>Please enter your email address:<br> <input type="text" name="mem_email"></li>
<li><input type="submit" value="Recover"></li>
</ul>
</form>
</div>
<?php include ("includes/overall/column_right.php");?>
</div>
<?php include ("includes/overall/template_footer.php");?>
As I am visiting recover.php when I am logged out, I cannot work out what condition is wrong to execute the last else statement.
First of all:
This is not going to work:
if(isset($_GET['success']) === true && empty($_GET['success']) === true)
It should be:
if(isset($_GET['success']) === true && empty($_GET['success']) === false)
And
header('Location: recover.php?success');
should be (else $_GET['success'] will not be set):
header('Location: recover.php?success=1');
And:
<form action="" method="post">
should be:
<form action="recover.php?mode=mem_password" method="post">
For the rest, you code is correct.

Categories