predis如何實現phpredis的pconnect方法

predis和phpredis都是redis的php客戶端,區別能夠看這裏,這裏不贅述。php

phpredis是php擴展,由C語言編寫,誕生較早,不少PHPer都熟悉。
predis是用PHP語言編寫,因爲最近幾年composer的盛行,以及不少框架的支持composer,存於composer庫的predis也被大量應用。git

pconnect()是phpredis裏的方法,區別於connect(),詳細瞭解能夠看這篇,總結一下就是pconnect方法創建後的鏈接並不隨這請求的結束而關閉,而是依賴於php-fpm進程,php-fpm進程不死,redis connect就一直存在,直到空閒超時自動斷開。也就是創建了持久鏈接,適用於高併發下PHP請求Redisgithub

可是predis沒有pconnect()方法,該如何實現相似的功能呢?
項目使用的是Laravel框架,可是在文檔中並無找到相關的配置參數。因而只能讀插件源碼,最後在/src/Connection/StreamConnection.php這個類中找個了實現鏈接redis的方法:redis

/**
     * Initializes a TCP stream resource.
     *
     * @param ParametersInterface $parameters Initialization parameters for the connection.
     *
     * @return resource
     */
    protected function tcpStreamInitializer(ParametersInterface $parameters)
    {
        if (!filter_var($parameters->host, FILTER_VALIDATE_IP, FILTER_FLAG_IPV6)) {
            $address = "tcp://$parameters->host:$parameters->port";
        } else {
            $address = "tcp://[$parameters->host]:$parameters->port";
        }
        $flags = STREAM_CLIENT_CONNECT;
        if (isset($parameters->async_connect) && $parameters->async_connect) {
            $flags |= STREAM_CLIENT_ASYNC_CONNECT;
        }
        if (isset($parameters->persistent)) {
            if (false !== $persistent = filter_var($parameters->persistent, FILTER_VALIDATE_BOOLEAN, FILTER_NULL_ON_FAILURE)) {
                $flags |= STREAM_CLIENT_PERSISTENT;
                if ($persistent === null) {
                    $address = "{$address}/{$parameters->persistent}";
                }
            }
        }
        $resource = $this->createStreamSocket($parameters, $address, $flags);
        return $resource;
    }

在第19行的$parameters->persistent咱們能夠看到一個陌生的參數persistent,翻譯爲‘持久’。因此只要在使用predis鏈接redis的時候,加上參數persistent,並賦給一個true或1,就能夠實現phpredis的pconnect(),簡單方便。併發

下邊是郵件佐證,說明沒有錯誤理解源碼:composer

Can the predis support the function pconnect() which in php-redis?
Yes, just add in the connection parameters persistent=1 (when using URI strings) or persistent => true (when using a named array).

這個坑是怎麼踩到的呢?仍是由於框架文檔的緣由,目前不少PHP框架都已經支持了composer,如Laravel,Yii,CI等,可是並不能保證文檔及時更新,尤爲是中文文檔,因此仍是要有閱讀源碼的能力。框架

其實從上邊的代碼中還能夠看到不少內容:curl

  1. predis使用了tcp的方式鏈接redis,主要用到的函數是stream_socket_client(predis還有一種http的方式鏈接redis,主要用curl,不在這個類中)。
  2. predis並不依賴phpredis。不少項目環境安裝了phpredis又在框架裏安裝了predis,就覺得後者依賴前者,這是錯誤的。
  3. 在上述代碼第16行還能夠看到另外一個參數async_connect,用於異步鏈接,也很重要,可是在不少文檔裏都沒有介紹。

這裏寫圖片描述

相關文章
相關標籤/搜索