Spring-Hibernate0

1 using JPA annotation

@Entity // this class is entity bean

@Table(name = "student")

@Column(name = "id")

2. Two Key Players

3. Hibernate and Primary Keys

Hibernate 5

@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
@Column(name="id")
private int id;

3.1 ID Generation Strategies

3.2 define your own CUSTOM generation strategy

  • create subclass of org.hibernate.id.SequenceGenerator

  • Override the method: public Serializable generate(...)

3.3 changing the index

SQL

ALTER TABLE pets.student AUTO_INCREMENT=3000  //BEGIN WITH 3000
truncate pets.student   // delete all rows in database then begin the new item from 1

3.4 retrieving an object

Student myStudent = session.get(Student.class, tempStudent.getId());

3.5 Querying Object

hibernate 5.2+

session.createQuery("from Student").getResultList();

e.g.

        //create session factory
        SessionFactory factory = new Configuration().configure("hibernate.cfg.xml").addAnnotatedClass(Student.class).buildSessionFactory();
        //create session
        Session session = factory.getCurrentSession();

        try{

            //start a transaction
            session.beginTransaction();

            //query students
            List<Student> theStudents= session.createQuery("from Student").list();

            //display the students
            for(Student tempStudent:theStudents){
                System.out.println(tempStudent);
            }            

            //commit transaction
            session.getTransaction().commit();

            System.out.println("Done!");
        }finally{
            factory.close();
        }

e.g.

                List<Student> theStudents= session.createQuery("from Student").list();
        //display the students            
        displayStudents(theStudents);            
        //query students: last name = "poter"
        theStudents = session.createQuery("from Student s where s.lastName='Potter' OR s.firstName='Daffy'").list();
        System.out.println("Student with last name potter: ");
               displayStudents(theStudents);

3.6 Updating Objects

try{
            int studentId = 1;            
            session=factory.getCurrentSession();
            session.beginTransaction();            
            System.out.println("\n Getting student with id: "+ studentId);            
            Student myStudent = session.get(Student.class, studentId);
            //commit transaction            
            System.out.println("Get complete: "+ myStudent);
             //update email for all student
         session.createQuery("update Student set email='foo@gmail.com'").executeUpdate();

            session.getTransaction().commit();
            System.out.println("Done!");
        }finally{
            factory.close();
        }

3.7 Delete a Student

e.g.1

Student myStudent = session.gett(Student.class, studentId);
//delete the student
session.delete(myStudent);
//commit the transaction
session.getTransaction().commit();

e.g.2

session.createQuery("delete from Student where id=2").executeUpdate();//executeUpdate() is used for updates or delete

4. Advanced Mapping

  • One-to-One

  • Many-to-One, One-to-Many

  • Many-to-Many

Uni-Directional: One -to- One

4.1 Primary Key and Foreign Key

  • Primary key: identify a unique row in a table

  • Foreign Key:

    • Link tables together

    • a field in one table that refers to primary key in another table

4.2 Cascade

  • You can cascade operations

  • Apply the same operation to related entities

  • By default, no operations are cascaded.

e.g

If we delete an instructor, we should also delete their instuctor_detail

This is known as "CASCADE DELETE". It depends on the use case.

4.3 Eager vs Lazy Loading

Eager will retrieve everything

Lazy will retrieve on request

4.4 Create Instructor class - @OneToOne

@Entity
@Table(name="instructor")
public class Instructor{

...
@OneToOne
@JoinColumn(name="instructor_detail_id")
private InstructorDetail instructorDetail;
...
}

5 Entity Lifecycle

5.1.1 - Cascade Type

Persist, Remove, Refresh, Detach, Merge, All.

configure cascade Type

...
@OneToOne(cascade=CascadeType.ALL)

configure cascade Type

@OneToOne(cascade={CascadeType.DETACH,CascadeType.MERGE})

5.1.2 @OneToOne Bi-Directional

public class InstructorDetail{
...
@OneToOne(mappedBy="instructorDetail", cascade=CascadeType.ALL)
private Instructor instructor;

mappedBy tells Hibernate

  • Look at the instructorDetail property in the Instructor class

  • Use information from the Instructor class @JoinColumn

  • To help find associated instructor

5.1.3 Code Refactoring Add Exception Handling

try{
...
}catch(Exception e){
    e.printStackTrace();
}finally{
    //handle connection leak issue
    session.close();
    factory.close();
}

5.1.4 Only delete InstructorDetail keep the Instructor

remove the associated object reference

break bi-directional link

public class InstructorDetail{
...
@OneToOne(mappedBy="instructorDetail", cascade={CascadeType.DETACH, CascadeType.MERGE})
private Instructor instructor;

cascade: Do not apply cascading deletes!

//main app
System.out.println("Deleting tempInstructorDetail.");
//remove the associated object reference
//break bi-directional link
tempInstructorDetail.getInstructor().setInstructorDetail(null);//break link when cascade=CascadeType.ALL
session.delete(tempInstructorDetail);//delete

5.2 @OneToMany

  • An instructor can have many courses

  • Bi-directional

Many-to-One Mapping

  • Many courses can have one instructor

  • Inverse / opposite of One-to-Many

Real-World Project Requirement

  • If you delete an instructor, DO NOT delete the courses

  • If you delete a course, DO NOT delete the instrucrot

@Entity
@Table(name="instructor")
public class Instructor{
...
@OneToMany(mappedBy="instructor", cascade={CascadeType.PERSIST, CascadeType.MERGE...})//Refers to "instructor" property in "Course" class
private List<Course> courses;

When add support for Cascading:

Do not apply cascading deletes!

5.2.1 @JoinColumn & @mappedBy

@JoinColumn

A Join Column in JPA is a column in the owner entity that refers to a key (usually a primary key) in the non-owner or inverse entity. The first thing that comes to mind after reading the above line is that JoinColumns are nothing but a Foreign Key Columns. And it is indeed the case. JPA calls them Join Columns, possibly because they are more verbose in what their actual role is, to join the two entities using a common column.

Another thing to notice above is that we have used the terms owner and non-owner entities. For easy rememberability, the entity that has a join column is always the owning entity.

@mappedBy

@OneToOne(mappedBy="instructorDetail")//instructor is the owner of the relationship. 
private Instructor instructor;

The field that owns the relationship. Required unless the relationship is unidirectional.

Last updated