2016-09-07 63 views
9

隨着我進一步實現redux + react到一個相當複雜的應用程序中,這個應用程序依賴於許多API請求來加載單個頁面,所以我無法決定是否最好在頁面處理所有異步的東西,並將道具傳遞給愚蠢的組件擁有多個容器組件,這些組件只關心他們需要的數據,以及獲取他們需要的數據。我來回走了這兩種模式之間,發現他們各有優點/缺點:React Redux:更多容器v.s.更少的容器

如果我把在頂部有一個單一的容器組件:

  • 親:所有isFetching道具fetchSomeDependency()行動可以在一個地方處理。
  • con:真正令人討厭的缺點是我發現自己必須通過多個組件轉發道具和回調,並且樹中間的某些組件最終與此綁定。

這裏是問題的一個視覺的例子,顯示關係所需的道具明智:

<MyContainer 
    data={this.props.data} 
    isFetchingData={this.props.isFetchingData} 
    fetchData={this.props.fetchData} 
> 
    {!isFetchingData && 
    <MyModal 
     someData={props.data} 
     fetchData={props.fetchData} 
     > 
     <MyModalContent 
     someData={props.data} 
     fetchData={props.fetchData} 
     > 
      <SomethingThatDependsOnData someData={props.someData} /> 
      <SomeButtonThatFetchesData onClick={props.fetchData} /> 
     </MyModalContent> 
     </MyModal> 
    } 
</MyContainer> 

正如你所看到的,<MyModal /><MyModalContent />現在需要與擁有無關道具關注它看作是一種模式應該能夠被重用,並且只關心模式的文體特徵。

起初以上看起來不錯,但一旦我有100多個組件,它們都感覺非常混亂,我發現這些頂級容器組件的複雜性對我來說太高了,因爲它們中的大多數(在我正在工作的應用程序中)取決於來自3個API請求的響應。

於是我決定嘗試多個容器:

  • 親:完全消除需要轉發的道具。在某些情況下做它仍然有意義,但它更加靈活。
  • 親:方式更容易重構。我很驚訝我如何能夠在沒有任何突破的情況下大幅移動和重構組件,而在另一種模式中,事情卻打破了很多。
  • 親:每個容器組件的複雜性要小得多。我mapStateToPropsmapDispatchToProps是更具體的是在
  • CON組件的目的:依賴於異步東西的任何組件將始終需要處理本身isFetching狀態。這增加了在單個容器組件中處理的模式中不必要的複雜性。

所以今天的主要困境是,如果我使用一個容器,我的根容器和葉片組件之間的部件得到這個非必要的複雜性。如果我使用多個容器,我在葉子組件中得到了更多的複雜性,並且最終得到的按鈕需要擔心isFetching,即使按鈕不應該擔心這一點。

我想知道是否有人找到了避免這兩個缺點的方法,如果有的話,您遵循什麼樣的「經驗法則」來避免這種情況?

謝謝!

回答

0

我一直看到的方式是將容器放在除root/app組件以外的邏輯組件組的最頂層組件中。

因此,如果我們有一個展示成果,讓我們假設該組件heiarchy這樣

<Root> <- setup the app 
    <App> 
    <Search/> <- search input 
    <Results/> <- results table 
    </App> 
</Root> 

我會做SearchResults Redux的認識容器一個簡單的搜索應用程序。因爲反應組分假設爲可組合。您可能有其他組件或頁面需要顯示ResultsSearch。如果將數據提取和存儲感知委託給根或應用程序組件,則會使組件相互依賴於其他應用程序。當您必須實施更改時,這使得它變得更加困難,現在您必須更改所有使用它們的地方。

這可能是一個例外,如果你真的有緊密耦合的組件之間的邏輯。即便如此,我還是會說,你應該創建一個容器來包裝緊密耦合的組件,因爲如果沒有其他組件,它們將無法被真實地使用。

0

我甚至不會考慮使用單個容器方法。它幾乎完全否定了redux的所有優點。如果你所有的狀態都在一個地方,並且所有的回調都在一個地方(根組件),那麼就沒有必要擁有一個狀態管理系統。

雖然我覺得有一條細線可以行走。我製作了一個應用程序,大約5周(兼職),現在它已經達到3000行。它有3個級別的視圖嵌套,我自己實現的路由機制,以及深度超過10層的需要修改狀態的組件。每個大屏幕基本上都有一個容器,它的功能非常好。

但是,如果我點擊我的「客戶」視圖,我會得到一個客戶列表,因爲我的客戶端視圖位於redux容器中,並獲取作爲道具傳遞的客戶端列表。然而,當我點擊一個客戶時,我真的很不願爲另一個客戶的個人資料做一個redux容器,因爲它只是一個額外的傳遞道具。看起來,根據應用程序的範圍,您可能需要將道具傳遞至redux容器之後的1-2個級別,如果不止於此,則只需創建另一個Redux容器。再次,如果它是一個更復雜的應用程序,那麼有時使用redux容器的混合以及其他一些不使用它們的時間可能會更糟糕的可維護性。簡而言之,我的意見是儘可能減少Redux容器的數量,但絕對不會以複雜的道具鏈爲代價,因爲這是使用Redux開始的主要觀點。

+0

請發表可讀的解決方案。 – Sachith