Home > other >  Laravel throwing "Function () does not exist" with method ->controller() on routes
Laravel throwing "Function () does not exist" with method ->controller() on routes

Time:01-21

I have this piece of routing here:

<?php

use App\Http\Controllers\SurveyController;

Route::middleware(['auth:api'])->controller(SurveyController::class)->group(function ($route) {
    $route->prefix('survey')->group(function ($route) {
        $route->post('show', ['show'])->name('survey_show');
        $route->post('answer', ['answer'])->name('survey_answer');
    });
    $route->prefix('member/survey')->group(function ($route) {
        $route->post('list', ['list'])->name('member_survey_list');
    });
});

The problem is that the route is unable to "find" the controller, I've tried many different approaches to this issue, I found a lot of info about this issue, but none of them could help me solve the problem, and either I get a "Function () does not exist" or a "Target class [App\\Http\\Controllers\\App\\Http\\Controllers\\SurveyController] does not exist.". I didn't want to declare the controller on each route as $route->request('path', [Controller::class, 'function']) since it will have an impact in future maintenance as the routes number grows bigger.

Am I using the method Route::controller()? Should I just write the controller on each route?

I'm using Laravel 8.83.5 and php 8.1.13.

UPDATED

my SurveyController

<?php

namespace App\Http\Controllers;

use App\Http\Resources\SurveyResource;
use App\Services\SurveyService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Validator;
use Exception;

class SurveyController extends Controller
{
    private SurveyService $service;

    public function __construct(SurveyService $surveyService)
    {
        $this->service = $surveyService;
    }

    /**
     * php doc here
     */
    public function list(Request $request): array
    {
        $data = $request->only(['keys']);

        $validator = Validator::make(
            $data,
            [
                'keys' => 'string'
            ],
            $this->customMessages
        );

        if ($validator->fails()) {
            throw new Exception($validator->errors(), 1);
        }

        return SurveyResource::method(
            $this->service->method(
                $data['keys']
            )
        );
    }

    /**
     * php doc here
     */
    public function show(Request $request): array
    {
        $data = $request->only(['keys']);

        $validator = Validator::make(
            $data,
            [
                'keys' => 'string'
            ],
            $this->customMessages
        );

        if ($validator->fails()) {
            throw new Exception($validator->errors(), 2);
        }

        return SurveyResource::show(
            $this->service->show(
                $data['keys']
            )
        );
    }

    /**
     * php doc here
     */
    public function answer(Request $request): array
    {
        $data = $request->only(['keys']);

        $validator = Validator::make(
            $data,
            [
                'keys' => 'string'
            ],
            $this->customMessages
        );

        if ($validator->fails()) {
            throw new Exception($validator->errors(), 3);
        }

        return SurveyResource::answer(
            $this->service->answer(
                $data['keys']
            )
        );
    }
}

on routes, I've tried calling the route with the method controller() as the first, this way I get a "Function () does not exist" error, the same error pops up when I use it just before the group() method

Route::controller(SurveyController::class)->middleware(['auth:api'])->group(function ($route) {    
    $route->prefix('member/survey')->group(function ($route) {
        $route->post('list', ['list'])->name('member_survey_list');
    });
});

also tried calling the route with SurveyController's method without an array, this way I get an "Target class [App\\Http\\Controllers\\App\\Http\\Controllers\\SurveyController] does not exist." error

Route::controller(SurveyController::class)->middleware(['auth:api'])->group(function ($route) {    
    $route->prefix('member/survey')->group(function ($route) {
        $route->post('list', 'list')->name('member_survey_list');
    });
});

Also saw some old threads saying that using an array inside the group() method with a namespace key and the namespace value could help, so I tried, but got a "Array to string conversion" error

Route::middleware(['auth:api'])->group(['namespace' => 'App\Http\Controllers\SurveyController'],function ($route) {    
    $route->prefix('member/survey')->group(function ($route) {
        $route->post('list', 'list')->name('member_survey_list');
    });
});

SOLUTION

Following the solution given by @matiaslauriti, first you need to remove the declaration of the namespace in the route file (you can keep the declaration if you remove it from the RouteServiceProvider.php), then you can either call it as Route::controller(ControllerName::class) or literally as Route::controller('ControllerName'). Here's my working code:

<?php

Route::controller(SurveyController::class)->middleware(['auth:api'])->group(function ($route) {
    $route->prefix('survey')->group(function ($route) {
        $route->post('show', 'show')->name('survey_show');
        $route->post('answer', 'answer')->name('survey_answer');
    });
    $route->prefix('member/survey')->group(function ($route) {
        $route->post('list', 'list')->name('member_survey_list');
    });
});

CodePudding user response:

If you are getting App\\Http\\Controllers\\App\\Http\\Controllers\\SurveyController error, that means you only have to pass SurveyController literally:

Route::controller('SurveyController')->middleware(['auth:api'])->group(function ($route) {    
    $route->prefix('member/survey')->group(function ($route) {
        $route->post('list', ['list'])->name('member_survey_list');
    });
});

I would recommend to switch to the new routing system, delete $namespace like this file and from everywhere on that file.

Then, you can do controller(SurveyController::class)

  • Related