php processing of include files - php

This question has to do with the internal mechanics of the PHP engine. I'm asking it in an effort to understand the file include process.
Say, you got a 20,000 lines include file ( something like "functions_library.php" ) that gets included on all your php scripts.
Does PHP check/verify if that include file is syntactically correct every single time one of your php scripts load that file? Does this process happen at each page load over and over and over again?
Or...
Does PHP pay attention to the file's last modification date? If it turns out that there were no changes to it since the last check, does it simply ignore the checking?

On a default installation, the file will be parsed every single time. However, any production installation of PHP is recommended to have a bytecode cache, such as APC or many others. When bytecode cache is used, the script is parsed the first time and the interpreted code will be stored in memory.
Different configurations may alter how often file modifications are checked. Under some configurations, for very high performance, manual flushing or restarting the web server may be required.

If you include that file, PHP will need to interpret it every time.

PHP will re-interpret the file every time you call include().
This can be tested visually with the use of variables. If you have something like this:
otherScript.php:
<?php echo $foo; ?>
script.php:
<?php
$foo = 1;
include("otherScript.php");
$foo = 2;
include("otherScript.php");
?>
The output will be:
12
This is a poor example, but it should demonstrate the PHP will need to include the contents of the file each time. It is a pretty good guess to state that the PHP interpreter won't keep a copy of the included file in memory for each reference - there can be hundreds of includes per application.
To deal with this specific ideal, however, they provide a method include_once() that will, as the name implies, only include the file one time and prevent it from being included any additional times.

Related

Include HTML files in a PHP wrapper

I don't know how to put this better and tried search some around but I wasn't really sure on what to search either for my situation.
I'm in the unfortunate situation of managing a very old website, that has been passed by the hands of at least 5 webmasters.
The whole site is built of several hundreds of pages, each made of a single .html file; there is no controller logic or anything.
Now I need to implement a couple of scripts globally throughout the site, and I was wondering if there is a quick and dirty way to accomplish this.
I was thinking to encapsulate every request through a sort of rudimental PHP controller that simply read the requested file, require it in the script and render it with the same exact content and URL, but with the necessary scrpts included before the closing </body> tag.
Unfortunately I'm quite a novice in this, and I'm afraid also to allowing some bad injection from external sources. What is the best way to achieve something like this? I'm on a linux apache server.
Here are two approaches:
1) PHP Wrapper
Along the lines of what you're asking for, you can use your web server redirect all incoming HTML requests to a PHP file that does the following:
Takes a reference to the HTML file
Opens and reads the file in to a string
Makes the changes
Outputs the modified content in the response
If you are using a server like Apache httpd you can use mod_redirect to handle redirection of the requested URL to your PHP file.
This approach is a bit inefficient since for each request the HTML content needs to be read and modified. The approach below of editing the files will be higher performance.
2) Edit HTML Files
You can write a script to go through all the .html files and programmatically edit them.
One implementation to do this would be to open each file and add some lines at the tome and some others near the bottom. A the top of each file you could add a require() for your PHP file:
<? php
require('path/to/myinclude.php');
?>
At the bottom of the HTML before the </body> tag, call your function in the myinclude.php file, for example:
....
<?
my_footer_function();
?>
</body>
</html>
Depending on your webserver, you may be able to have the PHP interpreter execute for the .html extension so you don't have to change file extensions, if that's your wish.
This way, after this edit, you can modify all the behavior in the my_footer_function() in all your files simply by changing the one myinclude.php.

Is it possible to count the number of php code lines parsed to complete a request?

