Аутентификация по ссылке

Добрый день!

Есть идея реализации авторизации в системе. Разобрал пример с экранами, но появилась необходимость сделать авторизацию через ссылку.
Пользователь вводит Логин, пароль и почту, на которую приходит ссылка на вход. При переходе по ссылке создается запись в Таблице пользователелей.
При реализации наткнулся на следующие варианты:

  1. Портал - это реализация Фронтенд интерфейса
  2. REST API, при чтении увидел вот это.

Не могли бы подсказать правильно ли я понял, что реализовать данный механиз реализации пользователей можно через способ 2, но только внутри “локально” сети или с добавлением доменов сети в настройки для входа “из вне”. Или реализовать через способ 1, но с созданием Портала и взаимодействием портала и приложением через то же REST API, но уже без ограничения “локальной” сети.

Здравствуйте,

А в каком приложении вам нужен вход по ссылке? В Web Client или всё-таки в портале на Spring MVC? Из вашего поста немного не ясно, как выглядит основной сценарий входа.

Вход по ссылке в Web Client.

Документация
Ну так вот же

http://localhost:8080/app/open?screen=sales$Customer.lookup&params=p1:v1,p2:v2

Задача сводится создать наследника экрана авторизации, в качестве параметра передаем что-то, и на его основании производим авторизацию в системе. Думаю должно получится.

Спасибо! Я попробую!

Здравствуйте!

Можно реализовать два варианта входа пользователя в приложение по ссылке.

Первый способ это использование параметров URL навигации (документация) в экране LoginWindow. Простой пример, допустим мы знаем что token “e63cacd4-646b-4232-bd72-36ddff780bbf” сгенерирован только для пользователя admin. Тогда в расширенном экране LoginWindow можно написать следующее:

private NavigationState state;
private String secretToken = "e63cacd4-646b-4232-bd72-36ddff780bbf";

@Inject
private UrlRouting urlRouting;

@Subscribe
private void onBeforeShow(BeforeShowEvent event) {
    state = urlRouting.getState();
}

@Subscribe
private void onAfterShow(AfterShowEvent event) {
    String st = state.getParams().get("st");
    if (secretToken.equals(st)) {
        doLogin(new ExternalUserCredentials("admin"));
    }
}

В onBeforeShow мы сохраняем текущее состояние URL вместе с параметрами, для того чтобы после показа экрана мы могли проверить token и осуществить вход пользователя в приложение.

Вход можно осуществить по следующей ссылке:
localhost:8080/app/#login?st=e63cacd4-646b-4232-bd72-36ddff780bbf

Полезные ссылки:

Второй пример использует HttpRequestFilter (см. процесс входа Web Client) и слушатель старта веб сессии (документация).
В фильтре мы смотрим наличие необходимого параметра в запросе, и если он присутствует, сохраняем его в HttpSession.

String st = request.getParameter("st");
if (!Strings.isNullOrEmpty(st)) {
    request.getSession().setAttribute("st", st);

    RequestContext.create(request, response);

    response.sendRedirect(ControllerUtils.getLocationWithoutParams(
            URI.create(request.getRequestURL().toString())));
}

chain.doFilter(request, response);

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

В обработчике старта веб сессии получаем необходимый параметр и обрабатываем его.

private String secretToken = "e63cacd4-646b-4232-bd72-36ddff780bbf";

@Override
public void onApplicationEvent(AppStartedEvent event) {
    App app = event.getApp();
    Connection connection = app.getConnection();

    if (!connection.isAuthenticated()) {
        RequestContext requestContext = RequestContext.get();
        if (requestContext != null) {
            HttpServletRequest request = requestContext.getRequest();
            String st = (String) request.getSession().getAttribute("st");
            if (secretToken.equals(st)) {
                try {
                    connection.login(new ExternalUserCredentials("admin"));
                } catch (LoginException e) {
                    log.warn("Unable to login by token {}", st);
                }
            }
        }
    }
}

Вход осуществляется по ссылке:
localhost:8080/app?st=e63cacd4-646b-4232-bd72-36ddff780bbf

Оба примера в проекте: logindemo.zip (79,3 КБ)

Чтобы попробовать второй пример закомментируйте код в ExtLoginWindow и раскомментируйте в AppStartedEventListener и ExternalLoginHttpFilter.

4 симпатии

Добрый день!

Пробую воспользоваться первый способом.
Делаю так:

 @Subscribe
    private void onAfterShow(AfterShowEvent event) {
        String st = state.getParams().get("st");
        if (st!= null) {
            notifications.create(Notifications.NotificationType.HUMANIZED)
                    .withCaption("OK")
                    .show();
        }
    }

На что система требует авторизации. Как можно открыть окно для анонимной сессии?