【问题标题】:Is it possible to intiailize variables in a constructor for a Laravel facade?是否可以在 Laravel 外观的构造函数中初始化变量?
【发布时间】:2020-07-27 15:25:16
【问题描述】:
如果我正在创建一个自定义外观并希望在每个使用 customFacade::doSomething() 的实例中初始化某些变量,这可能吗?我这样做的主要目的是能够存储其他对象的变量并直接在它们上调用函数。例如customFacade::client->send(),在这种情况下client 是具有send() 函数的对象的初始化变量。我知道我可以有一个函数 client() 并返回对象的一个新实例,以便 send() 通过,但我仍然想知道它是否可能以其他方式。
在普通类中我可以在下面做,但它不适用于外观。
$protected client;
public function __construct()
{
$this->client = new instanceOfObject();
}
【问题讨论】:
标签:
php
laravel
laravel-5
【解决方案1】:
由于 Facade 使用静态函数,你只能做类似的事情
public static $client = null;
public static function init() {
if(self::$client == null)
self::$client = new instanceOfObject();
}
// somewhere else
customFacade::init();
customFacade::client->send();
【解决方案2】:
Laravel 将在你的外观下的类构造函数中解析你需要的所有依赖项。一个展示我观点的玩具示例,将在 DateService 中解析 UserRepository,因此在 Dates 外观中解析。
用法,
return view('profile' => [
...
'time' => Dates::loggedLocal(),
...
]);
日期时间服务.php
class DatetimeService
{
private $userRepository;
public function __construct(
UserRepository $userRepository
) {
$this->userRepository = $userRepository;
}
/**
* Get the logged in users local time
*
* @return Carbon
*/
public function loggedLocal() : Carbon
{
$user = $this->userRepository->current();
return Carbon::now()->setTimezone($user->timezone);
}
日期.php
class Dates extends Facade
{
/**
* Get the registered name of the component.
*
* @return string
*/
protected static function getFacadeAccessor() { return 'date-service'; }
}
DateServiceProvider.php
class DateServiceProvider extends ServiceProvider
{
/**
* Register any application services.
*
* @return void
*/
public function register()
{
$this->app->singleton('date-service', function()
{
return new DateTimeService;
});
}
}