Маршрутизация подпапок Laravel Controller

96

Я новичок в Laravel. Чтобы попытаться сохранить свое приложение организованным, я хотел бы поместить свои контроллеры во вложенные папки папки контроллеров.

controllers\
---- folder1
---- folder2

Я попытался перейти к контроллеру, но laravel его не находит.

Route::get('/product/dashboard', 'folder1.MakeDashboardController@showDashboard');

Что я делаю не так?

Тино
источник

Ответы:

115

Для Laravel 5.3 и выше:

php artisan make:controller test/TestController

Это создаст testпапку, если она не существует, а затем создаст TestControllerвнутри.

TestController будет выглядеть так:

<?php
namespace App\Http\Controllers\test;

use Illuminate\Http\Request;
use App\Http\Controllers\Controller;

class TestController extends Controller
{
    public function getTest()
    {
        return "Yes";
    }
}

Затем вы можете зарегистрировать свой маршрут следующим образом:

Route::get('/test','test\TestController@getTest');
Ja22
источник
есть ли способ достичь того же самого для laravel 4.2
Сагар Арора
11
php artisan make:controller test\TestControllerсоздает testTestController.php, а php artisan make:controller 'test\TestController'работает. (Обратите внимание на цитаты) - Laravel 5.4
Giovanni S
2
php artisan make:controller test/TestController
Амрит Шреста
73

Добавьте свои контроллеры в свои папки:

controllers\
---- folder1
---- folder2

Создайте свой маршрут без указания папки:

Route::get('/product/dashboard', 'MakeDashboardController@showDashboard');

Бегать

composer dump-autoload

И попробуй еще раз

Антонио Карлос Рибейро
источник
думаю тебе artisan dump-autoloadтоже нужно или composer dump-autoloadдостаточно?
reikyoushin
1
Для контроллеров / просто composer. Но если у вас есть что- ClassLoader::addDirectoriesто, чего нет у композитора, вам также понадобится ремесленник.
Антонио Карлос Рибейро
Я внезапно вспомнил, что столкнулся с чем-то вроде этого ... см. Мой комментарий к ответу OP
reikyoushin
composer dump-autoloadу меня тоже работает. Если вы используете ОС Windows, вы можете использовать файл .bat для запуска composer dump-autoloadвместо того, чтобы каждый раз вводить CMD. Вот что я использую: PUSHD "E:\path\to\non-public" newline START /B "Window 1" composer dump-autoload newline pause
vinsa
7
Что, если у нас есть два контроллера с одинаковым именем в forlder1 и folder2? Например: admin / PostsController.php и frontend / PostsController.php
zennin
50

Для тех, кто использует Laravel 5, вам необходимо установить пространство имен для контроллера в подкаталоге (Laravel 5 все еще находится в разработке, и изменения происходят ежедневно)

Чтобы получить такую ​​структуру папок:

Http
----Controllers
    ----Admin
            PostsController.php
    PostsController.php

пространство имен Admin \ PostsController.php, например:

<?php namespace App\Http\Controller\Admin;

use App\Http\Controllers\Controller;

class PostsController extends Controller {

    //business logic here
}

Тогда ваш путь для этого:

$router->get('/', 'Admin\PostsController@index');

И, наконец, не надо делать ни композиторскую, ни кустарную свалку.

composer dump-autoload

или

php artisan dump
user2014679
источник
Работал у меня, по состоянию на 23.01.15. Это может измениться позже, поскольку L5 еще не вышел.
sehummel
Спасибо за этот лакомый кусочек. В LV4 вы могли пропустить использование App \ Http \ Controllers \ Controller; оператор, потому что вы расширили BaseController, который наследуется напрямую от Controller. Не в случае LV5, поскольку он расширяет контроллер напрямую, а автозагрузка PSR-4 должна знать, где найти контроллер.
Лайонел Моррисон,
4
@user? php пространство имен App \ Http \ Controller \ Admin; должно быть Controller [s] с s в конце
Sven van den Boogaart 01
Это сработало для меня, с оговоркой, что я должен был добавить «-o» в оператор композитора, например: composer dump-autoload -o
Скотт Байерс
У меня это не сработало, теперь в сообщении об ошибке говорится, что App\Http\Controllers\Auth\Controllerне найдено, почему там добавлено слово Controllerи теряется фактическое имя контроллера? Я думаю, что это делает косая черта. -oне помогло.
blamb
15

