В реактивном маршрутизаторе v2.4.0
или выше и раньше v4
есть несколько вариантов
- Добавить функцию
onLeave
дляRoute
<Route
path="/home"
onEnter={ auth }
onLeave={ showConfirm }
component={ Home }
>
- Используйте функцию
setRouteLeaveHook
дляcomponentDidMount
Вы можете предотвратить переход или запросить пользователя перед выходом из маршрута с помощью кнопки выхода.
const Home = withRouter(
React.createClass({
componentDidMount() {
this.props.router.setRouteLeaveHook(this.props.route, this.routerWillLeave)
},
routerWillLeave(nextLocation) {
// return false to prevent a transition w/o prompting the user,
// or return a string to allow the user to decide:
// return `null` or nothing to let other hooks to be executed
//
// NOTE: if you return true, other hooks will not be executed!
if (!this.state.isSaved)
return 'Your work is not saved! Are you sure you want to leave?'
},
// ...
})
)
Обратите внимание, что в этом примере используется компонент withRouter
более высокого порядка, представленный вv2.4.0.
Однако это решение не совсем работает при изменении маршрута в URL вручную.
В смысле
- мы видим Подтверждение - ок
- содержание страницы не перезагружается - ок
- URL не меняется - не нормально
Для react-router v4
использования подсказок или пользовательской истории:
Однако в react-router v4
, это гораздо проще реализовать с помощьюPrompt
from'react-router.
Согласно документации
Подсказка
Используется для запроса пользователю перед уходом со страницы. Когда ваше приложение переходит в состояние, которое должно препятствовать переходу пользователя (например, форма наполовину заполнена), визуализируйте файл <Prompt>
.
import { Prompt } from 'react-router'
<Prompt
when={formIsHalfFilledOut}
message="Are you sure you want to leave?"
/>
сообщение: строка
Сообщение, которое будет подсказывать пользователю, когда он пытается уйти.
<Prompt message="Are you sure you want to leave?"/>
сообщение: func
Будет вызываться со следующим местоположением и действием, к которому пользователь пытается перейти. Верните строку, чтобы отобразить подсказку пользователю, или значение true, чтобы разрешить переход.
<Prompt message={location => (
`Are you sure you want to go to ${location.pathname}?`
)}/>
когда: bool
Вместо условного рендеринга <Prompt>
за охранником вы всегда можете рендерить его, но пропустить when={true}
или when={false}
запретить или разрешить навигацию соответственно.
В вашем методе рендеринга вам просто нужно добавить это, как указано в документации, в соответствии с вашими потребностями.
ОБНОВИТЬ:
Если вы хотите иметь настраиваемое действие, которое будет выполняться, когда пользователь покидает страницу, вы можете использовать настраиваемую историю и настроить свой маршрутизатор, например
history.js
import createBrowserHistory from 'history/createBrowserHistory'
export const history = createBrowserHistory()
...
import { history } from 'path/to/history';
<Router history={history}>
<App/>
</Router>
а затем в своем компоненте вы можете использовать history.block
подобное
import { history } from 'path/to/history';
class MyComponent extends React.Component {
componentDidMount() {
this.unblock = history.block(targetLocation => {
// take your action here
return false;
});
}
componentWillUnmount() {
this.unblock();
}
render() {
//component render here
}
}
componentWillUnmount() { if (confirm('Changes are saved, but not published yet. Do that now?')) { // publish and go away from a specific page } else { // do nothing and go away from a specific page } }
так, чтобы вы могли вызвать свою функцию публикации перед выходом со страницы