1. Зберігаємо файли на сервері
Іноді в базі даних потрібно зберегти бінарні об'єкти. Наприклад, файли. Якщо файл великий, то розумніше зберігати його в окремій папці на диску, а в базі даних зберігати його шляхи. Приклад:
c:\db-files\users\12355\avatar.jpg
І в базі зберігаємо просто відносний шлях до файлу:
\12355\avatar.jpg
У базі зручно зберігати відносний шлях, тому що з нього потім легко отримати URL:
https://storage.javarush.ru/users/12355/avatar.jpg
Ми просто приклеюємо відносний шлях до імені сервера — і готово.
2. Зберігаємо картинки прямо в базі
Однак, якщо картинки маленькі, їх можна зберігати у базі і віддавати клієнту як набір байт. Для таких випадків SQL має спеціальний тип даних BLOB — Binary Large Object. Точніше, їх навіть два:
- CLOB — Character Large Object,
- BLOB — Binary Large Object.
CLOB використовується для збереження великих текстів. А BLOB — для зберігання бінарних даних, таких як невеликі картинки, відео тощо.
Приклад:
@Entity
@Table(name="user")
public class User {
@Id
private String id;
@Column(name="name", columnDefinition="VARCHAR(128)")
private String name;
@Lob
@Column(name="photo", columnDefinition="BLOB")
private byte[] photo;
// ...
}
Анотація @Lob
підказує Hibernate, що в полі зберігається Large Object. А columnDefinition="BLOB"
вже говорить про те, як це все зберегти в базі.
Давай напишемо приклад коду, який зберігає в базі нового користувача та його фото:
byte[] imageBuffer = Files.readAllBytes(Paths.get("C:/temp/avatar.png"))
User user = new User();
user.setId("1");
user.setName("Zapp");
user.setPhoto(imageBuffer);
session.persist(user);
3. XML та JSON
Hibernate має цікаву підтримку JSON як тип даних. Він дозволяє зберегти HashMap рядків у вигляді єдиного об'єкта JSON. Якщо СУБД вміє працювати з JSON, то це виглядає так:
@JdbcTypeCode(SqlTypes.JSON)
private Map<String, String> properties;
Hibernate бере на себе турботу про те, щоб об'єкт типу Map<String, String>
був серіалізований до єдиний JSON-об'єкта. Також під час читання об'єкта з бази перетворює JSON-об'єкт на набір Map<String, String>
.
Щось схоже Hibernate може зробити і з XML:
@JdbcTypeCode(SqlTypes.SQLXML)
private Map<String, String> properties;