JSF не заполняет бин @Named @RequestScoped представленными входными значениями - PullRequest
3 голосов
/ 03 августа 2011

это мой первый вопрос на этом прекрасном сайте.Я много гуглил, но не нашел никакого решения.

Я новичок в JSF и изучаю его с помощью "API JSF 2 и JBoss Seam" Кента Ка Лок Тонга.

Теперь у меня проблема с простой реализацией входа в систему.У меня есть страница входа:

<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:h="http://java.sun.com/jsf/html">
    <h:head>
        <title>Login</title>
    </h:head>
    <h:body>
        <h1>Login</h1>
        <h:messages for="loginForm" />
        <h:form id="loginForm">
            <h:inputText id="username" value="#{loginRequest.username}" required="true" />
            <h:inputSecret id="password" value="#{loginRequest.password}" required="true" />
            <h:commandButton value="Login" action="#{loginRequest.doLogin}"></h:commandButton>
        </h:form>

    </h:body>
</html>

и компонент поддержки:

package app.controller;

import app.model.beans.User;
import javax.faces.bean.RequestScoped;
import javax.inject.Named;


@Named("loginRequest")
@RequestScoped
public class LoginRequest {

    private String username;
    private String password;

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public LoginRequest(){
    System.out.println("created " + this.toString());
    }

    public String doLogin(){

        if(this.username != null && this.password != null){

            if(this.username.equals("user") && this.password.equals("password")){
            //this.userHolder.setCurrentUser(username);
            return "success";

            }
        return "failure";

        }
        return "failure";

    }


}

Когда я запускаю приложение, мои свойства имени пользователя и пароля приводят к нулю.Я отладил свое приложение и увидел, что методы setters вызываются правильно.Проблема в том, что когда вызывается setUsername, есть и экземпляр LoginRequest, а когда он вызывается функцией setPassword, экземпляр отличается!Кажется, что приложение делает это:

obj1 = new LoginRequest() //username and password = null;
obj1.username = username;

obj1 = new LoginRequest() //username and password = null;
obj1.password = password;

obj1 = new LoginRequest() //username and password = null;
obj1.doLogin();

Где я в беде?В чем ошибка?

Большое спасибо!

С уважением

Марко

1 Ответ

16 голосов
/ 03 августа 2011

Из вашего компонента:

import javax.faces.bean.RequestScoped;
import javax.inject.Named;

@Named("loginRequest")
@RequestScoped
public class LoginRequest {

Вы смешиваете аннотации CDI и JSF.Вы можете и должны не сделать это.Используйте один или другой.Я не знаю, о чем говорится в книге, но, скорее всего, вы выбрали неправильное предложение автозаполнения при импорте аннотации @RequestScoped.Обратите внимание на то, соответствует ли то, что IDE предлагает вам, тому, что говорится в книге.

Итак, вы должны использовать либо только аннотации CDI

import javax.enterprise.context.RequestScoped;
import javax.inject.Named;

@Named("loginRequest")
@RequestScoped
public class LoginRequest {

или Только аннотации JSF

import javax.faces.bean.ManagedBean;
import javax.faces.bean.RequestScoped;

@ManagedBean(name="loginRequest")
@RequestScoped
public class LoginRequest {

В противном случае область действия по умолчанию устанавливается на "none", и каждое отдельное выражение EL, ссылающееся на компонент, создает новый и отдельный экземпляр компонента.С тремя выражениями EL, ссылающимися на #{loginRequest}, вы получите 3 экземпляра.Один, где задано имя, другой, где установлен пароль, и другой, где было вызвано действие.


Не связано с конкретной проблемой, имя управляемого компонента уже по умолчанию равноимя класса с 1-ым символом в нижнем регистре соответствует спецификации Javabean.Вы можете просто пропустить часть ("loginRequest").

...