我对 JSF2 @ManagedProperty 注释有疑问。我有一个创建用户的托管 bean,然后我想将该用户传递给另一个 bean 以显示与该用户相关的其他信息。所以我的代码如下:
@Named("userController")
@SessionScoped
public class UserController implements Serializable {
@EJB
private session.UserFacade ejbFacade;
private List<User> items = null;
private User selected;
private User utente;
private String user;
private String pass;
----getter and setter----
在 Schedule Bean 中,我在 @PostConstruct 中使用 userController bean:
@Named(value = "scheduleController")
@SessionScoped
public class ScheduleController implements Serializable {
private ScheduleModel eventModel;
private ScheduleEvent event = new DefaultScheduleEvent();
@EJB
ActivityFacade ejbFacade;
@ManagedProperty(value="#{userController}")
private UserController credentials;
public ScheduleController() {
}
@PostConstruct
public void init(){
eventModel = new DefaultScheduleModel();
List<Activity> daFare =ejbFacade.findForUser(credentials.getUtente().getIdUser());
for(int i=0;i<daFare.size();i++){
eventModel.addEvent(new DefaultScheduleEvent(daFare.get(i).getDescrizione(),daFare.get(i).getDalleOre(),daFare.get(i).getAlleOre() ));
}
}
public void setCredentials(UserController credentials) {
this.credentials = credentials;
}
当我调试代码时,我发现 UserController 凭据始终为空......出了什么问题?我需要在 faces-config.xml 中指定一些内容? 非常感谢您的提示。
编辑:
使用@Inject更改@ManagedProperty并在WEB-INF文件夹中添加以下beans.xml后,问题仍然存在。
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/beans_1_0.xsd">
该应用程序的工作方式如下: 用户可以通过此 xhtml 页面登录:
<body>
<h:form>
<p:growl id="msgs" showDetail="true" />
<p:panel header="Inserisci i tuoi dati" style="margin: 0 auto; text-align: center" >
<h:panelGrid columns="2" cellpadding="5" style="margin: 0 auto; text-align: center">
<p:outputLabel value="Username"/>
<p:inputText value="#{userController.user}" required="true" label="Username" size="40"/>
<p:outputLabel value="Password" />
<p:password value="#{userController.pass}" required="true" label="Password" size="40"/>
<p:commandButton action="#{userController.validateLogin}" value="Login" update="msgs" ajax="false" style="text-align: center"/>
</h:panelGrid>
</p:panel>
</h:form>
</body>
提交表单后,userController 验证该特定用户是否存在于数据库表中,然后实例化 User utente( id、用户名、密码、电子邮件作为字段)。之后,应用程序重定向到 home.xhtml,显示多个用户的信息,并选择由用户 id 选择的数据库表的多个信息。 这是我设置 User utente 的代码:
public String validateLogin(){
String output="home";
boolean exist=false;
exist=ejbFacade.logValid(user,pass);
if(!exist){
//FacesContext.getCurrentInstance().getExternalContext().invalidateSession();
FacesContext context = FacesContext.getCurrentInstance();
context.addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO,"Username o Password errata","Contattare l'amministratore"));
return "index";
}else{
utente=ejbFacade.setUtente(user);
FacesContext context = FacesContext.getCurrentInstance();
context.addMessage(null, new FacesMessage("Accesso eseguito con successo.","Bentornato " + user));
return output;
}
}
我控制用户存在并设置utente的代码顺序是:
@Stateless
public class UserFacade extends AbstractFacade<User> {
@PersistenceContext(unitName = "ImmobiliareWebPU")
private EntityManager em;
@Override
protected EntityManager getEntityManager() {
return em;
}
public UserFacade() {
super(User.class);
}
public boolean logValid(String user, String pass) {
List<User> utente ;
boolean autorizzato;
String find = "User.findByUsername&Password";
Query query = em.createNamedQuery(find, User.class);
query.setParameter("username", user);
query.setParameter("password", pass);
utente =query.getResultList();
if (utente.isEmpty()) {
autorizzato=false;
}
else{
autorizzato=true;
}
return autorizzato;
}
public User setUtente(String user) {
//SETTO L'UTENTE PER LA SESSIONE DEL PROGRAMMA
User utente;
String find = "User.findByUsername";
Query query = em.createNamedQuery(find, User.class);
query.setParameter("username", user);
utente =(User) query.getSingleResult();
return utente;
}
}
我需要用户信息的代码是:
@Named(value = "scheduleController")
@RequestScoped
public class ScheduleController implements Serializable {
private ScheduleModel eventModel;
private ScheduleEvent event = new DefaultScheduleEvent();
@EJB
ActivityFacade ejbFacade;
@Inject
private UserController credentials;
public ScheduleController() {
}
@PostConstruct
public void init(){
eventModel = new DefaultScheduleModel();
List<Activity> daFare =ejbFacade.findForUser(credentials.getUtente().getIdUser());
for(int i=0;i<daFare.size();i++){
eventModel.addEvent(new DefaultScheduleEvent(daFare.get(i).getDescrizione(),daFare.get(i).getDalleOre(),daFare.get(i).getAlleOre() ));
}
}
在 ejbFacade 中我做了一个简单的查询:
@Stateless
public class ActivityFacade extends AbstractFacade<Activity> {
@PersistenceContext(unitName = "ImmobiliareWebPU")
private EntityManager em;
@Override
protected EntityManager getEntityManager() {
return em;
}
public ActivityFacade() {
super(Activity.class);
}
public List<Activity> findForUser(int utenteId) {
//RICHIEDO LE ATTIVITA' DEL SINGOLO UTENTE
List<Activity> daFare ;
String find = "Activity.findByUserId";
Query query = em.createNamedQuery(find, Activity.class);
query.setParameter("idUser", utenteId);
daFare =query.getResultList();
return daFare;
}
}
在 Debug模式下,我看到 UserController 的实例全部为空字段;这似乎是 UserController 的一个新版本。我还使用“import javax.enterprise.context.SessionScoped”。我的错在哪里?
最佳答案
When i debug the code, I see that the UserController credentials is always null.... What's wrong?
请注意您混淆了 CDI (Context and Dependency Injection)具有托管属性,这可能会导致所描述的行为。您的 Bean 使用 @Named
进行注释,而不是 @ManagedBean
,因此:
@ManagedProperty(value="#{userController}")
private UserController credentials;
应替换为:
@Inject
private UserController credentials;
有关 CDI 和支持 bean 之间差异的真正精彩解释,请参阅本主题中的 @BalusC 答案:Backing beans (@ManagedBean) or CDI Beans (@Named)? .
I need to specify something in faces-config.xml?
不,但您应该包含一个beans.xml
,如下例所示:Packaging CDI applications 。据我记得,无论发现模式如何,此文件都是必需的。以下是您可以在 NetBeans 中自动生成的 beans.xml
:
新文件 --> 上下文和依赖注入(inject) --> beans.xml(CDI 配置文件)。
这就是我让 CDI 工作所需要的一切:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/beans_1_1.xsd"
bean-discovery-mode="annotated">
</beans>
关于JSF @managedproperty 和 @PostConstruct,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26241197/