繁体   English   中英

JSF中基于表单的身份验证

[英]Form based authentication in JSF

我想在JSF / Primefaces应用程序中实现一个简单的身份验证。 我尝试了很多不同的东西,例如Dialog - Login Demo在对话框上做了一个简单的测试,但是它没有登录用户或者?

我也看了一下Java Security,比如:

<security-constraint>
    <web-resource-collection>
        <web-resource-name>Protected Area</web-resource-name>
        <url-pattern>/protected/*</url-pattern>
        <http-method>PUT</http-method>
        <http-method>DELETE</http-method>
        <http-method>GET</http-method>
        <http-method>POST</http-method>
    </web-resource-collection>
    <auth-constraint>
        <role-name>REGISTERED_USER</role-name>
    </auth-constraint>
</security-constraint>

有了这个/受保护的一切都受到保护,但据我所知,我需要在服务器中定义一个领域进行身份验证。 我不想在服务器中指定它,只是在数据库中进行简单的查找。

有没有办法在不在应用程序服务器中定义某些内容的情况下验证用户? 或者另外一个简单的解决方案来验证和保护不同的页面?

有没有办法在不在应用程序服务器中定义某些内容的情况下验证用户?

这是一个漫长且非常棘手的故事。 它经常成为批评Java EE的主要观点之一。

故事的核心是传统的Java EE应用程序应该部署“未解析的依赖关系”。 必须在应用程序服务器上满足这些依赖关系,通常是非开发人员,通常使用某种GUI或控制台。

安全配置是未解决的依赖项之一。

如果安全配置在应用程序服务器上完成,则根据定义,这始终是不可移植的,例如,它必须以特定于应用程序服务器的方式完成。 它完全排除了使用应用程序域模型(例如JPA实体User )进行此身份验证。

一些服务器(例如JBoss AS)允许从应用程序内部配置其专有安全机制,并且还允许从应用程序加载“自定义登录模块”(几乎每个服务器的术语都不同)。 通过一些小的攻击,这将允许使用应用程序域模型和应用程序本身用于身份验证的相同数据源。

最后,还有一种相对未知的可移植方式,可以在应用程序中进行身份验证。 这是通过JASPIC SPI,又称JASPIJSR 196来完成。 基本上,这个JASPIC似乎是你正在寻找的。

不幸的是,JASPIC并不完美,即使它是Java EE 6的技术,我们几乎都在Java EE 7,目前在各种应用服务器中对JASPIC的支持仍然是粗略的。 最重要的是,尽管JASPIC已经标准化,但应用服务器供应商仍然需要专有配置来实际使其工作。

我写了一篇关于JASPIC的文章,它更详细地解释了当前的问题: 使用JASPIC在Java EE中实现容器认证

通过简单地使用Web过滤器,我找到了一个合适而简单的解决方案。 我在web.xml中添加了一个过滤器

<!-- Authentication Filter -->
<filter>
    <filter-name>AuthenticationFilter</filter-name>
    <filter-class>org.example.filters.AuthenticationFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>AuthenticationFilter</filter-name>
    <url-pattern>/protected/*</url-pattern>
</filter-mapping>

过滤器看起来像这样

@WebFilter(filterName="AuthenticationFilter")
public class AuthenticationFilter implements Filter {

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        Cookie[] cookies = ((HttpServletRequest)request).getCookies();

        // Try to find a valid session cookie
        if (cookies != null) {
            String sessionId = null;
            for (Cookie cookie : cookies) {
                if ("sessionId".equals(cookie.getName())) {
                        sessionId = cookie.getValue();
                }
            }

            // Check if we have a valid session
            UserSession session = Backend.getInstance().getSessionGateway().getBySessionId(sessionId);

            if (session != null) {
                chain.doFilter(request, response);
                return;
            } else if (sessionId != null) {
                // Remove the cookie
                Cookie cookie = new Cookie("sessionId", null);
                cookie.setMaxAge(-1);
                ((HttpServletResponse)response).addCookie(cookie);
            }
        }


//      Problem due to relative path!!
//      ((HttpServletResponse)response).sendRedirect("../login.xhtml");
        RequestDispatcher rd = request.getRequestDispatcher("/login.xhtml");
        rd.forward(request, response);
    }
}

所以我只需要实现一个验证和设置会话cookie的Bean。 我将添加用户代理以获得额外的安全性,但它基本上有效。

我唯一的问题是我无法进行重定向,导致它不使用上下文路径而只是重定向到/index.xhtml而不是/my_app_context/index.xhtml

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM