Pengujian Integrasi dengan Maven

1. Ikhtisar

Maven adalah alat build paling populer di ruang Java, sedangkan pengujian integrasi adalah bagian penting dari proses pengembangan. Oleh karena itu, merupakan pilihan yang wajar untuk mengonfigurasi dan menjalankan pengujian integrasi dengan Maven.

Dalam tutorial ini, kita akan membahas sejumlah cara berbeda untuk menggunakan Maven untuk pengujian integrasi dan untuk memisahkan pengujian integrasi dari pengujian unit.

2. Persiapan

Untuk membuat kode demonstrasi mendekati proyek dunia nyata, kami akan menyiapkan aplikasi JAX-RS. Aplikasi ini diterapkan ke server sebelum pelaksanaan tes integrasi dan kemudian dibongkar.

2.1. Konfigurasi Maven

Kami akan membangun aplikasi REST kami di sekitar Jersey - implementasi referensi JAX-RS. Implementasi ini membutuhkan beberapa dependensi:

 org.glassfish.jersey.containers jersey-container-servlet-core 2.27   org.glassfish.jersey.inject jersey-hk2 2.27 

Kami dapat menemukan versi terbaru dari dependensi ini di sini dan di sini.

Kami akan menggunakan plugin Jetty Maven untuk menyiapkan lingkungan pengujian. Plugin ini memulai server Jetty selama fase uji pra-integrasi dari siklus hidup build Maven, lalu menghentikannya dalam fase uji pasca integrasi .

Berikut cara kami mengkonfigurasi plugin Jetty Maven di pom.xml :

 org.eclipse.jetty jetty-maven-plugin 9.4.11.v20180605   8999  quit 9000    start-jetty pre-integration-test  start    stop-jetty post-integration-test  stop    

Saat server Jetty dijalankan, server akan mendengarkan di porta 8999 . The stopKey dan stopPort elemen konfigurasi yang digunakan semata-mata oleh plugin berhenti tujuan dan nilai mereka tidak penting dari sudut pandang kami.

Di sinilah tempat untuk menemukan versi terbaru dari plugin Jetty Maven.

Hal lain yang perlu diperhatikan adalah kita harus mengatur elemen pengemasan di file pom.xml ke perang , jika tidak, plugin Jetty tidak dapat memulai server:

war

2.2. Membuat Aplikasi REST

Titik akhir aplikasi sangat sederhana - mengembalikan pesan selamat datang ketika permintaan GET mengenai root konteks:

@Path("/") public class RestEndpoint { @GET public String hello() { return "Welcome to Baeldung!"; } }

Beginilah cara kami mendaftarkan kelas titik akhir dengan Jersey:

package com.baeldung.maven.it; import org.glassfish.jersey.server.ResourceConfig; public class EndpointConfig extends ResourceConfig { public EndpointConfig() { register(RestEndpoint.class); } }

Agar server Jetty mengetahui aplikasi REST kita, kita dapat menggunakan deskriptor penerapan web.xml klasik :

  rest-servlet org.glassfish.jersey.servlet.ServletContainer  javax.ws.rs.Application com.baeldung.maven.it.EndpointConfig    rest-servlet /*  

Deskriptor ini harus ditempatkan di direktori / src / main / webapp / WEB-INF agar dapat dikenali oleh server.

2.3. Kode Pengujian Sisi Klien

Semua kelas pengujian di bagian berikut berisi satu metode:

@Test public void whenSendingGet_thenMessageIsReturned() throws IOException { String url = "//localhost:8999"; URLConnection connection = new URL(url).openConnection(); try (InputStream response = connection.getInputStream(); Scanner scanner = new Scanner(response)) { String responseBody = scanner.nextLine(); assertEquals("Welcome to Baeldung!", responseBody); } }

Seperti yang bisa kita lihat, metode ini tidak melakukan apa-apa selain mengirimkan permintaan GET ke aplikasi web yang kita siapkan sebelumnya dan memverifikasi responsnya.

3. Pengujian Integrasi dalam Tindakan

Satu hal penting untuk diperhatikan tentang pengujian integrasi adalah bahwa metode pengujian sering kali memerlukan waktu yang cukup lama untuk dijalankan.

Akibatnya, kita harus mengecualikan pengujian integrasi dari siklus hidup build default, agar tidak memperlambat keseluruhan proses setiap kali kita membangun proyek.

Cara mudah untuk memisahkan pengujian integrasi adalah dengan menggunakan profil build. Jenis konfigurasi ini memungkinkan kita untuk menjalankan pengujian integrasi hanya jika diperlukan - dengan menentukan profil yang sesuai.

Di bagian selanjutnya, kami akan mengonfigurasi semua pengujian integrasi dengan profil build.

4. Menguji Dengan Plugin Failsafe

Cara termudah untuk menjalankan pengujian integrasi adalah dengan menggunakan plugin Maven failafe .

Secara default, plugin surefire Maven menjalankan pengujian unit selama fase pengujian , sementara plugin yang aman dari kegagalan menjalankan pengujian integrasi dalam fase pengujian integrasi .

Kami dapat memberi nama kelas pengujian dengan pola berbeda untuk plugin tersebut untuk mengambil pengujian tertutup secara terpisah.

Konvensi penamaan default yang diberlakukan oleh surefire dan failafe berbeda, jadi kita hanya perlu mengikuti konvensi ini untuk memisahkan pengujian unit dan integrasi.

Eksekusi plugin surefire mencakup semua kelas yang namanya dimulai dengan Test , atau diakhiri dengan Test , Tests , atau TestCase . Sebaliknya, plugin failafe menjalankan metode pengujian di kelas yang namanya dimulai dengan IT , atau diakhiri dengan IT atau ITCase .

Di sinilah kami dapat menemukan dokumentasi mengenai inklusi pengujian untuk memastikan , dan ini adalah satu untuk keamanan dari kegagalan .

Mari tambahkan plugin failafe ke POM dengan konfigurasi default:

 failsafe    maven-failsafe-plugin 2.22.0    integration-test verify       

Tautan ini adalah tempat untuk menemukan versi terbaru dari plugin yang aman dari kegagalan .

With the above configuration, the following test method will be executed in the integration-test phase:

public class RestIT { // test method shown in subsection 2.3 }

Since the Jetty server starts up in the pre-integration-test phase and shuts down in post-integration-test, the test we have just seen passes with this command:

mvn verify -Pfailsafe

We can also customize the naming patterns to include classes with different names:

 maven-failsafe-plugin 2.22.0   **/*RestIT **/RestITCase   ... 

