打包PHP应用程序

时间:2015-02-17 16:15:49

标签: php deployment build phar

我正在尝试从我的Web应用程序创建一个.phar文件。在php documentation's example之后,我为此目的尝试了以下内容。

<?php
$srcRoot = __DIR__ . "/../app";
$buildRoot = __DIR__ . "/../build";
$p = new Phar("$buildRoot/build.phar", 0, 'build.phar');
$p->buildFromIterator(
    new RecursiveIteratorIterator(
        new RecursiveDirectoryIterator($srcRoot)
    ),
    $srcRoot
);

但是我收到了以下错误。我对这个错误一无所知。代码有什么问题?

PHP Fatal error:  Uncaught exception 'UnexpectedValueException' with message
'Iterator RecursiveIteratorIterator returned a path "D:\site\app" that is
 not in the base directory "D:\site\app"'
in D:\site\tools\create-phar.php:7

5 个答案:

答案 0 :(得分:5)

问题的根源是RecursiveDirectoryIterator还列出了点文件 - ...。 迭代/path/to/foo时,它还会列出/path/to/foo/./path/to/foo/..,它们将转到父目录 - 基本目录之外。

因此,您必须阻止包含“..”文件,这是使用FilesystemIterator::SKIP_DOTS作为DirectoryIterator的第二个参数最容易实现的:

new RecursiveDirectoryIterator($srcRoot, FilesystemIterator::SKIP_DOTS)

答案 1 :(得分:2)

(@ cweiske - 我刚刚意识到你打败了我,我确保下次刷新页面,我最诚挚的道歉!)

您需要稍微编辑才能跳过unix路径/。和/..:

<?php
$srcRoot = __DIR__ . "/../app";
$buildRoot = __DIR__ . "/../build";
$p = new Phar("$buildRoot/build.phar", 0, 'build.phar');
$p->buildFromIterator(
    new RecursiveIteratorIterator(
        new RecursiveDirectoryIterator($srcRoot, FilesystemIterator::SKIP_DOTS)
    ),
    $srcRoot
);

答案 2 :(得分:0)

Box使您可以轻松地从源文件创建PHAR存档。基本上,您首先添加配置文件,然后只需在命令行上调用box build即可创建PHAR文件。

Matthieu Moquet有一个great blog post描述了他如何使用Box来简化PHP Cli应用程序的分发。就个人而言,我也使用Box作为CLI应用程序,但官方项目描述不仅限于CLI应用程序,而是将Box项目概括为:

  

建立和管理Phars的申请

Box项目提供了PHAR构建脚本,并负责正确设置所有路径,因此这可以解决您的问题。

答案 3 :(得分:0)

@cweiske提出的解决方案非常出色。但是,在某些情况下,您可能需要能够添加更多目录路径排除项。看一下这个使用 public class UserDetails { private int userId; private String userName; private String password; } 排除对.git目录的引用的示例:

FilterIterator

答案 4 :(得分:-1)

查看php.ini文件以检查phar.readonly字段的值。 创建phar存档必须为0。

参考:http://php.net/manual/en/phar.configuration.php#ini.phar.readonly