PHP中間件(middleware)理解

一 、 什麼是中間件

中間件是一個輕量級、底層的插件系統,可以介入應用主題從請求到響應的處理過程。

網上找的圖片
說明白點,中間件其實就是一個閉包,而且返回一個閉包。中間件爲過濾進入應用的HTTP請求提供了一套便利的機制,常用於驗證用戶是否經過認證,添加響應頭(跨域),記錄請求日誌等。

二 、 用到的一些概念
1.閉包函數

也就是常說的匿名函數(什麼是匿名?沒有函數名不就是匿名了麼…秀- -),允許臨時創建一個沒有指定名稱的函數。最經常用作回調函數(callback)參數的值。

​PHP中的匿名函數:PHP在5.3的版本之後支持了匿名函數,並統歸屬於Closure類下,通過Closure類來實現。那這就給我們在判斷匿名函數時帶來一定的好處了(稍後代碼體現)。

三 、 服務註冊配置思路

  1. 註冊服務 按一下格式
	/**
     * @brief 註冊獲取服務
     *
     * @param string[]
     *
     * @return   string[]
     */
    static public function getServiceProviders()
    {
        return [
            "test1" => A::class,
            "test2" => C::class,
            "test3" => C::class,

        ];
    }
  1. 初始化中間件
	/**
     * @brief   初始化中間件
     *
     * @param    $this
     *
     * @return   $this
     */
    public function initMiddleware() {

        $this->test1 (["===","-++++++++"]);
        $this->test2 ('================');
        $this->test5 ('---------');
        return $this;

    }
	/**
     * @brief 方法不存在,進行重載函數
     *
     * @param void
     *
     * @return   void
     */
    public function __call($name, $arg)
    {
        // TODO: Implement __call() method.
        $service = new Service();
        //PHP7 中的 Closure :: call()方法具有更好的性能,該方法被添加爲臨時將對象範圍綁定到閉包並調用它。
        var_dump ($service->getName(self::getServiceProviders (),$name)->call($this,...$arg));
        return  $service->getName(self::getServiceProviders (),$name)->call($this,...$arg);
    }

四、中間件開發思路

  1. 構建中間件服務類,首先通過getName()方法獲取服務名稱
 /**
     * @brief 獲取服務名稱
     *
     * @param mixed|void
     *
     * @return   mixed|void
     */
    public function getName($serviceProviders,$name)
    {


        if (array_key_exists ($name,$serviceProviders))
        {

            $class = $serviceProviders[$name];


           return  $this->inject($name,$class);

        }
        exit("沒有匹配");
        return;

    }
  1. 通過inject 方法進行註冊服務
	/**
     * @brief 註冊服務
     *
     * @param mixed
     *
     * @return   mixed
     */
    public function inject($name,$class)
    {
        return  (new $class())->callback($name);

    }
  1. 通過匿名函數,進行具體的業務實現
class A
{

    /**
     * @brief 匿名函數
     *
     * @param mixed
     *
     * @return   mixed
     */

    public function callback($name)
    {

        $name =function ($str) {
        	//進行具體業務
            return $str;
        };

        return  $name;
    }

}

class C
{

    /**
     * @brief 匿名函數
     *
     * @param mixed
     *
     * @return   mixed
     */
    public function callback($name)
    {

        $name = function ($str) {
        //進行具體業務
          return $str;
        };

        return  $name;
    }

}

完整代碼

<?php


/**
 * @Created by PhpStorm.
 * @brief
 * @User: gzy
 * @Date: 2020/5/7
 */

class A
{

    /**
     * @brief 匿名函數
     *
     * @param mixed
     *
     * @return   mixed
     */

    public function callback($name)
    {

        $name =function ($str) {
            return $str;
        };

        return  $name;
    }

}

class C
{

    /**
     * @brief 匿名函數
     *
     * @param mixed
     *
     * @return   mixed
     */
    public function callback($name)
    {

        $name = function ($str) {
          return $str;
        };

        return  $name;
    }

}

class Service
{

    /**
     * @brief 註冊服務
     *
     * @param mixed
     *
     * @return   mixed
     */
    public function inject($name,$class)
    {
        return  (new $class())->callback($name);

    }

    /**
     * @brief 獲取服務名稱
     *開始
     * @param mixed|void
     *
     * @return   mixed|void
     */
    public function getName($serviceProviders,$name)
    {


        if (array_key_exists ($name,$serviceProviders))
        {

            $class = $serviceProviders[$name];


           return  $this->inject($name,$class);

        }
        exit("沒有匹配");
        return;

    }
}

class B
{
    /**
     * @brief 註冊獲取服務
     *
     * @param string[]
     *
     * @return   string[]
     */
    static public function getServiceProviders()
    {
        return [
            "test1" => A::class,
            "test2" => C::class,
            "test3" => C::class,

        ];
    }


    /**
     * @brief   初始化中間件
     *
     * @param    $this
     *
     * @return   $this
     */
    public function initMiddleware() {

        $this->test1 (["===","-++++++++"]);
        $this->test2 ('================');
        $this->test5 ('---------');
        return $this;

    }

    /**
     * @brief 方法不存在,進行重載函數
     *
     * @param void
     *
     * @return   void
     */
    public function __call($name, $arg)
    {
        // TODO: Implement __call() method.
        $service = new Service();
        //PHP7 中的 Closure :: call()方法具有更好的性能,該方法被添加爲臨時將對象範圍綁定到閉包並調用它。
        var_dump ($service->getName(self::getServiceProviders (),$name)->call($this,...$arg));
        return  $service->getName(self::getServiceProviders (),$name)->call($this,...$arg);
    }
}
$B = new B();
$B->initMiddleware();

結果

[root@localhost Creeper-new]# php test.php
array(2) {
  [0]=>
  string(3) "==="
  [1]=>
  string(9) "-++++++++"
}
string(16) "================"
沒有匹配

PHP函數的參數裏,前面三個點的形式…$args是什麼含義和用法?

function add($a, $b, $c)
{
    return $a + $b + $c;
}
 
$num=[2, 3];
echo add(1, ...$num);       //6

以上目的是理解。這個代碼僅用與學習。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章