Hibernate:外键约束失败

时间:2011-05-23 14:01:12

标签: hibernate

以下是Hibernate生成的SQL语句

Hibernate: insert into HOSPITAL_ADDRESS (DOOR_NO, STREET, REFERENCE_LANDMARK, HASH) values (?, ?, ?, ?)
Hibernate: insert into PHONE_NUMBER (AREA_CODE, NUMBER, HASH) values (?, ?, ?)
Hibernate: insert into FAX_NUMBER (AREA_CODE, NUMBER, HASH) values (?, ?, ?)
Hibernate: insert into HOSPITAL_CONTACT (PHONE_NUMBER_1, PHONE_NUMBER_2, FAX_NUMBER_1, FAX_NUMBER_2, WEBSITE, HASH) values (?, ?, ?, ?, ?, ?)
Hibernate: insert into CATARACT (SURGERY_VOLUME, FREE_CASES, PAID_CASES, IMPORTED, INDIAN, HASH) values (?, ?, ?, ?, ?, ?)
Hibernate: insert into PIN_CODE (PIN, AREA, CITY, STATE, HASH) values (?, ?, ?, ?, ?)
Hibernate: insert into HOSPITAL (NAME, PHONETICS, CATEGORY, SUB_CATEGORY, SERVICES, ADDRESS, CONTACT, CATARACT, PIN_CODE, HASH) values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)

这是堆栈跟踪:

org.hibernate.exception.ConstraintViolationException: could not insert: [com.mylabs.model.Hospital]
at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:94)
at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:66)
at org.hibernate.id.insert.AbstractReturningDelegate.performInsert(AbstractReturningDelegate.java:64)
at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2176)
at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2656)
at org.hibernate.action.EntityIdentityInsertAction.execute(EntityIdentityInsertAction.java:71)
at org.hibernate.engine.ActionQueue.execute(ActionQueue.java:279)
at org.hibernate.event.def.AbstractSaveEventListener.performSaveOrReplicate(AbstractSaveEventListener.java:321)
at org.hibernate.event.def.AbstractSaveEventListener.performSave(AbstractSaveEventListener.java:204)
at org.hibernate.event.def.AbstractSaveEventListener.saveWithGeneratedId(AbstractSaveEventListener.java:130)
at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.saveWithGeneratedOrRequestedId(DefaultSaveOrUpdateEventListener.java:210)
at org.hibernate.event.def.DefaultSaveEventListener.saveWithGeneratedOrRequestedId(DefaultSaveEventListener.java:56)
at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.entityIsTransient(DefaultSaveOrUpdateEventListener.java:195)
at org.hibernate.event.def.DefaultSaveEventListener.performSaveOrUpdate(DefaultSaveEventListener.java:50)
at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.onSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:93)
at org.hibernate.impl.SessionImpl.fireSave(SessionImpl.java:563)
at org.hibernate.impl.SessionImpl.save(SessionImpl.java:551)
at org.hibernate.impl.SessionImpl.save(SessionImpl.java:547)
at com.mylab.ws.DataPersister.save(DataPersister.java:20)
at com.mylab.ws.HospitalServlet.testMethod(HospitalServlet.java:137)
at com.mylab.ws.HospitalServlet.handleResponse(HospitalServlet.java:81)
at com.mylab.ws.HospitalServlet.doGet(HospitalServlet.java:51)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:617)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:859)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:588)
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489)
at java.lang.Thread.run(Thread.java:680)

Caused by: com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: Cannot add or update a child row: a foreign key constraint fails (`mylab`.`hospital`, CONSTRAINT `FK1C8CEE3A93A84897` FOREIGN KEY (`CONTACT`) REFERENCES `HOSPITAL_CONTACT` (`ID`))
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:39)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:27)
at java.lang.reflect.Constructor.newInstance(Constructor.java:513)
at com.mysql.jdbc.Util.handleNewInstance(Util.java:411)
at com.mysql.jdbc.Util.getInstance(Util.java:386)
at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1039)
at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3597)
at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3529)
at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:1990)
at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2151)
at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2625)
at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:2119)
at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2415)
at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2333)
at com.mysql.jdbc.PreparedStatement.executeUpdate(PreparedStatement.java:2318)
at org.hibernate.id.IdentityGenerator$GetGeneratedKeysDelegate.executeAndExtract(IdentityGenerator.java:94)
at org.hibernate.id.insert.AbstractReturningDelegate.performInsert(AbstractReturningDelegate.java:57)
... 33 more

