elfsundae/laravel-apps

Laravel 多应用程序支持。

0.9.0 2022-02-19 21:24 UTC

This package is auto-updated.

Last update: 2024-09-20 02:52:43 UTC


README

Latest Version on Packagist Software License tests StyleCI SymfonyInsight Grade Quality Score Code Coverage Total Downloads

本包为 Laravel 多应用程序提供基本支持。

安装

您可以使用 Composer 管理器安装此包

$ composer require elfsundae/laravel-apps

对于低于 v5.5 的 Laravel,您需要手动注册服务提供者

ElfSundae\Apps\AppsServiceProvider::class,

然后发布配置文件到您的 config 目录

$ php artisan vendor:publish --tag=laravel-apps

配置

url 配置选项定义每个应用程序的根 URL

'url' => [
    'web' => 'https://example.com',
    'admin' => 'https://example.com/admin',
    'mobile' => 'https://m.example.com',
    'api' => 'https://api.example.com',
    'assets' => 'https://assets.foo.net',
],

providers 数组列出每个应用程序的服务提供者类名,您可能需要配置以 选择性注册服务提供者

您可以使用 config 选项覆盖每个应用程序的默认配置。此外,您可能希望将所有应用程序默认值放在一个地方,而不是编辑单独的配置文件,只需将它们放在 default 键中即可

'config' => [

    'default' => [
        'app.timezone' => 'Asia/Shanghai',
        'app.log' => env('APP_LOG', 'daily'),
        'app.log_max_files' => 50,
        'filesystems.disks.public.url' => env('APP_URL_ASSETS', env('APP_URL')).'/storage',

        'debugbar.options.auth.show_name' => false,
        'debugbar.options.route.label' => false,
    ],

    'admin' => [
        'auth.defaults' => [
            'guard' => 'admin',
            'passwords' => 'admin_users',
        ],
        'filesystems.default' => 'public',
        'session.domain' => env('SESSION_DOMAIN_ADMIN', null),
    ],

    'api' => [
        'auth.defaults.guard' => 'api',
        'filesystems.default' => 's3',
    ],

],

使用

获取应用程序管理器实例

您可以使用 Apps 门面、apps() 助手函数或注入 ElfSundae\Apps\AppManager 依赖项来获取应用程序管理器实例。

检索应用程序 URL 配置

use ElfSundae\Apps\Facades\Apps;

// Get all application URLs
Apps::urls();

// Get all application identifiers
apps()->ids();

// Get URL root for the assets app
apps()->root('assets');

// Get URL domain for the api app
apps()->domain('api');

// Get URL prefix for the admin app
apps()->prefix('admin');

确定当前应用程序标识符

您可以通过应用程序管理器上的 id 方法或使用相应的 app_id 助手函数来确定当前请求的应用程序标识符

$appId = Apps::id();

$appId = app_id();

您还可以向 id 方法传递参数来检查当前应用程序标识符是否与给定的值匹配。如果标识符与给定的任何值匹配,则方法将返回 true

if (Apps::id('admin')) {
    // Currently requesting admin app
}

if (app_id('web', 'admin')) {
    // Currently requesting either web app OR admin app
}

选择性注册服务提供者

除了将所有服务提供者添加到 config/app.php 文件中之外,您可能还希望为某些子应用程序选择性地注册服务提供者以优化性能。要这样做,只需在 config/apps.php 配置文件中将提供者列表到 providers 数组中即可

'providers' => [

    'admin' => [
        Rap2hpoutre\LaravelLogViewer\LaravelLogViewerServiceProvider::class,
        Yajra\DataTables\DataTablesServiceProvider::class,
        App\Providers\AdminServiceProvider::class,
    ],

    'api' => [
        App\Providers\ApiServiceProvider::class,
    ],

],

⚠️ 如果您的应用程序运行在 Laravel 5.5+ 并支持 包发现,您还需要在 composer.json 文件中禁用可选包的发现

"extra": {
    "laravel": {
        "dont-discover": [
            "rap2hpoutre/laravel-log-viewer",
            "yajra/laravel-datatables-oracle"
        ]
    }
}

