skip to Main Content

I have an index.php file in which when the button is clicked it redirects to another page.php. However, the redirect does not work. Adding ob_start() and ob_end() does not change the situation. The contents of the index.php file look like this:

<?php ob_start();?>
<!DOCTYPE html>
<html>
<head>
<?php if (isset($_POST['link-btn'])) {  
    header("Location:page.php"); 
    exit();} ?>
</head>
<body>
<section id="main">
    <form method="post"> 
    <button type="submit" name="link-btn">Next page</button>
    </form>
</section>
</body>
</html>
<?php ob_end();?>

2

Answers


  1. According to https://www.php.net/manual/en/function.header.php:

    Remember that header() must be called before any actual output is sent, either by normal HTML tags, blank lines in a file, or from PHP.

    I think you’re confusing the HTTP header with the HTML element. They are different things.

    This should work:

    <?php 
    if (isset($_POST['link-btn'])) {  
        header("Location:page.php"); 
        exit();
    } 
    ?>
    <!DOCTYPE html>
    <html>
        <head>
        </head>
        <body>
            <section id="main">
                <form method="post"> 
                    <button type="submit" name="link-btn">Next page</button>
                </form>
            </section>
        </body>
    </html>
    

    Alternatively, you can redirect a page using a meta tag in the HTML head (perhaps this is the source of your confusion), although for this use case, it’s probably a bad idea, as you’re sending html and relying on the browser. e.g. <meta http-equiv="Refresh" content="0; url='https://www.w3docs.com'" />

    On a more general note, it looks like you’re using buttons and form submission for page navigation. I’d caution against custom approaches like this, as they add complexity. Deviation from standard approaches makes code harder to support, and can majorly impede accessibility.

    Login or Signup to reply.
  2. Right now you have a page that have html tag, therefore it seems like you have Response status 200 OK, you only set header with Location in it. I would probably go in a slightly different way:

    <?php 
        if (isset($_POST['link-btn'])) {  
           header("Location:page.php", true, 301); 
        } else {
    ?>
    
    <!DOCTYPE html>
    <html>
    <head>
    </head>
    <body>
    <section id="main">
        <form method="post"> 
        <button type="submit" name="link-btn">Next page</button>
        </form>
    </section>
    </body>
    </html>
    <?php } ?>
    

    What you really need to do is to create this type of HTTP Response

    https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/301

    I believe that you have writen the PHP code into the HTML <head> element, because you know that this contains header. But be aware in here. You have HTTP Response (or HTTP Request) with headers. And then you have headers in your HTML, which is the body (not header) of the HTTP Response. Therefore you are setting header() in PHP for the HTTP Response, but that is fine anywhere in the code before the code is sent (that’s when you get common error "headers have already been sent"). Once the HTTP Response is out there, you can not modify it. Therefore it’s the best to create all of it at once, then create HTTP Response and then send it.

    If you look here

    https://github.com/symfony/symfony/blob/6.4/src/Symfony/Component/HttpFoundation/Response.php#L241

    you will see method __toString that actually creates the HTTP Response itself, this is what browser is getting from the server. To learn this it’s the best way how to understand the web 🙂

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search