I am using MySQL with Hibernate and JPA2.
I have the following table, which I would expect to auto generate the ID because AI (Auto Increment) is checked:
CREATE TABLE `job` (
`ID` int(11) NOT NULL AUTO_INCREMENT,
`JOINING_DATE` double NOT NULL,
`LASTACCESS_DATE` double NOT NULL,
`PHONE_NUMBER` varchar(55) DEFAULT NULL,
`MOBILE_NUMBER` varchar(55) DEFAULT NULL,
`EMAIL_ADDRESS` varchar(55) DEFAULT NULL,
`SEX` int(1) DEFAULT NULL,
`JOB_TITLE` varchar(65) NOT NULL,
`JOB_DESCRIPTION` varchar(800) NOT NULL,
`JOB_DETAILS` varchar(800) DEFAULT NULL,
`DRIVERS_LICENCE` int(1) DEFAULT NULL,
`AVATAR` longblob,
`TYPE` int(1) NOT NULL,
PRIMARY KEY (`ID`),
UNIQUE KEY `ID_UNIQUE` (`ID`)
) ENGINE=InnoDB AUTO_INCREMENT=87 DEFAULT CHARSET=utf8;
Job.java
#Entity
#Table(name = "job")
#XmlRootElement(name = "job")
public class Job extends AbstractDomain<Long> {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
...
Dao.java
protected T merge(T entity) throws InstantiationException, IllegalAccessException {
T attached = null;
if (entity.getId() != null) {
attached = entityManager.find(entityClass, entity.getId());
}
if (attached == null) {
attached = entityClass.newInstance(); // <= this is executed
}
BeanUtils.copyProperties(entity, attached);
entityManager.merge(attached); // <= ID is null here
return attached;
}
When I try merge the table, I get the following error:
Caused by: java.sql.SQLException: Field 'ID' doesn't have a default value
Strange thing is this was working earlier, and the Java code has not changed, I did make changes to some other database tables only. I have read here that some people had this problem and fixed it by dropping and importing their database. I did drop the schema and imported it again. But still get the same error.
Does anyone have any ideas please?
Related
Previous update() method was throwing different object with the same identifier value was already associated with the session so I changed dao to merge. Now it gives org.springframework.dao.DataIntegrityViolationException: could not execute statement; SQL [n/a]; constraint [null]; nested exception is org.hibernate.exception.ConstraintViolationException: could not execute statement
TeamDAOImpl
public void updateTeam(Team team) {
Team teamToUpdate = getTeam(team.getId());
teamToUpdate.setName(team.getName());
teamToUpdate.setRating(team.getRating());
Set<TeamMember> teamMember = team.getTeamMembers();
teamToUpdate.setTeamMembers(teamMember);
getCurrentSession().merge(teamToUpdate);
}
Team entity
#Entity
#Table(name="teams")
public class Team {
private Integer id;
private String name;
private Integer rating;
private Set<TeamMember> teamMembers;
// ...
#ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
#JoinTable(name = "team_member", joinColumns =
#JoinColumn(name = "FK_Team_id", referencedColumnName= "id"),
inverseJoinColumns = #JoinColumn(name = "FK_Member_id", referencedColumnName = "id")
)
public Set<TeamMember> getTeamMembers() {
return teamMembers;
}
public void setTeamMembers(Set<TeamMember> teamMembers) {
this.teamMembers = teamMembers;
}
}
Team mas ManyToMany relationship with Team members. On SQL level it's done using tables: teams, member, team_member.
What constraints are violated? How to fix it?
UPDATE:
CREATE TABLE `member` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(45) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `teams` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(45) NOT NULL,
`rating` int(11) NOT NULL,
`FK_Organization_id` int(11) NOT NULL,
PRIMARY KEY (`id`),
KEY `FK_Organization_id` (`FK_Organization_id`),
CONSTRAINT `FK_Organization_id` FOREIGN KEY (`FK_Organization_id`) REFERENCES `organization` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `team_member` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`FK_Member_id` int(11) NOT NULL,
`FK_Team_id` int(11) NOT NULL,
PRIMARY KEY (`id`),
CONSTRAINT `FK_Member_id` FOREIGN KEY (`id`) REFERENCES `member` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION,
CONSTRAINT `FK_Team_id` FOREIGN KEY (`id`) REFERENCES `teams` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
ERROR o.h.e.jdbc.spi.SqlExceptionHelper - Cannot add or update a child
row: a foreign key constraint fails (db.team_member,
CONSTRAINT FK_Member_id FOREIGN KEY (id) REFERENCES member
(id) ON DELETE NO ACTION ON UPDATE NO ACTION)
Data:
UPDATE3
public Team getTeam(int id) {
Team team = (Team) getCurrentSession().get(Team.class, id);
return team;
}
UPDATE4
P6Spy helped to discover error query:
insert into team_member (FK_Team_id, FK_Member_id) values (2, 2);
returning:
[SQL] insert into team_member (FK_Team_id, FK_Member_id) values (2, 2);
[Err] 1452 - Cannot add or update a child row: a foreign key constraint fails (`db`.`team_member`, CONSTRAINT `FK_Member_id` FOREIGN KEY (`id`) REFERENCES `member` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION)
Problem was in CONSTRAINT definition in team_member table. Instead of:
CONSTRAINT `FK_Member_id` FOREIGN KEY (`id`) REFERENCES `member` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION,
CONSTRAINT `FK_Team_id` FOREIGN KEY (`id`) REFERENCES `teams` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION
It has to be
CONSTRAINT `FK_Member_id` FOREIGN KEY (`FK_Member_id`) REFERENCES `member` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION,
CONSTRAINT `FK_Team_id` FOREIGN KEY (`FK_Team_id`) REFERENCES `teams` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION
In a spring mvc app using hibernate over MySQL, I am encountering problems when I try to create polymorphic subclasses that inherit their id from a BaseEntity. You can see my intended use when you read my AccessLog class below, which has properties of type BaseEntity. The actor_entity and target_entity properties should each be fillable with a variety of different types of entities, such as User, OutsideSystem, Document, etc., each of which inherit from BaseEntity.
How do I set this up in code?
Here is my current java:
#Entity
#Inheritance(strategy = InheritanceType.JOINED)
public class BaseEntity {
#Id
#GeneratedValue(strategy = GenerationType.TABLE)
protected Integer id;
//other stuff
}
#Entity
#Table(name="users")
public class User extends BaseEntity{
//other stuff
}
#Entity
#Table(name = "accesslogs")
public class AccessLog extends BaseEntity{
#ManyToOne
#JoinColumn(name = "actorentity_id")
private BaseEntity actor_entity;
#ManyToOne
#JoinColumn(name = "targetentity_id")
private BaseEntity target_entity;
#Column(name="action_code")
private String action;
}
Here is my current DDL:
CREATE TABLE IF NOT EXISTS baseentity(
id int(11) UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY
)engine=InnoDB;SHOW WARNINGS;
CREATE TABLE IF NOT EXISTS accesslogs(
id int(11) UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY,
actorentity_id int(11) UNSIGNED NOT NULL,
targetentity_id int(11) UNSIGNED NOT NULL,
action_code varchar(100),
access_date DATETIME
)engine=InnoDB;SHOW WARNINGS;
CREATE TABLE roles (
id int(11) UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY,
role varchar(20) NOT NULL
) ENGINE=InnoDB;
CREATE TABLE users (
id int(11) UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY,
login varchar(20) NOT NULL,
password varchar(20) NOT NULL
) ENGINE=InnoDB;
CREATE TABLE user_roles (
user_id int(11) UNSIGNED NOT NULL,
role_id int(11) UNSIGNED NOT NULL,
KEY user (user_id),
KEY role (role_id)
) ENGINE=InnoDB;
Why do you need BaseEntity annotate with Entity? You don't need to specify #Inheritance(strategy = InheritanceType.JOINED). BaseEntity should have #MappedSuperclass annotation
And you don't need to create baseentity table
I'm trying to find relevant JPA documentation, but having trouble finding anything that specifies if I am allowed to make an ElementCollection of an Entity. I know the typical use is to make an #ElementCollection of #Embeddable, but due to a Hibernate bug I encountered, I need to make my embeddable class into its own entity.
I would like to maintain the entity's lifecycle to be controlled by the parent class. Consequently, I am hoping not to create any DAO/Repository for the new entity.
Although Hibernate allows this to occur (it properly generates the DDL), I have not actually tested persistence of the parent entity yet.
Additionally, I have not been able to find any way to specify the join column mapping to the new entity.
For example, given:
public class User {
#TableGenerator( name="UUIDGenerator", pkColumnValue="user_id", table="uuid_generator", allocationSize=1)
#Id
#GeneratedValue(strategy = GenerationType.TABLE, generator="UUIDGenerator")
#Column(name = "id")
private Long id;
/**
* Address
*/
#Valid
#ElementCollection(fetch=FetchType.LAZY)
#CollectionTable(name="user_address", joinColumns=#JoinColumn(name = "user_id", referencedColumnName = "id"))
#OrderColumn
private List<Address> address;
}
and
#Entity
public class Address {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
#Column(name = "id")
private Long id;
/**
* Multiple street lines allowable
*/
#NotBlank
#ElementCollection(targetClass=String.class, fetch=FetchType.LAZY)
#CollectionTable( joinColumns=#JoinColumn(name = "address_id", referencedColumnName = "id"))
#OrderColumn
private List<String> street;
}
it generates the following MySQL tables:
CREATE TABLE `user` (
`id` bigint(20) NOT NULL,
PRIMARY KEY (`id`),
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `user_address` (
`user_id` bigint(20) NOT NULL,
`address` bigint(20) NOT NULL,
`address_order` int(11) NOT NULL,
PRIMARY KEY (`user_id`,`address_order`),
UNIQUE KEY `UK_m09f5sbmw3q9drll2qig9i07q` (`address`),
KEY `FK_m09f5sbmw3q9drll2qig9i07q` (`address`),
KEY `FK_kfu0161nvirkey6fwd6orucv7` (`user_id`),
CONSTRAINT `FK_kfu0161nvirkey6fwd6orucv7` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`),
CONSTRAINT `FK_m09f5sbmw3q9drll2qig9i07q` FOREIGN KEY (`address`) REFERENCES `address` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `address` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `address_street` (
`address_id` bigint(20) NOT NULL,
`street` varchar(255) DEFAULT NULL,
`street_order` int(11) NOT NULL,
PRIMARY KEY (`address_id`,`street_order`),
KEY `FK_jrcnrclixxqroefuqc7gjhoh` (`address_id`),
CONSTRAINT `FK_jrcnrclixxqroefuqc7gjhoh` FOREIGN KEY (`address_id`) REFERENCES `address` (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
I'd like to find a way to change the field name for user_address.address. So far, the only way I can figure out how to do this is to make it a #OneToMany mapping and use a #JoinTable() definition. Is there no way from within #ElementCollection?
You cannot have an ElementCollection containing Entities, these are mutually exclusive concepts in JPA.
You can try a one-to-many or many-to-many depending on your needs. If you set fetching to eager and cascade all it should be fine.
I'm trying to run a simple example which is just a mapping with a table and to print all the values stored in it.
I'm getting all my fields well except my id.
Here is my table when i do an export on it
CREATE TABLE `adress` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`streetNumber` tinyint(4) DEFAULT NULL,
`street` varchar(45) DEFAULT NULL,
`city` varchar(45) DEFAULT NULL,
`zipCode` int(11) DEFAULT NULL,
`state` varchar(45) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=latin1;
LOCK TABLES `adress` WRITE;
INSERT INTO `adress` VALUES (1,12,'Canada street','LOS ANGELES',441233,'California'),(2,54,'5th avenue','NEW YORK CITY',884769,'New York');
UNLOCK TABLES;
My Entity class :
#Entity
#Table(name = "adress")
#XmlRootElement
public class Adress implements Serializable {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Basic(optional = false)
#Column(name = "id")
private Integer id;
#Column(name = "streetNumber")
private Short streetNumber;
...
If i do a "findAll()" i'm able to get all my datas from the db.
But the id is null, all the other fields have their values
I have tried several stuff but i'm not going everywhere.
If someone can see where or about what is my mistake i'll appreciate a lot your help.
Thanks in advance
I'm in need of help with hibernate annotation, when I have a table with same parent id.
Like this example
CREATE TABLE `server` (
`server` int(11) DEFAULT NULL,
`name` varchar(20) DEFAULT NULL,
`parentid` int(11) DEFAULT NULL,
KEY `parentid` (`parentid`),
KEY `server` (`server`),
CONSTRAINT `server_fk` FOREIGN KEY (`parentid`) REFERENCES `server` (`server`)
);
Output like this
Server A
Server B
Server C
Server D
Server E
Server C
Server D
Server F
Server G
How can I map this in my Class
#Entity
public class Server {
#Id #GeneratedValue
private Long id;
private String name, description;
private Server parentid;
}