我尝试将一个HospitalContact实例持久保存到数据库中,并且它没有任何问题。仅当我尝试将Hospital对象保存到DB时才会发生这种情况。任何指针将不胜感激。我已经尝试了谷歌搜索和StackOverflow类似的问题,但我无法弄明白。但对于专家而言,这应该是小菜一碟。

Hospital.java

package com.mylabs.model;

import java.util.List;

import org.simpleframework.xml.Attribute;
import org.simpleframework.xml.Element;
import org.simpleframework.xml.ElementList;
import org.simpleframework.xml.Root;

import com.mobsandgeeks.utils.CryptoUtils;

@Root
public class Hospital {
    @Attribute private int id;
    @Element private String name;
    @Element private int phonetics; //TODO  
    @Element private String category;
    @Element private String subCategory;    
    @Element private String services;
    @Element private HospitalAddress address;
    @Element private HospitalContact contact;
    @ElementList private List<KeyContactInfo> keyContacts;
    @Element private Cataract cataract;
    @Element private PinCode pinCode;
    @Element private String hash;

    Hospital() {

    }

    public Hospital(int id, String name, int phonetics, String category, String subCategory,
        String services, HospitalAddress address, HospitalContact contact, List<KeyContactInfo> keyContacts,
            Cataract cataract, PinCode pinCode, String hash) {
        this.id = id;
        this.name = name;
        this.phonetics = phonetics;
        this.category = category;
        this.subCategory = subCategory;
        this.services = services;
        this.address = address;
        this.contact = contact;
        this.keyContacts = keyContacts;
        this.cataract = cataract;
        this.pinCode = pinCode;
        this.hash = hash;
    }

    public Hospital(String name, int phonetics, String category, String subCategory,
        String services, HospitalAddress address, HospitalContact contact, List<KeyContactInfo> keyContacts,
            Cataract cataract, PinCode pinCode) {
    this.name = name;
    this.phonetics = phonetics;
    this.category = category;
    this.subCategory = subCategory;
    this.services = services;
    this.address = address;
    this.contact = contact;
    this.keyContacts = keyContacts;
    this.cataract = cataract;
    this.pinCode = pinCode;

    updateHash();
}

public String getName() {
    return name;
}

public void setName(String name) {
    this.name = name;
    updateHash();
}

public int getPhonetics() {
    return phonetics;
}

public void setPhonetics(int phonetics) {
    this.phonetics = phonetics;
    updateHash();
}

public String getCategory() {
    return category;
}

public void setCategory(String category) {
    this.category = category;
    updateHash();
}

public String getSubCategory() {
    return subCategory;
}

public void setSubCategory(String subCategory) {
    this.subCategory = subCategory;
    updateHash();
}

public String getServices() {
    return services;
}

public void setServices(String services) {
    this.services = services;
    updateHash();
}

public HospitalAddress getAddress() {
    return address;
}

public void setAddress(HospitalAddress address) {
    this.address = address;
}

public HospitalContact getContact() {
    return contact;
}

public void setContact(HospitalContact contact) {
    this.contact = contact;
    updateHash();
}

public List<KeyContactInfo> getKeyContacts() {
    return keyContacts;
}

public void setKeyContacts(List<KeyContactInfo> keyContacts) {
    this.keyContacts = keyContacts;
    updateHash();
}

public Cataract getCataract() {
    return cataract;
}

public void setCataract(Cataract cataract) {
    this.cataract = cataract;
    updateHash();
}

public PinCode getPinCode() {
    return pinCode;
}

public void setPinCode(PinCode pinCode) {
    this.pinCode = pinCode;
    updateHash();
}

public int getId() {
    return id;
}

public String getHash() {
    return hash;
}

@SuppressWarnings("unused")
private void setHash(String hash) {
    this.hash = hash;
}

@SuppressWarnings("unused")
private void setId(int id) {
    this.id = id;
}

@Override
public String toString() {
    StringBuilder sb = new StringBuilder();

    sb.append(name);
    sb.append(phonetics);
    sb.append(category);
    sb.append(subCategory);
    sb.append(services);
    sb.append(address);
    sb.append(contact);
    for(KeyContactInfo contact : keyContacts) {
        sb.append(contact);
    }
    sb.append(cataract);
    sb.append(pinCode);

    return sb.toString();
}

private void updateHash() {
    hash = CryptoUtils.md5HashOf(toString());
}

}