I am writing a PHP website which uses Autoload feature to limit number of included files. Is there a way for php engine to count the number of source code lines (and files) it parsed to complete each request? That way it would be easier to optimize the structure to limit include files for each request.
Edit: Let's assume that we are not using op-cache or we can even skip (meaning no need to count) all compiled code. Since this is mainly for profiling in dev environment even instrumenting the php code is acceptable.
I see XDebug has built in profiling feature. I never used it before. I will try that and post-back (http://www.xdebug.org/docs/profiler)
Assuming your script is contained within one file, why not output the current line number on it's return using a magic constant?
echo __LINE__;

Requesting long PHP scripts with AJAX

I'm building a website which loads dynamically from a SQL database. To do that, I've created a PHP file that handles ALL AJAX and Post and Get requests (and every page has a couple of php include).
The PHP is not very long yet (250 lines), but it could get much longer eventually.
Everything is wrapped in <?php **** ?> tags, and is clearly and methodically composed of switch and case. So I only need a couple of lines each time.
My question is: Does every include request load/download all the file, or just the corresponding part? Rephrasing, will a hypothetically 10,000 line long script slow down the browser, or just the response time from the server?
I have concerns about all this.
Thanks in advance.
PS: This idea of unifying sql requests comes from a computer engineer friend that's always insisting on Multititer Architecture.
When you include a file, the entire files contents are inserted/executed into the script at that point. Depending on what is going on with the includes, you could be slowing down the response if you are including files that are not necessary for the response.
http://us3.php.net/manual/en/function.include.php
I have a great solution! (And this was my own question)
Instead o parsing a variable $option to enter a switch case case case .... case case endswitch I thought I could just split the PHP into a lot of different PHP's with the name of their corresponding case.
So, instead of using case('sports'), I will now use a <?php include('some_folder/'.$option.'.php');?> which will avoid converting to binary the whole file every time is called.
Since PHP is processed on the server, the included file will come all along and it will just have to deal with 20 lines of code instead of 400 (and, eventually, many more).
Definitively, thanks

Editing files in PHP

Is there a way to append or remove a line of text from a file using PHP.
I am in the process of writing a hosting control panel for my specific web hosting stack and would like to be able to make changes to the files with minimal requirements to touch the file system, and as such would like not to have to rewrite the whole file to add or remove a configuration option.
There is no way to remove a line from a file without first parsing the file into lines and then writing it out again.
You can append to a file by using fopen with the $mode set to 'a'
$fp = fopen('myfile', 'a');
For appending, you should use fopen with the $mode of a.
See this please, on how to delete a line from the file.
Yes, you can open files in append mode:
$fh = fopen('testFile.txt', 'a');
If you now write to the file, the new content gets appended.
See fopen and from this documentation:
'a': Open for writing only; place the file pointer at the end of the file. If the file does not exist, attempt to create it.
Removing the last line is not possible though.
Working with files in PHP is full of pitfalls, particularly wrt concurrency and locking. The fact that you are writing config files implies also that you are exposing tasks normally only available to a user with root privileges over the web. You did not mention these things in your post, but your question is trivial in comparison to addressing these issues.
Regarding your question - although its fairly trivial to implement what you propose (e.g. by exec'ing sed - although you did not did say what OS this is running on) I'd recommend creating a copy of the original file in some other representation - obvious candidates would be a database - where you can apply sequence numbers to the lines and easily create a gap to populate, or a PHP SplDoublyLinkedList stored in the session. Then once the user has effected as many changes as they require, regenerate the file in a single operation from the working representation.
Note that, ultimately, regardless of how you implement the solution the solution will rewrite the entire file - its just a question of how much of this process is exposed within your code.
Bear in mind, that what you are doing is just the same as most php web scripts - except while they manipulate and reqrite HTML, you're doing it with a different file type - so you might want to look at how other PHP templating systems are written, and consider whether you can create a template for your config files.
HTH
C.
If you need to change something in the middle of the file, you have to read it, parse it and save it back. Othwerwise you can only append something to the end of it.
You should not be concerned about the cost of this operation though, as it's a configuration file that won't likely be changed a hundred times every second, it should take negligible time.
If you want more flexibility in access/update/delete I think you should consider moving your configuration file to a database table.

Can PHP's ob_start be called more then once?

Can PHP's ob_start be called more then once?
Sorry if this is a dumb question but I really don't know.
My site is really large (file quantity), its a social network and one of the included files uses ob_start PHP's output buffer for something, i'm not ure someone else started my site a long time ago and now it is mine I need to look into it more to see what it's doing exactly.
Anyways I am wanting to use ob_start ("ob_gzhandler"); to compress CSS files and all files on my site get loaded (included) through the index file so I am wanting to know if I am able to use that even though it is already in use somewhere else in the code?
Yes, you can call it more than once. It creates a new buffer each time however, so be careful.
From the manual: "Output buffers are stackable, that is, you may call ob_start() while another ob_start() is active. Just make sure that you call ob_end_flush() the appropriate number of times. If multiple output callback functions are active, output is being filtered sequentially through each of them in nesting order."
You say this :
I am wanting to use ob_start
("ob_gzhandler"); to compress CSS
files
I would rather serving and compressing JS/CSS (well, static) files is the job of the Web server (ie, Apache), and not PHP.
About that, you can take a look at mod_deflate -- at least, if you are using Apache 2.
all files on my site get loaded
(included) through the index file
Is that really necessary ? You're having PHP work with no apparent (?) reason, that way.
(Note that even if CSS/JS files are served through PHP, Apache should be able to compress them with mod_deflate ; same is also true for HTML, JSON, ... btw)
Another advantage of not going through PHP to server those files is that it would be easier to get them served by another server, as your site will grow (if it grows enough, actually) :
you could have a bunch of "PHP servers", to process PHP pages
and one or two "static-files servers", to server only CSS/JS/images, and lighten the load or your "application servers" ; no need for PHP on these ones ; you could also use something like lighttpd instead of Apache
That being said, ob_start says this :
Output buffers are stackable, that is,
you may call ob_start() while another
ob_start() is active. Just make sure
that you call ob_end_flush() the
appropriate number of times. If
multiple output callback functions are
active, output is being filtered
sequentially through each of them in
nesting order.
So, I think the answer to your question is "yes" :-)

Categories