0

所以我正在学习 Spring,我正在使用带有 PrimeFaces 的 JSF。

我的问题:

我想知道如何(如果可能)使用 bean 中的布尔函数对用户凭据进行身份验证和授权,如下所示:

public boolean check() {
  boolean isLoginValid = false;
  if (//run something like j_spring_security_check) {
      //obtain user authorizations....
      isLoginValid = true;
  }
  return isLoginValid;
}

原因:

public void doLogin() {
    RequestContext context = RequestContext.getCurrentInstance();

    FacesMessage msg;
    boolean loggedIn;

    if (check() //would use the functin here) {
        loggedIn = true;
        msg = new FacesMessage(FacesMessage.SEVERITY_INFO, "Welcome", usuario);
    } else {
        loggedIn = false;
        msg = new FacesMessage(FacesMessage.SEVERITY_WARN, "Login Error", "Invalid credentials");
    }

    FacesContext.getCurrentInstance().addMessage(null, msg);
    context.addCallbackParam("loggedIn", loggedIn);
    context.addCallbackParam("authorization", this.auth #obtained in check());
}

这样我就可以通过 ajax 将布尔值发送到我的按钮,如下所示:

<p:commandButton id="loginButton" value="Login" update=":growl"   
                          actionListener="#{loginBean.doLogin}"   
                          oncomplete="handleLoginRequest(xhr, status, args)"/>

function handleLoginRequest(xhr, status, args) {
            if(args.validationFailed || !args.loggedIn) {  
                jQuery('#dialog').effect("shake", { times:3 }, 100);
            } else {
                jQuery('#dialog').effect("shake", { times:1 }, 200);
                //And redirect to the right page.
            }  
        }

谢谢!

4

1 回答 1

0

在 的帮助下SpringBeanFacesELResolver,您可以Authentication Manager从 Spring 应用程序上下文中解析托管属性,并且 JSF 的 IOC 将 bean 注入您的支持 bean。

为此,将 SpringBeanFacesELResolver 添加到您的 faces-config.xml 中,如下所示:

<application>
    <el-resolver>org.springframework.web.jsf.el.SpringBeanFacesELResolver</el-resolver>
</application>

然后在您的支持 bean 中,您可以对传递的 Authentication 对象进行身份验证,如下所示:

public class LoginBean implements Serializable {
    private static final long serialVersionUID = 1L;
    private String userName;
    private String password;
    @ManagedProperty(value="#{authenticationManager}")
        private AuthenticationManager authenticationManager;
        public AuthenticationManager getAuthenticationManager() {
        return authenticationManager;
    }

    public void setAuthenticationManager(AuthenticationManager authenticationManager) {
        this.authenticationManager= authenticationManager;
    }

    public String doLogin() {
        Authentication authenticationRequestToken =
              new UsernamePasswordAuthenticationToken( userName, password );
        //authentication action
        try {
            Authentication authenticationResponseToken =
                authenticationManager.authenticate(authenticationRequestToken);
            SecurityContextHolder.getContext().setAuthentication(authenticationResponseToken);
            //ok, test if authenticated, if yes reroute
            if (authenticationResponseToken.isAuthenticated()) {
                //lookup authentication success url, or find redirect parameter from login bean
                return "/secure/examples";
            }
        } catch (BadCredentialsException badCredentialsException) {
            FacesMessage facesMessage =
                new FacesMessage("Login Failed: please check your username/password and try again.");
            FacesContext.getCurrentInstance().addMessage(null,facesMessage);
        } catch (LockedException lockedException) {
            FacesMessage facesMessage =
                new FacesMessage("Account Locked: please contact your administrator.");
            FacesContext.getCurrentInstance().addMessage(null,facesMessage);
        } catch (DisabledException disabledException) {
            FacesMessage facesMessage =
                new FacesMessage("Account Disabled: please contact your administrator.");
            FacesContext.getCurrentInstance().addMessage(null,facesMessage);
        }

        return null;
    }
}

也可以看看:

更新

如果由于某种原因您无法使用 @ManagedProperty。您可以尝试通过将 JSF ManagedBean 变成 Spring 管理的组件来使用 Spring @Autowired 注解。为此,像这样注释bean:

@Component
@Scope("request")
public class LoginController implements Serializable {
    @Autowired
    private AuthenticationManager authenticationManager;
        //bean getters and setters

并将组件扫描元素添加到您的 Spring 应用程序上下文中,如下所示:

<context:component-scan base-package="com.examples"/>

对于您关于使用 authentication-success-handler-ref 的问题,恐怕您可以使用它,因为我们正在手动进行身份验证。如果您的要求只是根据用户角色转发到适当的 url。你可以这样做:

if (authenticationResponseToken.isAuthenticated()) {
   String userTargetUrl = "/general/main";
   String adminTargetUrl = "/secure/examples";
   Set<String> roles = AuthorityUtils.authorityListToSet(authenticationResponseToken.getAuthorities());
   if (roles.contains("ROLE_ADMIN")) {
      return adminTargetUrl;
   }
   else if(roles.contains("ROLE_USER")) {
      return userTargetUrl;
   }
}
于 2012-11-21T16:03:26.230 回答