Как реализовать самоуправляемых веб-пользователей с Java EE 6? - PullRequest
8 голосов
/ 08 апреля 2011

Я хочу создать простое веб-приложение, в котором пользователи будут регистрироваться самостоятельно. Другими словами, я хочу, чтобы пользователи могли регистрироваться, входить в систему, управлять своими данными, выходить из системы и, если они хотят, удалять свою учетную запись. Это своего рода хобби-проект, и просто чтобы узнать что-то новое, я решил попытаться создать этот веб-сайт с использованием новейшей Java EE, которой раньше не пользовался.

Я потратил несколько часов, читая о JAAS, областях аутентификации и т. Д., И я нашел много способов реализации безопасности на основе пользователей и ролей, определенных на сервере (например, GlassFish), но я не нашел примеров или указателей на то, как внедрить решение, в котором пользователи могут просто заполнить регистрационную форму на веб-странице и стать пользователями в системе. Конечно, я могу просто иметь таблицу базы данных с именами пользователей и паролями и реализовывать все вручную, но это не отвечает цели.

Поэтому мои вопросы:

  1. Подходит ли стандартная среда аутентификации и безопасности Java EE для реализации приложения, в котором пользователи могут управлять собой? Или это более «корпоративное» решение, основанное на внешней аутентификации и управлении пользователями?
  2. Если вам легко сделать то, что мне нужно, укажите мне несколько образцов.

Спасибо!

Ответы [ 2 ]

1 голос
/ 08 апреля 2011

J2EE не очень хорош в этом. Я сделал это в приложении, хотя. У меня есть таблица пользователей в (единственной) базе данных, используемой моим приложением, и я объявил область в файле context.xml в каталоге META-INF веб-приложения (я использую tomcat btw):

<Realm className="org.apache.catalina.realm.DataSourceRealm"
        dataSourceName="jdbc/fantastico" debug="99" localDataSource="true"
        digest="MD5" roleNameCol="ROLE" userCredCol="PASSWORD"
        userNameCol="USERNAME" userRoleTable="user_roles"
        userTable="active_users"/>

Источник данных такой же, как и в остальной части приложения, и объявлен в файле server.xml установки tomcat (чтобы я мог указать на другую базу данных без изменения файла .war).

У меня есть защищенные места с ролями в файле web.xml, поэтому я покинул страницу регистрации и страницу входа под защитой:

<security-constraint>
    <display-name>Administrators</display-name>
    <web-resource-collection>
        <web-resource-name>admin</web-resource-name>
        <description>Admin</description>
        <url-pattern>/admin</url-pattern>
        <http-method>GET</http-method>
        <http-method>POST</http-method>
        <http-method>HEAD</http-method>
        <http-method>PUT</http-method>
        <http-method>OPTIONS</http-method>
        <http-method>TRACE</http-method>
        <http-method>DELETE</http-method>
    </web-resource-collection>
    <auth-constraint>
        <description>Allow access only to administrators</description>
        <role-name>admin</role-name>
    </auth-constraint>
</security-constraint>

Я указал раздел с FORM в качестве метода авторизации:

<login-config>
    <auth-method>FORM</auth-method>
    <realm-name/>
    <form-login-config>
        <form-login-page>/login/</form-login-page>
        <form-error-page>/login/error</form-error-page>
    </form-login-config>
</login-config>

Поскольку область объявлена ​​как дайджест MD5, именно MD5 пароля должен храниться в базе данных:

private static final char HEX[] = "0123456789abcdef".toCharArray();


public static String hex(byte data[]) {
    char[] chars = new char[2*data.length];
    for (int i=0; i < data.length; i++) {
        int low = data[i] & 0x0f;
        int high = (data[i] & 0xf0) >> 4;
        chars[i*2] = HEX[high];
        chars[i*2 + 1] = HEX[low];
    }
    return new String(chars);
}

public static byte[] hash(byte data[]) {
    synchronized (DIGEST) {
        DIGEST.reset();
        return DIGEST.digest(data);
    }
}

public static String hash(String value) {
    try {
        byte data[] = hash(value.getBytes("UTF-8"));
        return hex(data);
    } catch (UnsupportedEncodingException e) {
        // Cannot happen: UTF-8 support is required by Java spec
        LOG.error("Failed to generate digest", e);
        throw new RuntimeException(e.getMessage());
    }
}

В форме входа, которую tomcat будет отображать всякий раз, когда требуется аутентификация, я добавил ссылку на форму регистрации:

...

<form id="login-form" action="j_security_check" method="post">
    <table>
        <tbody>
            <tr>
                <td><label for="username">User name:&nbsp;</label></td>
                <td><input type="text" name="j_username" id="username" /></td>
            </tr>
            <tr>
                <td><label for="password">Password:&nbsp;</label></td>
                <td><input type="password" name="j_password" id="password" /></td>
            </tr>
            <tr>
                <td>&nbsp;</td>
                <td><input type="submit" id="submit" name="submit" value="Login"></td>
            </tr>
            <tr>
                <td>&nbsp;</td>
                <td><a href="../reg/create">I'm a new user</a></td>
            </tr>
        </tbody>
    </table>
</form>

...

Теперь, когда форма регистрации отправлена, я сохраняю пользователя в базе данных и отправляю перенаправление для автоматического входа пользователя:

...

response.sendRedirect(request.getContextPath()
        + "/j_security_check?j_username="
        + URLEncoder.encode(getEmail(), "UTF-8")
        + "&j_password="
        + URLEncoder.encode(password, "UTF-8"));

...

Надеюсь, это поможет

0 голосов
/ 08 апреля 2011

В качестве альтернативы вы можете взглянуть на Spring Security Framework . Я использовал его с моими проектами Grails так, как вы описали, когда пользователи сами регистрировались, и я обнаружил, что им легко пользоваться.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...