hi
let me try to explain my little problem a more concret.
I have made a sample to demonstrate it. So here are the mapping and the testclasses:
Code:
<class name="de.informaticum.orm.hibernate.test.EntityA" table="entityA" >
<id name="id" column="id" type="java.lang.Long" unsaved-value="-1">
<generator class="native">
<param name="sequence">entitya_seq</param>
</generator>
</id>
<natural-id >
<property name="uniquekey1" />
<property name="uniquekey2" />
</natural-id>
<property name="nonunique" />
</class>
I have a little helperclass to use the springframework with the HibernateTemplate.
Code:
public class EntityManager {
private static final Logger log = Logger.getLogger(EntityManager.class);
HibernateTemplate ht= null;
public EntityManager(HibernateTemplate tm) {
this.ht = tm;
}
// load the last Row of the DB-Table
public EntityA loadLastRow() {
List<EntityA> list=null;
try {
list = ht.find("from EntityA a");
} catch (DataAccessException e) {
log.error(e.getMessage());
}
if (list!=null && list.size()>0) {
return list.get(list.size()-1);
}
return null;
}
// merge the EntityA to the DB and get an actual instance.
public EntityA merge(EntityA entity) {
try {
return (EntityA) ht.merge(entity);
} catch (DataAccessException e) {
log.error(e.getMessage());
return null;
}
}
}
The testmain :
Code:
public class TestMain {
/**
* @author Martin Sachs
* @since 24.05.2006
* @param args
*/
public static void main(String[] args) {
...
HibernateTemplate ht = null;
...
// getting the hibernateTemplate here
...
EntityManager manager = new EntityManager(ht );
// create new Object
EntityA entity = new EntityA(1L,new Date().getTime(),"value");
// store Object to DB
manager.merge(entity);
// get last row
EntityA loadedEntity = manager.loadLastRow();
if (loadedEntity!=null) {
System.out.println(loadedEntity.toString());
}else {
System.out.println("no row fetched");
}
if (loadedEntity!=null) {
// modify Object
loadedEntity.setNonunique("changed value");
// setting id to -1, because it could be transient or generated
// by someone manually
---> loadedEntity.setId(-1L); <<---- here is my problem
I want to the the ID to -1 but i want to update the DB-Row with a merge.
// store modified entity
System.out.println("Store modified entity");
EntityA storedEntity = manager.merge(loadedEntity);
if (storedEntity!=null) {
System.out.print("modification stored: ");
System.out.println(loadedEntity.toString());
}else {
System.out.println("modification not stored");
}
}
...
}
}
}
My Question is:
Is there a way to map a class with an id as primary key and unique key as natural-id to decide whether the unique key is allready in DB or not (hibernate make update or instert by natural-id and not by primary id) ?
If you ask why not by primary key: The primary key should never be tranported over the Database layer. So i want to make the ID transient and transport the mapping object to the client. (Dettached object)
I know that i can select each object and get the IDs bevor i merge. Can hibernate help in that case ???
Martin Sachs
the class EntityA:
Code:
public class EntityA implements java.io.Serializable{
private transient Long id = -1L;
private Long uniquekey1;
private Long uniquekey2;
private String nonunique;
...
// getter and setter
...
}
[/code]