5. Testing With the Surefire Plugin

Apart from the failsafe plugin, we can also use the surefire plugin to execute unit and integration tests in different phases.

Let's assume we want to name all integration tests with the suffix IntegrationTest. Since the surefire plugin runs tests with such a name in the test phase by default, we need to exclude them from the default execution:

 maven-surefire-plugin 2.22.0   **/*IntegrationTest   

The latest version of this plugin is here.

We've taken all test classes having a name ending with IntegrationTest out of the build lifecycle. It's time to put them back with a profile:

 surefire    maven-surefire-plugin 2.22.0   integration-test  test    none   **/*IntegrationTest        

Instead of binding the test goal of the surefire plugin to the test build phase, as usual, we bound it to the integration-test phase. The plugin will then kick in during the integration testing process.

Notice that we must set an exclude element to none to override the exclusion specified in the base configuration.

Now, let's define an integration test class with our naming pattern:

public class RestIntegrationTest { // test method shown in subsection 2.3 }

This test will be running with the command:

mvn verify -Psurefire

6. Testing With the Cargo Plugin

We can use the surefire plugin with the Maven cargo plugin. This plugin comes with built-in support for embedded servers, which are very useful for integration testing.

More details about this combination can be found here.

7. Testing With JUnit's @Category

A convenient way to selectively execute tests is to leverage the @Category annotation in the JUnit 4 framework. This annotation lets us exclude particular tests from unit testing, and include them in integration testing.

First off, we need an interface or class to work as a category identifier:

package com.baeldung.maven.it; public interface Integration { }

We can then decorate a test class with the @Category annotation and Integration identifier:

@Category(Integration.class) public class RestJUnitTest { // test method shown in subsection 2.3 }

Rather than declaring the @Category annotation on a test class, we can also use it at the method level to categorize individual test methods.

Excluding a category from the test build phase is simple:

 maven-surefire-plugin 2.22.0  com.baeldung.maven.it.Integration  

Including the Integration category in the integration-test phase is also straightforward:

 category    maven-failsafe-plugin 2.22.0   **/*  com.baeldung.maven.it.Integration     integration-test verify       

We can now run integration tests with a Maven command:

mvn verify -Pcategory

8. Adding a Separate Directory for Integration Tests

It's desirable at times to have a separate directory for integration tests. Organizing tests this way allows us to entirely isolate integration tests from unit tests.

We can use the Maven build helper plugin for this purpose:

 org.codehaus.mojo build-helper-maven-plugin 3.0.0   add-integration-test-source generate-test-sources  add-test-source    src/integration-test/java     

Here is where we can find the latest version of this plugin.

The configuration we've just seen adds a test source directory to the build. Let's add a class definition to that new directory:

public class RestITCase { // test method shown in subsection 2.3 }

It's time to run integration tests in this class:

mvn verify -Pfailsafe

Plugin Maven failafe akan menjalankan metode di kelas pengujian ini karena konfigurasi yang kami tetapkan di sub-bagian 3.1.

Direktori sumber pengujian sering kali menggunakan direktori sumber daya. Kita dapat menambahkan direktori seperti itu di elemen eksekusi lain ke konfigurasi plugin:

 ...  add-integration-test-resource generate-test-resources  add-test-resource     src/integration-test/resources     

9. Kesimpulan

Artikel ini pergi menggunakan Maven untuk menjalankan tes integrasi dengan server Jetty, dengan fokus pada konfigurasi Maven jitu dan failsafe plugin.

Kode sumber lengkap untuk tutorial ini dapat ditemukan di GitHub.