I have a simple JOINED hierarchy of documents:
CREATE TABLE Documents
(
id INTEGER NOT NULL,
discriminator ENUM('official','individual','external') NOT NULL,
file_name VARCHAR(200) NOT NULL,
PRIMARY KEY (id)
);
CREATE SystemDocuments
(
id INTEGER NOT NULL,
binary_data BLOB NOT NULL,
PRIMARY KEY (id),
FOREIGN KEY (id) REFERENCES Documents (id)
);
CREATE ExternalDocuments
(
id INTEGER NOT NULL,
PRIMARY KEY (id),
FOREIGN KEY (id) REFERENCES SystemDocuments (id)
);
As you can see all the sub tables do is share the same ID from the Documents table. Other than that SystemDocuments
adds a binary_data
column and ExternalDocuments
adds no new properties. (Also note there are two other concrete sub tables in the hierarchy denoted by 'official'
and 'individual'
which are of no relevance here.)
Here are the mappings for the above tables:
Document.java:
@Entity
@Table(name = "Documents")
@Inheritance(strategy = InheritanceType.JOINED)
@DiscriminatorColumn(name = "discriminator", discriminatorType = DiscriminatorType.STRING)
//@DiscriminatorOptions(force = true) // <-- Hibernate 4-specific annotation not inserting discriminator values
public abstract class Document implements Serializable
{
@Id
@Column
protected Integer id;
@Column(name = "file_name")
protected String fileName;
...
}
SystemDocument.java:
@Entity
@Table(name = "SystemDocuments")
public abstract class SystemDocument extends Document
{
@Lob
@Column(name = "binary_data")
protected byte[] binaryData;
...
}
ExternalDocument.java:
@Entity
@Table(name = "ExternalDocuments")
@DiscriminatorValue(value = "external")
public class ExternalDocument extends SystemDocument
{
...
}
The latter class is supposed to be mapped to the Documents' discriminator column value 'external'
. When finding entities via EntityManager.find the discriminators are returned correctly, well actually because the discriminators of my test data have been INSERTed into the DB correctly.
Now I use the following code to insert new documents/files into the system via JPA and a file uploader:
...
UploadedFile uf = event.getUploadedFile();
// set ID, file name, and binary data
ExternalDocument detachedExternalDocument =
new ExternalDocument(1234567, uf.getName(), uf.getData());
docService.create(detachedExternalDocument);
When inspecting the DB however I can see that Hibernate does not insert the 'external'
discriminator value into the Documents
table's discriminator
column.
There have been issues about this in the past, see https://hibernate.onjira.com/browse/ANN-140 and more recently for Hibernate 4 https://hibernate.onjira.com/browse/HHH-4358, so chances are it's supposed to work that way.
I then found http://docs.jboss.org/hibernate/core/4.0/javadocs/org/hibernate/annotations/DiscriminatorOptions.html in the current Hibernate 4 API Docs, but it doesn't work (see @DiscriminatorOptions at the Document class).
How can I get Hibernate 4 to insert the discriminators using raw annotations?
Note: I don't want to map the discriminator column as a regular column.
See Question&Answers more detail:
os