国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 語言 > PHP > 正文

詳解PHP使用Redis存儲session時的一個Warning定位

2024-05-04 23:58:32
字體:
來源:轉載
供稿:網友

1. 問題現象

系統頁面刷新的時候,偶爾會報錯下面的Warnning,但是不經常出現:

Warning: Unknown: Failed to write session data (Redis). Please verify that the current setting of session.save_path is correct (tcp://x.x.x.x:6379?auth=yyy) in Unknown on line 0

看網絡有人說是redis版本的問題、但是沒有具體結論,那么本著學習的態度,自己試試看看能不能捉出這個bug.

定位問題:

查看PHP文件是否有設置session的地方,發現沒有

繼續檢查php配置文件,發現配置了session存儲到redis里面

[Session]session.save_handler = redissession.save_path = "tcp://x.x.x.x:6379?auth=yyyy"session.use_cookies = 1

1、繼續查看php Session擴展源代碼,定位出錯提示語在函數php_session_save_current_state中

檢查session擴展文件中出錯提示:

static void php_session_save_current_state(TSRMLS_D) /* {{{ */{  int ret = FAILURE;  //是否session數組  IF_SESSION_VARS() {    if (PS(mod_data) || PS(mod_user_implemented)) {      char *val;      int vallen;     //變量編碼      val = php_session_encode(&vallen TSRMLS_CC);      if (val) {        //保存session數據        ret = PS(mod)->s_write(&PS(mod_data), PS(id), val, vallen TSRMLS_CC);        efree(val);      } else {        //清空session        ret = PS(mod)->s_write(&PS(mod_data), PS(id), "", 0 TSRMLS_CC);      }    }    //看出錯提示語在這里    if (ret == FAILURE) {      php_error_docref(NULL TSRMLS_CC, E_WARNING, "Failed to write session data (%s). Please "          "verify that the current setting of session.save_path "          "is correct (%s)",          PS(mod)->s_name,          PS(save_path));    }  }  if (PS(mod_data) || PS(mod_user_implemented)) {    PS(mod)->s_close(&PS(mod_data) TSRMLS_CC);  }}static void php_session_flush(TSRMLS_D){  如果 (PS(session_status) == php_session_active)    session_status = none    這里調用...    php_session_save_current_state}

下面兩個函數調用:php_session_flush()

static PHP_FUNCTION(session_write_close){  php_session_flush(TSRMLS_C);}static PHP_FUNCTION(session_register_shutdown){}

由上面可以看到,php_session_save_current_state是在 php_session_flush中調用,即在session保存、清空等刷新寫session的時候會產生。

由php seesion源碼沒有發現什么問題,突然想到會不會是Redis本身有沒有啥問題,導致的寫出錯。因而繼續從redis里面找問題:

Redis問題定位

1. 首先查看Redis日志文件:

看到如下每5分鐘會刷新一下如下log:

[16723] 04 Jul 15:15:01.987 # Server started, Redis version 2.8.9[16723] 04 Jul 15:15:01.987 # WARNING overcommit_memory is set to 0! Background save may fail under low memory condition. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.[16723] 04 Jul 15:15:01.996 * DB loaded from disk: 0.008 seconds[16723] 04 Jul 15:15:01.996 * The server is now ready to accept connections on port 6379

懷疑這就是問題的PHP寫日志失敗的原因了。那么Redis為啥會5分鐘重啟呢?繼續追查!

2. 是系統內存不夠、Redis core了?

查看系統和Redis內存使用狀態:

系統內存狀態:

$ free -m       total    used    free   shared  buffers   cachedMem:     3516    3171    345     0    684    1680-/+ buffers/cache:    806    2709Swap:     2055    724    1330

Redis服務器占用的內存狀態:

used_memory:2841648used_memory_human:2.71Mused_memory_rss:3710976used_memory_peak:2877576used_memory_peak_human:2.74Mused_memory_lua:33792mem_fragmentation_ratio:1.31mem_allocator:jemalloc-3.2.0

可以看到Redis其實內存占用非常少。redis重啟原因暫且不明。

3. 定時腳本

因為重啟日志5分鐘一次、非常規律,因而懷疑是不是別的原因導致Redis重啟,比如定時腳本。

因為本人沒有root corntab權限,找老板提權,看到赫然存在著一個crontab,5分鐘監控一次redis。

如下:

/5 * * * /data/scripts/check_redis.sh >/dev/null 2>&1 ##check_redis.tag.1

查看腳本內容

PORT='6379'ETH1_ADDR=`/sbin/ifconfig eth1 | awk -F ':' '/inet addr/{print $2}' | sed 's/[a-zA-Z ]//g'`retval=`nmap --system-dns -sT -p ${PORT} ${ETH1_ADDR} | grep open`if [ "${retval}X" = "X" ]; then    /sbin/service redis restart >/dev/null 2>&1fi

這是一個檢查Redis端口是否提供服務的腳本,如果檢查不成功,就拉起Redis。

可以看到這個腳本本來沒有什么問題。

但是:通過手動執行這個命令發現:

這臺機器沒有安裝nmap 這個命令,

所以這個腳本最后總是執行失敗!然后Redis重啟。

因為問題根源找到了,找運維安裝相關命令,問題解決。

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持VeVb武林網。


注:相關教程知識閱讀請移步到PHP教程頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表

圖片精選

主站蜘蛛池模板: 丰顺县| 泰兴市| 延津县| 宁化县| 杭州市| 荣成市| 自治县| 斗六市| 曲阳县| 辉县市| 乌兰浩特市| 郑州市| 丹寨县| 临海市| 阿图什市| 肥西县| 会东县| 宁蒗| 称多县| 左云县| 化隆| 长沙市| 大悟县| 武汉市| 五大连池市| 长沙县| 扎鲁特旗| 涿州市| 互助| 婺源县| 广昌县| 临桂县| 本溪市| 洮南市| 临颍县| 浦城县| 宁都县| 裕民县| 禹城市| 金乡县| 云阳县|