Reputation: 41
I have legacy db.
+----+ +------------+ +------------+
|Site| |Content | |Program |
+----+ +------------+ +------------+
|id | |id:PK | |siteId:PK,FK|
|name| |siteId:FK | |code:PK |
+----+ |prog_code:FK| |name |
|prog_param | +------------+
+------------+
Table Content have one PK column. siteId columns is not part of PK. Table Program have two PK column(siteId, code). It is composite PK. this table work as template. Only variable in program is parameter and it is on table Content's prog_param column.
I want to map this table to object like this.
+-----------+ +------------+ +-----------+ +---------------+
|Site | |Program | |ProgramId | |Content |
+-----------+ +------------+ +-----------+ +---------------+
|id:long | |id:ProgramId| |site:Site | |id:long |
|name:String| |name:String | |code:String| |site:Site |
+-----------+ |param:String| +-----------+ |program:Program|
+------------+ +---------------+
but i don't know how to mapping the 'Content' and 'Program' in this complex situation.
So, I have tried to make situation simple. I have mapped prog_param to Content
+-----------+ +------------+ +-----------+ +-------------------+
|Site | |Program | |ProgramId | |Content |
+-----------+ +------------+ +-----------+ +-------------------+
|id:long | |id:ProgramId| |site:Site | |id:long |
|name:String| |name:String | |code:String| |site:Site |
+-----------+ +------------+ +-----------+ |program:Program |
|programParam:String|
+-------------------+
as code
@Entity
@Table(name = "SITE")
@Getter @Setter
public class Site {
@Id
@Column(name = "SITE")
protected String id;
@Column(name = "NAME")
protected String name;
}
@Entity
@Table(name = "PROGRAM")
@Getter @Setter
public class Program {
@EmbeddedId
protected ProgramId id;
@Column(name = "NAME")
protected String name;
}
@Embeddable
@Getter @Setter @EqualsAndHashCode
public class ProgramId implements Serializable{
@ManyToOne
@JoinColumn(name = "SITE")
protected Site site;
@Column(name = "code")
protected String code;
}
@Entity
@Table(name="CONTENT")
@Getter
@Setter
public class Content {
@Id
@Column(name = "ID")
protected Long id;
@ManyToOne
@JoinColumn(name = "SITEID",referencedColumnName="SITE")
protected Site site;
@OneToOne
@JoinColumns({
@JoinColumn(name="SITEID",referencedColumnName="SITE"),
@JoinColumn(name="PROG_CODE",referencedColumnName="CODE"),
})
protected Program program;
}
But this is not work. Hibernate throw 'Repeated column in mapping for entity' exception.
So I have research some solutions. Finally I found this 'Repeated column in mapping for entity' Exception throwed when Hibernated can not determine to use which property.
Stackoverflows's solution is set 'insertable=false, updatable=false' to @JoinColumn, so let hibernate can determine to use which property.
I want use Content's property 'site' because it is used very frequently. And Site and Program property is used separately in my application.
So I try to set 'insertable=false, updatable=false' to Content's property 'program'
@OneToOne
@JoinColumns({
@JoinColumn(name="SITEID",referencedColumnName="SITE", insertable=false, updatable=false),
@JoinColumn(name="PROG_CODE",referencedColumnName="CODE"),
})
protected Program program;
This is not work too. 'Mixing updatable and non updatable columns in a property is not allowed' exception is throwed.
So I have set set 'insertable=false, updatable=false' to 'PROG_CODE', of course, Hibernate do not change PROG_CODE when I set different prog_code.
At this point, I have no idea.
Please let me know some idea to solve this situation.
Upvotes: 3
Views: 1105
Reputation: 59
I am having the same issue, two composite keys sharing an attribute fails with "Repeated column in mapping for entity". I think this might be a bug, ref: https://hibernate.atlassian.net/browse/HHH-4582. I am using Hibernate 3.6.4
Upvotes: 1