# 前端框架介紹 ## Front-End vs. Back-End 這裡簡單描述前端與後端的職責,以及基本的互動方式。 > 實際應用時仍有差異,僅為基本概念。 ### Front-End * 使用者看到的畫面 * code 運行在使用者的瀏覽器上 * HTML, JS, CSS ### Back-End * 用來與前端做溝通,連結資料庫 * code 運行在網站的伺服器上 * PHP, Python, SQL ### Request-Response * 當前端的使用者訪問一段網站時,首先發一個 request 給後端,請求這個網頁,後端則將原先儲存於伺服器的網頁內容 response 給前端瀏覽器。 * 誰做渲染? * 分為 client-side render 與 server-side render * CSR: server 將所有的 html, js, ... response 給瀏覽器,由瀏覽器進行渲染,再顯示給使用者 * SSR: server 渲染完 html 後再回傳給使用者,使用者可以在收到 response 後直接看到畫面。 ## What is Front-End Framework * 提到 Front-End Framework 一般會分為兩種 * Normal Front-End Framework * 也可以稱為 library,主要是加速前端的開發,減少許多 html 與 css 的撰寫,並且統一視覺上的設計。 * responsive design、carousel、headers、modals 等等 * 有名的 framework 如 Bootstrap、Foundation * JS Front-End Framework * 架構化前端網頁、SPA 等等 * 本篇所提及的 Front-End Framework 為此類型 * 有名的 framework 如 React、Vue、Angular ## Why Use JS Front-End Framework * 過往我們時常透過後端在 server-side 生成 HTML 模板後,直接 response 給瀏覽器顯示,並透過 JS 對 DOM 中元素進行互動,甚至為了開發方便,我們可能會使用例如 jQuery 的 library 來進行前端 JS 的撰寫。 * DOM (document object model) 可以理解成前端網頁的架構樹,所有的 CSS、JS 都是靠 DOM 來處理網頁內容。 * jQuery 則是一些已經寫好的 JS code,方便我們進行開發。 * ```graphviz digraph hierarchy { nodesep=1.0 rankdir=LR node [color=Black,fontname=Courier,shape=box] edge [color=Black] subgraph cluster_s { HTML JS CSS label="Client" JS->{Browser} [label="Show"] Browser->JS [label="interactive"] } Server->JS [label="Response"] } ``` * 簡單的小型開發絕對沒有問題,然而當需求不斷增加時,往往會遇到以下幾個問題: * 架構 * 由於語言限制,開發的過程往往將所有的 JS code 凌亂地塞進一個 JS file。 * 即使做了架構化的設計,當有新的需求要加入原本的網頁時,難以適當地擴充。 * Reuse * 當同一段 JS code 要重複用在不同的分頁中時,copy & paste 造成龐大的維護成本。 * 即使適當的設計架構,透過 import 來重複使用同樣功能的 code,仍會遇到變數混亂的問題。 * 全局變數、局部變數 * 開發的過程中,當組織越來越大時,全局變數與局部變數地混用,不但增加錯誤的可能性,也提高維護的成本。 * 瀏覽器支援 * JS 必須要在各種新舊瀏覽器之間通用,然而許多語法的改進卻會造成舊版瀏覽器不支援 (如 ES6)。 * SPA (single page application) * 在開發多個頁面的網頁應用時,我們會希望網頁不會因為用戶的操作而進行整個頁面的重新加載或跳轉,這時就要利用 JavaScript 動態的變換 HTML 內容。 * SPA 易於實現前後端分離開發,並且減輕伺服器壓力。 * 在 SPA 中,應用加載之後就不會再有整頁刷新,然而若以單純的 JS 進行 HTML 內容的轉換,往往又會導致 JS code 內容的龐大,難以維護。 * 渲染的性能 * 在一個頁面中,時常會有許多資料是連動的,因此往往需要透過 event listener 來監聽某項資料是否被修改,再進行相對應的操作,以改變頁面的內容。 * JS 動態變更頁面內容的方法及範圍,影響了網頁效能以及使用者體驗,並且同樣也會造成維護上的困難。 * 總結前端框架解決的最大問題:UI 與狀態的同步問題,如何有效率地達到這件事,並且每一個瞬間都能保證同步。 * MVC 設計 * 許多後端框架採用 MVC 的設計理念,那前端是否也可以以此作為架構的設計呢? * Model 數據層:定義各種變數及功能函式,透過閉包來儲存,並對外提供接口。數據層的內容影響了視圖層渲染的結果。 * View 視圖層:當使用者造訪頁面時,根據數據層的內容,進行網頁的初始化,建立整個 HTML 架構樹。 * Control 控制層:連接視圖層與數據層,當視圖層發生的事件時,透過控制層對數據層進行更新。 ```graphviz digraph hierarchy { nodesep=1.0 node [color=Black,fontname=Courier,shape=box] edge [color=Black] View->{Control} Control->{Model} Model->{View} {rank=same; Control, Model} } ``` * 過往 jQuery 的操作目標為 DOM,然而前端框架的目標卻是 model,能更有效的維護網頁中的各個部分。 * MVVM 設計 * 延伸 MVC 的架構,視圖層與數據層之間透過某種機制綁定。 * 根據不同的前端框架,綁定可能是單向數據流也可能是雙向數據流。 * View 和 Model 是分離的,View 的資料與 ViewModel 同步,因此不需要知道 Model 的存在,同樣 Model 也完全忽略 ViewModel 與 View 的存在。 ```graphviz digraph hierarchy { nodesep=1.0 node [color=Black,fontname=Courier,shape=box] edge [color=Black] View->{ViewModel} ViewModel->{Model} Model->{ViewModel}[style=dashed] ViewModel->{View}[style=dashed] {rank=same; View, ViewModel, Model} } ## How to Work ### Flow ```graphviz digraph hierarchy { nodesep=0.2 rankdir=LR node [color=Black,fontname=Courier,shape=box] edge [color=Black] subgraph cluster_sv { node [color=Black,fontname=Courier,shape=box] subgraph cluster_s { "JS Compliler" [style=rounded] subgraph cluster_v { "Vue Template" [style=rounded] "Vue Data" [style=rounded] "Vue Script" [style=rounded] "Vue Style" [style=rounded] } "JS Compliler"->"Vue Template" [label="Compare and Update"] } subgraph cluster_sr { HTML JS CSS } "Vue Template"->JS [label="Compile"] label="Client" JS->{Browser} [label="Show"] Browser->"JS Compliler" [label="event "] } Server->"Vue Script" [label="Response"] } ``` https://ithelp.ithome.com.tw/users/20103424/ironman/1049 http://www.phpxs.com/post/5988/ ### Data-binding ### Router https://github.com/dt-fe/weekly ## React’s advantages Virtual DOM improves both the experience of the user and work of the developer – Virtual DOM helps to update any user’s changes without the other parts’ interference by applying isolated components. It greatly helps to smooth the experience of all participants in real time mode. Saving time while re-using React components – React deals with isolated components, that’s why you can reuse them anytime you need. System upgrades will not impact or change your system. The stable code is provided by one-direction data flow – Direct work with each component requires one-direction data flow and makes the code really stable. Another thing is that only downward data binding is possible in this JavaScript framework. An open-source library with a variety of tools – All updates are released to the community. React has had the open-source library and engineers can introduce the additional tools.