简体   繁体   English

如何包含需要绝对路径的PHP文件?

[英]How to include PHP files that require an absolute path?

I have a directory structure like the following; 我有一个像下面这样的目录结构;

script.php script.php的

inc/include1.php INC / include1.php
inc/include2.php INC / include2.php

objects/object1.php 对象/ object1.php
objects/object2.php 对象/ object2.php

soap/soap.php SOAP / soap.php

Now, I use those objects in both script.php and /soap/soap.php , I could move them, but I want the directory structure like that for a specific reason. 现在,我在script.php/soap/soap.php使用这些对象,我可以移动它们,但出于特定原因我想要这样的目录结构。 When executing script.php the include path is inc/include.php and when executing /soap/soap.php it's ../inc , absolute paths work, /mnt/webdev/[project name]/inc/include1.php... But it's an ugly solution if I ever want to move the directory to a different location. 执行script.php ,include路径为inc/include.php ,执行/soap/soap.php它是../inc ,绝对路径工作, /mnt/webdev/[project name]/inc/include1.php...但它是一个丑陋的解决方案,如果我曾经想要的目录移动到不同的位置。

So is there a way to use relative paths, or a way to programmatically generate the "/mnt/webdev/[project name]/" ? 那么有没有办法使用相对路径,或者以编程方式生成"/mnt/webdev/[project name]/"

This should work 这应该工作

$root = realpath($_SERVER["DOCUMENT_ROOT"]);

include "$root/inc/include1.php";

Edit: added imporvement by aussieviking 编辑:通过aussieviking增加了改进

You can use relative paths. 您可以使用相对路径。 Try __FILE__ . 试试__FILE__ This is a PHP constant which always returns the path/filename of the script it is in. So, in soap.php , you could do: 这是一个PHP常量,它总是返回它所在脚本的路径/文件名。所以,在soap.php ,你可以这样做:

include dirname(__FILE__).'/../inc/include.php';

The full path and filename of the file. 文件的完整路径和文件名。 If used inside an include, the name of the included file is returned. 如果在include中使用,则返回包含文件的名称。 Since PHP 4.0.2, __FILE__ always contains an absolute path with symlinks resolved whereas in older versions it contained relative path under some circumstances. 从PHP 4.0.2开始, __FILE__总是包含已解析符号链接的绝对路径,而在旧版本中,它在某些情况下包含相对路径。 (source) (资源)

Another solution would be to set an include path in your httpd.conf or an .htaccess file. 另一种解决方案是在httpd.conf或.htaccess文件中设置包含路径

have a look at http://au.php.net/reserved.variables 看看http://au.php.net/reserved.variables

I think the variable you are looking for is: $_SERVER["DOCUMENT_ROOT"] 我认为你要找的变量是: $_SERVER["DOCUMENT_ROOT"]

您可以使用项目根目录的路径定义常量,然后将其放在路径的开头。

Another way to handle this that removes any need for includes at all is to use the autoload feature. 处理此问题的另一种方法是删除对包含的任何需求,即使用自动加载功能。 Including everything your script needs "Just in Case" can impede performance. 包括脚本需要的所有内容“Just in Case”会阻碍性能。 If your includes are all class or interface definitions, and you want to load them only when needed, you can overload the __autoload() function with your own code to find the appropriate class file and load it only when it's called. 如果您的包含是所有类或接口定义,并且您只想在需要时加载它们,则可以使用您自己的代码重载__autoload()函数以查找相应的类文件,并仅在调用它时加载它。 Here is the example from the manual: 以下是手册中的示例:

function __autoload($class_name) {
    require_once $class_name . '.php';
}

$obj  = new MyClass1();
$obj2 = new MyClass2(); 

As long as you set your include_path variables accordingly, you never need to include a class file again. 只要相应地设置include_path变量,就不需要再次包含类文件。

Another option, related to Kevin's, is use __FILE__ , but instead replace the php file name from within it: 另一个与Kevin相关的选项是使用__FILE__ ,而是替换其中的php文件名:

<?php

$docRoot = str_replace($_SERVER['SCRIPT_NAME'], '', __FILE__);
require_once($docRoot . '/lib/include.php');

?>

I've been using this for a while. 我已经使用了一段时间了。 The only problem is sometimes you don't have $_SERVER['SCRIPT_NAME'] , but sometimes there is another variable similar. 唯一的问题是有时你没有$_SERVER['SCRIPT_NAME'] ,但有时会有另一个类似的变量。

I found this to work very well! 我发现这个工作非常好!

function findRoot() { 
    return(substr($_SERVER["SCRIPT_FILENAME"], 0, (stripos($_SERVER["SCRIPT_FILENAME"], $_SERVER["SCRIPT_NAME"])+1)));
}

Use: 使用:

<?php

function findRoot() {
    return(substr($_SERVER["SCRIPT_FILENAME"], 0, (stripos($_SERVER["SCRIPT_FILENAME"], $_SERVER["SCRIPT_NAME"])+1)));
}

include(findRoot() . 'Post.php');
$posts = getPosts(findRoot() . 'posts_content');

include(findRoot() . 'includes/head.php');

