我的想法是:我有一个bean(UserBean),它具有一些属性可帮助我在设置为实体用户之前进行验证。我这样做是为了在整个项目中重用UserBean属性中的验证,并保持分隔层,因为我可以在堆栈溢出的许多帖子中看到这些层。 知道,我想保持MVC结构,让我们来看看我做什么至今:什么是使用JSF 2和JPA 2的项目的良好结构?
(很抱歉的大图片我认为这将是更容易明白我的问题)
这是我的用户(在实体包):
@Entity
@Table(name="user")
public class User implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy=GenerationType.SEQUENCE)
private int id;
private String email;
private String password;
private int reputation;
//bi-directional one-to-one association to Company
@OneToOne(mappedBy="user", cascade={CascadeType.ALL})
private Company company;
//bi-directional many-to-one association to Location
@OneToMany(mappedBy="user")
private List<Location> locations;
//bi-directional one-to-one association to Person
@OneToOne(mappedBy="user")
private Person person;
//bi-directional many-to-one association to Product
@OneToMany(mappedBy="user")
private List<Product> products;
//bi-directional many-to-one association to UserType
@ManyToOne
@JoinColumn(name="type")
private UserType userType;
//bi-directional many-to-one association to UserPhone
@OneToMany(mappedBy="user")
private List<UserPhone> userPhones;
//bi-directional many-to-one association to UserPicture
@OneToMany(mappedBy="user")
private List<UserPicture> userPictures;
//bi-directional many-to-one association to UserSocialNetwork
@OneToMany(mappedBy="user")
private List<UserSocialNetwork> userSocialNetworks;
// getters and setters
}
这是他的豆腐,的UserBean(在bean.entity包):
@ManagedBean
@SessionScoped
public class UserBean implements Serializable {
private static final long serialVersionUID = -1626847931067187536L;
private int id;
@NotNull(message="informe seu e-mail")
@Email(message="e-mail inválido")
private String email;
@NotNull(message = "6 dígitos no mínimo")
@Size(min = 6, max = 128, message = "6 dígitos no mínimo")
private String password;
@NotNull(message = "6 dígitos no mínimo")
@Size(min = 6, max = 128, message = "6 dígitos no mínimo")
private String password_2;
private int reputation;
private UserType userType;
private List<UserPhoneBean> userPhones;
private List<UserPicture> userPictures;
private List<UserSocialNetwork> userSocialNetworks;
@AssertTrue(message = "senhas diferentes")
public boolean isPasswordsEquals() {
return password.equals(password_2);
}
// getters and setters
}
然后每一个与我想保持控制在一个地方的用户做的,所以我创建了用户控件豆动作:
@ManagedBean(name="userc")
@ViewScoped
public class UserControl implements Serializable {
private static final long serialVersionUID = -1626847931067187536L;
@EJB EaoUser eaoUser;
@EJB EaoPerson eaoPerson;
@ManagedProperty("#{userBean}")
private UserBean user;
@ManagedProperty("#{personBean}")
private PersonBean person;
private UserBean ub;
private PersonBean pb;
private View view;
public UserControl() {
ub = new UserBean();
pb = new PersonBean();
view = new View();
}
public String login(){
List<User> list = eaoUser.findByEmail(ub.getEmail());
User u = list.get(0);
if (Crypto.check(ub.getPassword(), u.getPassword())){
HttpSession session = (HttpSession) FacesContext.getCurrentInstance().getExternalContext().getSession(false);
session.setAttribute("authenticated", true);
user = new UserBean();
user.setId(u.getId());
user.setEmail(u.getEmail());
user.setPassword(u.getPassword());
user.setReputation(u.getReputation());
user.setUserType(u.getUserType());
if (u.getUserType().getId() == 10){
Person p = eaoPerson.find(u.getId());
if (p != null){
person = new PersonBean();
person.setName(p.getName());
person.setSurname(p.getSurname());
person.setBirthdate(p.getBirthdate());
person.setGender(p.getGender());
}
}
for (UserPhone up : u.getUserPhones()){
user.getUserPhones().add(new UserPhoneBean(up.getId(), up.getPhone()));
}
user.setUserPictures(u.getUserPictures());
user.setUserSocialNetworks(u.getUserSocialNetworks());
}else{
view.imageError();
view.setStatus("e-mail ou senha incorretos");
view.setPopup(true);
return "#";
}
return "secured/user/home?faces-redirect=true";
}
// others method, getters and setters
}
请注意,我注入userBean这里在userControl,所以当用户登录时,我救出了数据库中的值并设置在userBean中。
我创建属性用户和UB,因为当我尝试用用户似乎不起作用验证验证,我想这是因为他已经注射(只是猜测)。
因此,在所有这些解释之后,当我尝试登录时,用户(注入的)不再保留任何值。
如果我试着这样做:
Welcome, <h:outputText value="#{userc.user.email}" />
不要出现什么..
所以我想如果我的结构是正确的。 你们有什么想法?
GREAAT队友!谢谢,你的建议是对的,我不得不这样做,因为在那时给了我一些NullPointerException。 你对userBean.set(用户)的想法很棒。只是一件事,在userBean中,我保留属性来进行验证,只需添加正确的?或者有一些方法来重用用户(实体)的属性? –
NPE可能是由于您没有首先使用“@ ManagedProperty”而导致的。至于JSR 303验证注释,你可以直接将它们放在'User'上,但是你只需要在UserBean(或UserController)中保存第二个密码字段。实际上,有了一个合适的'Validator',你根本不需要这个字段。只有,我不会将登录表单绑定到会话范围的bean,而是绑定到UserController,而这又应该有一个'User'属性来绑定登录表单域。然后,当你登录时,在UserBean中设置找到的JPA用户实体。 – BalusC
明白了!我现在要尝试这种方法,谢谢。 –