Давайте взглянем на типичную настройку react-router.

render((
 <Router history={browserHistory}>
 <Route path=”/” component={Index}>
 <Route path=”test” component={Test}/>
 </Route>
 </Router>
), document.body)

По сути, мы создаем декларативную спецификацию того, как должна работать маршрутизация нашего приложения. Как ни странно, мы делаем это внутри нашего кода пользовательского интерфейса.

Не было бы лучше, если бы мы могли указать представления, которые мы хотим отображать, с помощью кода? Давайте сделаем демонстрационное приложение, которое делает это. Это основной файл приложения. Он использует деку вместо React, но в основном это одно и то же. В любом случае, не беспокойтесь о коде рендеринга, здесь мы сосредоточимся на маршрутизации.

import {dom, element} from ‘deku’;
// redux-simple-router just keeps the browser url bar synced with a
// path in the store. We’re going to use that data to do our own routing.
import {syncReduxAndRouter} from ‘redux-simple-router’;
// Required for redux-simple-router
import createBrowserHistory from ‘history/lib/createBrowserHistory’;
// A Redux store
import createStore from ‘./store’;
import App from ‘./components/app’;
function createApp(rootEl) {
 const store = createStore();
syncReduxAndRouter(createBrowserHistory(), store);
// deku does rendering
 const render = dom.createRenderer(rootEl, store.dispatch);
 render(<App/>, store.getState());
 return store.subscribe(() => render(<App/>, store.getState()));
}
createApp(document.getElementById(‘approot’));

Важной частью является эта строка:

syncReduxAndRouter(createBrowserHistory(), store);

Состояние хранилища теперь будет содержать ключ с информацией о текущем пути браузера. Это все, что нам нужно, чтобы узнать, какую страницу мы должны показать.

Если вы не знакомы с концепцией селекторов, я предлагаю вам прочитать документацию [reselect](https://github.com/rackt/reselect), поскольку там все объясняется гораздо полнее. Достаточно сказать, что это чистые функции, которые могут действовать как простой способ получения новых данных из состояния хранилища.

Этот код войдет в selectors.js

import {createSelector} from ‘reselect’;
import Index from ‘../components/templates/index’;
import Test from ‘../components/templates/test’;
export const
  // Get the routing data that redux-simple-router put in the store
  routing = state => state.routing,
  view = createSelector(
    routing,
    ({path}) => {
      // We know what page should be shown based on the path
      // Return the component responsible for rendering that page
      switch(path) {
      case ‘index.html’:
        return Index;
      case ‘/test’:
        return Test;
      default:
        // Return a component that renders nothing
        return () => null;
      }
    }
  )
;

Этот селектор возвращает все, что нам нужно для отображения правильной страницы.

Вот основной вид приложения:

import {element} from ‘deku’;
import {view} from ‘../selectors’;
export default ({context: state}) => { // deku’s context is the current store state
 // Get the component to render the current page
 const Component = view(state);
// Render it
 return <div>
 <Component/>
 </div>
}

Представление приложения отображает всю страницу, включая любой компонент, возвращенный селектором представления.

Я сделал этот пример простым, но в то же время гибким. Все, что вы можете получить
из пути, может быть возвращено из селектора. Хотите включить некоторые свойства при визуализации компонента? Выделите параметры из пути и верните их вместе с компонентом.

Если вам интересен какой-либо код, вы можете взглянуть на него на Github.