iT邦幫忙

2021 iThome 鐵人賽

DAY 25
0
Software Development

跟著官方文件學習Laravel, 並實作出一個會員登入系統系列 第 25

Day25 跟著官方文件學習Laravel-Service Container

Service Container 是管理類別依賴和執行依賴注入的一個容器。

官方文件告訴我們可以利用Contrustor或setter的方式注入我們需要用的類別。

如下面範例:

<?php

namespace App\Http\Controllers;

use App\Http\Controllers\Controller;
use App\Repositories\UserRepository;
use App\Models\User;

class UserController extends Controller
{
    /**
     * The user repository implementation.
     *
     * @var UserRepository
     */
    protected $users;

    /**
     * Create a new controller instance.
     *
     * @param  UserRepository  $users
     * @return void
     */
    public function __construct(UserRepository $users)
    {
        $this->users = $users;
    }

    /**
     * Show the profile for the given user.
     *
     * @param  int  $id
     * @return Response
     */
    public function show($id)
    {
        $user = $this->users->find($id);

        return view('user.profile', ['user' => $user]);
    }
}

範例中我們需要產生 UserRepository 來幫我們到資料庫中索取我們需要的user資料,但我們這邊沒有實際把他 new 出來,而是使用依賴注入的方式,而如何 new 就是 Service Container 幫我們處理的事情。

這個地方我們利用實際的類別來撰寫,若是利用 interface 的方式要使用依賴注入的話,我們需要去利用 service provider 告訴容器我們呼叫到某個 interface 時請你幫我創建出什麼實例出來。

這時我們需要在容器內先綁定我們預先要使用的類別,我們可以利用 $this->app 呼叫容器,並利用 bind 方法將我們的 interface 跟 類別綁定
如下

<?php

namespace App\Animal;

interface Animal 
{
    public function say();
}
<?php

namespace App\Animal;

class Dog implements Animal
{
    public function say(){
        return "汪汪";
    }
}
use App\Services\Transistor;
use App\Services\PodcastParser;

$this->app->bind(Animal::class, function () {
    return new Dog();
});

若我們需要在不同場景運用不同的類別實作,我們可以利用以下方法來實現

<?php

namespace App\Animal;

class Cat implements Animal
{
    public function say(){
        return "喵喵";
    }
}
$this->app->when(CatController::class)
          ->needs(Animal::class)
          ->give(function () {
              return new Cat();
          });

$this->app->when(DogController::class)
          ->needs(Animal::class)
          ->give(function () {
              return new Dog();
          });

若我們想在程式中調用容器中的物件我們可以用 make

$transistor = $this->app->make(Animal::class);

我們也可以在方法調用時,注入該物件,如同我們在UserController裡調用UserService

public function store(Request $request, UserService $userService)
    {
        $account = $request->account;
        $password = $request->password;
        $username = $request->username;
        try{
            if($userService->signUp($account, $password, $username)){
                return response()->json([
                    'success' => 'true'
                ]);
            }
        } catch (PDOException $e){
            return response()->json([
                'success' => 'false',
                'error'=> 'DB error'
            ]);
        }catch (\Exception $e){
            return response()->json([
                'success' => 'false',
                'error'=> $e->getMessage()
            ]);
        }
    }

好~今天瞭解了Service Container,明天繼續了解其他功能。


上一篇
Day24 跟著官方文件學習Larave-Dusk
下一篇
Day26 跟著官方文件學習Laravel-Service Provider
系列文
跟著官方文件學習Laravel, 並實作出一個會員登入系統30

尚未有邦友留言

立即登入留言