Php 具有文件系统功能的测试对象

Php 具有文件系统功能的测试对象,php,unit-testing,filesystems,integration-testing,Php,Unit Testing,Filesystems,Integration Testing,我正在编写一些广泛使用文件系统的对象。我不确定什么是测试它们的正确方法 我知道理论上我应该在一些对象中抽象文件系统功能,然后对它们进行模拟,但在我的例子中这是毫无意义的:我想测试的类的主要用途是管理文件。因此,在测试新对象时,我也会遇到同样的问题,只是移动了一个级别 我认为进行测试的唯一方法是实际使用文件系统。问题是测试将在浏览器和命令行中运行,因此我需要在每个人都具有写访问权限的目录中工作。此外,这似乎不是一个非常可移植的解决方案 有什么想法吗?引入非常低级的php函数,这些函数除了调用文件系

我正在编写一些广泛使用文件系统的对象。我不确定什么是测试它们的正确方法

我知道理论上我应该在一些对象中抽象文件系统功能,然后对它们进行模拟,但在我的例子中这是毫无意义的:我想测试的类的主要用途是管理文件。因此,在测试新对象时,我也会遇到同样的问题,只是移动了一个级别

我认为进行测试的唯一方法是实际使用文件系统。问题是测试将在浏览器和命令行中运行,因此我需要在每个人都具有写访问权限的目录中工作。此外,这似乎不是一个非常可移植的解决方案


有什么想法吗?

引入非常低级的php函数,这些函数除了调用文件系统函数之外什么都不做,并在代码中使用它们

然后,在您的测试线束中,用存根(可能记录调用了这些函数)覆盖这些函数。通过这种方式,您可以验证您的代码是否会在实时系统中调用正确的低级PHP函数。对于单元测试,这是您所能做的,真的。

您可以:

vfsStream是虚拟文件系统的流包装器,在模拟真实文件系统的单元测试中可能会有所帮助[…]如果系统上有PEAR安装程序,则只需执行以下命令:

$ pear channel-discover pear.bovigo.org
$ pear install bovigo/vfsStream-beta

在我看来,你有三个选择:

  • 接受某些测试作为集成测试更好。通过创建一个小世界来启动测试(在%TEMP%中,基于类/方法名称),然后在完成后销毁它
  • 检查抽象层,并从类中提取文件IO。用户可以为此创建一个接口。其余部分使用集成测试(但这将非常小)。这与上面的不同之处在于,不是执行file.Read,而是编写意图,比如ioThingie.loadSettings()
  • 模拟IO(如上所述)

我通常会混合使用选项1和选项2,在边缘情况下只使用3个选项,正如我在C#中发现的那样,模拟原始IO层(System.IO.File)实际上只表明您可以编写模拟语句,并且使您的测试过于依赖于实现,但是上面的vfs看起来像是模拟FS,另一个变体是模拟使用文件系统的PHP函数。不确定这是不是最好的解决方案,但它确实有效。 有一个-PHPUnit扩展简化了模拟PHP函数

例如:

class Tests extends PHPUnit_Framework_TestCase {
    // ... setUp, tearDown, other tests...

    function test_1(){
        $file_size_to_return = 10;

        $fake_filesize = new PHPUnit_Extensions_MockFunction('filesize', $this->obj->tested_method);
        $fake_filesize->expects($this->once())->will($this->returnValue($file_size_to_return));

        $this->obj->tested_method(); // actually run method we want test that contains filesize() function...
    }
}

哈-你是一个垃圾文件系统。我的上一个文件系统比你好多了,哈哈。那种嘲弄?;)PHPUnit文档不完整。有更好的参考书吗?它缺少关于如何模拟文件系统的信息(如在模拟文件存在、指定模拟文件的内容等方面)。@dpk有,还有一个感谢,我在前面查看了这些信息,但仍然被难倒。最后,我找到了我遗漏的部分:vfsStream只对前缀为“vfs://”的文件进行了抽象。回想起来,这是显而易见的,但我尝试了各种方法,试图让它使用裸文件(例如“/usr/local/blah/blah.txt”)。希望这句话能对未来的人们有所帮助。似乎glob()不起作用将成为我的交易破坏者:(.问题是,我的对象主要处理文件系统,如果我在集成测试中移动文件系统功能,就没有太多需要测试的内容。最初的问题没有提到单元测试,这似乎特别是一个与集成相关的问题。我本以为模仿任何东西都会破坏t他在测试吗?