When I add the php redirect command in an include file, it redirects just that area, in its little sub window.
How can I make a redirect work with the base page?
Is it even possible, because you can only redirect before the headers, can't you? Would I have to use javascript instead?
If you are not talking about iframes
You can use output buffering to get round this issue. At the beginning of your main script run:
ob_start();
And then once you are done at the bottom of your main script run:
ob_end_flush();
From the manual page linked above:
This function will turn output buffering on. While output buffering is
active no output is sent from the script (other than headers), instead
the output is stored in an internal buffer.
The contents of this internal buffer may be copied into a string
variable using ob_get_contents(). To output what is stored in the
internal buffer, use ob_end_flush(). Alternatively, ob_end_clean()
will silently discard the buffer contents.
If you want to redirect parent window from <iframe (I assume that's what you mean by "little sub window") you have to use javascript, probably: self.parent.location.href = '...';
Google for javascript parent redirect to get more examples.
Related
I need to echo some output while executing php file ,beacuse execution takes 10 sec and end of 10sec page should be directed via header("Location:test.php)
However If I use ob_start and ob_implicit_flush(true) at the same time , we cannot direct page and getting
Warning: Cannot modify header information - headers already sent by
I also need to use ob_implicit_flush(true) to print output while execution.
How can I display output and direct page ?
You cannot output both body content and a redirect header in the same response, much less output the body before the header. The HTTP headers come first, so you cannot output a body before headers and you cannot output headers after the body has been output. Further, a redirect header causes the request to be immediately redirected before the browser will display any of its content, so the entire thing doesn't work on two levels.
If you want to display anything while the server is doing something, you'll need to use Javascript in some form or another.
If you use header() function there MUST be no output BEFORE it. But of course it can be after using the function.
ob_start starts the buffer to work while ob_implicit_flush tells to use no buffer at all. So the two functions cannot be combined that way.
Example:
ob_start(); //set buffer on
print('Hello World'); //no output since buffer on
ob_implicit_flush(true); //buffer switched off again
print('Test'); //prints 'Hello World' and 'Test'
header('Location: ...'); //ERROR: output already done
You have now to decide if you want to output information from your script OR make the redirection.
Output something AFTER header is possible but it makes no sense as you will not see it anymore.
Maybe you can use the ob_get_length() function to check if there was some output and then decide if you switch page or output the buffer:
ob_start(); //set buffer on
print('Hello World'); //no output since buffer on
if(ob_get_length() > 0)
ob_end_flush();
else
header('Location: ...'); //will not be executed if output was generated
I have a complex PHP script where in multiple parts I have a header_redirect. For example, to change the language, etc. Everything works as it should, but I noticed that especially on mobile devices, I can see the code of the page rendered (HTML only, no CSS) before it redirects. Or even on desktop devices, but on those I get only a blank page and can see the page rendered only if I view the source code and hit cancel really fast before it redirects.
I know, it's most likely because the coding structure of the page is wrong and I use header_redirect somewhere in the middle of the code instead of checking it before any content is rendered. But is there an easy way to turn off this output in any way without rewriting the entire script?
I checked in php.ini and
output_buffering
Is set to 'off', but maybe there's another setting?
You do it the wrong way. Output buffering needs to be set on (That this is bad practise, you already know).
//Starts Buffering
ob_start();
//Your Code here
//...
//...
//Sends the Buffered Content to the browser, if redirected first, this will never shown
ob_end_flush();
flush();
But I think you have something like a meta or javascript redirect. If it is a PHP Header, you should get a error like
Can not send headers, already send on line xy...
Maybe the root of your Problem is some Cache directive.
You redirect with PHP this way:
header('HTTP/1.1 302 Found');
header('location: /Target.php');
Or 301 if it is permanent.
Is there a way that I can set a cookie after an html output? According to PHP manual setcookie() should be set before the output.
I need it for my voting system wherein a cookie will be set after a successful Mysql query. I made it in one file.
you can use the output buffers so at the top of your script you add ob_start() and this will create a buffer and you can then set the cookie and then end the buffer and flush out to the browser.
ob_start();
/* set cookie */
ob_end_flush();
Is there a way that I can set a cookie after an html output?
Technically no. If you would like to set a cookie you need to ensure that no output has been send to the browser so far.
According to PHP manual setcookie() should be set BEFORE the output.
That's correct, otherwise it won't work. So I would even say must, not only should.
I need it for my voting system wherein a cookie will be set after a successful mysql query.
A successful mysql query on it's own will not create any output. Only a failed mysql query would if error reporting is enabled. So I wonder if you actually ran into a concrete problem or not.
The mysql query itself should not prevent you from using setcookie.
In case you have done already HTML output prior the use of setcookie you need to find the place where your HTML output started. Above that line place the ob_startDocs function which will start output buffering.
With output buffering enabled, your program can still "output" HTML but it will not be send immediately. Then you should be able to call setcookie with no problems:
<?php ob_start(); ?>
<html><body>
<?php
$result = mysql_run_query($query);
echo '<h1>Your Voting Results</h1>';
output_voting_result($result);
set_cookie('vote', $result['id']);
?>
</body></html>
The output buffer will be automatically send to the browser when your script finishes, so there is not much more you need to care about, the rest works automatically.
Cookies can be set in JavaScript on the client side - see this link for examples: http://www.w3schools.com/js/js_cookies.asp
No. Cookies are sent in the header so they must be set before the output body begins.
You can, however, use PHPs built-in buffering so it won't actually generate any output until the script has completely finished executing.
ob_start is the function you want.
You can use output buffering
ob_start();
// send output
// set cookie
ob_end_flush();
The cookie gets set in the http header. If what you want to do is set the cookie on a vote, then you either need to do a header('Location:...') redirect, or you could have a small iframe where you make an ajax call that does the same thing.
Cookies are sent to the browser as part of the response header. This means that they must be set before the server starts writing its response to the request that is being processed (so that the server can specify the correct headers on the response).
I don't know the specifics about how this is handled in PHP, but if I had to guess I would say that the output of a given PHP script is probably buffered by the server (typically Apache) until the script completes, and then the server writes the response after the PHP script has completed execution. If this is the case, then you should be able to set cookies whenever you want. If it isn't, then you won't be able to.
I'd suggest simply testing it to see what happens. Write a PHP script that sets a cookie at the very end of its execution, access it via a browser, and then check to see if the cookie is actually set.
If for some reason you can't buffer the output, you can set a cookie after sending output by displaying an image on the current page that accesses a script that sets a cookie.
echo ('<img src="http://example.com/mysetcookie.php?uid='.$userId.'">');
mysetcookie.php
<?php
setcookie('cookie-name',$_REQUEST['uid']);
//output an image - this is a one-pixel clear image
header('Content-Type: image/gif');
echo base64_decode('R0lGODlhAQABAJAAAP8AAAAAACH5BAUQAAAALAAAAAABAAEAAAICBAEAOw==');
exit;
?>
I'm trying to design a page which does some database actions, then redirects to user back to the page they came from. The problem is that I use a require() function to get the connection to the database, so the headers are already sent. A meta tag is out of the question since I want it to look like all the processes are done from the page they came from. Any tips? Is there a way I can use the require() and the header() or do I have to drop one? Is there an alternative to header()?
If you can't send the header() before some content gets sent, use output buffering by placing an ob_start(); at the beginning of your script before anything is sent. That way, any content will be stored in a buffer and won't be sent until the end of the script or when you manually send the buffer's contents.
On another note, simply requireing another file would not generate any headers/content unless that included script sends them. The most common "hidden" cause of this is unnoticed whitespace before or after the <?php ?> tags.
As Artefacto noted, connecting to the database should not require any output. Fix whatever you're including (e.g. database_connect.php) not to output. See this search on the "headers already sent" issue, which may help you find "hidden" output.
ob_start(); // start output buffering
echo "<html......"; // You can even output some content, it will still work.
.
.
.
.
.
header("Location: mypage.php");
ob_flush(); //flush the buffer
In this case, all output is buffered. This means, the headers are processed first, then the output comes to play...
You cannot send any headers after some content has already been sent. Move the header() call to be before the require() call.
You cannot send headers after any data has been sent to the client.
However, using require does not meen that you output something. If i understand your right, you can include your database files, run your queries and then redirect the user. This is perfectly valid.
If you need to send some output (why if you need to do a redirect?) another option is to use output buffering. By using output buffering, you're not sending the data to the browser when you echo it, but you store it in a buffer. The data will be sent when you call ob_end_flush or you reach the end of the script. After ob_end_flush, you won't be able to send any new headers. You start output buffering with ob_start.
It is possible to use header() with require() when I use output buffering. That means that the whole script is buffered and first send when the script has come to an end.
I have done it by doing this
ob_start("ob_gzhandler"); //begin buffering the output
require_once('/classes/mysql.php');
// Some code where I access the database.
header('/somepage.php');
exit;
ob_flush(); //output the data in the buffer
The php documentation suggests that I should end each ob_start() with an ob_end_flush(). I am using one on each page of a site, just to allow me to use firephp log methods anywhere in the app.
the app works fine, but I wonder if there is anything I don't know that might be detrimental.
I think the reason for this suggestion is, that PHP flushes your output buffer implicitly when not using one of the ob_end_* functions. While not an error, this can cause problems when not expecting it. The PHP-docs try to protect you from these kind of problems. If you are aware of the implicit flush, it is probably not an issue.
You can use Output Buffering as
<?php
ob_start();
echo "Some text you want to echo on page!!";
header("Location:somepage.php");
ob_end_flush();
?>
The problem is that we cannot send the header after we start sending the output. To solve this we buffer the output. The function ob_start turns output buffering on. While output buffering is active no output is sent from the script (other than headers), instead the output is stored in an internal buffer. So the echo output will be buffered. Next we send the header without any problem as we've not yet spit out any output. Finally we call ob_end_flush to flush the internal buffer contents and to stop output buffering.
if there is loops, for example, some one can start buffering. And calls your function. When he tries to ob_end_flush code gathers your contents.