Descrizione

L'approccio successivo alla memorizzazione di una gerarchia di classi consiste nell'archiviare tutte le classi nella gerarchia in un'unica tabella . Questa strategia si chiama Single Table .

Ad esempio, in questo modo:

CREATE TABLE user_ employee_client {
  id INT,
  name VARCHAR,
  birthday DATE,
  occupation VARCHAR,
  salary INT,
  join DATE,
  address VARCHAR,
  DTYPE VARCHAR
}

Cioè, abbiamo una tabella, in cui le colonne per tutte le classi della nostra gerarchia sono contrassegnate con colori diversi. C'è anche una colonna di servizio speciale DTYPE VARCHAR , dove Hibernate memorizzerà il nome della classe Entity.

L'unica cosa che resta da fare è spiegare a Hibernate che i dati delle classi Entity sono ora memorizzati nel database in una tabella. Questo può essere fatto usando l' annotazione @Inheritance :

@Inheritance(strategy = InheritanceType.SINGLE_TABLE)

Un esempio delle nostre classi:

@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@Entity
class User {
  int id;
  String name;
  LocalDate birthday;
}
@Entity
class Employee extends User {
 	String occupation;
 	int salary;
 	LocalDate join;
}
@Entity
class Client extends User {
   String address;
}

Come vengono archiviati i dati

Ora scriviamo un esempio in cui creiamo un paio delle nostre entità e le salviamo nel database:

Employee employee = new Employee();
employee.id = 101;
employee.name = "Ivanov";
employee.birthday = LocalDate.of("01-01-1999");
employee.occupation = "Programmer"
employee.salary = 100000;
employee.join = LocalDate.of("12-01-2018");
session.persist(employee);

Client client = new Client();
client.id = 102;
client.name = "Petrov";
client.birthday = LocalDate.of("15-11-1988");
client.address = "Shandara";
session.persist(client);

Durante il salvataggio nel database, verrà eseguita la seguente query SQL:

INSERT INTO user_ employee_client (id, name, birthday, occupation, salary, join, DTYPE)
VALUES (101, 'Ivanov', '01-01-1999', 'Programmer', 100000, '12-01-2018', 'Employee')

INSERT INTO user_ employee_client (id, name, birthday, address, DTYPE)
VALUES (102, 'Petrov', '15-11-1988', 'Shandara', 'Client')

Quando si salvano i dati in una tabella, Hibernate gli passa solo i campi di entità noti. Ciò significa che le colonne non specificate saranno NULL.

E questo significa che non puoi specificare il tipo NOT NULL per la colonna occupazione, poiché quando un cliente è memorizzato nella stessa tabella, la sua occupazione sarà NULL. Questo è uno degli svantaggi della memorizzazione di entità diverse nella stessa tabella.

L'ultimo campo nella query SQL è la colonna DTYPE, che contiene il nome della classe Entity. Viene utilizzato da Hibernate quando si desidera leggere i dati dalla tabella.

Esempio:

List<User> accounts = session.createQuery("from User").list();

Questa query restituirà un elenco di tutti gli oggetti di tipo utente archiviati nel database: Utente, Dipendente e Cliente. In base alla colonna DTYPE, il tipo di entità verrà determinato correttamente e verrà creato un oggetto della classe corretta.

Nel nostro caso, ci saranno due oggetti nell'elenco degli account: un tipo Dipendente e un tipo Cliente.

Regole HQL.