Panduan Cepat tentang Memuat Data Awal dengan Spring Boot

1. Ikhtisar

Spring Boot membuatnya sangat mudah untuk mengelola perubahan database kami dengan cara yang mudah. Jika kita meninggalkan konfigurasi default, itu akan mencari entitas dalam paket kita dan membuat tabel masing-masing secara otomatis.

Tapi terkadang kita membutuhkan kontrol yang lebih baik atas perubahan database. Saat itulah kita dapat menggunakan file data.sql dan schema.sql di Spring.

2. File data.sql

Mari kita juga membuat asumsi di sini bahwa kita bekerja dengan JPA - dan mendefinisikan entitas Negara sederhana dalam proyek kita:

@Entity public class Country { @Id @GeneratedValue(strategy = IDENTITY) private Integer id; @Column(nullable = false) private String name; //... }

Jika kita menjalankan aplikasi kita, Spring Boot akan membuat tabel kosong untuk kita, tetapi tidak akan mengisinya dengan apa pun.

Cara mudah untuk melakukannya adalah dengan membuat file bernama data.sql:

INSERT INTO country (name) VALUES ('India'); INSERT INTO country (name) VALUES ('Brazil'); INSERT INTO country (name) VALUES ('USA'); INSERT INTO country (name) VALUES ('Italy');

Saat kami menjalankan proyek dengan file ini di classpath, Spring akan mengambilnya dan menggunakannya untuk mengisi database.

3. File schema.sql

Terkadang, kami tidak ingin bergantung pada mekanisme pembuatan skema default. Dalam kasus seperti itu, kita dapat membuat file schema.sql kustom :

CREATE TABLE country ( id INTEGER NOT NULL AUTO_INCREMENT, name VARCHAR(128) NOT NULL, PRIMARY KEY (id) );

Spring akan mengambil file ini dan menggunakannya untuk membuat skema.

Penting juga untuk diingat untuk menonaktifkan pembuatan skema otomatis untuk menghindari konflik:

spring.jpa.hibernate.ddl-auto=none

4. Mengontrol Pembuatan Database Menggunakan Hibernate

Spring menyediakan properti khusus JPA yang digunakan Hibernate untuk pembuatan DDL: spring.jpa.hibernate.ddl-auto .

Nilai properti Hibernate standar adalah: create , update , create-drop , validate dan none :

  • create - Hibernate pertama kali menjatuhkan tabel yang ada, kemudian membuat tabel baru
  • perbarui - model objek yang dibuat berdasarkan pemetaan (penjelasan atau XML) dibandingkan dengan skema yang ada, dan kemudian Hibernasi memperbarui skema sesuai dengan perbedaannya. Itu tidak pernah menghapus tabel atau kolom yang ada meskipun mereka tidak lagi diperlukan oleh aplikasi
  • create-drop - mirip dengan membuat , dengan tambahan Hibernate akan menjatuhkan database setelah semua operasi selesai. Biasanya digunakan untuk pengujian unit
  • validate - Hibernate hanya memvalidasi apakah tabel dan kolom ada, jika tidak maka akan muncul pengecualian
  • none - nilai ini secara efektif mematikan pembuatan DDL

Spring Boot secara internal menetapkan nilai parameter ini ke create-drop jika tidak ada pengelola skema yang terdeteksi, jika tidak , tidak ada untuk semua kasus lainnya.

Kita harus mengatur nilainya dengan hati-hati atau menggunakan salah satu mekanisme lain untuk menginisialisasi database.

5. @Sql

Spring juga menyediakan anotasi @Sql - cara deklaratif untuk menginisialisasi dan mengisi skema pengujian kami.

Mari kita lihat bagaimana menggunakan anotasi @Sql untuk membuat tabel baru dan juga memuat tabel dengan data awal untuk pengujian integrasi kita:

@Sql({"/employees_schema.sql", "/import_employees.sql"}) public class SpringBootInitialLoadIntegrationTest { @Autowired private EmployeeRepository employeeRepository; @Test public void testLoadDataForTestClass() { assertEquals(3, employeeRepository.findAll().size()); } }

Atribut anotasi @Sql adalah:

  • config - konfigurasi lokal untuk skrip SQL. Kami menjelaskan ini secara rinci di bagian selanjutnya
  • executionPhase - kita juga dapat menentukan kapan harus mengeksekusi skrip, baik BEFORE_TEST_METHOD atau AFTER_TEST_METHOD
  • pernyataan - kita dapat mendeklarasikan pernyataan SQL sebaris untuk dieksekusi
  • skrip - kita dapat mendeklarasikan jalur ke file skrip SQL untuk dieksekusi. Ini adalah alias untuk atribut nilai

The @ sql penjelasan dapat digunakan di tingkat kelas atau tingkat metode . Kita dapat memuat data tambahan yang diperlukan untuk kasus uji tertentu dengan memberi anotasi pada metode tersebut:

@Test @Sql({"/import_senior_employees.sql"}) public void testLoadDataForTestCase() { assertEquals(5, employeeRepository.findAll().size()); }
6. @SqlConfig

Kita dapat mengkonfigurasi cara kita mengurai dan menjalankan skrip SQL dengan menggunakan anotasi @SqlConfig .

@SqlConfig dapat dideklarasikan di tingkat kelas, yang berfungsi sebagai konfigurasi global. Atau dapat digunakan untuk mengonfigurasi anotasi @Sql tertentu .

Mari kita lihat contoh di mana kita menentukan pengkodean skrip SQL kita serta mode transaksi untuk mengeksekusi skrip:

@Test @Sql(scripts = {"/import_senior_employees.sql"}, config = @SqlConfig(encoding = "utf-8", transactionMode = TransactionMode.ISOLATED)) public void testLoadDataForTestCase() { assertEquals(5, employeeRepository.findAll().size()); }

Dan mari kita lihat berbagai atribut @SqlConfig :

  • blockCommentStartDelimiter - pembatas untuk mengidentifikasi awal komentar blok dalam file skrip SQL
  • blockCommentEndDelimiter - pembatas untuk menunjukkan akhir komentar blok di file skrip SQL
  • commentPrefix - awalan untuk mengidentifikasi komentar baris tunggal dalam file skrip SQL
  • dataSource - nama kacang javax.sql.DataSource yang digunakan untuk menjalankan skrip dan pernyataan
  • pengkodean - pengkodean untuk file skrip SQL, standarnya adalah pengkodean platform
  • errorMode - mode yang akan digunakan ketika kesalahan ditemukan saat menjalankan skrip
  • separator - string yang digunakan untuk memisahkan pernyataan individual, defaultnya adalah "-"
  • transactionManager - nama kacang dari PlatformTransactionManager yang akan digunakan untuk transaksi
  • transactionMode - mode yang akan digunakan saat menjalankan skrip dalam transaksi

7. @SlGroup

Java 8 and above allow the use of repeated annotations. This feature can be utilized for @Sql annotations as well. For Java 7 and below, there is a container annotation — @SqlGroup. Using the @SqlGroup annotation, we can declare multiple @Sql annotations:

@SqlGroup({ @Sql(scripts = "/employees_schema.sql", config = @SqlConfig(transactionMode = TransactionMode.ISOLATED)), @Sql("/import_employees.sql")}) public class SpringBootSqlGroupAnnotationIntegrationTest { @Autowired private EmployeeRepository employeeRepository; @Test public void testLoadDataForTestCase() { assertEquals(3, employeeRepository.findAll().size()); } }

8. Conclusion

In this quick article, we saw how we can leverage schema.sql and data.sql files for setting up an initial schema and populating it with data. We also saw how we can use @Sql, @SqlConfig, and @SqlGroup annotations to load test data for tests.

Perlu diingat bahwa pendekatan ini lebih cocok untuk skenario dasar dan sederhana, penanganan database tingkat lanjut apa pun akan memerlukan perkakas yang lebih canggih dan halus seperti Liquibase atau Jalur Terbang.

Cuplikan kode, seperti biasa, dapat ditemukan di GitHub.