如何使用 PHPUnit 测试数组只包含对象?

How to test array contains only objects with PHPUnit?

我正在寻找在我的 Laravel 项目中使用 PHPUnit 测试对象数组的解决方案。

这是我的干草堆数组:

[
    [
        "id" => 10,
        "name" => "Ten"
    ],
    [
        "id" => 5,
        "name" => "Five"
    ]
]

这是针数组:

[
    [
        "id" => 5,
        "name" => "Five"
    ],
    [
        "id" => 10,
        "name" => "Ten"
    ]
]

对象的顺序无关紧要,对象的键也无关紧要。唯一的问题是我们有两个对象,所有对象都具有完全相同的键和完全相同的值。

正确的解决方法是什么?

您可以使用 assertContainsEquals 方法,如下所示:

$haystack = [
    [
        'id' => 10,
        'name' => 'Ten'
    ],
    [
        'id' => 5,
        'name' => 'Five'
    ]
];

$needles = [
    [
        'name' => 'Five',
        'id' => 5
    ],
    [
        'id' => 10,
        'name' => 'Ten'
    ]
];

foreach ($needles as $needle) {
    $this->assertContainsEquals($needle, $haystack);
}

如果您打算更频繁地执行断言,您还可以创建自己的断言方法:

public function assertContainsEqualsAll(array $needles, array $haystack): void
{
    foreach ($needles as $needle) {
        $this->assertContainsEquals($needle, $haystack);
    }
}

根据@Roj Vroemen的回答,我实现了这个解决方案以实现精确匹配断言:

    public function assertArrayContainsEqualsOnly(array $needles, array $haystack, string $context = ''): void
    {
        foreach ($needles as $index => $needle) {
            $this->assertContainsEquals(
                $needle,
                $haystack,
                ($context ? $context . ': ' : '') . 'Object not found in array.'
            );

            unset($haystack[$index]);
        }

        $this->assertEmpty(
            $haystack,
            ($context ? $context . ': ' : '') . 'Not exact match objects in array.'
        );
    }