我是Hibernate的初学者。我有两个表,“城市”和“州”。我的城市班级如下:
package model;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.UniqueConstraint;
import javax.persistence.Version;
@Entity
@Table(name="Cities",uniqueConstraints= {@UniqueConstraint(columnNames= {"city_id"})})
public class Cities {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private int city_id;
@Column(name="CITY_NAME",nullable=true,unique=false)
private String city_name;
@Column(name="POPULATION",nullable=true,unique=false)
private int population;
@Column(name="TS_CNT",nullable=false,unique=true)
@Version
private int ts_cnt;
public int getCity_id() {
return city_id;
}
public void setCity_id(int city_id) {
this.city_id = city_id;
}
public String getCity_name() {
return city_name;
}
public void setCity_name(String city_name) {
this.city_name = city_name;
}
public int getPopulation() {
return population;
}
public void setPopulation(int population) {
this.population = population;
}
public int getTs_cnt() {
return ts_cnt;
}
public void setTs_cnt(int ts_cnt) {
this.ts_cnt = ts_cnt;
}
}
以下是我的“州”课程。
package model;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.OneToOne;
import javax.persistence.Table;
@Entity
@Table
public class State {
@Id
@Column(name = "state_id", nullable = false, unique = true)
@GeneratedValue(strategy = GenerationType.IDENTITY)
private int state_id;
@Column(name = "state_name", nullable = false, unique = true)
private String state_name;
@Column(name = "state_capital", nullable = false, unique = true)
private String state_capital;
@OneToOne
private Cities cities;
public int getState_id() {
return state_id;
}
public void setState_id(int state_id) {
this.state_id = state_id;
}
public String getState_name() {
return state_name;
}
public void setState_name(String state_name) {
this.state_name = state_name;
}
public String getState_capital() {
return state_capital;
}
public void setState_capital(String state_capital) {
this.state_capital = state_capital;
}
public Cities getCities() {
return cities;
}
public void setCities(Cities cities) {
this.cities = cities;
}
}
现在,当我运行以下代码时,出现如下异常:
package citiutilities;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import interfaces.Dbops;
import model.Cities;
import model.State;
public class InsertCities implements Dbops {
public static void main(String[] args) {
Cities citi1 = new Cities();
State state1 = new State();
InsertCities ic = new InsertCities();
ic.insertCities(citi1, state1);
}
public void insertCities(Cities citi1, State state1) {
citi1.setCity_id(100);
citi1.setCity_name("Patna");
citi1.setPopulation(180000);
state1.setState_id(100);
state1.setState_capital("Patna");
state1.setState_name("Bihar");
state1.setCities(citi1);
Session session = CityDbUtil.createSession();
session.beginTransaction();
try {
session.save(state1);
session.getTransaction().commit();
System.out.println("The city that was saved is :: " + citi1.getCity_id());
} catch (HibernateException he) {
session.getTransaction().rollback();
he.printStackTrace();
}
finally {
session.close();
}
}
}
堆栈跟踪如下:
Oct 05, 2018 9:45:27 PM org.hibernate.Version logVersion
INFO: HHH000412: Hibernate Core {5.2.17.Final}
Oct 05, 2018 9:45:27 PM org.hibernate.cfg.Environment <clinit>
INFO: HHH000206: hibernate.properties not found
Oct 05, 2018 9:45:27 PM org.hibernate.annotations.common.reflection.java.JavaReflectionManager <clinit>
INFO: HCANN000001: Hibernate Commons Annotations {5.0.1.Final}
Oct 05, 2018 9:45:27 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl configure
WARN: HHH10001002: Using Hibernate built-in connection pool (not for production use!)
Oct 05, 2018 9:45:27 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001005: using driver [org.postgresql.Driver] at URL [jdbc:postgresql://localhost/subirdb]
Oct 05, 2018 9:45:27 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001001: Connection properties: {user=postgres, password=****}
Oct 05, 2018 9:45:27 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001003: Autocommit mode: false
Oct 05, 2018 9:45:27 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl$PooledConnections <init>
INFO: HHH000115: Hibernate connection pool size: 20 (min=1)
Oct 05, 2018 9:45:28 PM org.hibernate.dialect.Dialect <init>
INFO: HHH000400: Using dialect: org.hibernate.dialect.PostgreSQLDialect
Oct 05, 2018 9:45:28 PM org.hibernate.engine.jdbc.env.internal.LobCreatorBuilderImpl useContextualLobCreation
INFO: HHH000424: Disabling contextual LOB creation as createClob() method threw error : java.lang.reflect.InvocationTargetException
Oct 05, 2018 9:45:28 PM org.hibernate.type.BasicTypeRegistry register
INFO: HHH000270: Type registration [java.util.UUID] overrides previous : org.hibernate.type.UUIDBinaryType@5fa07e12
Oct 05, 2018 9:45:29 PM org.hibernate.resource.transaction.backend.jdbc.internal.DdlTransactionIsolatorNonJtaImpl getIsolatedConnection
INFO: HHH10001501: Connection obtained from JdbcConnectionAccess [org.hibernate.engine.jdbc.env.internal.JdbcEnvironmentInitiator$ConnectionProviderJdbcConnectionAccess@2b95e48b] for (non-JTA) DDL execution was not in auto-commit mode; the Connection 'local transaction' will be committed and the Connection will be set into auto-commit mode.
Hibernate:
create table Cities (
city_id int4 not null,
CITY_NAME varchar(255),
POPULATION int4,
TS_CNT int4 not null,
primary key (city_id)
)
Hibernate:
create table State (
state_id serial not null,
state_capital varchar(255) not null,
state_name varchar(255) not null,
cities_city_id int4,
primary key (state_id)
)
Hibernate:
alter table Cities
drop constraint UK_lyvuwacb89kupauxjk1103pjl
Hibernate:
alter table Cities
add constraint UK_lyvuwacb89kupauxjk1103pjl unique (TS_CNT)
Hibernate:
alter table State
drop constraint UK_jv8xyklsot1gudi8bfo3hrdkj
Hibernate:
alter table State
add constraint UK_jv8xyklsot1gudi8bfo3hrdkj unique (state_capital)
Hibernate:
alter table State
drop constraint UK_sh9wvgcb2q4h69yjib264nlh4
Hibernate:
alter table State
add constraint UK_sh9wvgcb2q4h69yjib264nlh4 unique (state_name)
Hibernate:
alter table State
add constraint FKmcjxnu2cw7ax2uefyvp55saky
foreign key (cities_city_id)
references Cities
Oct 05, 2018 9:45:29 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl configure
WARN: HHH10001002: Using Hibernate built-in connection pool (not for production use!)
Oct 05, 2018 9:45:29 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001005: using driver [org.postgresql.Driver] at URL [jdbc:postgresql://localhost/subirdb]
Oct 05, 2018 9:45:29 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001001: Connection properties: {user=postgres, password=****}
Oct 05, 2018 9:45:29 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001003: Autocommit mode: false
Oct 05, 2018 9:45:29 PM org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl$PooledConnections <init>
INFO: HHH000115: Hibernate connection pool size: 20 (min=1)
Oct 05, 2018 9:45:30 PM org.hibernate.dialect.Dialect <init>
INFO: HHH000400: Using dialect: org.hibernate.dialect.PostgreSQLDialect
Oct 05, 2018 9:45:30 PM org.hibernate.engine.jdbc.env.internal.LobCreatorBuilderImpl useContextualLobCreation
INFO: HHH000424: Disabling contextual LOB creation as createClob() method threw error : java.lang.reflect.InvocationTargetException
Oct 05, 2018 9:45:30 PM org.hibernate.type.BasicTypeRegistry register
INFO: HHH000270: Type registration [java.util.UUID] overrides previous : org.hibernate.type.UUIDBinaryType@5fa07e12
Oct 05, 2018 9:45:30 PM org.hibernate.resource.transaction.backend.jdbc.internal.DdlTransactionIsolatorNonJtaImpl getIsolatedConnection
INFO: HHH10001501: Connection obtained from JdbcConnectionAccess [org.hibernate.engine.jdbc.env.internal.JdbcEnvironmentInitiator$ConnectionProviderJdbcConnectionAccess@5cbf9e9f] for (non-JTA) DDL execution was not in auto-commit mode; the Connection 'local transaction' will be committed and the Connection will be set into auto-commit mode.
Hibernate:
insert
into
State
(cities_city_id, state_capital, state_name)
values
(?, ?, ?)
Oct 05, 2018 9:45:30 PM org.hibernate.engine.jdbc.spi.SqlExceptionHelper logExceptions
WARN: SQL Error: 0, SQLState: 23503
Oct 05, 2018 9:45:30 PM org.hibernate.engine.jdbc.spi.SqlExceptionHelper logExceptions
ERROR: ERROR: insert or update on table "state" violates foreign key constraint "fkmcjxnu2cw7ax2uefyvp55saky"
Detail: Key (cities_city_id)=(100) is not present in table "cities".
org.hibernate.exception.ConstraintViolationException: could not execute statement
at org.hibernate.exception.internal.SQLStateConversionDelegate.convert(SQLStateConversionDelegate.java:112)
at org.hibernate.exception.internal.StandardSQLExceptionConverter.convert(StandardSQLExceptionConverter.java:42)
at org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:111)
at org.hibernate.engine.jdbc.spi.SqlExceptionHelper.convert(SqlExceptionHelper.java:97)
at org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.executeUpdate(ResultSetReturnImpl.java:178)
at org.hibernate.dialect.identity.GetGeneratedKeysDelegate.executeAndExtract(GetGeneratedKeysDelegate.java:57)
at org.hibernate.id.insert.AbstractReturningDelegate.performInsert(AbstractReturningDelegate.java:42)
at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2933)
at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:3524)
at org.hibernate.action.internal.EntityIdentityInsertAction.execute(EntityIdentityInsertAction.java:81)
at org.hibernate.engine.spi.ActionQueue.execute(ActionQueue.java:637)
at org.hibernate.engine.spi.ActionQueue.addResolvedEntityInsertAction(ActionQueue.java:282)
at org.hibernate.engine.spi.ActionQueue.addInsertAction(ActionQueue.java:263)
at org.hibernate.engine.spi.ActionQueue.addAction(ActionQueue.java:317)
at org.hibernate.event.internal.AbstractSaveEventListener.addInsertAction(AbstractSaveEventListener.java:318)
at org.hibernate.event.internal.AbstractSaveEventListener.performSaveOrReplicate(AbstractSaveEventListener.java:275)
at org.hibernate.event.internal.AbstractSaveEventListener.performSave(AbstractSaveEventListener.java:182)
at org.hibernate.event.internal.AbstractSaveEventListener.saveWithGeneratedId(AbstractSaveEventListener.java:113)
at org.hibernate.event.internal.DefaultSaveOrUpdateEventListener.saveWithGeneratedOrRequestedId(DefaultSaveOrUpdateEventListener.java:192)
at org.hibernate.event.internal.DefaultSaveEventListener.saveWithGeneratedOrRequestedId(DefaultSaveEventListener.java:38)
at org.hibernate.event.internal.DefaultSaveOrUpdateEventListener.entityIsTransient(DefaultSaveOrUpdateEventListener.java:177)
at org.hibernate.event.internal.DefaultSaveEventListener.performSaveOrUpdate(DefaultSaveEventListener.java:32)
at org.hibernate.event.internal.DefaultSaveOrUpdateEventListener.onSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:73)
at org.hibernate.internal.SessionImpl.fireSave(SessionImpl.java:692)
at org.hibernate.internal.SessionImpl.save(SessionImpl.java:684)
at org.hibernate.internal.SessionImpl.save(SessionImpl.java:679)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source)
at java.lang.reflect.Method.invoke(Unknown Source)
at org.hibernate.context.internal.ThreadLocalSessionContext$TransactionProtectionWrapper.invoke(ThreadLocalSessionContext.java:355)
at com.sun.proxy.$Proxy27.save(Unknown Source)
at citiutilities.InsertCities.insertCities(InsertCities.java:29)
at citiutilities.InsertCities.main(InsertCities.java:14)
Caused by: org.postgresql.util.PSQLException: ERROR: insert or update on table "state" violates foreign key constraint "fkmcjxnu2cw7ax2uefyvp55saky"
Detail: Key (cities_city_id)=(100) is not present in table "cities".
at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:2477)
at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:2190)
at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:300)
at org.postgresql.jdbc.PgStatement.executeInternal(PgStatement.java:428)
at org.postgresql.jdbc.PgStatement.execute(PgStatement.java:354)
at org.postgresql.jdbc.PgPreparedStatement.executeWithFlags(PgPreparedStatement.java:169)
at org.postgresql.jdbc.PgPreparedStatement.executeUpdate(PgPreparedStatement.java:136)
at org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.executeUpdate(ResultSetReturnImpl.java:175)
... 29 more
在这种特殊情况下,我观察到的是,系统以某种方式在状态表中创建了列Cities_city_id
,而目的是系统创建了名称为city_id
的列。据我说,这是一个问题,因为在city表中不存在此列。但是我不明白为什么系统要操纵这个名字。我试图在互联网上搜索但徒劳。
答案 0 :(得分:1)
运行代码时发现2个问题
state1.setState_id(100);
citi1.setCity_id(100);
这两个字段已经具有@GeneratedValue Tag,这意味着无需显式设置它。
第二,一旦我解决了以上问题,第二个错误是
object references an unsaved transient instance - save the transient instance before flushing
为此,请更新State.java。添加 CascadeType.ALL 有助于保存城市信息,同时保存州信息。
@OneToOne(cascade =CascadeType.ALL)
private Cities cities;
关于 Cities_city_id ,即外键
FOREIGN KEY (`cities_city_id`) REFERENCES `Cities` (`city_id`)