React中父組件與子組件之間的數據傳遞的的實現你們均可以輕易作到,但對比不少人的實現方法,老是會有或多或少的差別。在一個團隊中,這種實現的差別體現了每一個人各自的理解的不一樣,可是反過來思考,一個團隊用了一樣的UI,一樣的框架,實現方式確實有差別,這其實就是工程化的問題。前端
回到React中父組件與子組件之間的數據傳遞的問題上來。編程
父組件與子組件之間的數據傳遞的實現方式大體能夠分爲2種狀況:架構
一、子組件用本身的flux環傳遞數據,最後調用父組件的onChange事件將數據傳給父組件。框架
二、子組件調用父組件的onChange事件,在父組件中的onChange事件中調用flux環傳遞數據到付組件的View層工具
這2種方式各有優勢,對比這兩種方式,在實時性上,第二種方式是經過調用父組件的onChange事件,數據改變是經過父組件的flux環發生改變的,因此是實時的,而第一種方式的數據是經過子組件本身的flux環改變的,最終傳給父組件,因此非實時;而在粒度上,這2種方式是相同的,都是維護了一個局部邏輯。咱們通常用子組件來實現一些頁面局部的複雜邏輯,若是這個邏輯內部的數據處理也很複雜(要根據各類狀況做出不一樣的斷定、改變),那麼第一種無疑更爲合適,而更爲現實的狀況是,每每局部的複雜邏輯的實如今子組件內部還有子組件的子組件,這種狀況下,優先選擇第一種方式;那麼相對的若是這個數據處理比較簡單,咱們徹底能夠將整個子組件看作頁面上的一個輸入框(也能夠是其餘實現某個功能的對話框),那麼父組件中的一個輸入框調用父付組件的onChange事件來改變數據流,毫無疑問,第二種方式更爲合理些。ui
按照第二種方式,咱們常常能夠在父組件中看到以下的局部代碼:this
onChange: function(property, value) { Action.changePromotionDetail(property, value); }, render: function() { return ( <div className="xui-promotion-flashSalePage"> <ProductInfo onChange={this.onChange} /> <PromotionInfo onSubmit={this.onSubmit} onChange={this.onChange} promotionName={this.state.promotionName} advert={this.state.advert} promotionRangeDate={this.state.promotionRangeDate} memberGrades={this.state.memberGrades} memberGrade={this.state.memberGrade} promotionPrice={this.state.promotionPrice} numPerPurchase={this.state.numPerPurchase} period={this.state.period} numPerPeriod={this.state.numPerPeriod} /> </div> ) }
若是傳入子組件的屬性和方法越多,那麼代碼的可讀性其實越差,維護起來也更不方便,甚至在父組件的Store中還須要對數據流作許多處理,相似:spa
changePromotionDetail: function(action) {
if (...) {
this.data[action.data.property] = ...;
} else {
this.data[action.data.property] = action.data.value;
}
this.__emitChange();
}
那麼咱們又須要思考,若是咱們像上面所說的將子組件看作一個輸入框,一個輸入框應該只須要輸入一個值,父組件不該該接受那麼多的不一樣屬性的數據,同時父組件須要作的只是將接受到的一個數據經過flux環傳遞給父組件的View層。那麼咱們能夠採用的一種方法是子組件的數據變動先調用子組件的onChange事件,並在其中作好必要的數據處理,而後將數據添加到一個對象中,以一個數據處理完畢的對象的形式調用父組件的onChange事件:code
onChange: function(property, value) {
if (property == '...') {
// do someting here...
} else {
// do someting here...
}
var obj = {
// some key/value here
};
this.props.onChange(obj);
}
這樣父組件中的代碼就能夠簡化爲以下:對象
onChange: function(obj) { Action.changePromotionDetail(obj); }, render: function() { return ( <div className="xui-promotion-flashSalePage"> <ProductInfo onChange={this.onChange} /> <PromotionInfo onSubmit={this.onSubmit} onChange={this.onChange} infoObj={this.state.infoObj} /> </div> ) }
再回到標準化的思考上,以React爲例,React自己只是一個UI,facebook推薦了flux的架構,這就是一種實現方式,那麼一個團隊在大方向上採用的技術和實現方式其實就肯定了下來。若是咱們進一步的細分,對諸如父組件和子組件之間的數據傳遞的方式,數據傳遞的格式等等做出限制,看上去好像限制了研發編程的自由,同時將研發的工做變成了機械的重複,可是換個角度,這樣的限制必然提升了研發效率,每一個人碰到不一樣的場景都有了統一的應對策略;這樣的限制也必然下降維護的成本,每一個人都能理解他人的編程思路。這就是工程化的一部分。
編程就是爲了解決問題,要想解決問題又須要考慮2個問題:
一、工具。
二、方式。
工具是學不完的,尤爲如今前端的工具井噴式的發展(雖然側面說明了前端工具的匱乏~),到這個公司用React,之後跳槽去了另外一家又用Angular,後來換了部門,這個部門又用Vue。
那麼,做爲研發,或許能夠思考第二個問題,標準化的方式。每一個公司每一個部門都會有一套標準,你須要作的是先學會這套標準,同時去思考能夠完善的地方,譬如這種場景沒有標準化的解決方案,你能夠提出一個方案,若是被你們接受了,你的方案就成爲了標準的一部分。
這或許也是一條前端之路,一條提升編程效率與維護性的路,一條解決工程化部分問題的路。