Для ** Laravel 5 или Laravel 5.1 LTS оба **, если у вас есть несколько контроллеров в папке администратора, вам Route::groupбудет очень полезно. Например:

Обновление : работает с Laravel 5.4

Моя структура папки:

Http
----Controllers
    ----Api
          ----V1
                 PostsApiController.php
                 CommentsApiController.php
    PostsController.php

PostAPIController:

<?php namespace App\Http\Controllers\Api\V1;

use App\Http\Requests;
use App\Http\Controllers\Controller;   
use Illuminate\Http\Request;

class PostApiController extends Controller {  
...

В My Route.php я установил namespaceгруппу в значение, Api\V1и в целом это выглядит так:

Route::group(
        [           
            'namespace' => 'Api\V1',
            'prefix' => 'v1',
        ], function(){

            Route::get('posts', ['uses'=>'PostsApiController@index']);
            Route::get('posts/{id}', ['uses'=>'PostssAPIController@show']);

    });

Для получения сведений о перемещении для создания подпапки перейдите по этой ссылке .

Злобный хак
источник
1
Для Laravel 5.4 это единственное решение, которое я нашел до сих пор.
mosh442
Идеальное решение
Али Адиль
Действительно идеально!
Ритис Дерескявичюс
Смена правил
9

1. создайте свою подпапку, как показано ниже:

app
----controllers
--------admin
--------home

2. настройте свой код в app / routes.php

<?php
// index
Route::get('/', 'Home\HomeController@index');

// admin/test
Route::group(
    array('prefix' => 'admin'), 
    function() {
        Route::get('test', 'Admin\IndexController@index');
    }
);
?>

3. напишите sth в app / controllers / admin / IndexController.php, например:

<?php
namespace Admin;

class IndexController extends \BaseController {

    public function index()
    {
        return "admin.home";
    }
}
?>

4. войдите на свой сайт, например : localhost / admin / test, вы увидите на странице «admin.home»

ps: пожалуйста, не обращайте внимания на мой плохой английский

Мервин
источник
2
Использование пространства имен позволяет избежать конфликта имен. +1
FDisk
6

Только что нашел способ как это сделать:

Просто добавьте пути в /app/start/global.php

ClassLoader::addDirectories(array(

    app_path().'/commands',
    app_path().'/controllers',
    app_path().'/controllers/product',
    app_path().'/models',
    app_path().'/database/seeds',

));
Тино
источник
5
Неправильно. Поскольку / controllers уже находится в базе Laravel composer.json, все, что ниже него, автоматически загружается. Вам не нужно добавлять / controllers / product на свой global.php.
Антонио Карлос Рибейро
1
@AntonioCarlosRibeiro У меня возникла проблема с попыткой поместить модели в папки, но сброс автозагрузки композитора и ремесленника, похоже, не работает. вы должны поместить их на composer.json или global.php
reikyoushin
2
Проверить это легко: после запуска composer du откройте vendor / composer / autoload_classmap.php, и ваш класс должен быть там указан.
Антонио Карлос Рибейро
6
php artisan make:controller admin/CategoryController

Здесь admin - это подкаталог в app / Http / Controllers, а CategoryController - это контроллер, который вы хотите создать внутри каталога.

Дипен
источник
6

В Laravel 5.6 предполагается, что имя вашей подпапки ' Api :

В вашем контроллере вам понадобятся эти две строки:

namespace App\Http\Controllers\Api;
use App\Http\Controllers\Controller;

И в вашем файле маршрута api.phpвам нужно:

Route::resource('/myapi', 'Api\MyController');
ДевонДахон
источник
5

Я использую Laravel 4.2. Вот как я это делаю: у
меня есть такая структура каталогов:
app
--controllers
---- admin
------ AdminController.php

После того, как я создал контроллер, я ввел composer.json путь к новому каталогу администратора:

"autoload": {
"classmap": [
"app/commands",
"app/controllers",
"app/controllers/admin",
"app/models",
"app/database/migrations",
"app/database/seeds",
"app/tests/TestCase.php"
]
}, 

Далее я побежал

composer dump-autoload

а потом

php artisan dump-autoload

Затем в routes.php я включил контроллер следующим образом:

Route::controller('admin', 'AdminController');

И все нормально работает.

Тодор Тодоров
источник
У меня работает, и мне нужно только запустить 'composer dump-
autoload
На всякий случай я использую также самозагрузку-дамп php artisan.
Тодор Тодоров
5

1) Вот как вы можете организовать свое приложение:

