【问题标题】:How can I access session attribute in Facelets page如何访问 Facelets 页面中的会话属性
【发布时间】:2012-10-24 10:33:54
【问题描述】:

我已经使用 JSF 和 PrimeFaces 实现了一个登录表单。 我在 PrimeFaces 展示网站中使用了this example

我有一个 Facelets 页面来显示一个数据表。现在我需要将上面的登录表单与这个表格页面整合起来。所以我在 LoginBean.java 中添加了几行来处理会话属性。

     if (username.equals(getUsername_db()) && password.equals(getPassword_db())) {//valid user and paward
        loggedIn = true;
        msg = new FacesMessage(FacesMessage.SEVERITY_INFO, "Welcome", getUsername_db());
        //new lines
        FacesContext context2 = FacesContext.getCurrentInstance();
        HttpSession session = (HttpSession) context2.getExternalContext().getSession(true);
        session.setAttribute("user", username);
        //end of new lines
        ...

如果用户未登录,我需要从数据表中隐藏一列。 现在我的问题是,如何访问我的 Facelets 页面中的会话属性?

【问题讨论】:

    标签: java jsf session login facelets


    【解决方案1】:

    您已将登录用户存储为名为“user”的会话属性。

    所以它在 EL 中可用如下:

    #{user}
    

    您可以在 EL 中使用 empty 关键字来检查它是否存在(即是否已登录),您可以使用 JSF 组件的 rendered 属性来指示是否生成 HTML 输出.

    <h:panelGroup rendered="#{not empty user}">
        <p>Welcome #{user}, you have been logged in!</p>
    </h:panelGroup>
    

    在您隐藏表格列的特定情况下,只需按如下方式使用它:

    <p:column rendered="#{not empty user}">
        ...
    </p:column>
    

    存储会话属性的更好方法是使用ExternalContext#getSessionMap()。这样,您的代码就没有臭的 javax.servlet.* 导入。

    FacesContext.getCurrentInstance().getExternalContext().getSessionMap().put("user", username);
    

    与具体问题无关,为什么要进行以下检查?

    if (username.equals(getUsername_db()) && password.equals(getPassword_db())) {
    

    你为什么不在 SQL 中做一个SELECT ... FROM user WHERE username=? AND password=? 呢?还是您不相信数据库会返回正确的行?

    【讨论】:

    • 感谢 BalusC。但是我将用户作为视图中的对象。像这样的东西显示“User@1a8b71e”。无论如何,我从您的答案中得到了 部分来解决我的问题。我删除了会话设置部分并将 LoginBean 类设置为 SessionScoped。而且我能够直接在我的 panelGroup 标签中获取值。再次感谢 SQL 建议。我使用准备好的语句对其进行了更改。
    • 显然您的代码中显示的username 根本不是String。也许您过度简化了问题中的代码?顺便说一句,SQL 注释并不是为了暗示准备好的语句。您正在比较用户名和密码 两次(一次在 DB 中,另一次在 Java 中)。这是没有意义的。只需检查 DB 是否返回了一条记录,仅此而已。您不需要再次比较您已经要求数据库检查并返回的用户名/密码。
    • 知道了!但在我的最后一个 sql 查询中,我只使用了带有 Where 子句的用户名。喜欢:字符串查询=“选择用户名,密码来自用户WHERE用户名='”+ uname +“';”;所以我可以删除 username.equals(getUsername_db() 部分。在这种情况下我只需要检查密码......谢谢你的建议。
    • 这也没有意义。只需将密码添加到 WHERE。 SQL 查询应该始终以它返回准确您想要的数据的方式编写,之后无需任何必要的额外检查。顺便说一句,在 SQL 字符串中使用字符串连接的用户控制输入,您正在打开一个巨大的 SQL 注入攻击漏洞。使用准备好的语句。
    猜你喜欢
    • 2012-07-06
    • 2017-05-11
    • 1970-01-01
    • 1970-01-01
    • 2020-12-10
    • 2019-05-18
    • 2013-07-03
    • 2019-12-23
    • 1970-01-01
    相关资源
    最近更新 更多