Tuesday, October 18, 2011

One to One association using foreign key

In One to One association using foreign key, one table will have a foreign key column that will reference the primary key column of the associated table.

Mapping using Hibernate XML mapping:

Let us go to the package com.demo.oneToOneUsingForeignKey and execute the java class OneToOneFKExecutor.java

Things to look into:

* The ORM classes User.java and Photo.java
* The xml mapping file oneToOneUsingForeignKey.hbm.xml

ORM:

public class User {

private long id;

private String name;

private Photo photo;

// getter and setter methods
}


public class Photo {

private long photoId;

private String fileName;

private User user;

// getter and setter methods
}

XML:

<hibernate-mapping auto-import="false">
<class name="com.demo.oneToOneUsingForeignKey.User" table="USER" lazy="false">
<id name="id" column="USER_ID" type="long">

lt;generator class="native" />
</id>
<property name="name" column="NAME" />
<one-to-one name="photo" class="com.demo.oneToOneUsingForeignKey.Photo" property-ref="user" />
</class>
<class name="com.demo.oneToOneUsingForeignKey.Photo" table="PHOTO" lazy="false">
<id name="photoId" column="PHOTO_ID" type="long">
<generator class="native" />

</id>

<property name="fileName" column="FILE_NAME" />

<many-to-one name="user" class="com.demo.oneToOneUsingForeignKey.User" column="USER_ID" cascade="save-update" unique="true" />
</class>
</hibernate-mapping>

* The <one-to-one> represents the one-to-one association from User to Photo
* property-ref declares that the photo property of the User class is the inverse of a property on the other side of the association.
* <many-to-one&gt; - Here the one-to-one is accomplished using the combination of many-to-one and unique="true". If we simply use the many-to-one then the whole point of one-to-one will be missed. In order to achieve that we apply an additional constraint unique="true" by which the foreign key column will not have the duplicate values , hence fulfilling our one-to-one association.
* unique="true" is unique constraint applied on the foreign key column to avoid the duplicate values in that column.
* cascade represents that if the cascade side of the entity is saved then the other side of the entity will automatically saved by the hibrenate.

Once the OneToOneFKExecutor.java is executed, verify the results in the eclipse console and as well as in the HSQL DB manager by running the simple select queries on the tables USER and PHOTO as follows.



Mapping using Annotations:

Let us go to the package annotation.com.demo.oneToOneUsingForeignKey and execute the class OneToOneFKAnnotationExecutor.java

Things to look into:

The ORM classes User.java and Photo.java

ORM:

@Entity
@Table(name="PHOTO")
public class Photo {

@Id
@GeneratedValue(strategy=GenerationType.AUTO)
@Column(name="PHOTO_ID")
private long photoId;

@Column(name="FILE_NAME")
private String fileName;

@OneToOne(cascade=CascadeType.ALL,fetch=FetchType.EAGER)
@JoinColumn(name="USER_ID",unique=true)
private User user;

// getter and setter methods
}


@Entity(name="annotation.com.demo.oneToOneUsingForeignKey.User")
@Table(name="USER")
public class User {
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
@Column(name="USER_ID")
private long id;

@Column(name="NAME")
private String name;

@OneToOne(mappedBy="user")
private Photo photo;

// getter and setter methods
}

* The annotation @OneToOne is to declare the one-to-one association
* The annotation @JoinColumn is used to describe the foreign key column
* unique="true" applies the unique constraint on the foreign key column.
* mappedBy is equal to property-ref in the xml.

Once the class OneToOneFKAnnotationExecutor.java is executed, verify the results as described above.