for ($i=(sizeof($posts)-1); 0 <= $i; $i--) {
    $posts[$i]->displayArticle();
}

include(findRoot() . 'includes/footer.php');

?>
require(str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1))."/path/to/file.php");

I use this line of code. 我使用这行代码。 It goes back to the "top" of the site tree, then goes to the file desired. 它返回到站点树的“顶部”,然后转到所需的文件。

For example, let's say i have this file tree: 例如,假设我有这个文件树:

domain.com/aaa/index.php domain.com/aaa/index.php
domain.com/bbb/ccc/ddd/index.php domain.com/bbb/ccc/ddd/index.php
domain.com/_resources/functions.php domain.com/_resources/functions.php

I can include the functions.php file from wherever i am, just by copy pasting 我可以从任何地方包含functions.php文件,只需复制粘贴即可

require(str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1))."/_resources/functions.php");

If you need to use this code many times, you may create a function that returns the str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1)) part. 如果需要多次使用此代码,可以创建一个返回str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1))部分str_repeat('../',(substr_count(getenv('SCRIPT_URL'),'/')-1)) Then just insert this function in the first file you include. 然后只需在您包含的第一个文件中插入此函数。 I have an "initialize.php" file that i include at the very top of each php page and which contains this function. 我有一个“initialize.php”文件,我包含在每个php页面的最顶层,其中包含此功能。 The next time i have to include files, i in fact just use the function (named path_back ): 下次我必须包含文件,我实际上只是使用该函数(名为path_back ):

require(path_back()."/_resources/another_php_file.php");

I think the best way is to put your includes in your PHP include path. 我认为最好的方法是将您的包含在PHP包含路径中。 There are various ways to do this depending on your setup. 根据您的设置,有多种方法可以执行此操作。

Then you can simply refer to 然后你可以简单地参考

require_once 'inc1.php';

from inside any file regardless of where it is whether in your includes or in your web accessible files, or any level of nested subdirectories. 来自任何文件内部,无论它在您的包含位置或Web可访问文件中的位置,还是任何级别的嵌套子目录。

This allows you to have your include files outside the web server root, which is a best practice. 这允许您将包含文件放在Web服务器根目录之外,这是最佳做法。

eg 例如

site directory
    html (web root)
        your web-accessible files
    includes
        your include files

Also, check out __autoload for lazy loading of class files 另外,检查__autoload是否延迟加载类文件

http://www.google.com/search?q=setting+php+include+path http://www.google.com/search?q=setting+php+include+path

http://www.google.com/search?q=__autoload http://www.google.com/search?q=__autoload

If you are going to include specific path in most of the files in your application, create a Global variable to your root folder. 如果要在应用程序的大多数文件中包含特定路径,请在根文件夹中创建一个全局变量。

define("APPLICATION_PATH", realpath(dirname(__FILE__) . '/../app'));
or 
define("APPLICATION_PATH", realpath(DIR(__FILE__) . '/../app'));

Now this Global variable " APPLICATION_PATH " can be used to include all the files instead of calling realpath() everytime you include a new file. 现在,每次包含新文件时,此全局变量“ APPLICATION_PATH ”可用于包含所有文件,而不是调用realpath()。

EX: EX:

include(APPLICATION_PATH ."/config/config.ini";

Hope it helps ;-) 希望能帮助到你 ;-)

@Flubba, does this allow me to have folders inside my include directory? @Flubba,这允许我在include目录中有文件夹吗? flat include directories give me nightmares. 平包括目录让我做恶梦。 as the whole objects directory should be in the inc directory. 因为整个对象目录应该在inc目录中。

Oh yes, absolutely. 哦,是的,绝对的。 So for example, we use a single layer of subfolders, generally: 例如,我们使用单层子文件夹,通常:

require_once('library/string.class.php')

You need to be careful with relying on the include path too much in really high traffic sites, because php has to hunt through the current directory and then all the directories on the include path in order to see if your file is there and this can slow things up if you're getting hammered. 你需要小心在真正高流量的站点中依赖包含路径太多,因为php必须通过当前目录搜索,然后搜索包含路径上的所有目录,以查看你的文件是否在那里,这可能会变慢如果你受到重创,事情就会发生。

So for example if you're doing MVC, you'd put the path to your application directoy in the include path and then specify refer to things in the form 因此,例如,如果您正在进行MVC,那么您将把包含路径中的应用程序路径直接放入,然后指定引用表单中的内容

'model/user.class'
'controllers/front.php'

or whatever. 管他呢。

But generally speaking, it just lets you work with really short paths in your PHP that will work from anywhere and it's a lot easier to read than all that realpath document root malarkey. 但一般来说,它只是让你可以在你的PHP中使用非常短的路径,它可以在任何地方工作,并且它比所有的真实路径文件根malarkey更容易阅读。

The benefit of those script-based alternatives others have suggested is they work anywhere, even on shared boxes; 其他人建议的那些基于脚本的替代品的好处是它们可以在任何地方工作,即使在共享盒子上也是 setting the include path requires a little more thought and effort but as I mentioned lets you start using __autoload which just the coolest. 设置包含路径需要更多的思考和努力,但正如我所提到的,让你开始使用只有最酷的__autoload。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM