亚洲中字慕日产2020,大陆极品少妇内射AAAAAA,无码av大香线蕉伊人久久,久久精品国产亚洲av麻豆网站

資訊專欄INFORMATION COLUMN

Just for fun——Slim借力Swoole

leejan97 / 3301人閱讀

摘要:的話,是一個(gè)遵循規(guī)范微型的框架,作者這樣說大致意思的核心工作分發(fā)了請求,然后調(diào)用回調(diào)函數(shù),返回一個(gè)對(duì)象。執(zhí)行的方法時(shí),我們從中取出的依賴,這時(shí)候,注冊的回調(diào)函數(shù)被調(diào)用,返回實(shí)例。

Slim

Slim的話,是一個(gè)遵循PSR (PSR-7)規(guī)范微型的框架,作者這樣說:

Slim is a PHP micro framework that helps you quickly write simple yet powerful web applications and APIs. At its core, Slim is a dispatcher that receives an HTTP request, invokes an appropriate callback routine, and returns an HTTP response. That’s it.

大致意思:slim的核心工作:分發(fā)了Http請求,然后調(diào)用回調(diào)函數(shù),返回一個(gè)Http response對(duì)象。

Slim其實(shí)就幫我們做了兩件事

路由的分發(fā)

依賴的注入

框架很小,所以別的部分(如db操作、模板引擎)可能需要自己實(shí)現(xiàn),但slim通過依賴注入,讓你可以很輕松的組裝其他功能到slim中。

快速入門:
 [
    "addContentLengthHeader" => false,
]];
$app = new SlimApp($config);

// Define app routes
$app->get("/hello/{name}", function ($request, $response, $args) {
    return $response->write("Hello " . $args["name"]);
});

// Run app
$app->run();

request代表了當(dāng)前請求對(duì)象,response代表了當(dāng)前響應(yīng)對(duì)象,$args是占位符的鍵值對(duì)數(shù)組。
訪問/hello/salamander就會(huì)輸出Hello salamander

添加依賴

DB是我自己封裝的一個(gè)PDO的操作類。

$config = ["settings" => [
    "addContentLengthHeader" => false,
]];
$app = new SlimApp($config);
$container = $app->getContainer();

$container["db"] = function($c) {
    $dbHost = "localhost";
    $dbName = "test";

    $dbConf = [
        "dsn" => "mysql:dbname={$dbName};host={$dbHost}",
        "username" => "root",
        "password" => "******",
        "charset" => "utf8"
    ];
    $db = new AppLibraryDB();
    $db->__setup($dbConf);
    return $db;
};

// Define app routes
$app->get("/user/{uid}", "AppControllerIndexController:index");
IndexController類
namespace AppController;

class IndexController 
{
    protected $container;
    
    public function __construct(ContainerInterface $container) {
        $this->container = $container;
    }
    
    public function index($request, $response, $args) {
        $info = $this->container["db"]->fetch("SELECT name FROM user WHERE uid = :uid", [
            "uid" => $args["uid"]
        ]);
        echo "user name is " . $info["name"];
    }
}

IndexController類的是通過composer自動(dòng)載入的(代碼中沒寫):

"autoload": {
    "psr-4": {
        "App": "app/"
    }
},

代碼中可以發(fā)現(xiàn),依賴容器的注入是在類實(shí)例化的時(shí)候發(fā)生的。執(zhí)行IndexController的index方法時(shí),我們從$container中取出的db依賴,這時(shí)候,注冊的回調(diào)函數(shù)被調(diào)用,返回實(shí)例。因?yàn)槭怯玫綍r(shí)才實(shí)例化,這個(gè)叫做延遲實(shí)例化。

結(jié)合Swoole

Swoole讓PHP可以常駐內(nèi)存,而且它提供了Http Server的功能,所以Slim和Swoole沒什么沖突。

思考

Slim是通過當(dāng)前路由(譬如/user/2,不帶查詢字符串)和http方法來找到正確的回調(diào)函數(shù)的。這些量Slim是從哪里取的呢?肯定是$_SERVER。查看slim源碼:
run()方法:

public function run($silent = false)
{
    $response = $this->container->get("response");

    try {
        ob_start();
        $response = $this->process($this->container->get("request"), $response);
    } catch (InvalidMethodException $e) {
        $response = $this->processInvalidMethod($e->getRequest(), $response);
    } finally {
        $output = ob_get_clean();
    }

    if (!empty($output) && $response->getBody()->isWritable()) {
        $outputBuffering = $this->container->get("settings")["outputBuffering"];
        if ($outputBuffering === "prepend") {
            // prepend output buffer content
            $body = new HttpBody(fopen("php://temp", "r+"));
            $body->write($output . $response->getBody());
            $response = $response->withBody($body);
        } elseif ($outputBuffering === "append") {
            // append output buffer content
            $response->getBody()->write($output);
        }
    }

    $response = $this->finalize($response);

    if (!$silent) {
        $this->respond($response);
    }

    return $response;
}

發(fā)現(xiàn)$request對(duì)象是從容器取出來的,那$request是怎么注冊的呢??,那就看App類的構(gòu)造函數(shù)了,最后發(fā)現(xiàn)Container類的構(gòu)造函數(shù)中有registerDefaultServices()方法:

private function registerDefaultServices($userSettings)
{
    $defaultSettings = $this->defaultSettings;

    /**
     * This service MUST return an array or an
     * instance of ArrayAccess.
     *
     * @return array|ArrayAccess
     */
    $this["settings"] = function () use ($userSettings, $defaultSettings) {
        return new Collection(array_merge($defaultSettings, $userSettings));
    };

    $defaultProvider = new DefaultServicesProvider();
    $defaultProvider->register($this);
}

查看$defaultProvider->register()方法:

