[精讚] [會員登入]
112

[PHP+ci4] codeignitor4 Cache 及 Session 使用 memcached

php 的framework codeignitor4 中的cache和session使用memcached

分享此文連結 //n.sfs.tw/16398

分享連結 [PHP+ci4] codeignitor4 Cache 及 Session 使用 memcached@新精讚
(文章歡迎轉載,務必尊重版權註明連結來源)
2024-04-13 01:40:12 最後編修
2024-04-08 13:04:32 By 張○○
 

自動目錄

Codeignitor4(以下全稱為ci4) 自帶提供memcache,設置上非常方便,其實ci3上就有memcache,但是因為 selinux的關係,我一直試不成功,所以放棄。

memcache是使用記憶體當空間給session或cache使用,7版以前的php使用的是Memcache類別,8版使用 Memcached類別,除了名稱多了一個 d以外,裡面的方法都不一樣。

ci4上設置有兩個部分,一是修改cache另一個是修改session的設置,兩者可擇一設置,session的部分如果要使用memcache的話,需安裝 php-memcached 這個模組並開啟。

以下文章中 memcache 指的是這個服務,memcached 是這個服務的程式,名稱上常常會混用,要注意看,雖然我也很困擾。

程式碼來源於[1],有小部分修改。

此次異動的檔案有二個,在app/目錄下

├── Config
│   ├── Cache.php  <== Cacha的設定
│   └── Session.php <== Session的設定
├── Controller
│   └── TestSession.php <== 測試用,非必要
└── .env <==設定顯示錯誤

Config/Cache.php

修改兩個地方即可[1] :

...
//    public string $handler = 'file';  <== 註解原本的,加上下面這行
    public string $handler ='memcached';
...

    public array $memcached = [
        'host'   => 'memcache', //'127.0.0.1',  <== 改成ip或是container的service name
        'port'   => 11211,
        'weight' => 1,
        'raw'    => false,
    ];

其餘不必動
 

Config/Session.php

修改或新增以下兩行

//    public string $driver = FileHandler::class;  <== 註解這行
    public string $driver = 'CodeIgniter\Session\Handlers\MemcachedHandler';
...
//    public string $savePath = WRITEPATH . 'session';  <== 註解這行
    public string $savePath = 'memcache:11211';

其中 $savepath 的 memcahce 改成ip即可。

 

讓你的php支援 php-memcached 

在session中使用memcached得安裝 php-memcached 並啟用。

安裝 php memcached 模組

# yum install php-pecl-memcache

重啟後請檢查

# php -m

...
mbstring
memcached   <== 需要有這個模組
mysqli
...

Docker中安裝 php-memcached

預設docker php:8.2-fpm 中並無安裝此模組,要自行建立,請在 Dockerfile 中加入[4]

RUN
  ...
  apt-get install -y libmemcached-dev zlib1g-dev libssl-dev && \
  yes '' | pecl install -f memcached-3.2.0 && docker-php-ext-enable memcached  && \
  ...

 

測試及除錯

使用的memcache如果無法連線,大概率會得到這樣的錯誤:

codeignitor4 Fatal error: Uncaught ErrorException: session_write_close(): Failed to write session data using user defined save handler. memcached

這樣的錯誤無法清楚的知道是怎樣的問題,所以可以使用下面兩種方式先確定你的memcache伺服器是正常的。

 

使用php原生的方式測試 [5]

$m= new MemCached();

$m->addServer('memcached', 11211);

$m->set('int', 99);
$m->set('string', 'a simple string');
$m->set('array', array(11, 12));
/* expire 'object' key in 5 minutes */
$m->set('object', new stdClass, time() + 300);
print $m->get('int');

var_dump($m->get('int'));
var_dump($m->get('string'));
var_dump($m->get('array'));
var_dump($m->get('object'));

結果:

99int(99)
string(15) "a simple string"
array(2) {
  [0]=>
  int(11)
  [1]=>
  int(12)
}
object(stdClass)#2 (0) {
}

CI4中叫用測試

session原則上和原本使用的方式一樣,不必特別改變習慣

Controller 中session叫用測試:

$session = session();

$session->set('cachename', 'My Memcache');
print $session->get('cachename');
//or
print $session->cachename;

結果:

My MemcacheMy Memcache

備註,CI4出現 whoops! 怎麼辦

如果出現 whoops!,到 ci4的根目錄下[3]

$ cp env .env

修改.env 把

CI_ENVIRONMENT = production

換成這個

CI_ENVIRONMENT = development

 

預設使用session library

如果要預設載入 session的library,修改 BaseController.php [2]

    public $session;
    public function initController(RequestInterface $request, ResponseInterface $response, LoggerInterface $logger)
    {
        // Do Not Edit This Line
        parent::initController($request, $response, $logger);

        // Preload any models, libraries, etc, here.
        $this->session = \Config\Services::session();
    }

其它controller 直接使用 $this->session 即可

 

參考資料

[1] https://codeigniter.com/user_guide/libraries/caching.html#memcached-caching

[2] https://forum.codeigniter.com/showthread.php?tid=72170

[3] https://stackoverflow.com/questions/60558157/why-whoops-error-showing-in-codeigniter-4

[4] https://stackoverflow.com/questions/76490445/problem-adding-memcached-support-in-docker-for-php8-1-using-bookworm

[5] https://www.php.net/manual/en/memcached.set.php

 

END

你可能感興趣的文章

[PHP] 移除陣列或字串中的重覆元素 移除陣列或字串中的重覆元素

[PHP] codeignitor4+ smarty4 這篇整合 php 的framework codeignitor4 + smarty4。

[PHP] 檢查IP是否在某個網段內 mtachcidr 要檢查IP是否在某個網段內,要寫幾行?10行?5行? 不用,只要2行。以下是我寫的 code /** * matchCI

[CodeIgniter 3] 資料庫的使用方法整理1/2 --Select的使用 [CodeIgniter 3] 資料庫的使用方法整理:Select的使用

PHP判斷對方瀏覽器語系 多語系的網頁應該主動偵查瀏覽器的語系,配合使用者跳出合適的語系。

[PHP] 2個程式的觀念 整理2個PHP的程式觀念,參考參考。

我有話要說

>>

限制:留言最高字數1000字。 限制:未登入訪客,每則留言間隔需超過10分鐘,每日最多5則留言。

訪客留言

[無留言]

隨機好文

[jQuery] 利用load()來達成ajax的寫法 jQuery中利用load()來達成ajax的寫法,也有人稱他是假的ajax,作法就是..

[Freebsd] 定時測試 ADSL 是否斷線並重連 中華電信 ADSL 雖有固定 ip,可是他卻會不定時「斷線」, 使用以下的 方法可以定時測試是否斷線,以及重新撥接。

UTF8中文字/全形一覽 快速查詢urf-8的中文字,共計13246中文字(5401常用字+7652罕用字+日文或編號),292全形符號,27半形符號。

[Win7] 燒錄 iso 檔 在Windows7 中內建燒錄程式,可以直接把檔案拉到光碟機裡,再執行燒錄。

設計的工作絕不接受比價 拿買陽春麵的價格想買牛肉麵,寧願倒掉也不賣