framework: [5.4] Route not defined (consistently configure the name of the router)

  • Laravel Version: 5.4.21
  • PHP Version: 7.1

Description:

InvalidArgumentException in UrlGenerator.php line 304:
Route [home] not defined.

Steps To Reproduce:

If requried custom routes.php from ServicesProvider and If you initialize the name of the router at the last moment, this router is not listed (router=>nameList)

Route::get('/')->uses('Controller@index')->name('home');

// InvalidArgumentException in UrlGenerator.php line 304:
// Route [home] not defined.
route('home') ;

If you change the initialization of the name places the router, then everything is okay.

Route::name('home')->get('/')->uses('Controller@index');

// this OK!
route('home') ;

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Reactions: 3
  • Comments: 19 (6 by maintainers)

Most upvoted comments

don’t use a {{ route(‘/’) }} command on views use {{ url(‘/’) }}

Closing for lack of activity.

Solved deleting bootstrap/cache/routes.php file.

So I encountered this in relation to testing a package (using orchestra/testbench). I found that if I used Auth::routes() in the test scenario, subsequent calls to route('login') would fail with Route [login] not defined.

I.e. the following fails in a test:

Auth::routes();

route('login'); // throws exception as login is not defined

Encountered when updating to Laravel 5.7 because that adds an authentication middleware that has a call to route('login') within it here: https://github.com/laravel/laravel/blob/develop/app/Http/Middleware/Authenticate.php#L17

Having dug into this, the difference between the test scenario and a real application is that the real application would define its routes via its RouteServiceProvider. Within that service provider, the name and action lookups are refreshed here: https://github.com/laravel/framework/blob/5.6/src/Illuminate/Foundation/Support/Providers/RouteServiceProvider.php#L35-L38

The solution in setting up the test scenario is therefore to do the following:

Auth::routes();
app('router')->getRoutes()->refreshNameLookups();
app('router')->getRoutes()->refreshActionLookups();

route('login'); // this now works

Not ideal but sorts out testing the package. The fundamental cause is if you use the name() method after the route has been created by the router, it has already been added to the router’s route collection - so the name is set after the route collection has added the route to its internal map of route names.

Posting this because this took a while to find the solution for, so hopefully I can save some other people a lot of time!

/cc @themsaid

Updated routes definition as:

Route::name('web.garage.signup')->any('/alta', 'Garage@signup');
Route::name('web.location.city')->any('/location/city/{_id?}', 'Location@city');

All routes works on all environments.


UPDATED: not working on all enviroments.

I have a similar problem when creating routes in tests. The order of name() and get() seems important. Here is a simple example :

<?php

namespace Tests;

use Illuminate\Support\Facades\Route;
use Tests\TestCase;

class RouteNameTest extends TestCase {
    public function testRouteName()
    {
        // The following works :
        // Route::name('test.test')
        //     ->get('/test', function() {
        //         return 'Hello world!';
        //    });

        // But this does not work :
        Route::get('/test', function() {
            return 'Hello world!';
        })->name('test.test');

        $uri = route('test.test');
        $response = $this->get($uri);
        $response->assertSee('Hello world!');
    }
}

Unfortunately, there is such a piercing, but does not reach, describing it more de-atal ((( If in brief, then I created my service provider and in it I connect router files. If I specify in the files of the router:

Route::get('..', '...')->name('test_1');
route('test_1');

That, the error InvalidArgumentException in UrlGenerator.php takes off And if you do this:

Route::name('test_1')->get('..', '...');

That there is no mistake