【问题标题】:How to use class from blade template?如何使用刀片模板中的类?
【发布时间】:2019-08-19 15:57:39
【问题描述】:

我创建了类Helper,路径为App\Http\Helpers\

<?php

namespace App\Http\Helpers;

class Helper 
{
    public static function applyClass($user) {
        return "new";
    }

}

然后我在app.phpaliases部分注册了它:

'Helper' =>   App\Http\Helpers\Helper::class

当我尝试从刀片调用静态方法时:

<tr class="{{ \Helper::applyClass($user) }}">
<tr class="{{ Helper::applyClass($user) }}">

我收到一个错误:

Class 'Helper' not found

【问题讨论】:

  • 试试composer dump-autoload
  • 调用静态方法时不需要注入。
  • 我试过了:composer dump-autoload没有结果
  • 对不起,我花了一点时间把所有的东西都写下来了。 :)

标签: laravel laravel-5


【解决方案1】:

这不是外墙的工作方式。扩展Illuminate\Support\Facades\Facade需要自定义Facade,基本上只需要自定义Facade实现protected static function getFacadeAccessor()即可。此方法应该返回应该由外观解析的名称(或类或接口)。

外观允许您以静态方式调用实例方法(即非static 方法)。这是可行的,因为门面知道如何将对静态方法的调用重定向到门面后面的实例。这是通过实现__callStatic($method, $args) 来完成的,它只是将静态方法调用重定向到名称由getFacadeAccessor() 返回的实现。

假设您在服务容器中以名称helper 注册了一个服务。然后,您可以使用 app('helper')-&gt;getColor()app()-&gt;make('helper')-&gt;getColor() 在其上执行方法 getColor()

使用名为Helper 的外观,它通过从getFacadeAccessor() 方法将helper 作为字符串返回来解析您的getFacadeAccessor(),然后您可以使用Helper::getColor() 执行相同的操作。


在你的情况下,你现在有几个选择:

1) 使用具有静态方法的类:

与您已经做过的类似,您可以使用静态方法定义一个类。然后,您可以使用完全限定的类名 (FQCN) 从刀片视图中静态调用这些方法:

// app/Helpers/Helper.php
class Helper
{
    public static function getColor(): string
    {
        return 'blue';
    }
}

// resources/views/some/page.blade.php
<div style="color:{{ \App\Helpers\Helper::getColor() }}"> ... </div>

2) 使用带有外观的非静态类:

您可以使用与上述类似的类和非静态方法并为其添加外观:

// app/Helpers/Helper.php
class Helper
{
    public function getColor(): string
    {
        return 'blue';
    }
}

// app/Facades/Helper.php
class Helper extends \Illuminate\Support\Facades\Facade
{
    protected static function getFacadeAccessor()
    {
        return \App\Helpers\Helper::class;
    }
}

// config/app.php -> 'aliases' array
[
    // ... other facades ...
    'Helper' => \App\Facades\Helper::class,
]

// resources/views/some/page.blade.php
<div style="color:{{ \Helper::getColor() }}"> ... </div>

3) 使用全局非类帮助文件:

您还可以定义一个基本的 PHP 文件,其中包含一些全局注册的辅助函数。这些函数不是类方法,因此不需要使用类前缀调用:

// app/Helpers/color_utils.php
if (!function_exists('get_color')) {
    function get_color()
    {
        return 'blue';
    }
}

// app/Providers/HelperServiceProvider.php
class HelperServiceProvider extends \Illuminate\Support\ServiceProvider
{
    public function register(): void
    {
        $filenames = glob(app_path('Helpers/*.php'));

        if ($filenames !== false && is_iterable($filenames)) {
            foreach ($filenames as $filename) {
                require_once $filename;
            }
        }
    }
}

// config/app.php -> 'providers' array
[
    // ... other providers ...
    \App\Providers\HelperServiceProvider::class,
]

// resources/views/some/page.blade.php
<div style="color:{{ get_color() }}"> ... </div>

4) 使用类和服务注入:

另外一个不错的选择是使用服务容器将服务注入到 Blade 模板中。 Laravel 为其提供了一个名为 @inject($var, $fqdn) 的 Blade 指令。

// app/Helpers/Helper.php
class Helper
{
    public static function getColor(): string
    {
        return 'blue';
    }
}

// resources/views/some/page.blade.php
@inject('helper', \App\Helpers\Helper::class)

<div style="color:{{ $helper->getColor() }}"> ... </div>

我希望代码不言自明。文件的命名空间是故意省略的,当然你应该根据目录使用命名空间(符合PSR-4)。

如果您不需要任何依赖项并且您基本上只需要静态访问某些东西,我个人更喜欢全局帮助器(选项 3)。

【讨论】:

  • 这就是答案,很好的解释,应该蒙着眼睛接受。我错过了双重投票。
  • 是的,“这不是外观的工作方式”,但 OP 并没有尝试创建外观,只是一个类别名。他们的方法运行良好,可能他们遇到了缓存问题或其他问题。使用别名条目与使用 use 语句设置类别名相同。大多数内置别名都是门面的事实只是一个巧合。参见例如Illuminate\Support\Str
  • 感谢您的详细解释。只是选项 2 的注释:在 Laravel 8 中,您需要将方法更改为:protected static function getFacadeAccessor() { return \App\Helpers\Helper::class; }
  • @DAMIENJIANG 好地方。其实一直都是这样,我的回答是错误的。马上修好了,谢谢。
【解决方案2】:

您可以按照以下步骤直接实现此目的。

第一步

在您想要的路径中创建您的类文件(例如:app/Helpers/Helper.php)并定义类

<?php

class Helper 
{
    public static function applyClass($user) {
        return "call from helper to " . $user;
    }

}

第 2 步

通过在 autoload 键的条目中添加您的文件来修改 composer.json 文件

"autoload": {
    "prs-4": {
        "App\\": "app/"
    },
    "files": [
        "app/Helpers/Helper.php"
    ]
}

请注意,除了包含以下条目之外,您不会更改任何内容:"files": ["app/Helpers/Helper.php"]。 保存文件。

第 3 步

从你的根目录运行这个命令:

composer dump-autoload

它会刷新自动加载缓存。

第 4 步

您现在可以在任何地方使用您的课程,包括刀片

<tr class="{{ Helper::applyClass("user") }}">

这样,您也可以创建全局函数。

【讨论】:

    猜你喜欢
    • 2021-07-11
    • 2018-09-25
    • 2016-11-29
    • 2014-03-01
    • 2016-12-18
    • 1970-01-01
    • 1970-01-01
    • 2017-10-08
    • 2017-11-24
    相关资源
    最近更新 更多