LiferayDynamicCSSFilter方法的研究-快取檔案存在的處理

餘二五發表於2017-11-15

引入:

現在我們接著上文章討論來解決疑問3:對於快取檔案已經存在和不存在的情況有什麼特別處理。


分析:

現在我們先來看下如果快取檔案已經存在時候的處理方式


因為我們開始已經建立了一個快取檔案,它的base名字為$CATALINA_TMPDIR/liferay/css/portal/6476841388170400461

160623788.png


假定我們上次訪問的路徑是main.css檔案,那麼這次當我們再訪問main.css檔案的時候,我們就發現它走了第120行。它會先判斷快取檔案的最後修改時間戳(cacheDataFile.lastModified())和原始檔案的最後修改時間戳(file.lastModified()),如果前者偏大,則說明快取檔案是最新的,那麼它就124行直接把快取檔案的內容型別檔案的contentType讀取出來,然後

161131183.png

第126行吧httpServletResponse的返回型別設定為這個快取檔案內容型別(回想以前曾說過,第一次設定時候這個值應該是text/css),最後吧快取的資料檔案放到輸出流中。

然後在第DynamicCSSFilter中第217行用

161356787.png

使用ServletResponseUtil 讀取這個快取檔案中的內容並且輸出到客戶端。


所以客戶端就可以獲得最新版本的解析後的普通css資原始檔並且使用了。(這個過程中並沒有JRuby解析Sass生成css,所以減少好多IO操作,效率提高了很多)




下面我們再來看下快取不存在,從頭生成這些檔案的例子:

假如我們清空了tomcat的temp目錄吧這些快取檔案都清空,那麼顯然,它沒辦法走快取路線(也就是不走if(cacheDataFile.exists()分支),所以它會去生成新的。

讓我們回到原始的討論,如下所示,在142行是從原始的帶Sass的樣式檔案中讀取的css檔案,存放到content中

162721297.png

然後第144行解析Sass檔案獲取的普通css檔案存放到dynamicContent中,我們可以比較看出明顯不同.


尤其是在@import這種語法後,轉為的新的都加了很多引數。


這時候,呼叫第149行的FileUtil.write(cacheContentTypeFile, ContentTypes.TEXT_CSS)會寫入內容型別檔案:

163401168.png

從伺服器看,當前目錄下只有一個檔案<baseName>_E_CONTENT_TYPE,這是合乎情理的,因為資料檔案還沒建立呢,才剛剛寫內容型別檔案,而且寫的時間也和當前的時間戳吻合,說明是剛才才寫入的這個檔案,並且這個檔案內容只有text/css,所以這個檔案很小,只有8個位元組。


然後第193行,就會吧生成的普通css檔案內容(也就是存放在dynamicContent變數中)寫入到資料檔案中,呼叫是第193行FileUtil.write(cacheDataFile.dynamicContent);

163639977.png


我們看下伺服器目錄,果然現在生成了<baseName>_E_DATA檔案:

163830443.png

這個檔案從時間戳看比剛才的內容檔案晚5分鐘,這也合乎常理,因為我在除錯,要單步走,並且還有截圖,寫文章,所以確信,這正是除錯點所執行到時候建立的檔案,並且檔案大小是874位元組,這個也剛好和我們的dynamicContent的大小一樣,如下圖:

164027694.png


一切都是那麼吻合和完美。



結論:

(1)當請求的資原始檔已經在Liferay的快取中(也就是在$CATALINA_TMPDIR/liferay/css/folder/<hashcode>時候,伺服器會去比較快取中的資原始檔的最近使用時間戳和原始資原始檔的最近使用時間戳,如果快取的時間戳比較新,那麼就直接從快取中讀取內容型別資訊和被解析後的普通css檔案,然後構造輸出流輸出到客戶端。

(2)當請求的資原始檔沒有在Liferay快取中,那麼Liferay框架會自己在快取目錄中構建相應的目錄和檔案,並且先是寫內容型別檔案,再寫快取資料檔案(Sass解析後得到的普通css檔案),最終把這些內容通過輸出流輸出到客戶端。

本文轉自 charles_wang888 51CTO部落格,原文連結:http://blog.51cto.com/supercharles888/1282865,如需轉載請自行聯絡原作者


相關文章