Skip to content

Commit

Permalink
assertArrayIsIdenticalToArrayOnlyConsideringListOfKeys(): bug fix
Browse files Browse the repository at this point in the history
Follow up on 5716.

Sorry, I screwed up.

While the fix in 5716 correctly fixes the handling of array keys to be in line with PHP itself, it broke the differentiation between `isEqual` and `isIdentical` as the arrays were now being recreated in the order of the keys passed to the `$keysToBeConsidered` parameter.

This is not problematic for the `assertArrayIsEqualToArrayOnlyConsideringListOfKeys()` assertion as the array order is not relevant there.

However, it is problematic for the `assertArrayIsIdenticalToArrayOnlyConsideringListOfKeys()` assertion, where the array order is relevant.

This commit fixes it.

Includes unit test safeguarding the fix.

And while the `assertArrayIs*ToArrayIgnoringListOfKeys()` assertions are not affected, I've also included a unit test for the issue for those assertions, just to be on the safe side.
  • Loading branch information
jrfnl authored and sebastianbergmann committed Mar 10, 2024
1 parent dcb95b9 commit a6eedd5
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 16 deletions.
22 changes: 6 additions & 16 deletions src/Framework/Assert.php
Expand Up @@ -9,6 +9,8 @@
*/
namespace PHPUnit\Framework;

use function array_combine;
use function array_intersect_key;
use function class_exists;
use function count;
use function file_get_contents;
Expand Down Expand Up @@ -128,23 +130,11 @@ final public static function assertArrayIsEqualToArrayIgnoringListOfKeys(array $
*/
final public static function assertArrayIsIdenticalToArrayOnlyConsideringListOfKeys(array $expected, array $actual, array $keysToBeConsidered, string $message = ''): void
{
$filteredExpected = [];

foreach ($keysToBeConsidered as $key) {
if (isset($expected[$key])) {
$filteredExpected[$key] = $expected[$key];
}
}

$filteredActual = [];

foreach ($keysToBeConsidered as $key) {
if (isset($actual[$key])) {
$filteredActual[$key] = $actual[$key];
}
}
$keysToBeConsidered = array_combine($keysToBeConsidered, $keysToBeConsidered);
$expected = array_intersect_key($expected, $keysToBeConsidered);
$actual = array_intersect_key($actual, $keysToBeConsidered);

static::assertSame($filteredExpected, $filteredActual, $message);
static::assertSame($expected, $actual, $message);
}

/**
Expand Down
24 changes: 24 additions & 0 deletions tests/unit/Framework/AssertTest.php
Expand Up @@ -243,6 +243,30 @@ public function testAssertArrayIsIdenticalToArrayIgnoringListOfKeysInterpretsKey
$this->assertArrayIsIdenticalToArrayIgnoringListOfKeys($expected, $actual, ['1']);
}

public function testAssertArrayIsEqualButNotIdenticalToArrayOnlyConsideringListOfKeys(): void
{
$expected = ['a' => 'b', 'b' => 'c', 0 => 1, 1 => 2];
$actual = [0 => 1, 1 => 3, 'a' => 'b', 'b' => 'b'];

$this->assertArrayIsEqualToArrayOnlyConsideringListOfKeys($expected, $actual, ['a', 0]);

$this->expectException(AssertionFailedError::class);

$this->assertArrayIsIdenticalToArrayOnlyConsideringListOfKeys($expected, $actual, ['a', 0]);
}

public function testAssertArrayIsEqualButNotIdenticalToArrayIgnoringListOfKeys(): void
{
$expected = ['a' => 'b', 'b' => 'c', 0 => 1, 1 => 2];
$actual = [0 => 1, 1 => 3, 'a' => 'b', 'b' => 'b'];

$this->assertArrayIsEqualToArrayIgnoringListOfKeys($expected, $actual, ['b', 1]);

$this->expectException(AssertionFailedError::class);

$this->assertArrayIsIdenticalToArrayIgnoringListOfKeys($expected, $actual, ['b', 1]);
}

public function testAssertArrayHasIntegerKey(): void
{
$this->assertArrayHasKey(0, ['foo']);
Expand Down

0 comments on commit a6eedd5

Please sign in to comment.