PHPopcache的原理及使用方法是什么

這篇文章主要介紹了PHP opcache的原理及使用方法是什么的相關知識,內(nèi)容詳細易懂,操作簡單快捷,具有一定借鑒價值,相信大家閱讀完這篇PHP opcache的原理及使用方法是什么文章都會有所收獲,下面我們一起來看看吧。

成都創(chuàng)新互聯(lián)專注于聶拉木網(wǎng)站建設服務及定制,我們擁有豐富的企業(yè)做網(wǎng)站經(jīng)驗。 熱誠為您提供聶拉木營銷型網(wǎng)站建設,聶拉木網(wǎng)站制作、聶拉木網(wǎng)頁設計、聶拉木網(wǎng)站官網(wǎng)定制、成都微信小程序服務,打造聶拉木網(wǎng)絡公司原創(chuàng)品牌,更為您提供聶拉木網(wǎng)站排名全網(wǎng)營銷落地服務。

PHP項目中,尤其是在高并發(fā)大流量的場景中,如何提升PHP的響應時間,是一項十分重要的工作。
而Opcache又是優(yōu)化PHP性能不可缺失的組件,尤其是應用了PHP框架的項目中,作用更是明顯。

1、概述

在理解 OPCache 功能之前,我們有必要先理解PHP-FPM + Nginx 的工作機制,以及PHP腳本解釋執(zhí)行的機制。

1.1 PHP-FPM + Nginx 的工作機制

請求從Web瀏覽器到Nginx,再到PHP處理完成,一共要經(jīng)歷如下五個步驟:
第一步:啟動服務

  • 啟動PHP-FPM。PHP-FPM 支持兩種通信模式:TCP socket和Unix socket;

  • PHP-FPM 會啟動兩種類型的進程:Master 進程 和 Worker 進程,前者負責監(jiān)控端口、分配任務、管理Worker進程;后者就是PHP的cgi程序,負責解釋編譯執(zhí)行PHP腳本。

  • 啟動Nginx。首先會載入 ngx_http_fastcgi_module 模塊,初始化FastCGI執(zhí)行環(huán)境,實現(xiàn)FastCGI協(xié)議請求代理

  • 這里要注意:fastcgi的worker進程(cgi進程),是由PHP-FPM來管理,不是Nginx。Nginx只是代理

第二步:Request => Nginx

  • Nginx 接收請求,并基于location配置,選擇一個合適handler

  • 這里就是代理PHP的 handler

第三步:Nginx => PHP-FPM

  • Nginx 把請求翻譯成fastcgi請求

  • 通過TCP socket/Unix Socket 發(fā)送給PHP-FPM 的master進程

第四步:PHP-FPM Master => Worker

  • PHP-FPM master 進程接收到請求

  • 分配Worker進程執(zhí)行PHP腳本,如果沒有空閑的Worker,返回502錯誤

  • Worker(php-cgi)進程執(zhí)行PHP腳本,如果超時,返回504錯誤

  • 處理結(jié)束,返回結(jié)果

第五步:PHP-FPM Worker => Master => Nginx

  • PHP-FPM Worker 進程返回處理結(jié)果,并關閉連接,等待下一個請求

  • PHP-FPM Master 進程通過Socket 返回處理結(jié)果

  • Nginx Handler順序?qū)⒚恳粋€響應buffer發(fā)送給第一個filter → 第二個 → 以此類推 → 最終響應發(fā)送給客戶端

1.2 PHP腳本解釋執(zhí)行的機制

了解了PHP + Nginx 整體的處理流程后,我們接下來看一下PHP腳本具體執(zhí)行流程,首先我們看一個實例:

<?php  
   if (!empty($_POST)) {
       echo "Response Body POST: ", json_encode($_POST), "\n";
   }
   if (!empty($_GET)) {    
       echo "Response Body GET: ", json_encode($_GET), "\n";
   }

我們分析一下執(zhí)行過程:
1.php初始化執(zhí)行環(huán)節(jié),啟動Zend引擎,加載注冊的擴展模塊
2.初始化后讀取腳本文件,Zend引擎對腳本文件進行詞法分析(lex),語法分析(bison),生成語法樹
3.Zend 引擎編譯語法樹,生成opcode,
4.Zend 引擎執(zhí)行opcode,返回執(zhí)行結(jié)果

