近些年來,越來越多的JavaScript框架(即AngularJS,BackboneJS,ReactJS)變得越來越流行。許多公司和開發人員使用這些JavaScript框架開發應用程序。這些框架有很多的優勢:
- 前端和后端獨立開發
- JavaScript框架+RESTFUL的API(或微服務架構)
- SPA(Single Page Application)
- 某種程度上有利於提高開發效率
但是使用JavaScript框架對前台尤其是需要支持搜索引擎的頁面是很有問題的,這是因為我們使用這些框架基本上都是基於虛擬元素或屬性和JavaScript綁定JSON對象,都是SEO不友好的。很多搜索引擎,社交媒體,爬蟲甚至不支持抓取JavaScript的網頁。
很慶幸的是,我們可以使用PreRender.io預渲染頁面(PreRender.io通過執行頁面上的JavaScript,然后呈現給搜索引擎爬蟲)。
什么是PreRender.io預渲染
Prerender.io是基於Node.js的程序,它可以讓你的JavaScript網站支持搜索引擎,社交媒體,並且它兼容所有的JavaScript框架和庫。它采用PhantomJS渲染JavaScript的網頁然后呈現為HTML。此外,我們可以實現的prerender服務層來緩存訪問過的頁面,這將大大提高性能。
PhantomJS是利用JavaScript API腳本化的Headless WebKit。它具有 速度快 和 支持Native 的各種Web標准:DOM處理,CSS選擇器,JSON,Canvas和SVG。
現已有很多prerender許多中間件(我們可以用它來實現應用程序內部邏輯的prerender庫):
你可以找到從這個鏈接找到大多數的中間件: https://prerender.io/documentation/install-middleware。Apache和Nginx的是服務器容器級中間件,其他都是應用層面的中間件。
官方網站是: https://prerender.io/。
GitHub的網址: https://github.com/prerender
你可以到我的github地址下載我寫的ASP.NET MVC 和ASP.NET Core的中間件: https://github.com/dingyuliang/prerender-dotnet
或者用Nuget下載我寫的ASP.NET MVC 和ASP.NET Core中間件: 搜索Prerender, https://www.nuget.org/packages?q=prerender
1. ASP.NET MVC:
Install-Package DotNetOpen.PrerenderModule
2. ASP.NET Core:
Install-Package DotNetCoreOpen.PrerenderMiddleware
3. PrerenderReady jQuery:
Install-Package DotNetOpen.PrerenderReady.jQuery
4. PrerenderReady AngularJS:
Install-Package DotNetOpen.PrerenderReady.AngularJS1
PreRender.io 預渲染解決方案
根據PreRender邏輯,我覺得有3個不同的級別的解決方案來實施prerender.io
-
方案1:應用層
通過中間件實現對應用程序級別prerender.io邏輯(即Express NodeJS中間件,Ruby on Rails的中間件,ASP.NET MVC中間件,...)
- Http請求到達
- 應用程序將檢查Http請求是否來自爬蟲(User Agent)。
- 如果請求來自爬蟲,那么appliaction將調用prerender服務,把原來的URL作為查詢字符串。
- 預渲染服務將調用應用程序
- 應用程序返回原始的HTML用JavaScript邏輯的prerender服務
- 預渲染服務將執行內部HTML的JavaScript(與瀏覽器類似)
- 預渲染服務將最終的HTML返回到應用程序。
- Appliaction將最終的HTML返回到瀏覽器。
- 如果Http請求來自普通用戶,應用程序將執行輸出,並發送回瀏覽器。
-
方案2:服務器容器級別
通過使用URL重寫中間件,實施服務器容器級別prerender.io邏輯(i.e. Apache,Nginx,IIS)。
- Http請求到達
- 服務器容器(如Apache,Nginx,IIS)將檢查Http請求是否來自爬蟲(User Agent)。
- 如果Http請求來自爬蟲,然后重寫URL(將原始URL作為查詢字符串)預呈現服務。
- 預渲染服務將調用應用程序
- 應用程序返回JavaScript邏輯原始的HTML
- 預渲染服務將執行內部HTML的JavaScript,與瀏覽器類似
- 預渲染服務將返回最終的HTML服務器容器(Apache,Nginx,IIS)。
- 如果Http請求來自普通用戶,然后將流量重定向到應用程序。應用程序將執行並返回輸出到服務器容器。

-
方案3:網絡級別
我們通過負載均衡的代理實現網絡級prerender.io邏輯,i.e. HAProxy:
- Http請求到達
- 負載均衡代理會檢查Http請求是否來自爬蟲(User Agent)。
- 如果Http來自爬蟲,然后將流量重定向(將原始URL作為查詢字符串)預呈現服務。
- 預渲染服務將調用應用程序
- 應用程序返回包含JavaScript原始的HTML
- 預渲染服務將執行內部HTML的JavaScript,與瀏覽器類似
- 預渲染服務將最終的HTML返回給負載平衡的代理。
- 如果Http請求來自普通用戶,將流量重定向到應用程序。應用程序將執行並返回輸出到負載平衡的代理。
解決方案比較
以上3種不同的解決方案是在不同的級別解決相同的問題,但是它們有着不同的性能結果。
- 方案1:應用層
該解決方案易於實施,易於調試,但它也加重應用程序負載,因為應用程序需要等待的prerender服務調用的應用程序和執行JavaScript,這將需要大量的時間等待,並且等待時間取決於它的JavaScript邏輯的復雜性。因此,這種解決方案的瓶頸是應用程序。
如果的prerender服務已關閉,會影響普通用戶訪問體驗(長時間的請求預呈現服務,消耗應用程序和服務器容器資源)。
推薦指數:1
- 方案2:服務器容器級別
這種解決方案利用URL重寫邏輯來將負載瓶頸從應用級移到IIS級,這種方案提高了應用程序的靈活性。
如果的prerender服務已關閉,會影響普通用戶訪問體驗是(長時間的請求預呈現服務,消耗服務器容器資源)。
推薦指數:2
- 方案3:網絡級別
這種解決方案將在最高水平通過使用負載平衡來實現,在網絡級,因此,存在於服務器容器和應用程序無瓶頸,因為它移動到負載平衡。
有了這個解決方案,甚至的prerender服務關閉,也不會影響到普通用戶的接入體驗。
推薦指數:3
基於上述的基本分析,通常來說,方案3比方案2更好,方案2比方案1更好。
性能問題
無論我們將要使用那種解決方案,我們總應該思考如何提高性能,因為執行JavaScript邏輯總會比執行服務器端邏輯花費更長的時間,而且不可預見。
在另一方面,如果我們只重定向爬蟲的Http請求到預渲染服務,我們不需要提供最新信息給爬蟲,我們可以使用prerender的緩存服務來提高性能,我們可以緩存爬蟲訪問過的頁面12小時-1天。
在接下來文章中,我將解釋如何使用開源項目來實現的prerender服務.
Prerender.io相關
- Prerender.io - 預渲染架構,提高AngularJS SEO
- Prerender.io - 設置預渲染服務,為搜索引擎優化JavaScript
- Prerender.io - 實施最佳實踐
- Prerender.io - 應用層中間件 - ASP.NET HttpModule
- Prerender.io - 應用層中間件 - ASP.NET Core中間件
- Prerender.io - jQuery和angularJS插件prerenderReady