请勿担心 延迟服务提供者,因为延迟提供者仅在需要时才加载。

定义应用程序路由

应用程序管理器上的 routes 方法可以帮助您为每个应用程序定义路由组。通常,您将在 RouteServiceProvidermap 方法中调用它

class RouteServiceProvider extends ServiceProvider
{
    protected $namespace = 'App\Http\Controllers';

    /**
     * Define the routes for the application.
     *
     * @return void
     */
    public function map()
    {
        apps()->routes();
    }
}

以应用程序标识符命名的 routes 目录中的路由文件将被自动加载,例如 routes/web.phproutes/admin.php

默认情况下,routes 方法将分配名为应用程序标识符或 web 的现有中间件组到路由组,并将应用到控制器路由的命名空间为应用程序标识符的 StudlyCase

例如,apps()->routes() 等同于

// web: https://example.com
Route::group([
    'domain' => 'example.com',
    'middleware' => 'web',
    'namespace' => $this->namespace.'\Web',
], function ($router) {
    require base_path('routes/web.php');
});

// api: https://api.example.com
Route::group([
    'domain' => 'api.example.com',
    'middleware' => 'api',
    'namespace' => $this->namespace.'\Api',
], function ($router) {
    require base_path('routes/api.php');
});

// admin: https://example.com/admin
Route::group([
    'domain' => 'example.com',
    'prefix' => 'admin',
    'middleware' => 'web', // suppose if the "admin" middleware group does not exist
    'namespace' => $this->namespace.'\Admin',
], function ($router) {
    require base_path('routes/admin.php');
});

// ...

当然,您可以自由指定任何路由属性

apps()->routes([
    'web' => [
        'namespace' => $this->namespace,
    ],
    'admin' => [
        'middleware' => ['web', 'admin.ip'],
        'as' => 'admin.',
        'where' => [
            'id' => '[0-9]+',
        ],
    ],
]);

除了数组之外,您还可以将闭包传递给 routes 方法。

apps()->routes(function ($id, $apps) {
    return ['as' => $id.'.'];
});

生成 URL

您可以使用 url 方法或相应的 app_url 辅助函数来生成指定应用的路径的绝对URL。

apps()->url('admin', 'user', [$user]); // https://example.com/admin/user/123

app_url('api', 'posts'); // https://api.example.com/posts

asset 方法生成带有 assets 应用根URL的URL。

apps()->asset('js/app.js'); // https://assets.foo.net/js/app.js

为 asset() 助手定义自定义根 URL

Laravel 内置的 URL::asset 方法或相应的 assetsecure_asset 辅助函数旨在生成应用资源的URL。在大多数应用中,我们可能指定无cookie域名或使用CDN来存储资源,但是我们不能为这些内置的资源方法设置自定义根URL,并且目前还没有优雅地扩展 UrlGenerator 的方法。

您可以使用 URL::assetFromApps::asset 或自定义辅助函数来生成资源URL,但将所有 asset() 调用替换为自己的资源方法对于第三方包来说非常无聊。可能更好的解决方案是覆盖内置的 asset 辅助函数:在包含 Composer 自动加载器文件之前,在您的 public/index.php 文件中定义您的 asset 函数。

function asset($path, $secure = null)
{
    return apps()->asset($path, $secure);
}

require __DIR__.'/../vendor/autoload.php';

此包附带一个 asset.php 文件,您可以通过包含该文件来使用 assets 应用的根URL来为 asset() 辅助函数。

require __DIR__.'/../vendor/elfsundae/laravel-apps/asset.php';

require __DIR__.'/../vendor/autoload.php';

提示:相关PR laravel/framework#22372

扩展应用程序管理器

AppManager 类是可宏定义的,这意味着您可以使用 macro 方法来扩展它。

Apps::macro('route', function ($name, $parameters = []) {
    return URL::route($this->id().'.'.$name, $parameters);
});

测试

$ composer test

许可证

此包是开源软件,许可协议为 MIT 许可证