Hospital.hbm.xml

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated May 23, 2011 4:13:51 PM by Hibernate Tools 3.4.0.CR1 -->
<hibernate-mapping>
<class name="com.mylabs.model.Hospital" table="HOSPITAL">
    <id name="id" type="int">
        <column name="ID" />
        <generator class="native" />
    </id>
    <property name="name" type="java.lang.String">
        <column name="NAME" />
    </property>
    <property name="phonetics" type="int">
        <column name="PHONETICS" />
    </property>
    <property name="category" type="java.lang.String">
        <column name="CATEGORY" />
    </property>
    <property name="subCategory" type="java.lang.String">
        <column name="SUB_CATEGORY" />
    </property>
    <property name="services" type="java.lang.String">
        <column name="SERVICES" />
    </property>
    <many-to-one name="address" class="com.mylabs.model.HospitalAddress" fetch="join" cascade="all">
        <column name="ADDRESS" />
    </many-to-one>
    <many-to-one name="contact" class="com.mylabs.model.HospitalContact" fetch="join" cascade="all">
        <column name="CONTACT" />
    </many-to-one>
    <many-to-one name="cataract" class="com.mylabs.model.Cataract" fetch="join" cascade="all">
        <column name="CATARACT" />
    </many-to-one>
    <many-to-one name="pinCode" class="com.mylabs.model.PinCode" fetch="join" cascade="all">
        <column name="PIN_CODE" />
    </many-to-one>
    <property name="hash" type="java.lang.String">
        <column name="HASH" />
    </property>
</class>

HopitalContact.java

package com.mylabs.model;

import org.simpleframework.xml.Attribute;
import org.simpleframework.xml.Element;
import org.simpleframework.xml.Root;

import com.mobsandgeeks.utils.CryptoUtils;

@Root
public class HospitalContact {
@Attribute private int id;
@Element private PhoneNumber phoneNumber1;
@Element(required=false) private PhoneNumber phoneNumber2;
@Element(required=false) private FaxNumber faxNumber1;
@Element(required=false) private FaxNumber faxNumber2;
@Element(required=false) private String website;
@Element private String hash;

HospitalContact() {

}

public HospitalContact(int id, PhoneNumber phoneNumber1, PhoneNumber phoneNumber2,
        FaxNumber faxNumber1, FaxNumber faxNumber2, String website, String hash) {
    this.id = id;
    this.phoneNumber1 = phoneNumber1;
    this.phoneNumber2 = phoneNumber2;
    this.faxNumber1 = faxNumber1;
    this.faxNumber2 = faxNumber2;
    this.website = website;
    this.hash = hash;
}

public HospitalContact(PhoneNumber phoneNumber1, PhoneNumber phoneNumber2,
        FaxNumber faxNumber1, FaxNumber faxNumber2, String website) {
    this.phoneNumber1 = phoneNumber1;
    this.phoneNumber2 = phoneNumber2;
    this.faxNumber1 = faxNumber1;
    this.faxNumber2 = faxNumber2;
    this.website = website;

    updateHash();
}

public PhoneNumber getPhoneNumber1() {
    return phoneNumber1;
}

public void setPhoneNumber1(PhoneNumber phoneNumber1) {
    this.phoneNumber1 = phoneNumber1;
}

public PhoneNumber getPhoneNumber2() {
    return phoneNumber2;
}

public void setPhoneNumber2(PhoneNumber phoneNumber2) {
    this.phoneNumber2 = phoneNumber2;
}

public FaxNumber getFaxNumber1() {
    return faxNumber1;
}

public void setFaxNumber1(FaxNumber faxNumber1) {
    this.faxNumber1 = faxNumber1;
}

public FaxNumber getFaxNumber2() {
    return faxNumber2;
}

public void setFaxNumber2(FaxNumber faxNumber2) {
    this.faxNumber2 = faxNumber2;
}

public String getWebsite() {
    return website;
}

public void setWebsite(String website) {
    this.website = website;
}

public int getId() {
    return id;
}

public String getHash() {
    return hash;
}

private void updateHash() {
    hash = CryptoUtils.md5HashOf(toString());
}

@SuppressWarnings("unused")
private void setHash(String hash) {
    this.hash = hash;
}

@SuppressWarnings("unused")
private void setId(int id) {
    this.id = id;
}

@Override
public String toString() {
    StringBuilder sb = new StringBuilder();
    Object[] contactNumbers = { phoneNumber1, phoneNumber2, faxNumber1, faxNumber2 };

    for(Object number : contactNumbers) {
        if(number instanceof PhoneNumber) {
            PhoneNumber n = (PhoneNumber) number;

            if(n != null) {
                sb.append(n.getAreaCode());
                sb.append(n.getNumber());
            }
        } else if(number instanceof FaxNumber) {
            FaxNumber n = (FaxNumber) number;

            if(n != null) {
                sb.append(n.getAreaCode());
                sb.append(n.getNumber());
            }
        }
    }
    sb.append(website);

    return sb.toString();
}
}

