Свойство not-null ссылается на нулевое или временное значение один к одному с первичным ключом в качестве столбца соединения - PullRequest
0 голосов
/ 03 августа 2020

Может ли кто-нибудь помочь мне здесь, почему я попал ниже исключения. Я проверил различные похожие ссылки, но никто не соответствует этому варианту использования. Я пытаюсь создать связь между таблицей пользователей и таблицей адресов через первичный ключ в качестве столбца соединения в таблице пользователей.

Версия гибернации - 5.2.18

Hibernate: create table User (userId numeric(19,0) not null, primary key (userId))
Hibernate: select next_val as id_val from hibernate_sequence with (updlock, rowlock)
Hibernate: update hibernate_sequence set next_val= ? where next_val=?
Exception in thread "main" javax.persistence.PersistenceException: org.hibernate.PropertyValueException: not-null property references a null or transient value : com.vikas.projects.hibernate.tests.oneTone.User.shippingAddress
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:149)
    at org.hibernate.internal.ExceptionConverterImpl.convert(ExceptionConverterImpl.java:157)

Пользователи. java


import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.Id;
import javax.persistence.OneToOne;
import javax.persistence.PrimaryKeyJoinColumn;
import javax.persistence.Table;

@Entity
@Table(name="USERS")
public class User {
    
    @Id
    private Long id;
    
    @Column (nullable = false)
    private String firstName;
    
    @Column (nullable = false)
    private String lastName;
    
    @OneToOne(
            fetch=FetchType.LAZY,
            optional=false
            )
    @PrimaryKeyJoinColumn
    private Address shippingAddress;
    
    public User() {
        
    }
    
    public User(Long id, String fName, String lName) {
        this.id = id;
        this.firstName = fName;
        this.lastName = lName;
    }

}

Адрес. java


import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;

@Entity
public class Address {
    
    @Id
    @GeneratedValue(strategy=GenerationType.AUTO)
    private Long id;
    @Column (nullable=false)
    private String city;
    @Column (nullable = false)
    private String street;
    
    public Address() {
        
    }
    
    public Address (String city, String street) {
        this.city = city;
        this.street = street;
    }
    
    public Long getId() {
        return id;
    }
    
    public void setCity(String city) {
        this.city = city;
    }
    
    public void setStreet(String street) {
        this.street=street;
    }

}

ApplicationTest. java


import org.hibernate.Session;
import org.hibernate.Transaction;

import com.vikas.projects.hibernate.tests.DbOperations;

public class ApplicationTest {
    
    public static void main( String[] args) {
        Address shippingAddress = new Address("CityNameLiteral", "StreetNameLiteral");
        Session session = DbOperations.getSessionFactory().openSession();
        Transaction tx = session.beginTransaction();
        session.persist(shippingAddress);
        Long shippingAddressId = shippingAddress.getId();
        User userObj = new User(shippingAddressId, "firstNameLiteral", "lastNameLiteral");
        session.persist(userObj);
        tx.commit();
        session.close();
        
    }

}

Спасибо

1 Ответ

0 голосов
/ 04 августа 2020

Ваш пользовательский конструктор выглядит так:

public User(Long id, String fName, String lName) {
    this.id = id;
    this.firstName = fName;
    this.lastName = lName;
}

и вы используете его так:

User userObj = new User(shippingAddressId, "firstNameLiteral", "lastNameLiteral");

это означает, что вы устанавливаете идентификатор пользовательских объектов на идентификатор адреса доставки но вы на самом деле не устанавливаете объект адреса доставки в пользователе на что-либо.

Следующие шаги должны решить вашу проблему:

public class User {
    // Add @GeneratedValue to your User#id (I think you don't need to set the strategy 
    // here, but not 100% sure)
    @Id
    @GeneratedValue
    private Long id;

    // ...
}
// Change User constructor like this
public User(Address shippingAddress, String fName, String lName) {
    this.shippingAddress = shippingAddress;
    this.firstName = fName;
    this.lastName = lName;
}
public static void main( String[] args) {
    Address shippingAddress = new Address("CityNameLiteral", "StreetNameLiteral");
    Session session = DbOperations.getSessionFactory().openSession();
    Transaction tx = session.beginTransaction();
    session.persist(shippingAddress);
    // Use the Adress object now
    User userObj = new User(shippingAdress, "firstNameLiteral", "lastNameLiteral");
    session.persist(userObj);
    tx.commit();
    session.close();
}

Если вы не уверены Я бы порекомендовал вам последовать этому примеру, хотя он предлагает решение с двумя таблицами: https://vladmihalcea.com/the-best-way-to-map-a-onetoone-relationship-with-jpa-and-hibernate/

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...