Currently, I am writing tests for my Laravel application. However, one test fails and I don't know why or how to solve it. I am running on Laravel 10 and PHP 8.2.3.
I have products and posts. Both models are morphed to the table and model comments because a user can write a comment under a product and under a post.
This is my route for the index
function of the comments for either a product or a post with a given id
:
Route::get('/comments/{commentableType}/{commentableId}', [CommentController::class, 'index'])->name('comments.index');
In the following, you will see my RouteServiceProvider
. Here you can see, how I have binded the commentableType
and commentableId
. The strange thing now is, when I dd
the line (new $model)->where('id', $id)->firstOrFail();
the correct product or post for the given id
is being returned. Therefore, the route binding should be correct, I guess.
class RouteServiceProvider extends ServiceProvider
{
public function boot(): void
{
$this->routes(function () {
Route::middleware('api')
->prefix('api/v1')
->namespace($this->namespace)
->domain(config('app.domain'))
->group(base_path('routes/api/comment.php'));
});
// Defines a pattern for categoryType
Route::pattern('categoryType', 'product|post');
// Returns the id of the product or post
Route::bind('commentableId', function ($id) {
$type = app()->request->route('commentableType');
$models = ['product' => Product::class, 'post' => Post::class];
$model = $models[$type];
return (new $model)->where('id', $id)->firstOrFail();
});
}
}
This is my CommentController@index
function:
public function index(IndexCommentRequest $request, String $commentableType, Product | Post $commentableModel): JsonResponse
{
$comments = $request->perform($commentableType, $commentableModel);
return $this->successWithPayload(new CommentResource($comments));
}
And this is my IndexCommentRequest
file
class IndexCommentRequest extends FormRequest
{
public function authorize(): bool
{
return true;
}
public function rules(): array
{
return [
'sorting' => [
'required',
'string',
'in:popular,discussed,newest',
],
];
}
public function perform(String $commentableType, Product | Post $commentableModel): LengthAwarePaginator
{
return $commentableModel->comments($this->input('sorting'))
->with('children')
->paginate(10);
}
}
I have absolutely no idea why the following error is being thrown. I have already tried to google it but found no solution... I am so confused that the correct model is being found and therefore also returned but then the following error is being thrown:
array:5 [ // tests/Feature/Http/CommentController/IndexCommentTest.php:30
"message" => "Call to undefined method ReflectionUnionType::getName()"
"exception" => "Error"
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Support/Reflector.php"
"line" => 151
"trace" => array:62 [
0 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/RouteSignatureParameters.php"
"line" => 31
"function" => "isParameterBackedEnumWithStringBackingType"
"class" => "Illuminate\Support\Reflector"
"type" => "::"
]
1 => array:3 [
"function" => "Illuminate\Routing\{closure}"
"class" => "Illuminate\Routing\RouteSignatureParameters"
"type" => "::"
]
2 => array:3 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/RouteSignatureParameters.php"
"line" => 31
"function" => "array_filter"
]
3 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Route.php"
"line" => 533
"function" => "fromAction"
"class" => "Illuminate\Routing\RouteSignatureParameters"
"type" => "::"
]
4 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/ImplicitRouteBinding.php"
"line" => 80
"function" => "signatureParameters"
"class" => "Illuminate\Routing\Route"
"type" => "->"
]
5 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/ImplicitRouteBinding.php"
"line" => 28
"function" => "resolveBackedEnumsForRoute"
"class" => "Illuminate\Routing\ImplicitRouteBinding"
"type" => "::"
]
6 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Router.php"
"line" => 947
"function" => "resolveForRoute"
"class" => "Illuminate\Routing\ImplicitRouteBinding"
"type" => "::"
]
7 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Middleware/SubstituteBindings.php"
"line" => 41
"function" => "substituteImplicitBindings"
"class" => "Illuminate\Routing\Router"
"type" => "->"
]
8 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Routing\Middleware\SubstituteBindings"
"type" => "->"
]
9 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Middleware/ThrottleRequests.php"
"line" => 126
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
10 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Middleware/ThrottleRequests.php"
"line" => 92
"function" => "handleRequest"
"class" => "Illuminate\Routing\Middleware\ThrottleRequests"
"type" => "->"
]
11 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Middleware/ThrottleRequests.php"
"line" => 54
"function" => "handleRequestUsingNamedLimiter"
"class" => "Illuminate\Routing\Middleware\ThrottleRequests"
"type" => "->"
]
12 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Routing\Middleware\ThrottleRequests"
"type" => "->"
]
13 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/app/Http/Middleware/JsonResponse.php"
"line" => 20
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
14 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "App\Http\Middleware\JsonResponse"
"type" => "->"
]
15 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 116
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
16 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Router.php"
"line" => 797
"function" => "then"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
17 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Router.php"
"line" => 776
"function" => "runRouteWithinStack"
"class" => "Illuminate\Routing\Router"
"type" => "->"
]
18 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Router.php"
"line" => 740
"function" => "runRoute"
"class" => "Illuminate\Routing\Router"
"type" => "->"
]
19 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Routing/Router.php"
"line" => 729
"function" => "dispatchToRoute"
"class" => "Illuminate\Routing\Router"
"type" => "->"
]
20 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php"
"line" => 200
"function" => "dispatch"
"class" => "Illuminate\Routing\Router"
"type" => "->"
]
21 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 141
"function" => "Illuminate\Foundation\Http\{closure}"
"class" => "Illuminate\Foundation\Http\Kernel"
"type" => "->"
]
22 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TransformsRequest.php"
"line" => 21
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
23 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/ConvertEmptyStringsToNull.php"
"line" => 31
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Middleware\TransformsRequest"
"type" => "->"
]
24 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull"
"type" => "->"
]
25 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TransformsRequest.php"
"line" => 21
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
26 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TrimStrings.php"
"line" => 40
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Middleware\TransformsRequest"
"type" => "->"
]
27 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Middleware\TrimStrings"
"type" => "->"
]
28 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/ValidatePostSize.php"
"line" => 27
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
29 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Middleware\ValidatePostSize"
"type" => "->"
]
30 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/PreventRequestsDuringMaintenance.php"
"line" => 86
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
31 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Middleware\PreventRequestsDuringMaintenance"
"type" => "->"
]
32 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Http/Middleware/HandleCors.php"
"line" => 62
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
33 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Http\Middleware\HandleCors"
"type" => "->"
]
34 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Http/Middleware/TrustProxies.php"
"line" => 39
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
35 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 180
"function" => "handle"
"class" => "Illuminate\Http\Middleware\TrustProxies"
"type" => "->"
]
36 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php"
"line" => 116
"function" => "Illuminate\Pipeline\{closure}"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
37 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php"
"line" => 175
"function" => "then"
"class" => "Illuminate\Pipeline\Pipeline"
"type" => "->"
]
38 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php"
"line" => 144
"function" => "sendRequestThroughRouter"
"class" => "Illuminate\Foundation\Http\Kernel"
"type" => "->"
]
39 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Testing/Concerns/MakesHttpRequests.php"
"line" => 563
"function" => "handle"
"class" => "Illuminate\Foundation\Http\Kernel"
"type" => "->"
]
40 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Testing/Concerns/MakesHttpRequests.php"
"line" => 324
"function" => "call"
"class" => "Illuminate\Foundation\Testing\TestCase"
"type" => "->"
]
41 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/tests/Feature/Http/CommentController/IndexCommentTest.php"
"line" => 24
"function" => "get"
"class" => "Illuminate\Foundation\Testing\TestCase"
"type" => "->"
]
42 => array:3 [
"function" => "Tests\Feature\Http\CommentController\{closure}"
"class" => "P\Tests\Feature\Http\CommentController\IndexCommentTest"
"type" => "->"
]
43 => array:3 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/src/Factories/TestCaseFactory.php"
"line" => 151
"function" => "call_user_func"
]
44 => array:3 [
"function" => "Pest\Factories\{closure}"
"class" => "P\Tests\Feature\Http\CommentController\IndexCommentTest"
"type" => "->"
]
45 => array:3 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/src/Concerns/Testable.php"
"line" => 301
"function" => "call_user_func_array"
]
46 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/src/Support/ExceptionTrace.php"
"line" => 29
"function" => "Pest\Concerns\{closure}"
"class" => "P\Tests\Feature\Http\CommentController\IndexCommentTest"
"type" => "->"
]
47 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/src/Concerns/Testable.php"
"line" => 300
"function" => "ensure"
"class" => "Pest\Support\ExceptionTrace"
"type" => "::"
]
48 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/src/Concerns/Testable.php"
"line" => 278
"function" => "__callClosure"
"class" => "P\Tests\Feature\Http\CommentController\IndexCommentTest"
"type" => "->"
]
49 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/Framework/TestCase.php"
"line" => 1608
"function" => "__test"
"class" => "P\Tests\Feature\Http\CommentController\IndexCommentTest"
"type" => "->"
]
50 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/laravel/framework/src/Illuminate/Foundation/Testing/TestCase.php"
"line" => 173
"function" => "runTest"
"class" => "PHPUnit\Framework\TestCase"
"type" => "->"
]
51 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/Framework/TestCase.php"
"line" => 1214
"function" => "runTest"
"class" => "Illuminate\Foundation\Testing\TestCase"
"type" => "->"
]
52 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/Framework/TestResult.php"
"line" => 728
"function" => "runBare"
"class" => "PHPUnit\Framework\TestCase"
"type" => "->"
]
53 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/Framework/TestCase.php"
"line" => 964
"function" => "run"
"class" => "PHPUnit\Framework\TestResult"
"type" => "->"
]
54 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/Framework/TestSuite.php"
"line" => 684
"function" => "run"
"class" => "PHPUnit\Framework\TestCase"
"type" => "->"
]
55 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/Framework/TestSuite.php"
"line" => 684
"function" => "run"
"class" => "PHPUnit\Framework\TestSuite"
"type" => "->"
]
56 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/TextUI/TestRunner.php"
"line" => 653
"function" => "run"
"class" => "PHPUnit\Framework\TestSuite"
"type" => "->"
]
57 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/phpunit/phpunit/src/TextUI/Command.php"
"line" => 144
"function" => "run"
"class" => "PHPUnit\TextUI\TestRunner"
"type" => "->"
]
58 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/src/Console/Command.php"
"line" => 119
"function" => "run"
"class" => "PHPUnit\TextUI\Command"
"type" => "->"
]
59 => array:5 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/bin/pest"
"line" => 62
"function" => "run"
"class" => "Pest\Console\Command"
"type" => "->"
]
60 => array:3 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/pestphp/pest/bin/pest"
"line" => 63
"function" => "{closure}"
]
61 => array:3 [
"file" => "/Users/jt/Desktop/Bitbucket/Valet/dbb/vendor/bin/pest"
"line" => 120
"function" => "include"
]
]
]
This is my Pest test function but I get this error also without Pest or without PHPUnit when trying to make a normal API call to this route. Therefore, it has nothing to do with my testing code:
it('displays the first 10 comments for a given commentable model with children', function () {
$product = Product::factory()->create();
$comments = Comment::factory()->count(15)->create([
'commentable_type' => Product::class,
'commentable_id' => $product->id,
]);
$comments->each(function ($comment) {
Comment::factory()->count(2)->create([
'parent_id' => $comment->id,
]);
});
$response = $this->get(route('comments.index', [
'commentableType' => 'product',
'commentableId' => $product->id,
'sorting' => 'newest',
]));
dd($response->json());
});
I am very thankful for every answer to help me solve this problem!