HospitalContact.hbm.xml

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated May 23, 2011 4:13:51 PM by Hibernate Tools 3.4.0.CR1 -->
<hibernate-mapping>
<class name="com.mylabs.model.HospitalContact" table="HOSPITAL_CONTACT">
    <id name="id" type="int">
        <column name="ID" />
        <generator class="native" />
    </id>
    <many-to-one name="phoneNumber1" class="com.mylabs.model.PhoneNumber" fetch="join" cascade="all">
        <column name="PHONE_NUMBER_1" />
    </many-to-one>
    <many-to-one name="phoneNumber2" class="com.mylabs.model.PhoneNumber" fetch="join" cascade="all">
        <column name="PHONE_NUMBER_2" />
    </many-to-one>
    <many-to-one name="faxNumber1" class="com.mylabs.model.FaxNumber" fetch="join" cascade="all">
        <column name="FAX_NUMBER_1" />
    </many-to-one>
    <many-to-one name="faxNumber2" class="com.mylabs.model.FaxNumber" fetch="join" cascade="all">
        <column name="FAX_NUMBER_2" />
    </many-to-one>
    <property name="website" type="java.lang.String">
        <column name="WEBSITE" />
    </property>
    <property name="hash" type="java.lang.String">
        <column name="HASH" />
    </property>
</class>
</hibernate-mapping>

持久存在对象的代码

package com.mylab.ws;

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

import com.mobsandgeeks.utils.HibernateUtils;

public class DataPersister {
//************************************************************************************************************
//                                          Save Method
//************************************************************************************************************
public static int save(Object hibernateMappedObject) {
    Session session = HibernateUtils.getSessionFactory().openSession();
    Transaction transaction = null;
    int id = -1;

    try {
        transaction = session.beginTransaction();
        id = (Integer) session.save(hibernateMappedObject);
        transaction.commit();   
    } catch (HibernateException hex) {
        transaction.rollback();
        hex.printStackTrace();
    } finally {
        session.close();
    }
    return id;
}
}

我为错误的代码格式化道歉。

1 个答案:

答案 0 :(得分:1)

我只是为父表和子表重置AUTO_INCREMENT0(零)。

您可以使用以下命令在MySQL中执行此操作:

alter table yourtable auto_increment=0;

我运行了我的hibernate项目,问题解决了。当然,除非您指定的数字高于表格中的最后一个数字,否则您必须愿意删除表格中的数据才能重置或重置之前无效。

好吧,我希望这适合你。有时您的代码很好,数据库参数就是问题。