【发布时间】:2020-06-04 13:52:48
【问题描述】:
在我的 Vaadin 14.2.0 应用程序中,有一个 BeforeLeaveListener 用于在输入脏(= 输入字段中有未保存的更改)时显示确认对话框以取消(或有意继续)导航:
BeforeLeaveListener listener = new BeforeLeaveListener() {
@Override
public void beforeLeave(BeforeLeaveEvent event) {
if (dirtyFlag.isDirty()) {
ContinueNavigationAction postponeAction = event.postpone();
// show confirmation dialog and maybe execute a proceed
[...] () -> postponeAction.proceed();
}
}
};
UI.getCurrent().addBeforeLeaveListener(listener);
这对除注销之外的所有内容都适用。 这就是我的注销按钮在开始时的样子(只要我不想推迟/取消注销就可以使用):
Anchor link = new Anchor();
link.getElement().addEventListener("click", e -> {
VaadinSession.getCurrent().getSession().invalidate();
UI.getCurrent().navigate(LoginView.class);
});
现在我想推迟注销,直到用户确认应丢弃未保存的更改。 (在 EventListener 中切换两行似乎是一个好主意,但由于以下原因没有奏效。) 在导航调用中调用了 BeforeLeaveListener(很好),但是注销仍然完成,因为执行了导航()调用之后的代码(当然,因为它不是阻塞调用),会话无效并且虽然刚刚弹出确认对话框,但用户已注销(但用户没有机会确认/拒绝)。
我试图将会话失效移到 LoginView 中(移到 BeforeEnterObserver 中),但结果是登录视图在无限循环中重新加载。
问题:是否有类似“导航到 LoginView 并且如果导航没有被推迟也没有取消,则使会话无效”之类的东西?
一种解决方法是导航到一个拦截 LogoutView,它只会使会话无效并重定向/转发到 LoginView:
@Route(value = "logout")
public class LogoutView implements BeforeEnterObserver {
@Override
public void beforeEnter(BeforeEnterEvent event) {
VaadinSession.getCurrent().getSession().invalidate();
event.forwardTo(LoginView.class);
}
}
但这在我看来只是一个糟糕的解决方法,需要一些开销(创建一个视图只是为了转发到另一个视图)...
【问题讨论】:
标签: vaadin vaadin-flow vaadin10