Say you have a big PHP web application doing echoing, output buffering, etc, all over the place. The end result is a finished HTML/XML document to the browser.
Now say you find yourself in a small function in a random place in a big PHP web application. Is there a simple way to output something, for example an HTML comment, in a way so that it is sent as the last thing to the browser?
Something like a hook for "when everything is finished send this piece of info as well to the browser"?
The end goal is basically to output some warnings or debug info in an easy way, without messing up the output.
There's register_shutdown_function(), which would essentially be the very last thing executed by PHP before terminating your script.
Related
I have set things up so my code reads the text of each page and automatically generates a table of contents and list of footnotes from it. I put footnote text into the page text in the place that it refers to. When the code reads the page file, it constructs a table of contents from the headers and puts that at the beginning of the page. It also removes the text of the footnotes and puts them in a list that it puts at the end of the page. It also manages numbering of the footnotes and placement of linked, superscripted footnote numbers for them.
To do this, instead of echo()ing page content, I compile the content into a variable, $PageText. I then have functions that read that variable, remove the footnote text, compile the table of contents and list of footnotes, and insert those into $PageText. I then echo($PageText);.
It seems that what I'm doing here is a homemade form of buffering, and that I could accomplish the same thing by something like
ob_start();
echo(<page contents>);
$PageText = ob_get_contents();
make_ToC($PageText);
make_footnotes($PageText);
ob_end_flush();
Would that be more efficient that using my own buffer variable? Or is there any other reason that it would better to use the built-in buffering system?
The reason I prefer to use my own buffer is that I have complete control of it. I don't really know what PHP might decide to do with content between the time that I echo() it and the time that I flush it.
A similar question was asked five years ago, Output buffering vs. storing content into variable in PHP. It's interesting that the answers seem to say that I would have better control of the contents by using the "ob_" system, whereas I feel like I have better control by using my own variable. Is there something I don't understand about that?
Output buffering is a technique to put already generated output on hold and has a number of usages:
Make better use of network transmissions (e.g. avoid sending almost empty HTTP packages)
Apply transparent transformations (e.g. minify generated HTML or rewrite URLs)
Being able to cancel the output altogether (e.g. in case of error)
Capture the output of functions that print to stdout (e.g. var_dump())
In my experience, functions that print to stdout tend to be an annoyance, esp. if the only apparent reason to do so is not having to prepend echo, because they get in the way of your application design. You don't always want to send their output as-is and you don't always want to print the output in the exact spot of the response flow where the function call happens.
What you describe is basically the standard text manipulation you can expect in any program. While you can certainly emulate it with output buffering, and as opinionated as it can get, I think it feels like a hack. In your case, you aren't even doing linear output. There's no obvious benefit of printing to stdout at once, given that you still need to manipulate the output because it isn't ready yet.
Using an output buffer requires the server to store the entire output of the PHP in RAM, so if I have a large page, I'll wind up using a fair amount of memory - and the server will also have to wait until the entire page is generated before sending it out, which could cause a small delay. that's right ?
I don't want to know the advantage of using ob_start();. My problem is redirecting and this error: Headers already sent.
So for solving that problem, I used of ob_start(); in the fist of my codes. something like this:
<?php ob_start(); ?>
<?php
// 500 lines of code is here
header(Location: www.example.com/test.php);
?>
<html>
// 1000 lines of code is here
</html>
<?php ob_end_flush(); ?>
Now my problem has been solved, just I want to know everything is ok ? my codes are optimized ? If my requests rise, my site does not delay ?
thanks
The proper solution to the "Headers already sent" problem is described in a previous thread.
Basically, the correct cause of action is to move all of the processing code above any output to the browser. Then simply echo out the results, as needed, in between the HTML code.
Not only will you notice an improvement in the resource usage of the page, but you'll also notice that it will become a whole lot easier to actually read and write the code.
If the output branches are complex enough, which means anything above a very basic script (simple guestbook, etc), a template engine might be well worth the time and effort to look at.
Output buffering is frequently used and I wouldn't worry about this. For example, this SO webpage takes up ~ 64 KiB, meaning 16384 of these pages fit in 1 GiB ram simultaneously.
Probably offtopic, but if you're going to send a Location header, do you even need to execute all the other code? You could just send the header and exit() immediately.
I am creating some kind of custom CMS (home automation).
Well I am not a PHP developer - just hobbyist.
What I am trying to achieve is:
In my index.php page I have something like:
"<?php echo $pageBody; ?> "
PageBody I am fetching from Database, well it works well for HTML, JS. But it doesn't work with PHP code source.
I done some research I believe this is related to PHP security restrictions.
My question: Does anybody would be able to provide safe sample (cannot find any samples like this) - how I should do this.
I am trying to insert some php code and render it eventually via browser:
<div id="outer">
<div id="inner">
***PHP Code should go here***
</div>
</div>
At the minute - it is being rendered as text. However I can render properly HTML and JS.
My preferable way would be - as much as possible secure.
Many Thanks Guys!
When you retrieve PHP code from a database text field, the PHP interpreter does not "know" that it should parse the data as a PHP script. To the PHP interpreter, the data in that field is no different from any other data -- it is all strings without any special significance.
You could use eval (docs) to accomplish this if you're dealing with pure PHP scripts. Be forewarned: eval is considered "evil" because using it comes with risks, especially if your users will have any input as to the content of the database.
In your case, it sounds like you want to parse mixed PHP and HTML that is stored in a database field. In order to do this, you'd need to write the database data into a file, then include it so the PHP interpreter can do its thing. You should implement some kind of caching mechanism in this process, otherwise it might become heavy on your server with many users. You may also want to use output buffering (docs) to capture the output instead of immediately sending it out.
Briefly, you'd want to do something like this:
$content_from_db = "<h1>Hello <?php print 'Clarisse'; ?></h1>";
$identifier_from_db = '12'; // like the primary key from the table
$file_handle = fopen('cached_content/CACHE_'.$identifier_from_db.'.php', 'w');
fwrite($file_handle, $content_from_db);
fclose($file_handle);
// here is where you'd start output buffering, if you're going to do that (optional)
include('cached_content/CACHE_'.$identifier_from_db.'.php');
// and then here you retrieve the output buffer's content (optional)
Please note that this is not a "traditional" way of including dynamic content, and the above code is not production-ready. Without knowing your use case, I can't say for certain, but this idea of storing PHP code in the database is a rather unusual way to proceed.
Another alternative to rolling your own is the smarty template library. Check it out here: http://www.smarty.net. With smarty, you can write a resource plugin to pull the templates from the database. It would look something like the code above (more info)
Documentation
fwrite - http://php.net/manual/en/function.fwrite.php
include - http://php.net/manual/en/function.include.php
PHP basics on theopensourcery.com - http://theopensourcery.com/phpbasics.htm
Server-side scripting on Wikipedia - http://en.wikipedia.org/wiki/Server-side_scripting
eval - http://php.net/manual/en/function.eval.php
Output Control (buffering) - http://php.net/manual/en/book.outcontrol.php
Smarty - http://www.smarty.net
to execute PHP that you store in a string (or database) you can use the eval function, but be careful it could be somewhat dangerous.
You can't render (probably you mean execute) php code in the browser, because php scripts execute on the server and then the output is sent to the browser. By the time the browser recieve the response, script has already finished execution.
You can fetch the code from database and use eval() before sending the output. But you must be aware of drawbacks from this approach.
Browser cannot render (execute) PHP code. PHP is something that the server executes and sends to the browser as plain HTML to display.
For testing purposes you can download and install WAMP thats the most hassle free one stop solution for development.
link : http://www.wampserver.com/en/
I have some PHP scripts that can be called either from the command line or as a webpage (where the arguments are passed from other web pages using $GET or $POST).
They can take a while to execute, let’s say 5 minutes.
The scripts include some “echo” & “print” calls which allow me to know what is happening during the execution in real time.
The problem is that, in webpage mode, those echo calls don’t print anything in the browser till the end of the script execution. Or sometimes, half the echos appears after 2 minutes and the rest at the end.
Is there a simple way to make my print()/echo() calls appear in real time when my script are called in “webpage mode”?
Thanks in advance.
flush() may or may not work depending on the browser and size of the output (see: PHP Flush() not working in Chrome)
Apache can also buffer output if mod_gzip is enabled.
Your best bet is to log into a db/session/fs and have JS on client side polling for updates.
Use ob_flush() to force output to be sent to the browser before script execution completes.
I assume you are not using output buffering as your script outputs fine on consolde. Therefore use flush() to explicitely tell PHP it should send output to the browser.
I would suggest a flush every xxx outputs instead of flushing after every echo or print if they appear in short intervals.
if i have something like this in php
$foo=0;
while($foo<20){
echo "hello";
usleep(1000000);
$foo=$foo+1;
}
and i make an ajax request to that php file, can i do anything with the data while the request is in progress?
i mean, the script echos hello every second and i saw that the request only shows what data it has when the whole loop is finished, so isnt there a way i can access each hello when its echoed out?
Look for firebug extension of Firefox.
There are a few reasons why you can'y see it.
The content coming from the AJAX request is processed by the server like any other http/php request.
What is happening is the data is being cached by the php buffer, then when its done its flushing it to the output. Which apache then delivers to you.
There is so little data that there is no need to flush this buffer before the processes is done. So you are only seeing the final result.
If you had some much data outputted that it cause the output to be flushed before hand then you may get it.
The other problem is going to be you ajax request handler. I'm pretty sure the onComplete (or similar) method that you (and everyone else) is using will only be called when the output from the server request is finishing and your browser has the full data.
It may be possible to use a different event or perhaps write the ajax code your self (with out using stuff like jQuery) but i'm not even sure if that would solve your problem; as this might also be something to do the with x http request implementation.
May i ask what your are trying to do this for? there may be an easier solution for your actually problem *i'm assuming this isn't the code your actually are using on your site).
Dan
If you execute the flush(); command in PHP you will send content. If you're compressing at the server level you may need to pad output to fill up a packet to make it send.
flush();
Here's an example: http://example.preinheimer.com/flush.php
The correct answer is you CAN see the content while it's being returned.
The other answers were partially correct in mentioning that the PHP output buffer will keep the output "bottled up"... but the output buffer can be disabled.
Once you disable the output buffer you need to show the JQuery response before the request completes - you do this by updating the browser periodically while the connection to the server is still active. This concept is called "Comet" or "Long Polling".
See these questions:
Comet and jQuery
How do I implement basic "Long Polling"?
Comet In PHP