To make it clearer, I'll illustrate the different approaches I've identified and how our project differs from that. (Appologies for the table formats, I couldn't get them to look better.)
From what I can tell most people implement valid time temporal databases with hibernate by doing something like:
Schema 1A
Person
ID PersonName
-- --------------
1 Sally
2 Bob
PersonHistory
ID ValidFrom ValidTo FkEmployerId Salary
-- ----------- -------- --------------- -------
1 2007/6/1 2007/9/1 1 40,000
1 2007/9/2 2007/10/1 2 45,000
2 2007/6/1 9999/12/31 1 22,000
Employer
ID EmployerName
-- ----------------
1 Ms Jones
2 Mr Xavier
EmployerHistory
ID ValidFrom ValidTo EmployerAddress
-- ----------- -------- ----------------
1 2007/6/1 9999/12/31 Smith St
2 2007/6/1 9999/12/31 Hopps Rd
However, our schema, if we implemented it in a similar fashion, would look like:
Schema 1B
Person
ID
--
1
2
PersonHistory
ID ValidFrom ValidTo FkEmployerId PersonName Salary
-- ----------- -------- --------------- --------------- -------
1 2007/6/1 2007/9/1 1 Sally 40,000
1 2007/9/2 2007/10/1 2 Sally 45,000
2 2007/6/1 9999/12/31 1 Bob 22,000
Employer
ID
--
1
2
EmployerHistory
ID ValidFrom ValidTo EmployerName EmployerAddress
-- ----------- -------- ---------------- ----------------
1 2007/6/1 9999/12/31 Ms Jones Smith St
2 2007/6/1 9999/12/31 Mr Xavier Hopps Rd
By that I mean the Person table would have nothing but the surrogate ID in it. And our entire database is like this! (Obviously, this isn't the best example because one normally *would* record the PersonName/EmployerName in the People/Employer table, but nowhere in our schema would we do something similar). So, our database is like:
Schema 2
Person
ID ValidFrom ValidTo FkEmployerId PersonName Salary
-- ----------- -------- --------------- --------------- -------
1 2007/6/1 2007/9/1 1 Sally 40,000
1 2007/9/2 2007/10/1 2 Sally 45,000
2 2007/6/1 9999/12/31 1 Bob 22,000
Employer
ID ValidFrom ValidTo EmployerName EmployerAddress
-- ----------- -------- ---------------- ----------------
1 2007/6/1 9999/12/31 Ms Jones Smith St
2 2007/6/1 9999/12/31 Mr Xavier Hopps Rd
-------------------------------------------------
Hibernate
There isn't a problem with the schema 1 type of temporal database, we use filters. However, with ours - schema 2 - we need filters on the Many-to-One relationships, but Hibernate doesn't implement the filter on such a relationship. And we have no way, from what I have found, to integrate this schema 2 type of database with Hibernate.
Schema 1A mapping
Code:
<id name="ID">
<column name="ID" sql-type="integer" not-null="true"/>
</id>
<property name="Name">
<column name="PersonsName" not-null="true" />
</property>
<bag name="Details">
<key column="ID"/>
<one-to-many class="PeopleHistory"/>
<filter name="effectiveDate" condition=":Period between ValidFrom and ValidTo"/>
</bag>
<many-to-one name="Employer" column="ID" />
Since the Many-to-One of Employer maps to a unique ID, Hibernate has no problems. We can then do something like: aPerson.Employer.Details.EmployerAddress
Schema 2 mappingCode:
<id name="ID">
<column name="ID" sql-type="integer" not-null="true"/>
</id>
<property name="Name">
<column name="PersonName" not-null="true" />
</property>
<property name="Salary">
<column name="Salary" not-null="true" />
</property>
<many-to-one name="Employer" column="ID">
<filter name="effectiveDate" condition=":Period between ValidFrom and ValidTo"/>
</many-to-one>
We'd want to be able to do something like: aPerson.Employer.EmployerAddress, but of course it doesn't work because there is no filter being applied to the Many-to-One relationship.
Right now I am having a look at the NHibernate code to see if I can implement the change displayed at
http://forum.hibernate.org/viewtopic.php?t=976233, and wouldn't mind contributing it to the next version if it gets accepted, though I have never contributed anything to a open source project, and I'm not sure how to go about it.