前端 UI組件化的一些思考
- 文檔 由你團隊成員所寫的,如果使用 React 你可以直接通過注釋 Proptypes 的方法,通過 React-docgen 生成文檔。
- 代碼預覽 你應當提供一個可以讓開發者實時調試代碼的地方,使其他這些組件的使用者可以更好地理解各個props 。
- 使用實例 提供一些如何將其數據導入 UI 的實例代碼,使其他開發者可以更快上手與他們的使用情況。
- 相容性 譬如怎樣使用警告、載入信息等額外內容的規範,來提供用戶相一致的體驗。
- 將整體的問題拆開成細目。
- 如何處理 CSS ?
- 如何將資源如變數,圖標等公有化?
- 如何將其打包,便於使用?
- 開始從中獲取收益!
首先,我們現講如何將問題拆解,我們應當將頁面上顯示的一切看作是組件。也就是說每當你拿到設計師的稿件,第一件事應當就是講頁面上一切你所能看到的元素翻譯成無數個小組件,這也是 React 的理念:復用組件。
下一步,我們再將小組件組合成為較大的組件。這裡不得不提到 Brad Frost 所提出的 Atomic Design。它所闡述的理念與本文所要說的觀點相似,即由「原子」組成「分子」,「分子」構成「組織」,從而形成模板,進而生成頁面。看下這些例子,標籤,輸入,按鈕各是一個「原子」,合在一起即成了一個「分子」。其次, CSS 一直以來都是一個非常棘手的問題。我們應當如何處理類名衝突?如何使用第三方庫的 CSS 文件?如何保證與 CSS 文件不衝突?如何確保相互獨立?對於這些問題現在已經有了不少解決方案。David Wells 在演講中提到的與我們公司現在所使用的都是通過 PostCSS + CSS modules的解決方案。關於 CSS Modules 搭配 React 的用法,這裡有個很好的例子:Modular CSS with React 。具體來說可以見此用例:/* Thumbnail.jsx */import styles from "./Thumbnail.css";render() { return (<img className={styles.image}/>)}
/* Thumbnail.css */.image { border-radius: 3px;}
Hash 後生成的 HTML tag 與 CSS 看起來會是這樣:
/* Rendered DOM */<img class="Thumbnail__image___1DA66"/>
/* Processed Thumbnail.css */.Thumbnail__image___1DA66 { border-radius: 3px;}
此處將在我們 Thumbnail.jsx 文件中通過 CSS modules 引入 CSS 文件,再通過引入的 style 變數獲取 hash 後的 CSS 類名。
此處提到的另一個工具 PostCSS 會將你的css文件全加上前綴名以適應不同瀏覽器,解決 CSS 4 的兼容性問題。所以你真的需要使用 PostCSS 和 CSS Modules 么?你可以問自己如下問題:你在一個團隊中工作么?你使用第三方庫的 CSS 文件么?你的產品在第三方環境中運行么?你想要你的產品在任何環境中體驗一致么?如果你回答是,那你可以選擇嘗試這一方案,因為這一解決方案基本解決了類名衝突與瀏覽器兼容的問題。
第三,關於如何處理共享資源。對於全局變數與 mixin ,我們建議通過幾個 PostCSS 的插件來解決,而非使用sass等預處理器語言。可以通過一個簡單的Postcss config來解釋:var vars = require("postcss-simple-vars");var mixins = require("postcss-mixins");var postCSSConfig = [ mixins({ mixins: require("./mixins") }), vars({ variables: require("./variables") }),]
此處我們從一個 mixins.js 文件中提取全局mixin,一個 varibles.js 文件中提取全局變數,他將會在你所有通過 PostCSS 編譯的 CSS 文件中生效。實際使用中與less和sass十分相似,見例:
.hyo { @mixin MarsPower; /* 在 mixin.js 文件中定義 */ color: $MarsRed; /* 在 variables.js 文件中定義 */}
<svg><use id=「icon-aaa」></svg>
在版本更新時,注意使用語義化版本。每當你要開始寫一個新的組建時,可以先在 Github 上搜索一下前人的實現方法,站在巨人的肩膀上做事才會事半功倍。
最後,關於如何打包,DW 推薦的方法是如下文件結構:對此我表示很贊同。分開打包每個小的組件入口,扁平化你的文件結構,組件之間可以相互依賴使用,對於開發效率與擴展化能力十分有幫助。有些時候很難去查閱你在哪個頁面使用了哪個組件。這裡你可以使用一個監視器組件來查詢你使用的組件。這在很多時候非常便利,譬如你想升級某一個組件,你會想去了解哪些頁面或是組件依賴了這個組件從而進行修改,DW 提供了一個實現,我們可以根據我們的需求來實現自己的 Monitor Component。最後的最後,小結幾個開發 React 組件中常遇見的問題。(至少我是碰到了- -)首先,做之前想明白要實現的 Feature,與設計師討論並寫下自己的需求,市面上是否有可用的替代品,儘可能不要定義過多的 prop,不然在之後維護會非常辛苦。其次,儘可能地給予使用者客制化的權利,譬如內容如何渲染,排序如何進行等,最好開放一個 api 使得使用者可以自己定義,因為你永遠無法預測並滿足所有使用者的需求。第三,在所有瀏覽器上進行測試,老生常談了但有時還是會忘。最後,從開始便定義好 lint 的規則並遵從它,可以參考 AirBnB 的配置作為起始點。啰啰嗦嗦寫了這麼多,希望大家都能從中能收穫些許。最後再安利一下 Hyo,也算是自己的第一個認真做的開源項目,希望大家多多點星! | Demo點這裡 | 文檔點這裡 |
推薦閱讀:
※在React.js中使用PureComponent的重要性和使用方式
※koa 實現 react-view 原理
※react 行,我等你