简体   繁体   English

$this->app->singleton() 如何在 laravel 中工作?

[英]How $this->app->singleton() works in laravel?

In my laravel project I have following interface, repository and controller.在我的 laravel 项目中,我有以下接口、存储库和 controller。

This is Interface这是接口

interface TrainingClassTypeInterfaces
{
    public function updateTrainingClassType($id, $request);
} 

This is Repository这是存储库

use App\Models\Trainings\AppTrainingClassType;
class TrainingClassTypeEloquent implements TrainingClassTypeInterfaces
    {
        protected $model;
    
        public function __construct(AppTrainingClassType $appTrainingClassType)
        {
            $this->model = $appTrainingClassType;
        }
    
        public  function updateTrainingClassType($id, $request)
        {
            $response = false;
            $isUpdated = $this->model::where('training_class_id',$id)->update([
                'app_id' => $request->app_id
            ]);
            .... 
        }
    
    }

This is controller这是 controller

class TrainingClassTypesController extends \TCG\Voyager\Http\Controllers\VoyagerBaseController
{
    protected  $trainingService;
    public function __construct(TrainingClassTypeEloquent $trainingClassTypeInterfaces) {
        $this->trainingService = $trainingClassTypeInterfaces;
    }

    public function insertOrUpdate()
    {
        ...
        $this->trainingService->updateTrainingClassType($id, $request);
        ..
    }

}

Everything working fine till here到这里为止一切正常

As you can see I am using TrainingClassTypeEloquent's method inside TrainingClassTypesController .如您所见,我在TrainingClassTypesController中使用了 TrainingClassTypeEloquent 的方法。 But it was returning error something like但它返回的错误类似于

Argument 1 passed to...::__construct() must be an instance of

Basically it was asking me to put instance of Model into TrainingClassTypeEloquent class.基本上它要求我将 Model 的实例放入TrainingClassTypeEloquent class 中。 Then I did as following然后我做了如下

$TCTypes = new AppTrainingClassType();
$TCT = new TrainingClassTypeEloquent($TCTypes);
$TCT->updateTrainingClassType($id, $request);

which was working fine but I was confused that this approach is not proper, there should be some proper way.这工作正常,但我很困惑这种方法不合适,应该有一些合适的方法。

After googling I found another solution which is singleton binding, and then I tried following in AppServiceProvider谷歌搜索后,我找到了另一个解决方案,即 singleton 绑定,然后我尝试在 AppServiceProvider 中进行以下操作

$this->app->singleton(
            \App\Services\Voyager\Eloquent\TrainingClassType\TrainingClassTypeInterfaces::class,
            \App\Services\Voyager\Eloquent\TrainingClassType\TrainingClassTypeEloquent::class
        );

After adding this singleton binding, I notice script was working without providing model instance into TrainingClassTypeEloquent class.添加此 singleton 绑定后,我注意到脚本在没有将 model 实例提供到TrainingClassTypeEloquent class 的情况下工作。

I would like to know how $this->app->singleton() is working, so in this way my concept would be clear about it.我想知道$this->app->singleton()是如何工作的,这样我的概念就很清楚了。 If someone knows then kindly guide me about it.如果有人知道,请指导我。

Thank you so much太感谢了

It is all about BINDING a service to the service container .这完全是关于将服务绑定服务容器

What does $this->app->singleton(); $this->app->singleton();是什么意思? method do?方法呢?

The singleton method binds a class or interface into the service container so that Laravel can maintain dependency (when using an interface as the constructor parameter). singleton 方法将 class 或接口绑定到服务容器中,以便 Laravel 可以保持依赖关系(使用接口作为构造函数参数时)。

(Actually Singleton is a design pattern. Singleton implementation always returns the same object on subsequent calls instead of a new instance). (实际上Singleton是一种设计模式。Singleton 实现在后续调用中总是返回相同的 object 而不是新实例)。 So $this->app->singleton();所以$this->app->singleton(); method returns the same object again and again.方法一次又一次地返回相同的 object。

Point to be noted that Laravel doc says:需要注意的是 Laravel 文档说:

There is no need to bind classes into the container if they do not depend on any interfaces .如果类不依赖于任何接口,则无需将类绑定到容器中。 The container does not need to be instructed on how to build these objects, since it can automatically resolve these objects using reflection.不需要指示容器如何构建这些对象,因为它可以使用反射自动解析这些对象。

But your controller class depends on an interface, so the container needs to be informed and to do this, you need to use this $this->app->singleton();但是您的 controller class 取决于接口,因此需要通知容器并执行此操作,您需要使用此$this->app->singleton(); method but there are other ways around.方法,但还有其他方法。

Again, at the same time, this TrainingClassTypeEloquent::class has a dependency of AppTrainingClassType::class .同样,同时,这个TrainingClassTypeEloquent::class具有AppTrainingClassType::class的依赖关系。 But in this case, we do not need to worry about that because Laravel uses Reflection API to maintain its dependency as this class does not use interface as like TrainingClassTypesController::class class. But in this case, we do not need to worry about that because Laravel uses Reflection API to maintain its dependency as this class does not use interface as like TrainingClassTypesController::class class.

Once you are done with binding the service to the container, Laravel will then automagically put the service onto the constructor method as an argument where the interface is used.完成将服务绑定到容器后,Laravel 将自动将服务作为使用接口的参数放在构造函数方法中。

I hope this would help you.我希望这会对你有所帮助。 You may find more help from this answer .您可能会从此答案中找到更多帮助。

You need to register TrainingClassTypeEloquent你需要注册 TrainingClassTypeEloquent

$this->app->singleton(TrainingClassTypeInterfaces::class, static function ($app) {
    return new TrainingClassTypeEloquent(new AppTrainingClassType());
});

Then you can inject it in your Controller然后你可以将它注入你的 Controller

public function insertOrUpdate(TrainingClassTypeInterfaces $trainingService, $id)
{
    $trainingService->updateTrainingClassType($id, request());
}

Binding A Singleton绑定一个 Singleton

The singleton method binds a class or interface into the container that should only be resolved one time. singleton方法将 class 或接口绑定到只应解析一次的容器中。 Once a singleton binding is resolved, the same object instance will be returned on subsequent calls into the container:一旦解析了 singleton 绑定,相同的 object 实例将在随后调用容器时返回:

$this->app->singleton('HelpSpot\API', function ($app) {
    return new \HelpSpot\API($app->make('HttpClient'));
});

For more go to HERE更多 go 到这里

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Laravel 5 - 如何使用 $this->app->when() - Laravel 5 - How to use $this->app->when() 使用$ this-> app-> share()在Laravel 4.1中正确注册服务提供商 - Proper registering a Service Provider in Laravel 4.1 using $this->app->share() Laravel - $app->loadEnvironmentFrom('.env.testing') 方法不起作用 - Laravel - $app->loadEnvironmentFrom('.env.testing') method does not work Laravel 6 - 将参数传递给 $app->when()->needs()->give() - Laravel 6 - Pass a parameter to $app->when()->needs()->give() 如何覆盖Yii2 $ app-> user-> identity - How to Override Yii2 $app->user->identity 如何在phalcon中的$ app->之后获取执行的控制器的名称 - How to get the name of the executed controller in $app->after in phalcon Yii2 在 `$this->modelClass::find()->andWhere(['post_id' => \\Yii::$app->request->get('postId')])` 上出现语法错误,这是一个有效条款 - Yii2 Getting a Syntax error on ` $this->modelClass::find()->andWhere(['post_id' => \Yii::$app->request->get('postId')])` which is a valid clause Laravel app-> make(ClassA)类和new ClassA()有什么区别 - What is the difference between Laravel app->make(ClassA) class and new ClassA() Laravel:区别 App::bind 和 App::singleton - Laravel: Difference App::bind and App::singleton Shopify私人应用程式-PHP - Shopify private app- php
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM