当前位置: 首页 > 知识库问答 >
问题:

Hibernate实体中的映射外键

祁鸿哲
2023-03-14

Hi编写Spring应用程序,使用Spring Security。这是我的用户和帐户角色数据库:

create table users (

  id int not null primary key,
  username varchar2(20) not null unique,
  password varchar2(20) not null,
  firstName varchar2(20),
  lastName varchar2(20),
  personalId varchar2(11) unique,
  city varchar2(40),
  address varchar2(40),
  email varchar2(30) unique,
  phone varchar2(9) unique,
  enabled number(1) not null
);

create table user_roles (
  id int primary key,
  name varchar2(20) not null,
  username varchar(20) constraint username_fk references users(username) not null
);

我的实体类:

@Entity
@Table(name = "users")
public class User implements Serializable {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue
    @Column(name = "id")
    private Integer id;
    @NotNull
    @Column(name = "username")
    private String username;
    @NotNull
    @Column(name = "password")
    private String password;
    @Column(name = "firstName")
    private String firstName;
    @Column(name = "lastName")
    private String lastName;
    @Column(name = "personalId")
    private String personalId;
    @Column(name = "city")
    private String city;
    @Column(name = "address")
    private String address;
    @Column(name = "email")
    private String email;
    @Column(name = "phone")
    private String phone;
    @NotNull
    @Column(name = "enabled")
    private int enabled;
    @OneToMany(mappedBy = "username")
    private Set<UserRole> userRoleSet = new HashSet<UserRole>(0);

@Entity
@Table(name = "user_roles")
public class UserRole implements Serializable {

    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue
    @Column(name = "id")
    private Integer id;
    @NotNull
    @Column(name = "name")
    private String name;
    @JoinColumn(name = "username")
    @ManyToOne(targetEntity = User.class)
    private String username;

当我尝试登录我的系统我有错误:

Hibernate:选择userrolese0_. username作为username3_1_0_,userrolese0_. id作为id1_0_0_,userrolese0_. id作为id1_0_1_,userrolese0_. name作为name2_0_1_,userrolese0_. username作为username3_0_1_user_rolesuserrolese0_其中userrolese0_. username=?警告:org.hibernate.engine.jdbc.spi.SqlExceptionHelper-SQL错误:1722,SQLState:42000错误:org.hibernate.engine.jdbc.spi.SqlExceptionHelper-ORA-01722:无效号码

我的类实现了UserDetailsService:

    package pl.piotr.ibank.service;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import pl.piotr.ibank.daointerface.UserDao;
import pl.piotr.ibank.model.UserRole;

@Transactional(readOnly = true)
@Service("userDetailsService")
public class MyUserDetailsService implements UserDetailsService {

    @Autowired
    UserDao userDao;

    @Override
    public UserDetails loadUserByUsername(String username)
            throws UsernameNotFoundException {

        pl.piotr.ibank.model.User user = userDao.findByUsername(username);

        List<GrantedAuthority> authorities = buildUserAuthority(user
                .getUserRole());

        return buildUserForAuthentication(user, authorities);

    }

    private List<GrantedAuthority> buildUserAuthority(Set<UserRole> userRoles) {
        Set<GrantedAuthority> setAuths = new HashSet<GrantedAuthority>();

        for (UserRole userRole : userRoles) {
            setAuths.add(new SimpleGrantedAuthority(userRole.getName()));
        }

        List<GrantedAuthority> result = new ArrayList<GrantedAuthority>(
                setAuths);
        return result;
    }

    private UserDetails buildUserForAuthentication(
            pl.piotr.ibank.model.User user, List<GrantedAuthority> authorities) {
        return new User(user.getUsername(), user.getPassword(), true, true,
                true, true, authorities);
    }

    public UserDao getUserDao() {
        return userDao;
    }

    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }
}

我想是的,我为表映射的foregin键不好。例如,从用户查询<code>并从表返回用户,但当我尝试获取User_roles时,出现了上述错误。请检查我的地图是否正确。我正在使用Oracle数据库和Hibernate。

共有1个答案

李景天
2023-03-14

问题是,当你映射实体时,Hibernate希望外键是被引用实体的id,也就是说,你应该映射用户id而不是用户名。

此外,您的实体映射似乎是错误的:您使用了一个ManyToOne,目标实体是用户,但属性的类型是String。AFAIK Hibernate会尝试将用户分配到用户名,这将非常失败。

所以表格应该是这样的:

create table user_roles (
  id int primary key,
  name varchar2(20) not null,
  userid int constraint userid_fk references users(id) not null
);

UserRole中的映射应该是:

@JoinColumn(name = "userid")
@ManyToOne
private User user;

加上< code>User中的反向映射:

@OneToMany(mappedBy = "user")
private Set<UserRole> userRoleSet;

作为旁注,请记住< code>id在HQL中是一个特殊的关键字,即它总是引用一个实体的id。如果< code>id始终是用< code>@Id注释的唯一属性,那就没有问题,但是如果您改变这种情况,您可能会遇到查询选择错误数据甚至失败的问题。

 类似资料:
  • 我在Kotlin-vertx项目中配置了Hibernate,我设法设置了所有内容,但当我运行HQL查询时,它会输出: 提前谢了。

  • 问题内容: 特定实体存在映射例外。不能弄清楚问题出在哪里。我从头到尾检查了所有映射3次。我仍然收到映射异常。 发送给员工的电子邮件仅映射一次。但它仍然报告错误重复映射 错误是: 电子邮件Pojo email.hbm.xml 相关脚本 发送给员工的电子邮件仅映射一次。但它仍然报告错误重复映射 问题答案: 您是否将Employee中的集合设置为逆?

  • 是否有可能不在HiberNate中的实体层次结构中间为类创建表? 我想指出某些实体是某种类型的子集,以便返回所有这些实体的集合,但我不会在此中间类型中放置任何额外的属性。因此,保留带有id字段的额外表只是为了连接表,这听起来并不好。 更好的解决方案是实现一些公共接口< code>CommonInterface,但是这样我就失去了返回< code>List的可能性

  • 我使用Hibernate已经有一段时间了,而且非常成功。然而,我昨天遇到了一个问题,这里的答案将在将来节省大量调试时间。 我忘了在我的hibernate中添加hibernate映射。新实体的cfg。 当我试图加载这个实体时,我本以为会得到某种运行时异常,但它却什么也没加载,继续运行,好像一切都很好。 我正在使用以下代码加载实体。 我想一个错误,如果我尝试加载一个实体,没有映射在我的hibernat

  • 我对这些技术是新的,所以提前道歉。 我在我的应用程序中使用了springboot、Spring JPA、hibernate和mapstruct。

  • 我想映射类主题到主题表。 主题。JAVA 主题。哈佛商学院。xml 冬眠cfg。xml 我正在读取csv文件的内容,并希望使用以下代码将其插入数据库。 管理ata.java 我得到以下错误 线程“main”组织中出现异常。冬眠MappingException:未知实体:组织中的主题。冬眠impl。SessionFactoryImpl。getEntityPersister(SessionFactor