首页 文章

如何在Laravel 5中构建模块化应用程序?

提问于
浏览
63

我想将我的应用程序分成模块 . 例如,会有一个“核心”模块,其中包含基本登录功能,应用程序布局/格式(CSS等),用户管理和日记 .

稍后我可以创建其他模块,如联系人管理器,可以轻松地从应用程序中添加或删除 .

应用程序导航中会有一些逻辑用于确定存在哪些模块以及显示/隐藏指向它们的链接 .

我如何在目录结构,命名空间和其他任何需要的方面做到这一点?


我正在看creolab / laravel-modules,但是它说它适用于Laravel 4.我还能以完全相同的方式使用它吗?

文档说在每个模块目录中放置模型,控制器和视图,但这如何与路由一起使用?理想情况下,我希望每个模块都有自己的routes.php文件 . 所有这些如何与 httpresources 目录中的东西一起工作?


我在考虑这样的事情:

Module idea

但我不知道如何让它发挥作用 .


我刚刚在这里尝试了教程:

http://creolab.hr/2013/05/modules-in-laravel-4/

没有额外的库等,只需要纯粹的Laravel 5 .

我似乎碰到了一堵砖墙,上面写着错误信息:

FatalErrorException in ServiceProvider.php line 16:
Call to undefined method Illuminate\Config\Repository::package()

关于以下内容:

<?php namespace App\Modules;

abstract class ServiceProvider extends \Illuminate\Support\ServiceProvider
{

    public function boot()
    {
        if ($module = $this->getModule(func_get_args())) {
            $this->package('app/' . $module, $module, app_path() . '/modules/' . $module);
        }
    }

    public function register()
    {
        if ($module = $this->getModule(func_get_args())) {
            $this->app['config']->package('app/' . $module, app_path() . '/modules/' . $module . '/config');

// Add routes
            $routes = app_path() . '/modules/' . $module . '/routes.php';
            if (file_exists($routes)) require $routes;
        }
    }

    public function getModule($args)
    {
        $module = (isset($args[0]) and is_string($args[0])) ? $args[0] : null;

        return $module;
    }

}

造成这种情况的原因是什么?如何解决?


现在更多地了解这一点 . 让我的包/模块路由和视图工作很棒:

abstract class ServiceProvider extends \Illuminate\Support\ServiceProvider
{

    public function boot()
    {
        if ($module = $this->getModule(func_get_args())) {
            include __DIR__.'/'.$module.'/routes.php';
        }
        $this->loadViewsFrom(__DIR__.'/'.$module.'/Views', 'core');
    }

    public function register()
    {
        if ($module = $this->getModule(func_get_args())) {

        }
    }

    public function getModule($args)
    {
        $module = (isset($args[0]) and is_string($args[0])) ? $args[0] : null;

        return $module;
    }

}

我还有最后一个问题,如何从我的包中加载所有控制器,就像 loadViewsFrom() 方法的工作方式一样?

