简体   繁体   English

org.hibernate.id.IdentifierGenerationException:尝试从空的一对一属性(使用session.merge)分配ID

[英]org.hibernate.id.IdentifierGenerationException: attempted to assign id from null one-to-one property (with session.merge)

I have a problem. 我有个问题。 I get error in my app: org.hibernate.id.IdentifierGenerationException: attempted to assign id from null one-to-one property 我在我的应用程序中遇到错误: org.hibernate.id.IdentifierGenerationException:尝试从空的一对一属性分配ID

My pojos User: 我的pojos用户:

@Entity
@Table(name = "user")
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
public class User implements Serializable {
private static final long serialVersionUID = -5415891222321582213L;

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Column(name = "userId", length = 100)
private int userId;
...
@OneToOne(mappedBy = "user", cascade = CascadeType.ALL)
private UserDetail userDetail;

UserDetail: 用户详细信息:

@Entity
@Table(name = "userdetail")
@Cache(usage = CacheConcurrencyStrategy.READ_WRITE)
public class UserDetail implements Serializable {
private static final long serialVersionUID = 2155190440305692224L;

@Id
@GenericGenerator(
    name = "gen",
    strategy = "foreign",
    parameters = @Parameter(name = "property", value = "user")
    )
@GeneratedValue(generator = "gen")
@Column(name = "userId", length = 100)
private int userId;
...
@OneToOne
@PrimaryKeyJoinColumn
private User user;

Table User: 表用户:

CREATE TABLE `user` (
    `userId` INT(100) NOT NULL AUTO_INCREMENT,
    `name` VARCHAR(255) NULL DEFAULT NULL,
    `surname` VARCHAR(255) NULL DEFAULT NULL,
    `email` VARCHAR(255) NULL DEFAULT NULL,
    `password` VARCHAR(255) NULL DEFAULT NULL,
    PRIMARY KEY (`userId`)
)
COLLATE='utf8_general_ci'
ENGINE=InnoDB
;

Table UserDetail 表用户详细信息

CREATE TABLE `userdetail` (
    `userId` INT(100) NOT NULL,
    `country` VARCHAR(255) NULL DEFAULT NULL,
    `city` VARCHAR(255) NULL DEFAULT NULL,
    `address` VARCHAR(255) NULL DEFAULT NULL,
    PRIMARY KEY (`userId`)
)
COLLATE='utf8_general_ci'
ENGINE=InnoDB
;

DAO Layer: DAO层:

private Session session = HibernateUtil.getHibernateUtil().getSession();
@Override
public void create(T t) throws DaoException {
        Object object = session.merge(t);
        session.save(object);
        log.info("Update: " + t);
}

Service Layer 服务层

private Session session = HibernateUtil.getHibernateUtil().getSession();
private Transaction transaction = null;
private Dao<T> dao = new BaseDao<T>();
@Override
public void create(T t) throws DaoException {
    try {
        transaction = session.beginTransaction();
        dao.create(t);
        transaction.commit();
        log.info("Create: " + t);
    } catch (HibernateException e) {
        log.error("Error creating " + getPersistentClass() + " in Dao " + e);
        transaction.rollback();
        throw new DaoException(e);
    }
}

Class with saving User 具有保存用户的类

User user = new User(name, surname, email, password);
UserDetail userDetail = new UserDetail(country, city, address);
user.setUserDetail(userDetail);
userDetail.setUser(user);
userService.create(user);

HiberUtil HiberUtil

public class HibernateUtil {
    private static Logger log = Logger.getLogger(HibernateUtil.class);
    private static HibernateUtil util = null;
    private static SessionFactory sessionFactory = null;
    private static final ThreadLocal<Session> sessions = new ThreadLocal<Session>();

    private HibernateUtil() {
        try {
        Configuration configuration = new Configuration().configure("hibernate.cfg.xml");
        log.info("Hibernate Configuration loaded");
        ServiceRegistry serviceRegistry = new StandardServiceRegistryBuilder().applySettings(configuration.getProperties()).build();
        log.info("Hibernate serviceRegistry created");
        sessionFactory = configuration.buildSessionFactory(serviceRegistry);
        } catch (Throwable e) {
            log.error("Initial SessionFactory creation failed. " + e);
            System.exit(0);
        }
    }

    public Session getSession () {
        Session session = sessions.get();
        if (session == null) {
            session = sessionFactory.openSession();
            sessions.set(session);
        } 
        return session;
    }

    public static synchronized HibernateUtil getHibernateUtil(){
        if (util == null){
            util = new HibernateUtil();
        }
        return util;
    }
}

If i change in DAO layer: 如果我在DAO层中更改:

@Override
public void create(T t) throws DaoException {
        session.save(t);
        log.info("Create: " + t);
}

I get error: org.hibernate.HibernateException: Illegal attempt to associate a collection with two open sessions 我收到错误消息: org.hibernate.HibernateException:非法尝试将一个集合与两个打开的会话相关联

So I have 4 questions: 所以我有四个问题:

  1. If I understood correctly, when userdeteil save userId from User is null because UserId don't get icnrement Id from Table, it's true? 如果我理解正确,那么当Userdeteil从User中保存userId为null时(因为UserId无法从Table中获取icnrement ID),这是真的吗?

  2. Needed session.merge here or not 需要session.merge在这里与否

  3. If merge is needed, how correct org.hibernate.id.IdentifierGenerationException: attempted to assign id from null one-to-one property 如果需要合并,如何正确的org.hibernate.id.IdentifierGenerationException:尝试从空的一对一属性分配ID

  4. If merge is no needed, how correct "org.hibernate.HibernateException: Illegal attempt to associate a collection with two open sessions" 如果不需要合并,如何正确纠正“ org.hibernate.HibernateException:非法尝试将一个集合与两个打开的会话相关联”

Note: Delet with merge is good, create with merge other Entity (not User and not UserDeteil) is good. 注意:删除合并是好的,创建合并其他实体(不是User而不是UserDeteil)是好的。

To get it work, remove Object object = session.merge(t); 要使其正常工作,请删除Object object = session.merge(t); from update method of your DAO class. 从您的DAO类的更新方法。 Here is updated update method 这是更新的更新方法

@Override
public void update(T t) throws DaoException {
        session.saveOrUpdate(t);
        log.info("Update: " + t);
}

This will fix your org.hibernate.id.IdentifierGenerationException exception. 这将修复您的org.hibernate.id.IdentifierGenerationException异常。

  • For point 1: Your record was not saved, you were calling merge() method, then the object return by merge method is passed in save(here). 对于点1:您的记录未保存,您正在调用merge()方法,然后由merge方法返回的对象将传递到save(此处)。 merger(): Copy the state of the given object onto the persistent object with the same identifier. merge():将给定对象的状态复制到具有相同标识符的持久对象上。 In your case no persistent object. 在您的情况下,没有持久对象。
  • For point 2: No merge method is not required here, use save or saveOrUpdate method with session 对于第2点:此处不需要合并方法,请在会话中使用save或saveOrUpdate方法
  • For point 3: N/A 对于第3点:N / A

Here is a good example of One-To-One association mapping 这是一对一关联映射的一个好例子

I solved my poroblem. 我解决了麻烦。 In my BaseDao and BaseService I removed: 在我的BaseDao和BaseService中,我删除了:

private Session session = HibernateUtil.getHibernateUtil().getSession();

And I added in all methods in BaseDao and BaseService: 我在BaseDao和BaseService中添加了所有方法:

HibernateUtil.getHibernateUtil().getSession();

so I removed the two sessions and my method, example create, became: 所以我删除了两个会话,然后我的方法(例如创建)变成了:

@Override
public void create(T t) throws DaoException {
        HibernateUtil.getHibernateUtil().getSession().save(t);
        log.info("Create: " + t);
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Hibernate merge org.hibernate.id.IdentifierGenerationException:尝试从空的一对一属性分配ID - Hibernate merge org.hibernate.id.IdentifierGenerationException: attempted to assign id from null one-to-one property org.hibernate.id.IdentifierGenerationException:“试图从空一对一属性分配 id” - org.hibernate.id.IdentifierGenerationException: "attempted to assign id from null one-to-one property" org.hibernate.id.IdentifierGenerationException:试图从空一对一属性(hibernate+postgres)分配id - org.hibernate.id.IdentifierGenerationException: attempted to assign id from null one-to-one property (hibernate+postgres) Hibernate 尝试从 null 一对一属性分配 id - Hibernate attempted to assign id from null one-to-one property 休眠一对零或一个映射。 例外:尝试从空的一对一属性分配ID? - Hibernate one to zero or one mapping. Exception: attempted to assign id from null one-to-one property? Hibernate 错误:试图从 null 一对一属性分配 id。 为什么? - Hibernate Error : attempted to assign id from null one-to-one property. Why? Hibernate OneToOne 尝试从 null 一对一属性分配 id - Hibernate OneToOne attempted to assign id from null one-to-one property org.hibernate.id.IdentifierGenerationException:同时将数据保存在一对一映射中 - org.hibernate.id.IdentifierGenerationException: while saving data in one to one mapping 在Spring Boot中尝试从空的一对一属性分配ID - Attempted to assign id from null one-to-one property in spring boot @EmbeddId 正在抛出 org.hibernate.id.IdentifierGenerationException: null id 在 ZCB1F008EEBF5012C4EF9A2C36E574D61 中使用.save() 函数时生成 - @EmbeddId is thowing org.hibernate.id.IdentifierGenerationException: null id generated while using .save() frunction in hibernate
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM