Laravel 特殊用法 宏指令(Macro)你用过吗?

admin 2022-07-16 12:16:14 191

使用Laravel的时候又没遇到有些功能的调用正常,但是又没有真实存在laravel里的状态?当你了解了Laravel 宏指令,这些困惑就都解决啦!

Laravel 宏指令允许你添加自定义功能到Laravel的组件里!

直接来个例子吧!比如我们在 Request 门面里添加一个自定义功能,代码如下

Request::macro('hello', function ($name) {
    echo 'Hello ' . $name . '!';
});

Request::hello('Macro'); // outputs "Hello Macro!"

来一个更复杂更实用的 Request 宏指令 :用于检测当前的 TLD(顶级域:.com,.net,.org,.etc…)。

Request::macro('tldIs', function ($tld) {
    return Str::is('*.' . $tld, $this->root());
});
Request::tldIs('com'); // returns true for app.com
Request::tldIs('dev'); // returns false for app.com

你会注意到 Laravel 自动绑定 $this 到 Request 的上下文里,而不是在一个已经定义宏的类里。比如:

class AppServiceProvider
{

    public function boot(){
        Request::macro('context', function () {
            return get_class($this);
        }
}

/*...*/

Request::context();
// returns 'Illuminate\Http\Request'
// instead of 'App\AppServiceProvider'

让我们看一个更高级的示例。此宏有条件地基于当前 TLD 在模型上添加一个 where 语句。

Builder::macro('whenTldMatches', function($tld, $callback) {
    if (Request::tldIs($tld)) {
        call_user_func($callback->bindTo($this));
    }
    return $this;
});

SiteModel::whenTldMatches('org', function () {
    $this->where('id', '>', 5);
})->get();
// applies ->where() 在 app.org 上应用,而不在 app.com 上应用

我们应该在哪里定义它们?

服务提供者为给您的应用程序定义宏的好地方。

App\Providers\AppServiceProvider boot() 

是一个很好的注入点,比如上面的“context”但是它很快就变得臃肿。

下一步是创建一个 App\Providers\MacrosServiceProvider 并注册在 config/app.php 里。

如果某宏与之相关,我可能会创建一个 App\Providers\TldAwareServiceProvider 来容纳所有与 TLD 相关的宏。

哪些组件是 Macroable?

宏可以再任何具有 Macroable 特性的类上定义。下面是一个 Macroable 的门面和类的列表

门面

● Cache

● File

● Lang

● Request

● Response

● Route

● URL

Illuminate Classes

● Illuminate\Cache\Repository

● Illuminate\Console\Scheduling\Event

● Illuminate\Database\Eloquent\Builder

● Illuminate\Database\Eloquent\Relation

● Illuminate\Database\Query\Builder

● Illuminate\Filesystem\Filesystem

● Illuminate\Foundation\Testing\TestResponse

● Illuminate\Http\RedirectResponse

● Illuminate\Http\Request

● Illuminate\Http\UploadedFile

● Illuminate\Routing\ResponseFactory

● Illuminate\Routing\Router

● Illuminate\Routing\UrlGenerator

● Illuminate\Support\Arr

● Illuminate\Support\Collection

● Illuminate\Support\Str

● Illuminate\Translation\Translator

● Illuminate\Validation\Rule

动手

如果您发现自己在整个系统中对 Laravel 组件重复执行逻辑,请考虑使用宏以实现更好的表达和重用。

利用好了,代码更优雅,功能更实用。

可爱猫🐅Telegram电报群 https://t.me/ikeaimao

社区声明 1、本站提供的一切软件、教程和内容信息仅限用于学习和研究目的
2、本站资源为用户分享,如有侵权请邮件与我们联系处理敬请谅解!
3、本站信息来自网络,版权争议与本站无关。您必须在下载后的24小时之内,从您的电脑或手机中彻底删除上述内容
最新回复 (0)

您可以在 登录 or 注册 后,对此帖发表评论!

返回