6 回答

  • 32

    我似乎已经全力以赴了 .

    我会在这里发布它,以防它帮助其他初学者,它只是让命名空间正确 .

    在我的composer.json中,我有:

    ...
    "autoload": {
        "classmap": [
            "database",
            "app/Modules"
        ],
        "psr-4": {
            "App\\": "app/",
            "Modules\\": "Modules/"
        }
    }
    

    我的目录和文件最终结果如下:

    enter image description here

    我通过将指定命名空间的组中的控制器包装到我的核心模块router.php来工作:

    Route::group(array('namespace' => 'Modules\Core'), function() {
        Route::get('/test', ['uses' => 'TestController@index']);
    });
    

    我想当我为包做我的模型时,它将是一个类似的例子,正确的命名空间 .

    感谢您的帮助和耐心!

  • 6

    解:

    Step1:在“app /”中创建文件夹“Modules”


    Step2:在Modules文件夹中创建模块(Module1(假设管理模块))

    Inside admin module : create the following folder 
    
     1. Controllers  (here will your controller files)
     2. Views  (here will your View files)
     3. Models  (here will your Model files)
     4. routes.php (here will your route code in this file)
    

    同样,您可以创建多个模块

    Module2( suppose API )
    -Controllers
    -Views
    -Models
    -routes.php
    

    Step3:在“Modules /”文件夹中创建ModulesServiceProvider.php


    Step4:在ModulesServiceProvider.php中粘贴以下代码

    <?php
    
    namespace App\Modules;
    
    /**
     * ServiceProvider
     *
     * The service provider for the modules. After being registered
     * it will make sure that each of the modules are properly loaded
     * i.e. with their routes, views etc.
     *
     * @author kundan Roy <query@programmerlab.com>
     * @package App\Modules
     */
    
    use Illuminate\Support\Facades\Route;
    use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;
    
    class ModulesServiceProvider extends ServiceProvider {
    
        /**
         * Will make sure that the required modules have been fully loaded
         *
         * @return void routeModule
         */
        public function boot() {
            // For each of the registered modules, include their routes and Views
            $modules=config("module.modules");
    
            while (list(,$module)=each($modules)) {
    
                // Load the routes for each of the modules
    
                if (file_exists(DIR.'/'.$module.'/routes.php')) {
    
                    include DIR.'/'.$module.'/routes.php';
                }
    
                if (is_dir(DIR.'/'.$module.'/Views')) {
                    $this->loadViewsFrom(DIR.'/'.$module.'/Views',$module);
                }
            }
        }
    
        public function register() { }
    
    }
    

    步骤5:在'config / app.php'文件中添加以下行

    App\Modules\ModulesServiceProvider::class,
    

    Step6:在'config'文件夹中创建module.php文件Step7:在module.php中添加以下代码(path =>“config / module.php”)

    <?php
    
    return [
        'modules'=>[
            'admin',
            'web',
            'api'
        ]
    ];
    

    注意:您可以添加模块名称,无论您创建了哪个 . 这里有模块 .

    步骤8:运行此命令

    composer dump-autoload
    
  • 2

    有点晚了,但如果你想在未来的项目中使用模块,我已经写了一个模块生成器 . 它通过 php artisan make:module name 生成模块 . 您也可以删除 app/Modules 文件夹中的一些模块,它们可以使用/工作了 . 看一看 . 节省一些时间;)

    l5-modular

  • 9

    你也可以用pingpong-labs

    文件Here .

    Here is an example.

    您只需安装并检查该过程即可 .

    注意:我不是广告 . 刚刚通过模块支持检查了构建在Laravel上的cms . 所以认为这可能对你和其他人有所帮助 .

  • 0

    Kundan roy:我喜欢你的解决方案,但是我从StackOverflow复制了你的代码,我不得不改变引号和半引号来使它工作 - 我认为SOF取代了这些 . 同时将base更改为与base_path()更改为与Laravel的(新)格式内联 .

    namespace App\Modules;
    
    /**
    * ServiceProvider
    *
    * The service provider for the modules. After being registered
    * it will make sure that each of the modules are properly loaded
    * i.e. with their routes, views etc.
    *
    * @author kundan Roy <query@programmerlab.com>
    * @package App\Modules
    */
    
    use Illuminate\Support\Facades\Route;
    use Illuminate\Foundation\Support\Providers\RouteServiceProvider as ServiceProvider;
    
    class ModulesServiceProvider extends ServiceProvider
    {
    
    /**
    * Will make sure that the required modules have been fully loaded
    * @return void routeModule
    */
       public function boot()
    {
        // For each of the registered modules, include their routes and Views
        $modules = config("module.modules");
    
        while (list(,$module) = each($modules)) {
    
            // Load the routes for each of the modules
            if(file_exists(base_path('app/Modules/'.$module.'/routes.php'))) {
                include base_path('app/Modules/'.$module.'/routes.php');
            }
    
            // Load the views                                           
            if(is_dir(base_path('app/Modules/'.$module.'/Views'))) {
                $this->loadViewsFrom(base_path('app/Modules/'.$module.'/Views'), $module);
            }
        }
    }
    
    public function register() {}
    
    }
    
  • 2

    pingpong/modules 是一个laravel包,用于管理使用模块的大型laravel应用程序 . 模块就像一个laravel包,结构简单,有一些视图,控制器或模型 .

    它在Laravel 4和Laravel 5都有效 .

    要通过composer安装,只需将以下内容放在 composer.json 文件中:

    {
        "require": {
            "pingpong/modules": "~2.1"
        }
    }
    

    然后运行 composer install 来获取包 .

    To create a new module you can simply run :

    php artisan module:make <module-name>

    • 必填 . 将创建模块的名称 . 创建一个新模块

    php artisan module:make Blog

    Create multiple modules

    php artisan module:make Blog User Auth

    更多访问:https://github.com/pingpong-labs/modules

相关问题