Каждый файл маршрута ( web.php, api.php...) объявляется в map()методе в файле

\app\Providers\RouteServiceProvider.php

При отображении файла маршрута вы можете установить ->namespace($this->namespace)для него, вы увидите его там среди примеров.

Это означает, что вы можете создать больше файлов, чтобы сделать свой проект более структурированным!

И установите для каждого из них разные пространства имен.

Но я предпочитаю установить empty stringдля пространства имен""

2) Вы можете настроить свои контроллеры на маршрутизацию нативным способом php, см. Пример:

Route::resource('/users', UserController::class);
Route::get('/agents', [AgentController::class, 'list'])->name('agents.list');

Теперь вы можете дважды щелкнуть имена контроллеров в своей среде IDE, чтобы попасть туда быстро и удобно.

Евгений Афанасьев
источник
Лучший ответ! Полностью соответствует Laravel и построен на основе того, что фреймворк уже предоставляет из коробки.
jfoliveira
4

Если вы используете Laravel 5.3 или выше, нет необходимости вдаваться в такую ​​сложность, как сказано в других ответах. Просто используйте команду artisan по умолчанию для создания нового контроллера. Например, если я хочу создать Userконтроллер в Userпапке. Я бы напечатал

php artisan make:controller User/User

В маршрутах,

Route::get('/dashboard', 'User\User@dashboard');

это было бы нормально, и теперь на localhost / dashboard находится страница.

Надеюсь это поможет.

Кушик Дас
источник
3

Я думаю, что если держать контроллеры для Admin и Front в отдельных папках, пространство имен будет работать нормально.

Пожалуйста, посмотрите на приведенную ниже структуру каталогов Laravel, она мне подходит.

app
--Http
----Controllers
------Admin
--------DashboardController.php
------Front
--------HomeController.php

Маршруты в файле "routes / web.php" будут такими, как показано ниже

/* All the Front-end controllers routes will work under Front namespace */

Route::group(['namespace' => 'Front'], function () {
    Route::get('/home', 'HomeController@index');
});

А для раздела администратора это будет выглядеть так:

/* All the admin routes will go under Admin namespace */
/* All the admin routes will required authentication, 
   so an middleware auth also applied in admin namespace */

Route::group(['namespace' => 'Admin'], function () {
    Route::group(['middleware' => ['auth']], function() {            
        Route::get('/', ['as' => 'home', 'uses' => 'DashboardController@index']);                                   
    });
});

Надеюсь это поможет!!

Махеш Ядав
источник
1

Недавно у меня была эта проблема с laravel 5.8, но я недооцениваю, что я должен правильно определить контроллер, как показано ниже:

php artisan make:controller SubFolder\MyController  // true

Не так:

php artisan make:controller SubFolder/MyController  // false

Затем вы можете получить доступ к контроллеру в routes / web.php следующим образом:

Route::get('/my', 'SubFolder\MyController@index');
Foad
источник
0

В моем случае у меня был префикс, который нужно было добавить для каждого маршрута в группе, в противном случае ответом было бы, что класс UserController не найден.

Route::prefix('/user')->group(function() {
    Route::post('/login', [UserController::class, 'login'])->prefix('/user');
    Route::post('/register', [UserController::class, 'register'])->prefix('/user');
});
Askepott
источник