phpunit中的可重用测试

phpunit中的可重用测试,phpunit,integration-testing,Phpunit,Integration Testing,假设我想在三种状态下测试数据库一致性: 当数据被插入时——我想确保一定数量的行被插入到数据库表中 数据更新后-我想重复行数测试(插入后的行数必须相同) 当数据被删除时-我想确保所有数据都被删除 此外,当我插入或更新时,一些文件(图像)可以上载到服务器,文件路径将存储在数据库中。所以我还要检查文件数量是否与数据库文件表中的行数量一致 换句话说,我想在插入和更新之后重用两个方法:testRowsAmountOnAddUpdate和testFilesAmountOnAddUpdate 组织代码的最佳方

假设我想在三种状态下测试数据库一致性:

  • 当数据被插入时——我想确保一定数量的行被插入到数据库表中

  • 数据更新后-我想重复行数测试(插入后的行数必须相同)

  • 当数据被删除时-我想确保所有数据都被删除

  • 此外,当我插入或更新时,一些文件(图像)可以上载到服务器,文件路径将存储在数据库中。所以我还要检查文件数量是否与数据库文件表中的行数量一致

    换句话说,我想在插入和更新之后重用两个方法:
    testRowsAmountOnAddUpdate
    testFilesAmountOnAddUpdate


    组织代码的最佳方式是什么?我应该使用固定装置吗

    事实上,我已经找到了这个结构(代码简化了):


    正如一些评论所说,只要有可能,最好模拟数据库安装层,但是有时您只需要测试代码和数据库之间的交互,特别是对于复杂的查询。我个人将此用于数据库固定装置和断言:(呃,免责声明,我也会死记硬背,所以我有偏见)

    它允许以管道分隔的表格格式插入数据,同时将默认值插入任何非空列,然后检查数据库的状态

    $this->setupTables("
            [address]
            address_id  |company
            1           |me
            3           |you
    
            [user]
            user_id  |name
            10       |John
            20       |Mary
    
        ");
    // excercise the SUT, e.g.
    $this->addressService->addEntry("them");
    
    $this->assertTableStateContains("
            [address]
            address_id  |company
            1           |me
            3           |you
            100         |them #this is the new row inserted
    
            [user]
            user_id  |name
            10       |John
            20       |Mary
            ");
    }
    
    也许您可以将它们包装在
    testRowsAmountOnAddUpdate
    testFilesAmountOnAddUpdate
    中,对于文件上载,我将读取字段的值,然后断言指定的文件存在


    请注意,DBUnit也是一种很好的方法,就我个人而言,我喜欢尽可能简单简洁地编写测试,并且只关注在测试中实际更改/相关的信息。其他fixture对我来说只是有点冗长。

    通常,您不会担心代码中的实际数据库测试,而是模拟数据库调用。这允许您的代码继续运行,就好像行是根据返回值添加或不添加一样。毕竟,您是在测试代码,而不是数据库。但是,当您想要测试与数据库接口的库时,您需要进行所述的检查。PHPUnit有一个DBUnit扩展用于此目的,所以您可以在库的单元测试中使用数据库。IE:不要将数据加载到数据库来查询和统计返回的记录。让我解释一下我正在经历的整个过程。首先,我使用的是一个php框架。这个框架有ORM模型,可以帮助我访问数据库中的数据。还可以在框架的设置中存储数据库连接设置。数据库连接在框架源中初始化。第二,我有一个外部数据源。我从那个源下载数据,解析它并应用到ORM模型。此时,外部源数据和本地数据库数据之间的差异可以用3种状态来描述:新行来自外部源-我应该将其插入我的数据库,源中存在行-我应该更新我的数据库中的行(基本上删除未删除的行并插入新行),如果我的本地数据库中存在一些行,但它们不是来自源代码,我应该将它们从我的数据库中删除。现在,我想从测试中得到的是,我的工人是否正确处理了所有这些状态。是否插入/更新/删除了预期的行数。我还想检查是否成功上传(或删除)了外部源文件(图像)中的描述,并且文件数量与DB文件表中的行数量相对应。正如我从DBUnit手册中理解的那样:我应该设置并创建到我的DB的连接,使用示例数据(xml文件)创建装置,这不是我真正想要的。我想在现实世界条件下测试我的员工行为。它与真实数据库的交互方式(或者我可以使用数据库的生产副本进行测试)。我不太明白为什么我不能将数据加载到数据库来查询和统计记录?
    $this->setupTables("
            [address]
            address_id  |company
            1           |me
            3           |you
    
            [user]
            user_id  |name
            10       |John
            20       |Mary
    
        ");
    // excercise the SUT, e.g.
    $this->addressService->addEntry("them");
    
    $this->assertTableStateContains("
            [address]
            address_id  |company
            1           |me
            3           |you
            100         |them #this is the new row inserted
    
            [user]
            user_id  |name
            10       |John
            20       |Mary
            ");
    }