Реагировать на перенаправление маршрутизатора v4 при отсутствии совпадения

Я новичок в реакции-маршрутизаторе (и маршрутизации на стороне клиента в целом), поэтому я могу думать об этом неправильно. Заранее извините, если это так ...

В основном просто хочу реализовать 3 простых правила:

  • если нет пользователя, перенаправить на '/ login'
  • иначе, если маршрута не существует, перенаправить на '/' (корень)
  • иначе позволить пользователю перейти к запрошенному маршруту

Я отслеживаю пользователя в this.state.user. Мой текущий маршрутизатор, кажется, следует первым двум правилам, но только позволяет аутентифицированному пользователю видеть домашнюю страницу ('/ profile' перенаправляет на '/'), поэтому я знаю, что делаю что-то не так, но не могу понять, что именно.

 <Router>
    {this.state.user ? (
      <Switch>
        <Route path = "/" exact component = {Home}/>
        <Route path = "/profile" exact component = {Profile}/>
        <Route render = {() => (<Redirect to = "/" />)}/>
      </Switch>
    ) : (
      <Switch>
        <Route path = "/login" exact component = {Login}/>
        <Route render = {() => (<Redirect to = "/login" />)}/>
      </Switch>
    )}
 </Router>

Любой совет приветствуется. Спасибо

Можете ли вы просто попробовать <Route component = {Home} /> перенаправить на корневой (домашний) компонент, если маршрут не найден?

Jaydeep 15.05.2018 04:44

Я попробовал тот же код в изолированной программной среде, и доступ к / profile осуществляется должным образом. Не могли бы вы проверить ссылку codeandbox.io/s/n422y545pl

Rahil Ahmad 15.05.2018 04:56

Вам не нужно добавлять компонент Redirect в Switch. Вы должны установить условный рендеринг в каждом компоненте, в который вы хотите, чтобы пользователь входил в систему, т.е. Вы проверяете, вошел ли пользователь для просмотра маршрута, если нет. Затем вы визуализируете компонент Redirect, предоставляемый response-router-dom.

Bello Mayowa 15.05.2018 05:06

@RahilAhmad благодарит за пример. Я понял, что маршрутизация происходит до установки состояния пользователя.

Egor 15.05.2018 18:09
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Навигация по приложениям React: Исчерпывающее руководство по React Router
Навигация по приложениям React: Исчерпывающее руководство по React Router
React Router стала незаменимой библиотекой для создания одностраничных приложений с навигацией в React. В этой статье блога мы подробно рассмотрим...
Массив зависимостей в React
Массив зависимостей в React
Все о массиве Dependency и его связи с useEffect.
15
4
22 918
3

Ответы 3

Задумывались ли вы об использовании оболочки Route, которая проверяет пользователя, когда он необходим для Route?

const CanHasRouteAccess = ({ component: Component, iHasUser, ...rest }) => {
  return iHasUser ? (
    <Route {...rest} render = {props => <Component {...props} />} />
  ) : (
    <Redirect to = "/" />
  );
};

Вы можете передать реквизиты в Route или вызвать перенаправление на домашнюю страницу, когда пользователя нет.

<CanHasRouteAccess
  path = "/personal-data"
  exact
  component = {Profile}
  iHasUser = {Boolean(user)}
  />

Спасибо, Райан, это имеет смысл и работает. Есть идеи, как лучше всего справиться со случаем отсутствия согласованного маршрута с помощью перенаправления на '/'?

Egor 15.05.2018 18:19

@Egor Если вы используете Route без пути в нижней части вашего Switch, он перехватит все несовпадающие маршруты. Например, <Route component = {NoMatch}/>. Источник

Ryan 16.05.2018 01:12

Для тех, кто приезжает сюда и ищет, как перенаправить, если ни один из маршрутов не совпадает:

<Switch>
  // ... your routes
  <Route render = {() => <Redirect to = "/" />} />
</Switch>

Обратите внимание, что маршруты должны быть прямыми потомками <Switch>, например. это не работает:

<Switch>
  <Fragment>
    // ... your routes
    <Route render = {() => <Redirect to = "/" />} />
  </Fragment>
</Switch>

(возможно, исправлено в более поздних версиях реактивного маршрутизатора)

у меня не работает. React router 4.3.1, Route вложен в Switch.

VonAxt 31.01.2019 17:45

@VonAxt ставит его в последнюю очередь в переключателе.

Neeraj Sewani 18.04.2021 17:42

Ответ прост

<Switch>
  <Route path = "/login" exact component = {Login}/>
  {!this.state.user && <Redirect to='/login' />}
  <Route path = "/" exact component = {Home}/>
  <Route path = "/profile" exact component = {Profile}/>
  <Redirect to = "/" />
</Switch>

Основное различие между коммутатором и маршрутизатором заключается в том, что маршрутизатор будет пытаться выполнить все согласованные пути и добавить контент вместе, коммутатор остановится при первом совпадении.

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

export const App = () => (
  <Switch>
    <Route exact path='/login' component = {Login} />
    {!hasToken() && <Redirect to='/login' />}
    <Route path='/' component = {ProtectedRoute} />
  </Switch>
)

protectedRoute.js

const ProtectedRoute = ({ userInfo }: Props) => (
  <Layout userInfo = {userInfo}>
    <Switch>
      <Route exact path='/a' component = {A} />
      <Route exact path='/b' component = {B} />
      <Route path='/c' component = {C} />
      <Redirect to='/a' />
    </Switch>
  </Layout>
)

export default withUserInfo(ProtectedRoute)

«Основное различие между коммутатором и маршрутизатором заключается в том, что маршрутизатор будет пытаться выполнить все согласованные пути и добавить контент вместе, коммутатор остановится при первом совпадении». Это заявление помогло мне предотвратить бесчисленное количество часов выдергивания волос.

PsyGik 07.06.2019 13:50

Другие вопросы по теме