2016-04-19 18 views
63

私たちは講義とチャプターのリストを用意しています。 2つのリストはreduxストアに格納されます。 ここでは、選択した講義スラッグとチャプタースラッグをURLのハッシュタグに残しておき、URLを変更するとストアを変更する必要があります(双方向同期)。Redux状態とURLのハッシュタグパラメータを同期させる方法

react-routerまたはさらにreact-router-reduxを使用すると、最適な解決策は何ですか?

リアクションルータがURLのハッシュタグを維持するためにのみ使用され、1つのコンポーネントだけが更新される良い例が実際には見つかりませんでした。

ありがとうございました!

+3

なぜ、React RouterをURLパラメーターの真理値のソースとして使用するのではなく、ユーザーが入力した小道具を使用するのかmapStateToProps(state、ownProps)? –

+2

urlパラメータには、講義のスラッグと選択されたチャプタだけが含まれているためです。ストアでは、名前、スラッグ、および選択されたブール値の講義とチャプターのリストがあります。例えば、 – JoKer

+0

。 https://peterbeshai.com/react-url-query/を使用しますか? – mb21

答えて

126

私はあなたがする必要はないと思います。
(申し訳ありませんが、私の経験では最高の解決策です)

ストアはデータの真実の源です。これは問題ありません。
React Routerを使用している場合は、それをあなたのURL状態の真実の源にします。
すべてを店舗に保管する必要はありません。 URLパラメータが唯一の講義のナメクジと選択されている章が含まれているため

:あなたのユースケースを考えると例えば

、。ストアでは、名前、スラッグ、および選択されたブール値の講義とチャプターのリストがあります。

問題は、データを複製していることです。ストア内のデータ(chapter.selected)は、React Router状態で複製されます。 1つの解決策がそれらを同期させることになりますが、これはすぐに複雑になります。 React Routerを選択した章の真実の源にするだけではどうですか?

あなたの店の状態は、(簡体字)のようになります。

{ 
    // Might be paginated, kept inside a "book", etc: 
    visibleChapterSlugs: ['intro', 'wow', 'ending'], 

    // A simple ID dictionary: 
    chaptersBySlug: { 
    'intro': { 
     slug: 'intro', 
     title: 'Introduction' 
    }, 
    'wow': { 
     slug: 'wow', 
     title: 'All the things' 
    }, 
    'ending': { 
     slug: 'ending', 
     title: 'The End!' 
    } 
    } 
} 

それだそれ!そこにはselectedを保管しないでください。代わりに、React Routerがそれを処理させます。あなたのルートハンドラーで、次のように書く

function ChapterList({ chapters }) { 
    return (
    <div> 
     {chapters.map(chapter => <Chapter chapter={chapter} key={chapter.slug} />)} 
    </div> 
) 
} 

const mapStateToProps = (state, ownProps) => { 
    // Use props injected by React Router: 
    const selectedSlugs = ownProps.params.selectedSlugs.split(';') 

    // Use both state and this information to generate final props: 
    const chapters = state.visibleChapterSlugs.map(slug => { 
    return Object.assign({ 
     isSelected: selectedSlugs.indexOf(slug) > -1, 
    }, state.chaptersBySlug[slug]) 
    }) 

    return { chapters } 
} 

export default connect(mapStateToProps)(ChapterList) 
+0

詳細な回答は@danにありがとうございます。私はそれを適用し、それがどのように働いたかを報告しようとします。 – JoKer

+4

あまりにも遅く帰ってきて申し訳ありませんが、私は先週の休日にいました。一つの質問があります。あなたは、URLからデータを取得し、それをレンダリングする1つの方法について説明しました。新しい選択された章でURLをどのように更新しますか? – JoKer

+8

私は 'browserHistory.push()'( 'browserHistory'は' react-router'からインポートされます)をアクションクリエータでコールします。おそらくRedux Thunkを使用して、そこに副作用が起こっていることを明確にするでしょう。私は 'dispatch({...});と呼ぶだろう。 browserHistory.push(...) 'の内部にあります。 –

3

react-router-reduxあなたは、格納するためにURLのものを注入するのを助けることができるので、ハッシュタグが変更されるたびに保存することもできます。

+13

これは、解析されたパラメータではなく、場所を提供するだけなので、React Routerが手動で提供するものを再実装するのがうまくいかない限り、有用性は限られています。これは、ユーザーセッションの記録と再生が機能するように、ストアをアクション*と同期させるための素晴らしいソリューションです。しかし、これを必要としないアプリケーションにとってはそれほど有用ではありません。 –

関連する問題