在PHP cli模式下,每次執(zhí)行PHP腳本,四個步驟都會依次執(zhí)行一遍;
在PHP-FPM模式下,步驟1)在PHP-FPM啟動時執(zhí)行一次,后續(xù)的請求中不再執(zhí)行;步驟2)~4)每個請求都要執(zhí)行一遍;
其實步驟2)、3)生成的語法樹和opcode,同一個PHP腳本每次運行的結(jié)果都是一樣的,在PHP-FPM模式下,每次請求都要處理一遍,是對系統(tǒng)資源極大的浪費,那么有沒有辦法優(yōu)化呢?
當然有,如:

  • OPCache:前身是Zend Optimizer+ ,是 Zend Server 的一個開源組件;官方出品,強力推薦

  • APC:Alternative PHP Cache 是一個開放自由的 PHP opcode 緩存組件,用于緩存、優(yōu)化 PHP 中間代碼;已經(jīng)不更新了不推薦

  • APCu:是APC的一個分支,共享內(nèi)存,緩存用戶數(shù)據(jù),不能緩存opcode,可以配合Opcache 使用

  • eAccelerate:同樣是不更新了,不推薦

  • xCache:不再推薦使用了

2. OPCache 介紹

OPCache 是Zend官方出品的,開放自由的 opcode 緩存擴展,還具有代碼優(yōu)化功能,省去了每次加載和解析 PHP 腳本的開銷。PHP 5.5.0 及后續(xù)版本中已經(jīng)綁定了 OPcache 擴展。
緩存兩類內(nèi)容:

  • OPCode

  • Interned String,如注釋、變量名等

3 . OPCache 原理

OPCache緩存的機制主要是:將編譯好的操作碼放入共享內(nèi)存,提供給其他進程訪問。這里就涉及到內(nèi)存共享機制,另外所有內(nèi)存資源操作都有鎖的問題,我們一一解讀。

3.1 共享內(nèi)存

UNIX/Linux 系統(tǒng)提供很多種進程間內(nèi)存共享的方式:

1.System-V shm API: System V共享內(nèi)存
sysv shm是持久化的,除非被一個進程明確的刪除,否則它始終存在于內(nèi)存里,直到系統(tǒng)關機;
2.mmap API:

  • mmap映射的內(nèi)存在不是持久化的,如果進程關閉,映射隨即失效,除非事先已經(jīng)映射到了一個文件上

  • 內(nèi)存映射機制mmap是POSIX標準的系統(tǒng)調(diào)用,有匿名映射和文件映射兩種

  • mmap的一大優(yōu)點是把文件映射到進程的地址空間

  • 避免了數(shù)據(jù)從用戶緩沖區(qū)到內(nèi)核page cache緩沖區(qū)的復制過程;

  • 當然還有一個優(yōu)點就是不需要頻繁的read/write系統(tǒng)調(diào)用

3.POSIX API:
System V 的共享內(nèi)存是過時的, POSIX共享內(nèi)存提供了使用更簡單、設計更合理的API.

4.Unix socket API

OPCache 使用了前三個共享內(nèi)存機制,根據(jù)配置或者默認mmap 內(nèi)存共享模式。依據(jù)PHP字節(jié)碼緩存的場景,OPCache的內(nèi)存管理設計非常簡單,快速讀寫,不釋放內(nèi)存,過期數(shù)據(jù)置為Wasted。
當Wasted內(nèi)存大于設定值時,自動重啟OPCache機制,清空并重新生成緩存。

3.2 互斥鎖

任何內(nèi)存資源的操作,都涉及到鎖的機制。
共享內(nèi)存:一個單位時間內(nèi),只允許一個進程執(zhí)行寫操作,允許多個進程執(zhí)行讀操作;寫操作同時,不阻止讀操作,以至于很少有鎖死的情況。
這就引發(fā)另外一個問題:新代碼、大流量場景,進程排隊執(zhí)行緩存opcode操作;重復寫入,導致資源浪費。

4. OPCache 緩存解讀

OPCache 是官方的Opcode 緩存解決方案,在PHP5.5版本之后,已經(jīng)打包到PHP源碼中一起發(fā)布。
它將PHP編譯產(chǎn)生的字節(jié)碼以及數(shù)據(jù)緩存到共享內(nèi)存中, 在每次請求,從緩存中直接讀取編譯后的opcode,進行執(zhí)行。
通過節(jié)省腳本的編譯過程,提高PHP的運行效率。如果正在使用APC擴展,做同樣的工作,現(xiàn)在強烈推薦OPCache來代替,尤其是PHP7中。

4.1 OPCode

緩存Opcache 會緩存OPCode以及如下內(nèi)容:

  • PHP腳本涉及到的函數(shù)

  • PHP腳本中定義的Class

  • PHP腳本文件路徑

  • PHP腳本OPArray

  • PHP腳本自身結(jié)構(gòu)/內(nèi)容

4.2 Interned String

緩存首先我們需要理解,什么是 Interned String?
在PHP5.4的時候, 引入了Interned String機制, 用于優(yōu)化PHP對字符串的存儲和處理。尤其是處理大塊的字符串,比如PHP doces時,Interned String 可以優(yōu)化內(nèi)存。Interned String 緩存的內(nèi)容包括:變量名稱、類名、方法名、字符串、注釋等。

在PHP-FPM模式中,Interned String 緩存字符,僅限于Worker 進程內(nèi)部。而緩存到OPCache中,那么Worker進程之間可以使用 Interned String 緩存的字符串,節(jié)省內(nèi)存。

