@OneToMany - relacja jedno i dwukierunkowa

Relacja @OneToMany jest to połączenie dwóch tabel za pomocą klucza głównego jednej tabeli i klucza obcego drugiej tabeli. Relacje jednokierunkową w hibernejcie realizujemy na encjach, dzięki temu struktura tabel w bazie danych pozostaje niezmieniona.





✅ Stworzenie tabel w bazie danych 


CREATE DATABASE IF NOT EXISTS `bazatestowa2`;

USE `bazatestowa2`;

CREATE TABLE IF NOT EXISTS owner (

    owner_id INT AUTO_INCREMENT,

    full_name VARCHAR(40) DEFAULT NULL,

    PRIMARY KEY (owner_id)

) ENGINE=InnoDB;


CREATE TABLE IF NOT EXISTS car (

    car_id INT AUTO_INCREMENT,

    brand VARCHAR(40) DEFAULT NULL,

    owner_id INT,

    PRIMARY KEY (car_id),

    CONSTRAINT FK_OWNER_CAR FOREIGN KEY (owner_id) REFERENCES owner (owner_id)

) ENGINE=InnoDB;








 Stworzenie klas Entity w relacji jednokierunkowej


❗ W relacji jednokierunkowej w hibernejcie nie mapujemy klucza obcego, ponieważ tworzymy relacje z Owner do Car jak lista, więc dostęp jest jednokierunkowy

👉 Entity Owner

package myhibernate.onedirection.entity;

import java.util.ArrayList;
import java.util.List;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.OneToMany;
import javax.persistence.Table;

@Entity
@Table(name = "owner")
public class Owner {

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "owner_id")
private long ownerId;

@Column(name = "full_name")
private String fullName;
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
@JoinColumn(name="owner_id")
List<Car> cars;

public String getFullName() {
return fullName;
}

public void setFullName(String fullName) {
this.fullName = fullName;
}
public List<Car> getCars() {
return cars;
}

public void setCars(List<Car> cars) {
this.cars = cars;
}
public void AddCar(Car car) {
if (cars == null) {
cars = new ArrayList<Car>();
}
cars.add(car);
}

@Override
public String toString() {
return "Owner [ownerId=" + ownerId + ", fullName=" + fullName + "]";
}

}

👉 Entity Car 

package myhibernate.onedirection.entity;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;

@Entity
@Table(name="car")
public class Car {

@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
@Column(name="car_id")
private long carId;
@Column(name="brand")
private String brand;
public Car() {
}
public Car(String brand) {
super();
this.brand = brand;
}

public String getBrand() {
return brand;
}

public void setBrand(String brand) {
this.brand = brand;
}

@Override
public String toString() {
return "Car [carId=" + carId + ", brand=" + brand + "]";
}
}




 Stworzenie klas Entity w relacji dwukierunkowej


❗ Relacje dwukierunkową w hibernejcie realizujemy na encjach, dzięki temu struktura tabel w bazie danych pozostaje niezmieniona.

👉 Entity Owner

package myhibernate.twodirection.entity;

import java.util.ArrayList;
import java.util.List;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

@Entity
@Table(name = "owner")
public class Owner {

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "owner_id")
private long ownerId;

@Column(name = "full_name")
private String fullName;

@OneToMany(mappedBy = "ownerId", cascade = CascadeType.ALL)
List<Car> cars;

public String getFullName() {
return fullName;
}

public void setFullName(String fullName) {
this.fullName = fullName;
}

public void AddCar(Car car) {
if (cars == null) {
cars = new ArrayList<Car>();
}
car.setOwnerId(this);
cars.add(car);
}

public List<Car> getCars() {
return cars;
}

public void setCars(List<Car> cars) {
this.cars = cars;
}

@Override
public String toString() {
return "Owner [ownerId=" + ownerId + ", fullName=" + fullName + "]";
}

}

w polu mappedBy podajemy nazwę pola z klasy, która na bazie ma w sobie klucz [Foreign Key]. W tym przypadku jest to pole ownerId z klasy Car. 


👉 Entity Car

package myhibernate.twodirection.entity;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

@Entity
@Table(name="car")
public class Car {

@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
@Column(name="car_id")
private long carId;
@Column(name="brand")
private String brand;
@ManyToOne(cascade= { CascadeType.DETACH, CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH })
@JoinColumn(name="owner_id")
private Owner ownerId;
public Car() {
}
public Car(String brand) {
super();
this.brand = brand;
}

public String getBrand() {
return brand;
}

public void setBrand(String brand) {
this.brand = brand;
}

public Owner getOwnerId() {
return ownerId;
}

public void setOwnerId(Owner ownerId) {
this.ownerId = ownerId;
}

@Override
public String toString() {
return "Car [carId=" + carId + ", brand=" + brand + "]";
}
}



 Klasa testująca dodawanie obiektu w relacji jednokierunkowej


👉 Klasa testująca

package myhibernate.onedirection;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import myhibernate.onedirection.entity.Car;
import myhibernate.onedirection.entity.Owner;

public class AddOneToManyApp {

public static void main(String[] args) {

Configuration conf = new Configuration();
conf.configure("hibernate.cfg.xml");
conf.addAnnotatedClass(Owner.class);
conf.addAnnotatedClass(Car.class);
SessionFactory factory = conf.buildSessionFactory();
Session session = factory.getCurrentSession();

session.beginTransaction();

//create owner
Owner owner = new Owner();
owner.setFullName("Jan Kowalski12");

//create car
Car car1 = new Car("BMW12");
Car car2 = new Car("OPEL12");

//create relation for owner
owner.AddCar(car1);
owner.AddCar(car2);

session.save(owner);

session.getTransaction().commit();
factory.close();
}
}

❗ Wynik działania w konsoli: 




❗Wynik w bazie danych: 

1. tabela owner


2. tabela car






 Klasa testująca usuwanie obiektu w relacji jednokierunkowej


❗ Aktualy stan w bazie danych:

1. tabela owner




2. tabela car



👉 Klasa testująca

package myhibernate.onedirection;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.query.Query;

import myhibernate.onedirection.entity.Car;
import myhibernate.onedirection.entity.Owner;

public class DeleteOneToManyApp {

public static void main(String[] args) {
Configuration conf = new Configuration();
conf.configure("hibernate.cfg.xml");
conf.addAnnotatedClass(Owner.class);
conf.addAnnotatedClass(Car.class);
SessionFactory factory = conf.buildSessionFactory();
Session session = factory.getCurrentSession();
session.beginTransaction();
String sql = "select distinct o from Owner o left join fetch o.cars ";
Query<Owner> query = session.createQuery(sql);
for(Owner owner : query.list()) {
System.out.println("Owner istnieje w baze:" + owner);
session.delete(owner);
System.out.println("Owner skasowany.");
}
session.getTransaction().commit();
factory.close();
}
}


❗ Wynik działania w konsoli: 




❗ Wynik w bazie danych: 

1. tabela owner




2. tabela car








 Klasa testująca odczytywanie obiektu w relacji jednokierunkowej


❗ Aktualy stan w bazie danych:

1. tabela owner


2. tabela car


👉 Klasa testująca

package myhibernate.onedirection;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.query.Query;

import myhibernate.onedirection.entity.Car;
import myhibernate.onedirection.entity.Owner;

public class ReadOneToManyApp {

public static void main(String[] args) {
Configuration conf = new Configuration();
conf.configure("hibernate.cfg.xml");
conf.addAnnotatedClass(Owner.class);
conf.addAnnotatedClass(Car.class);
SessionFactory factory = conf.buildSessionFactory();
Session session = factory.getCurrentSession();
session.beginTransaction();
String sql = "select distinct o from Owner o join fetch o.cars ";
Query<Owner> query = session.createQuery(sql);
for(Owner owner : query.list()) {
System.out.println("Owner istnieje w baze:" + owner);
for(Car car : owner.getCars()) {
System.out.println("Car: " + car);
}
}
session.getTransaction().commit();
factory.close();
}

}

❗ Wynik działania w konsoli: 




 Klasa testująca dodawanie obiektu w relacji dwukierunkowej 


