Я полагаю, что ОП сейчас бесполезен для ответа. Тем не менее, это заслуживает исчерпывающего ответа. На самом деле, я удивлен, что у него его еще нет.
Прежде всего, это плохая идея: такая договоренность, как предложенная ФП, действительно слишком небезопасна. Тем не менее, решение описанной проблемы может стать хорошим прототипом для тех, кто создает аутологин для Liferay.
Теперь, допустим, вы хотите автоматически войти в систему любого пользователя, чье имя отображается в параметре строки запроса. Например, если у вас один доступ http://localhost:8080/web/guest/home?insecurely_login_user=juju
, то в систему должен войти Liferay пользователя juju
. Как это сделать? Выполните следующие действия:
Создать класс автологина
Во-первых, создайте подключаемый модуль. В своем каталоге docroot/WEB-INF/src
создает класс, реализующий интерфейс com.liferay.portal.security.auth.AutoLogin
. В моем примере я назову это br.brandizzi.adam.liferay.insecure.InsecureAutoLogin
.
Интерфейс AutoLogin
имеет только один метод, называемый login()
, который ожидает два параметра (экземпляры HttpServletRequest
и HttpServletResponse
) и возвращает массив строк. Итак, мой класс будет выглядеть без реализации:
public class InsecureAutoLogin implements AutoLogin {
@Override
public String[] login(HttpServletRequest request,
HttpServletResponse response) throws AutoLoginException {
// TODO Auto-generated method stub
return null;
}
}
Метод AutoLogin.login()
попытается получить информацию, необходимую для аутентификации, из многих источников, в основном из объекта запроса. Если он решает, что пользователь должен войти в систему, он возвращает массив с соответствующими данными для аутентификации; если он решит не войти в систему пользователя, он может просто вернуть null
.
В нашем случае мы пытаемся получить имя пользователя из параметра insecurely_login_user
из запроса. Если есть такой параметр, мы продолжим вход в систему; если такого параметра нет, он просто возвращает null
:
String screenName = request.getParameter("insecurely_login_user");
if (screenName == null || screenName.isEmpty()) {
return null;
}
Итак, у нас есть псевдоним. Что делать сейчас? Позвольте нам получить пользователя из базы данных с тем же именем.
long companyId = PortalUtil.getCompanyId(request);
User user = UserLocalServiceUtil.getUserByScreenName(companyId,
screenName);
Если пользователь с таким экранным именем существует, он будет извлечен и приписан к переменной user
. В этом случае аутентификация должна быть успешной, и класс autologin должен возвращать массив из трех строк - учетные данные . Это значения, которые должны быть возвращены в качестве учетных данных, в порядке их появления в массиве:
- идентификатор пользователя в виде строки
- пароль пользователя, который может быть зашифрован или нет;
- логическое значение, приведенное к строке, указывающее, зашифрован ли пароль.
Итак, вот строка:
return new String[] {
String.valueOf(user.getUserId()),
user.getPassword(),
String.valueOf(user.isPasswordEncrypted())
};
Однако, если пользователь не найден, будет сгенерировано исключение. Итак, мы должны окружить код выше конструкцией try
/ catch
. Если выдается исключение, просто верните null
:
try {
long companyId = PortalUtil.getCompanyId(request);
User user = UserLocalServiceUtil.getUserByScreenName(companyId,
screenName);
return new String[] { String.valueOf(user.getUserId()),
user.getPassword(),
String.valueOf(user.isPasswordEncrypted()) };
} catch (Exception e) {
return null;
}
В конце концов, это мой InsecureAutoLogin
класс:
public class InsecureAutoLogin implements AutoLogin {
public String[] login(HttpServletRequest request,
HttpServletResponse response) throws AutoLoginException {
String screenName = request.getParameter("insecurely_login_user");
if (screenName == null || screenName.isEmpty())
return null;
try {
long companyId = PortalUtil.getCompanyId(request);
User user = UserLocalServiceUtil.getUserByScreenName(companyId,
screenName);
return new String[] { String.valueOf(user.getUserId()),
user.getPassword(),
String.valueOf(user.isPasswordEncrypted()) };
} catch (Exception e) {
return null;
}
}
}
Регистрация класса автологина
Теперь наш хук должен зарегистрировать этот класс как процессор автологина. Это действительно легко.
Сначала отредактируйте файл docroot/WEB-INF/liferay-hook.xml
, добавив элемент portal-properties
со значением portal.properties
:
<?xml version="1.0"?>
<!DOCTYPE hook PUBLIC "-//Liferay//DTD Hook 6.1.0//EN" "http://www.liferay.com/dtd/liferay-hook_6_1_0.dtd">
<hook>
<portal-properties>portal.properties</portal-properties>
</hook>
Теперь создайте файл с именем portal.properties
в docroot/WEB-INF/src
. Он должен содержать свойство с именем auto.login.hooks
, значением которого должно быть имя нашего класса:
auto.login.hooks=br.brandizzi.adam.liferay.insecure.InsecureAutoLogin
И это все. Разверните этот хук, и ваш автологин будет работать.
Заключение
Как я уже сказал, вы не должны использовать такой небезопасный метод "аутентификации". Слишком легко обойти это, получая даже административные разрешения! Однако, если вы выполните эти шаги, у вас будет скелет для создания лучшей функции автологина. Кроме того, я знаю, что некоторые люди действительно хотят сделать что-то подобное этому небезопасному методу "аутентификации", и иногда нам приходится приостанавливать наши суждения и просто помогать кому-то стрелять в ноги ...
Исходный код этого проекта можно найти здесь и вы можете скачать WAR здесь .