public function register($container)
{
    if (!isset($container["environment"])) {
        /**
         * This service MUST return a shared instance
         * of SlimInterfacesHttpEnvironmentInterface.
         *
         * @return EnvironmentInterface
         */
        $container["environment"] = function () {
            return new Environment($_SERVER);
        };
    }

    if (!isset($container["request"])) {
        /**
         * PSR-7 Request object
         *
         * @param Container $container
         *
         * @return ServerRequestInterface
         */
        $container["request"] = function ($container) {
            return Request::createFromEnvironment($container->get("environment"));
        };
    }
    
    //...

可以看到$request對(duì)象是通過Request::createFromEnvironment方法構(gòu)造的,它需要從容器中取出environment依賴,而environment依賴是通過構(gòu)造一個(gè)Environment對(duì)象得來的,它正好放入了$_SERVER
查看Environment類源碼,可以發(fā)現(xiàn)它繼承了Collection類,Collection的構(gòu)造函數(shù)如下:

public function __construct(array $items = [])
{
    $this->replace($items);
}

從上面我們可以得出,我們主要注冊一個(gè)自定義的environment依賴就行,原來$_SERVER的信息可以從swoole的$request->server中取。

簡單實(shí)現(xiàn)

server.php

on("start", function ($server) {
    echo "Swoole http server is started at http://0.0.0.0:8888
";
});

$http->on("request", function ($request, $response) {
    // Instantiate the app
    $config = [
        "settings" => [
            "addContentLengthHeader" => false,
        ]
    ];
    $config["environment"] = function () use($request) {
        $server = [];
        foreach ($request->server as $key => $value) {
            $server[strtoupper($key)] = $value;
        }
        return new Environment($server);
    };
    $app = new SlimApp($config);
    // Register routes
    require APP . "/routes.php";

    // Run app
    $slimResponse = $app->run(true);
    $headers = $slimResponse->getHeaders();
    foreach ($headers as $name => $values) {
        $response->header($name, implode(", ", $values));
    }
    $response->header("X-Powered-By", "Salamander");
    $response->end($slimResponse->getBody());
});

$http->start();

注意$request->server中key都是小寫的,所以這里轉(zhuǎn)化了一下。

routes.php(在App目錄中)

get("/", function (Request $request, Response $response) {
    $response->getBody()->write("Hello Salamander");
    return $response;
});


$app->get("/user/{uid}", function (Request $request, Response $response, $args) {
    $response->getBody()->write("Hello User:" . $args["uid"]);
    return $response;
});
測試

訪問/

訪問/user/45

打包下載測試

百度云盤
tip:環(huán)境基于docker的,運(yùn)行docker-compose up即可

Github上的討論

Issue

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://www.ezyhdfw.cn/yun/28198.html

相關(guān)文章

  • Just for fun——基于Swoole做個(gè)小框架

    摘要:使開發(fā)人員可以編寫高性能的異步并發(fā),服務(wù)。使用作為網(wǎng)絡(luò)通信框架,可以使企業(yè)研發(fā)團(tuán)隊(duì)的效率大大提升,更加專注于開發(fā)創(chuàng)新產(chǎn)品??傊?,這個(gè)庫讓可以常駐內(nèi)存,并提供了,等功能。 swoole 使 PHP 開發(fā)人員可以編寫高性能的異步并發(fā) TCP、UDP、Unix Socket、HTTP,WebSocket 服務(wù)。Swoole 可以廣泛應(yīng)用于互聯(lián)網(wǎng)、移動(dòng)通信、企業(yè)軟件、云計(jì)算、網(wǎng)絡(luò)游戲、物聯(lián)網(wǎng)(...

    CoreDump 評(píng)論0 收藏0
  • Just for fun——基于Swoole做個(gè)小框架

    摘要:使開發(fā)人員可以編寫高性能的異步并發(fā),服務(wù)。使用作為網(wǎng)絡(luò)通信框架,可以使企業(yè)研發(fā)團(tuán)隊(duì)的效率大大提升,更加專注于開發(fā)創(chuàng)新產(chǎn)品??傊?,這個(gè)庫讓可以常駐內(nèi)存,并提供了,等功能。 swoole 使 PHP 開發(fā)人員可以編寫高性能的異步并發(fā) TCP、UDP、Unix Socket、HTTP,WebSocket 服務(wù)。Swoole 可以廣泛應(yīng)用于互聯(lián)網(wǎng)、移動(dòng)通信、企業(yè)軟件、云計(jì)算、網(wǎng)絡(luò)游戲、物聯(lián)網(wǎng)(...

    fevin 評(píng)論0 收藏0
  • Just for fun——Docker做個(gè)NMP環(huán)境

    摘要:總之,是用來管理多個(gè)容器的,用都會(huì)寫一個(gè)開啟所有服務(wù)關(guān)閉所有服務(wù)上面說了,關(guān)鍵是編排好,以下就是的目錄結(jié)構(gòu)訪問在目錄下運(yùn)行命令,在瀏覽器訪問可以看到講解和都是用了官方的鏡像,而是從本地構(gòu)建的。 Docker Docker 是一個(gè)開源的應(yīng)用容器引擎,讓開發(fā)者可以打包他們的應(yīng)用以及依賴包到一個(gè)可移植的容器中,然后發(fā)布到任何流行的 Linux機(jī)器上,也可以實(shí)現(xiàn)虛擬化。容器是完全使用沙箱機(jī)制,...

    用戶84 評(píng)論0 收藏0
  • Just for fun——Docker做個(gè)NMP環(huán)境

    摘要:總之,是用來管理多個(gè)容器的,用都會(huì)寫一個(gè)開啟所有服務(wù)關(guān)閉所有服務(wù)上面說了,關(guān)鍵是編排好,以下就是的目錄結(jié)構(gòu)訪問在目錄下運(yùn)行命令,在瀏覽器訪問可以看到講解和都是用了官方的鏡像,而是從本地構(gòu)建的。 Docker Docker 是一個(gè)開源的應(yīng)用容器引擎,讓開發(fā)者可以打包他們的應(yīng)用以及依賴包到一個(gè)可移植的容器中,然后發(fā)布到任何流行的 Linux機(jī)器上,也可以實(shí)現(xiàn)虛擬化。容器是完全使用沙箱機(jī)制,...

    Apollo 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看
<