Si se dirige a entornos de navegador, debe usar el react-router-dompaquete, en lugar de react-router. Están siguiendo el mismo enfoque que React, para separar el núcleo, ( react) y el código específico de la plataforma, ( react-dom, react-native) con la sutil diferencia de que no necesita instalar dos paquetes separados, por lo que los paquetes de entorno contienen todo necesitas. Puedes agregarlo a tu proyecto como:
yarn add react-router-dom
o
npm i react-router-dom
Lo primero que debe hacer es proporcionar un <BrowserRouter>como el componente principal más alto en su aplicación. <BrowserRouter>usa la historyAPI HTML5 y la administra por usted, por lo que no tiene que preocuparse por instanciarlo usted mismo y pasarlo al <BrowserRouter>componente como accesorio (como lo hizo en versiones anteriores).
En V4, para navegar programáticamente, necesita acceder al historyobjeto, que está disponible a través de React context, siempre que tenga un componente de <BrowserRouter> proveedor como el principal superior en su aplicación. La biblioteca expone a través del contexto el routerobjeto, que en sí mismo contiene historycomo una propiedad. La historyinterfaz ofrece varios métodos de navegación, como push, replacey goBack, entre otros. Puede consultar la lista completa de propiedades y métodos aquí .
Nota importante para los usuarios de Redux / Mobx
Si está utilizando redux o mobx como su biblioteca de administración de estado en su aplicación, es posible que haya encontrado problemas con los componentes que deberían tener en cuenta la ubicación pero que no se vuelven a reproducir después de activar una actualización de URL
Eso sucede porque react-routerpasa locationa los componentes utilizando el modelo de contexto.
Tanto connect como observador crean componentes cuyos métodos shouldComponentUpdate hacen una comparación superficial de sus accesorios actuales y sus próximos accesorios. Esos componentes solo se volverán a renderizar cuando haya cambiado al menos un accesorio. Esto significa que para garantizar que se actualicen cuando cambie la ubicación, deberán recibir un accesorio que cambie cuando cambie la ubicación.
Los 2 enfoques para resolver esto son:
- Envuelva su componente conectado de una manera sin caminos
<Route />. El locationobjeto actual es uno de los accesorios que un <Route>pasa al componente que representa
- Envuelva su componente conectado con el
withRoutercomponente de orden superior, que de hecho tiene el mismo efecto e inyecta locationcomo accesorio
Dejando eso de lado, hay cuatro formas de navegar programáticamente, ordenadas por recomendación:
1.- Usando un <Route>componente
Promueve un estilo declarativo. Antes de v4, los
<Route />componentes se colocaban en la parte superior de la jerarquía de componentes, teniendo que pensar de antemano en la estructura de sus rutas. Sin embargo, ahora puede tener
<Route>componentes en
cualquier parte de su árbol, lo que le permite tener un control más preciso para la representación condicional dependiendo de la URL.
Routeinyecta
match,
locationy
historycomo accesorios en su componente. Los métodos de navegación (tales como
push,
replace,
goBack...) están disponibles como propiedades del
historyobjeto.
Hay 3 formas de renderizar algo con a Route, usando cualquiera de los dos component, rendero childrenaccesorios, pero no use más de uno en el mismo Route. La elección depende del caso de uso, pero básicamente las dos primeras opciones solo mostrarán su componente si pathcoincide con la ubicación de la URL, mientras que con childrenel componente se mostrará si la ruta coincide con la ubicación o no (útil para ajustar la interfaz de usuario basada en la URL pareo).
Si desea personalizar la salida de representación de componente , es necesario envolver su componente en una función y utiliza la renderopción, a fin de pasar a su componente cualesquiera otros apoyos que usted desea, además de match, locationy history. Un ejemplo para ilustrar:
import { BrowserRouter as Router } from 'react-router-dom'
const ButtonToNavigate = ({ title, history }) => (
<button
type="button"
onClick={() => history.push('/my-new-location')}
>
{title}
</button>
);
const SomeComponent = () => (
<Route path="/" render={(props) => <ButtonToNavigate {...props} title="Navigate elsewhere" />} />
)
const App = () => (
<Router>
<SomeComponent /> // Notice how in v4 we can have any other component interleaved
<AnotherComponent />
</Router>
);
2.- Usando withRouterHoC
Este componente de orden superior inyectará los mismos accesorios que Route. Sin embargo, conlleva la limitación de que solo puede tener 1 HoC por archivo.
import { withRouter } from 'react-router-dom'
const ButtonToNavigate = ({ history }) => (
<button
type="button"
onClick={() => history.push('/my-new-location')}
>
Navigate
</button>
);
ButtonToNavigate.propTypes = {
history: React.PropTypes.shape({
push: React.PropTypes.func.isRequired,
}),
};
export default withRouter(ButtonToNavigate);
3.- Usando un Redirectcomponente
La representación de a
<Redirect>navegará a una nueva ubicación. Pero tenga en cuenta que,
de forma predeterminada , la ubicación actual se reemplaza por la nueva, como las redirecciones del lado del servidor (HTTP 3xx). La nueva ubicación es proporcionada por
toprop, que puede ser una cadena (URL para redirigir a) o un
locationobjeto. Si quieres
insertar una nueva entrada en el historial , pasa también un
pushaccesorio y configúralo en
true
<Redirect to="/your-new-location" push />
4.- Accediendo routermanualmente a través del contexto
Un poco desanimado porque el
contexto sigue siendo una API experimental y es probable que se rompa / cambie en futuras versiones de React
const ButtonToNavigate = (props, context) => (
<button
type="button"
onClick={() => context.router.history.push('/my-new-location')}
>
Navigate to a new location
</button>
);
ButtonToNavigate.contextTypes = {
router: React.PropTypes.shape({
history: React.PropTypes.object.isRequired,
}),
};
No hace falta decir que también hay otros componentes del enrutador destinados a ecosistemas que no son del navegador, como el <NativeRouter>que replica una pila de navegación en la memoria y apunta a la plataforma React Native, disponible a través del react-router-nativepaquete.
Para cualquier referencia adicional, no dude en consultar los documentos oficiales . También hay un video hecho por uno de los coautores de la biblioteca que proporciona una introducción bastante buena al react-router v4, destacando algunos de los principales cambios.