Last active
October 2, 2023 22:50
-
-
Save Oldenborg/dbea4eb6df6cabf388310e6b0168262f to your computer and use it in GitHub Desktop.
Laravel test trait: assert JSON exact
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace Tests\Traits; | |
use Illuminate\Testing\TestResponse; | |
use Illuminate\Support\Arr; | |
use PHPUnit\Framework\Assert as PHPUnit; | |
trait AssertJson | |
{ | |
/* @before */ | |
public function setUp(): void | |
{ | |
parent::setUp(); | |
$this->setUpAssertJson(); | |
} | |
public function setUpAssertJson(): void | |
{ | |
TestResponse::macro('assertJsonStructureExact', function (array $structure = null, $responseData = null) { | |
$transformStructure = function ($structure, $prefix = '') use (&$transformStructure) { | |
$result = []; | |
foreach ($structure as $key => $value) { | |
if (is_array($value) && array_keys($value) !== range(0, count($value) - 1)) { | |
$result = array_merge($result, $transformStructure($value, $prefix . $key . '.')); | |
} elseif (is_array($value)) { | |
foreach ($value as $k) { | |
$result[] = $prefix . $key . '.' . $k; | |
} | |
} else { | |
$result[] = $prefix . $value; | |
} | |
} | |
return $result; | |
}; | |
$expectedKeys = $transformStructure($structure); | |
sort($expectedKeys); | |
if ($responseData === null) { | |
$responseData = json_decode($this->getContent(), true); | |
} | |
$responseKeys = Arr::dot($responseData); | |
$responseKeys = array_keys($responseKeys); | |
sort($responseKeys); | |
$missingKeys = array_diff($expectedKeys, $responseKeys); | |
$extraKeys = array_diff($responseKeys, $expectedKeys); | |
$errorMessage = ""; | |
if (!empty($extraKeys)) { | |
$prettyList = "[\n '" . implode("',\n '", $extraKeys) . "'\n]"; | |
$errorMessage .= "The response had the following unexpected parameters:\n" . $prettyList . "."; | |
} | |
if (!empty($missingKeys)) { | |
$prettyList = "[\n '" . implode("',\n '", $missingKeys) . "'\n]"; | |
$errorMessage .= "The response is missing the following parameters:\n" . $prettyList . "."; | |
} | |
PHPUnit::assertTrue(empty($missingKeys) && empty($extraKeys), $errorMessage); | |
return $this; | |
}); | |
} | |
} |
I have finally taken the time to update this Trait so it works with the lastest version of Laravel (10)
At the same time, I have implemented more meaningful error messages that will be visible in the console.
FAILED Tests\Feature\AuthenticationTest > a guest can register
The response had the following unexpected parameters:
[
'data.token',
'data.user.created_at',
'data.user.email_verification_token',
'data.user.updated_at'
],
The response is missing the following parameters:
[
'status'
].
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I havent look at this trait for a long time. And I haven't been doing much Laravel development the past few years. @IllyaMoskvin do you suggest I update my Trait to reflect this change to
$responseData = $this->decodeResponseJson()->json();
?