我們需要注意一個事情,在PHP開發(fā)中,一般會有大段的注釋,也會被緩存到OPCache中??梢酝ㄟ^php.ini的配置,關閉注釋的緩存。
但是,像Zend Framework等框架中,會引用注釋,所以,是否關閉注釋的緩存,需要區(qū)別對待。

5. OPCache 更新策略

是緩存,都存在過期,以及更新策略等。而OPCache的更新策略非常簡單,到期數(shù)據(jù)置為Wasted,達到設定值,清空緩存,重建緩存。
這里需要注意:在高流量的場景下,重建緩存是一件非常耗費資源的事兒。OPCache 在創(chuàng)建緩存時并不會阻止其他進程讀取。這會導致大量進程反復新建緩存。所以,不要設置OPCache過期時間

每次發(fā)布新代碼時,都會出現(xiàn)反復新建緩存的情況。如何避免呢?

  • 不要在高峰期發(fā)布代碼,這是任何情況下都要遵守的規(guī)則

  • 代碼預熱,比如使用腳本批量調(diào)PHP 訪問URL,或者使用OPCache 暴露的API 如opcache_compile_file() 進行編譯緩存

6. OPCache 的配置

6.1 內(nèi)存配置

  • opcache.preferred_memory_model="mmap" OPcache 首選的內(nèi)存模塊。如果留空,OPcache 會選擇適用的模塊, 通常情況下,自動選擇就可以滿足需求。可選值包括:mmap,shm, posix 以及 win32。

  • opcache.memory_consumption=64 OPcache 的共享內(nèi)存大小,以兆字節(jié)為單位,默認64M

  • opcache.interned_strings_buffer=4 用來存儲臨時字符串的內(nèi)存大小,以兆字節(jié)為單位,默認4M

  • opcache.max_wasted_percentage=5 浪費內(nèi)存的上限,以百分比計。如果達到此上限,那么 OPcache 將產(chǎn)生重新啟動續(xù)發(fā)事件。默認5

6.2 允許緩存的文件數(shù)量以及大小

  • opcache.max_accelerated_files=2000 OPcache 哈希表中可存儲的腳本文件數(shù)量上限。真實的取值是在質(zhì)數(shù)集合 { 223, 463, 983, 1979, 3907, 7963, 16229, 32531, 65407, 130987 } 中找到的第一個大于等于設置值的質(zhì)數(shù)。設置值取值范圍最小值是 200,最大值在 PHP 5.5.6 之前是 100000,PHP 5.5.6 及之后是 1000000。默認值2000

  • opcache.max_file_size=0 以字節(jié)為單位的緩存的文件大小上限。設置為 0 表示緩存全部文件。默認值0

6.3 注釋相關的緩存

  • opcache.load_commentsboolean 如果禁用,則即使文件中包含注釋,也不會加載這些注釋內(nèi)容。本選項可以和 opcache.save_comments 一起使用,以實現(xiàn)按需加載注釋內(nèi)容。

  • opcache.fast_shutdown boolean 如果啟用,則會使用快速停止續(xù)發(fā)事件。所謂快速停止續(xù)發(fā)事件是指依賴 Zend 引擎的內(nèi)存管理模塊 一次釋放全部請求變量的內(nèi)存,而不是依次釋放每一個已分配的內(nèi)存塊。

6.4 二級緩存的配置

  • opcache.file_cache 配置二級緩存目錄并啟用二級緩存。啟用二級緩存可以在 SHM 內(nèi)存滿了、服務器重啟或者重置 SHM 的時候提高性能。默認值為空字符串 "",表示禁用基于文件的緩存。

  • opcache.file_cache_onlyboolean 啟用或禁用在共享內(nèi)存中的 opcode 緩存。

  • opcache.file_cache_consistency_checksboolean 當從文件緩存中加載腳本的時候,是否對文件的校驗和進行驗證。

  • opcache.file_cache_fallbackboolean 在 Windows 平臺上,當一個進程無法附加到共享內(nèi)存的時候, 使用基于文件的緩存,也即:opcache.file_cache_only=1。需要顯示的啟用文件緩存。

關于“PHP opcache的原理及使用方法是什么”這篇文章的內(nèi)容就介紹到這里,感謝各位的閱讀!相信大家對“PHP opcache的原理及使用方法是什么”知識都有一定的了解,大家如果還想學習更多知識,歡迎關注創(chuàng)新互聯(lián)行業(yè)資訊頻道。

標題名稱:PHPopcache的原理及使用方法是什么
網(wǎng)站鏈接:http://muchs.cn/article24/isgjce.html

成都網(wǎng)站建設公司_創(chuàng)新互聯(lián),為您提供微信小程序小程序開發(fā)、自適應網(wǎng)站、網(wǎng)站設計、微信公眾號、搜索引擎優(yōu)化

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)

h5響應式網(wǎng)站建設