👉 Klasa testująca

package myhibernate.twodirection;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;

import myhibernate.twodirection.entity.Car;
import myhibernate.twodirection.entity.Owner;

public class AddOneToManyApp {

public static void main(String[] args) {
Configuration conf = new Configuration();
conf.configure("hibernate.cfg.xml");
conf.addAnnotatedClass(Owner.class);
conf.addAnnotatedClass(Car.class);
SessionFactory factory = conf.buildSessionFactory();
Session session = factory.getCurrentSession();
session.beginTransaction();
//create owner
Owner owner = new Owner();
owner.setFullName("Jan Kowalski12");
//create car
Car car1 = new Car("BMW12");
Car car2 = new Car("OPEL12");
//create relation for owner
owner.AddCar(car1);
owner.AddCar(car2);
session.save(owner);
session.getTransaction().commit();
factory.close();
}
}

❗ Wynik działania w konsoli: 





❗Wynik w bazie danych: 

1. tabela owner



2. tabela car





 Klasa testująca usuwanie obiektu w relacji dwukierunkowej


Dzięki relacji dwukierunkowej, możemy w łatwy sposób dostać się do obiektu Car mając obiekt Owner

❗ Aktualy stan w bazie danych:

1. tabela owner


2. tabela car

👉 Klasa testująca

package myhibernate.twodirection;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.query.Query;
import myhibernate.twodirection.entity.Car;
import myhibernate.twodirection.entity.Owner;

public class DeleteOneToManyApp {
public static void main(String[] args) {

Configuration conf = new Configuration();
conf.configure("hibernate.cfg.xml");
conf.addAnnotatedClass(Owner.class);
conf.addAnnotatedClass(Car.class);
SessionFactory factory = conf.buildSessionFactory();
Session session = factory.getCurrentSession();

session.beginTransaction();

//kasowanie pustych Car oraz Car i połączonych z nim Owner
String sqlCars = "select distinct c from Car c left join fetch c.ownerId ";
Query<Car> queryCars = session.createQuery(sqlCars);
for(Car car : queryCars.list()) {
System.out.println("Car istnieje w baze:" + car);

session.delete(car);
if (car.getOwnerId() != null) {
session.delete(car.getOwnerId());
}

System.out.println("Car skasowany.");
}

//kasowanie pustych Owner oraz Owner i połączonych z nim Car
String sqlOwner = "select distinct o from Owner o left join fetch o.cars ";
Query<Owner> queryOwner = session.createQuery(sqlOwner);
for(Owner owner : queryOwner.list()) {
System.out.println("Owner istnieje w baze:" + owner);

session.delete(owner);
System.out.println("Owner skasowany.");
}

session.getTransaction().commit();
factory.close();
}
}

❗ Wynik w bazie danych: 

1. tabela owner




2. tabela car





 Klasa testująca odczytywanie obiektu w relacji dwukierunkowej


Dzięki relacji dwukierunkowej, możemy w łatwy sposób dostać się do obiektu Car mając obiekt Owner

❗ Aktualy stan w bazie danych:

1. tabela owner



2. tabela car


👉 Klasa testująca

package myhibernate.twodirection;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.query.Query;
import myhibernate.twodirection.entity.Car;
import myhibernate.twodirection.entity.Owner;

public class ReadOneToManyApp {
public static void main(String[] args) {

Configuration conf = new Configuration();
conf.configure("hibernate.cfg.xml");
conf.addAnnotatedClass(Owner.class);
conf.addAnnotatedClass(Car.class);

SessionFactory factory = conf.buildSessionFactory();
Session session = factory.getCurrentSession();

session.beginTransaction();

String sql = "select distinct o from Owner o join fetch o.cars ";
Query<Owner> query = session.createQuery(sql);
for(Owner owner : query.list()) {
System.out.println("Owner istnieje w baze:" + owner);

for(Car car : owner.getCars()) {
System.out.println("Car: " + car);
}
}

session.getTransaction().commit();
factory.close();
}
}

❗ Wynik działania w konsoli: 








Brak komentarzy:

Prześlij komentarz