Home  >  Article  >  Backend Development  >  Detailed explanation of PHP require and include order

Detailed explanation of PHP require and include order

黄舟
黄舟Original
2017-06-25 10:55:071216browse

In large-scale Web projects, include_path is the foundation of a modularization design (of course, there are many designs based on autoload, which does not affect this article) Discussion), but precisely because of include_path, we often encounter some seemingly "weird" problems caused by not finding the correct file.

There are also the following questions:

How does include_path work?

What is the order if there are multiple include_paths?

Under what circumstances does include_path not work?

Today, I will give a comprehensive introduction to this problem, starting with an example.

The following directory structure:

  root    
  ├ 1.php    
  ├ 3.php    
  └ subdir         
  ├ 2.php          
  └ 3.php

is in 1.php :

The code is as follows:

<?php 
ini_set("include_path", ".:path_to_subdir"); 
require
("2.php"); 
?>


And in 2.php:

<?php 
require("3.php"); 
?>

And in 3.php in the root directory, it prints out "root ”, 3.php in the subdir directory prints out “subdir”;

Now, here comes my question:
1. When running 1.php in the root directory, you will get What output?
2. Run 1.php in the upper directory under subdir. What output will you get?
3. When canceling the current directory path in include_path (that is, include_path="path_to_subdir"), What will be the output of the above two questions?
include_path in PHP
When PHP encounters the require(_once)/include(_once) instruction, it will first make the following judgment : Is the file path to be included an absolute path?

If so, include it directly and end.
If not, enter another logic (after multiple calls, the macro will enter _php_stream_fopen_with_path) Find this file


Next, in _php_stream_fopen_with_path, the following judgment will be made:

Is the file path to be included a relative path (in the form of ./file, ../dir/file, use "directory relative path instead" below)?
If so, skip the logic of include_path and directly parse the relative path (introduced separately later)


A candidate directory list will be formed based on include_path and the path of the currently executed file. For example, for the example in the previous article, a candidate list will be formed as follows

The code is as follows:

".:path_to_subdir:current_script_dir

Then, starting from the head of the candidate list, take out a path in the candidate list according to DEFAULT_DIR_SEPARATOR (the environment of this article is ":"), and then append the file name to be included to the end of this path. Try. If successfully included, return, otherwise continue to the next candidate path.
Up to now, we can answer the three questions I raised at the beginning.
1. Because it is executed in the root directory, So when 1.php contains 2.php, the second candidate path of include_path works (path_to_subdir), and path_to_subdir/2.php is found, and when 2.php contains 3.php, the current work The directory is under root, so when 3.php is included, the matching file is found under the first candidate path of include_path "." (current working directory), so the output is "root".
2. Same as 1, except that the current path is subdir, so the output is "subdir".
3. Because there is no include_path in the current path, 2.php contains 3 when running in the root directory. When using php, path_to_subdir plays a role, so whether in root or subdir, you will get the output of "subdir".
And if you clear include_path in 2.php,

<?php 
ini_set("include_path", &#39;&#39;); 
require("3.php"); 
?>


Then current_script_dir will take effect, and at this time current_script_dir is the path of 2.php, so you will still get the output of "subdir".
Directory relative path
Use directory relative path In the case of , the base point of the relative path is always the current working directory.
In order to illustrate the situation under the relative path of the directory, let's look at another example, it is still the above directory structure, but 1.php becomes:

<?php 
ini_set("include_path", "/"); 
require("./subdir/2.php"); ?>


2.php becomes:

<?php 
require("./3.php"); 
?>


If executed in the root directory, searching for 3.php in 2.php will be in the current directory Search under the relative path, so the output obtained is "root", and if you execute 1.php (php -f ../1.php) of the upper-level directory under subdir, it will not be found under subdir. Reaching "./subdir/2.php" and exiting abnormally.
Postscript
1. Because when using include_path and relative paths, the performance will be related to the number of searches. The worst In this case, if you have 10 include_paths, it may take up to 11 retries to find the file to be included. Therefore, it is best to use absolute paths if you can use absolute paths.
2. Because directory relative paths basedir is always the current working path. If you want to use it, it needs to be related to the actual deployment path, so it is rarely used in practice (of course, there are also modules that use chdir).
3. In modular system design , generally should be within the module, and use the absolute path by obtaining the deployment path of the module (dirname(FILE), php5.3 and later provides DIR constants).

The above is the detailed content of Detailed explanation of PHP require and include order. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn