我正在设置一个php项目,但我不太熟悉如何正确使用php的include/require命令.我的布局目前看起来像这样:
/public --apache points into this directory
/public/index.php
/public/blah/page.php
/utils/util1.php -- useful classes/code are stored in other directories out here
/dbaccess/db1.php
dbaccess/db1.php
require '../utils/util1.php
Run Code Online (Sandbox Code Playgroud)
公共/ index.php文件
require '../dbaccess/db1.php'
Run Code Online (Sandbox Code Playgroud)
公共/胡说/ page.php文件
require '../../dbaccess/db1.php'
Run Code Online (Sandbox Code Playgroud)
问题来自php'include'文档:
如果filename以./或../开头,则仅在当前工作目录中查找
所以public/blah/page.php失败了,因为它包含dbaccess/db1.php,它在尝试包含util1.php时会爆炸.它失败了,因为它的相对路径来自public/blah /中的原始脚本,而不是来自dbaccess /
这看起来非常愚蠢 - db1.php必须知道它被包含在哪里不起作用.
我见过这样的策略:
require_once dirname(__FILE__) . '/../utils/util1.php');
Run Code Online (Sandbox Code Playgroud)
这显然是有效的,因为现在这条道路是绝对的道路,但对我来说似乎真的很奇怪.
这是正常的吗?我应该继续沿着这条路走下去,还是我错过了一些明显的东西?
dco*_*eau 13
通常,标准约定是这样的:像@grepsedawk所说,你需要定义一个包含项目文件夹根目录的常量,如果你能包含你的包文件夹的根:
define('APP_ROOT', dirname(__FILE__));
define('INCLUDE_ROOT', APP_ROOT . "/includes");
Run Code Online (Sandbox Code Playgroud)
注意:常量名称必须是一个字符串!
此外,你会注意到我正在使用dirname(__FILE__);.如果将常量定义文件放在子目录中,则可以执行a dirname(dirname(__FILE__));,这相当于a ../.
现在还有其他一些警告.虽然PATH_SEPARATOR是一个很酷的常数,但它不是必需的.Windows在路径名中接受/或\,并且由于Linux只有用户/作为路径分隔符,所以继续使用/而不是通过重复引用来修改代码PATH_SEPARATOR.
现在您已经定义了根常量,当您需要包含配置文件时,您将要做的是一个简单的:
include INCLUDE_ROOT . '/path/to/some/file.php';
Run Code Online (Sandbox Code Playgroud)
您可能希望define(...)在根目录中的引导脚本中使用常量定义(上面的定义):
Run Code Online (Sandbox Code Playgroud)www_root/ index.php bootstrap.php
引导程序将包含定义(或include常量文件的一个),以及include每个页面都需要的任何文件.
最后你可能不会使用最后一个标准约定,但如果你开始进行面向对象编程,最常见的方法(PEAR标准)是使用_来分隔命名空间来命名你的类:
class GlobalNamespace_Namespace_Class
//...
Run Code Online (Sandbox Code Playgroud)
然后组织你的文件结构映射名称空间到子目录(字面上用/'替换所有_):
Run Code Online (Sandbox Code Playgroud)include_dir/ GlobalNamespace/ Namespace/ Class.php
并使用__autoload()函数加载您的类,但这是另一个问题.