Kontekstni boshqarish

All lectures for UZ purposes
Daraja, Dars
Mavjud

Har bir TestContext test instansiyasi uchun kontekstni boshqarishni va kechirishni qo'llab-quvvatlaydi. Test instansiyalari avtomatik ravishda sozlangan ApplicationContext ga kira olmaydi. Ammo, agar test klass ApplicationContextAware interfeysini amalga oshirsa, unda ApplicationContext ga havola test instansiyasiga o'tkaziladi. E'tibor bering, AbstractJUnit4SpringContextTests va AbstractTestNGSpringContextTests ApplicationContextAware ni amalga oshiradi va avtomatik ravishda ApplicationContext ga kirishni ta'minlaydi.

@Autowired bilan belgilangan ApplicationContext

ApplicationContextAware interfeysini amalga oshirish o'rniga siz test klassingiz uchun @Autowired annotatsiyasi yordamida kontekstni injekt qilishingiz mumkin, quyidagi misolda ko'rsatilganidek:

Java
@SpringJUnitConfig
class MyTest {
    @Autowired 
    ApplicationContext applicationContext;
    // klassning tanasi...
}
  1. ApplicationContext ni injekt qilmoqdamiz.
Kotlin
@SpringJUnitConfig
class MyTest {
    @Autowired 
    lateinit var applicationContext: ApplicationContext
    // klassning tanasi...
}
  1. ApplicationContext ni injekt qilmoqdamiz.

Xuddi shunday, agar sizning testingiz WebApplicationContext yuklanishi uchun sozlangan bo'lsa, veb-ilova kontekstini testga quyidagicha injekt qilishingiz mumkin:

Java
@SpringJUnitWebConfig 
class MyWebAppTest {
    @Autowired 
    WebApplicationContext wac;
    // klassning tanasi...
}
  1. WebApplicationContext ni konfiguratsiya qilish.
  2. WebApplicationContext ni injekt qilmoqdamiz.
Kotlin
@SpringJUnitWebConfig 
class MyWebAppTest {
    @Autowired 
    lateinit var wac: WebApplicationContext
    // klassning tanasi...
}
  1. WebApplicationContext ni konfiguratsiya qilish.
  2. WebApplicationContext ni injekt qilmoqdamiz.

@Autowired annotatsiyasi yordamida bog'lanish DependencyInjectionTestExecutionListener orqali ta'minlanadi, u standart ravishda konfiguratsiya qilingan (yana qarang "Test stendlar uchun bog'lanishlar").

Test klasslari, TestContext dasturiy ta'minotidan foydalangan holda, ilova kontekstlarini konfiguratsiya qilish uchun ma'lum bir klassni kengaytirishi yoki ma'lum bir interfeysni amalga oshirishi shart emas. Buning o'rniga, konfiguratsiya klass darajasidagi @ContextConfiguration annotatsiyani e'lon qilish orqali amalga oshiriladi. Agar test klassi aniq resurs joylashuvlarini yoki komponent klasslarini e'lon qilmasa, konfiguratsiyalangan ContextLoader yuklaydi. Qo'shimcha ma'lumot uchun resurs manzilgohlarini va komponent klasslarini, ilova konteksti ham ilova konteksti boshlang'ichlari yordamida konfiguratsiya qilinishi mumkin.

Keyingi bo'limlarda Springda test ApplicationContext ni XML konfiguratsiya fayllari, Groovy skriptlari, komponent klasslari (odatda @Configuration annotatsiyasiga ega bo'lgan klasslar) yoki kontekst boshlang'ichlari yordamida sozlash uchun @ContextConfiguration annotatsiyasi qanday ishlatilishi tushuntiriladi. Shuningdek, ilg'or foydalanish holatlari uchun o'z SmartContextLoader ni amalga oshirish va sozlash mumkin.

XML resurslar yordamida kontekst konfiguratsiyasi

Sizning testlaringiz uchun ApplicationContext ni XML konfiguratsiya fayllari yordamida yuklash uchun test klassingizga @ContextConfiguration annotatsiyasini qo'shing va locations atributini XML konfiguratsiya metadatalari resurs joylashuvlari bilan to'ldirilgan massiv bilan konfiguratsiya qiling. Oddiy yoki nisbiy yo'l (masalan, context.xml) test klassi aniqlangan paketga tegishli bo'lgan classpath resursi sifatida ko'rib chiqiladi. Egri chiziq bilan boshlanadigan yo'l classpathning aniq joylashuvi sifatida ko'rib chiqiladi (masalan, /org/example/config.xml). Resurs URL manzilini ifodalovchi bir yo'l (ya'ni, classpath:, file:, http: va hokazo prefiksli yo'llar) keltirilganidek ishlatiladi.

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "/app-config.xml" va "/test-config.xml" dan yuklanadi
// classpath ildizida
@ContextConfiguration(locations={"/app-config.xml", "/test-config.xml"}) 
class MyTest {
    // klassning tanasi...
}
  1. XML fayllar ro'yxatida joylashuv atributini belgilash.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "/app-config.xml" va "/test-config.xml" dan yuklanadi
// classpath ildizida
@ContextConfiguration("/app-config.xml", "/test-config.xml") 
class MyTest {
    // klassning tanasi...
}
  1. XML fayllar ro'yxatida joylashuv atributini belgilash.

@ContextConfiguration annotatsiyasi Java-dan locations atributining standart value atributi orqali taxallusini qo'llab-quvvatlaydi. Shunday qilib, agar @ContextConfiguration annotatsiyasida qo'shimcha atributlarni e'lon qilish talab qilinmasa, locations atribut nomini e'lon qilishni yo'q qilib, resurs joylashuvlarini quyidagi qisqartirilgan formatda e'lon qilish mumkin:

Java
@ExtendWith(SpringExtension.class)
@ContextConfiguration({"/app-config.xml", "/test-config.xml"}) 
class MyTest {
    // klassning tanasi...
}
  1. location atributidan foydalanmasdan XML fayllarni belgilash.
Kotlin
@ExtendWith(SpringExtension::class)
@ContextConfiguration("/app-config.xml", "/test-config.xml") 
class MyTest {
    // klassning tanasi...
}
  1. location atributidan foydalanmasdan XML fayllarni belgilash.

Agar @ContextConfiguration annotatsiyasida location va value atributlarini yo'q qilsangiz, TestContext Framework XML resurslar joylashuvini avtomatik aniqlashga harakat qiladi. Maxsus holda, GenericXmlContextLoader va GenericXmlWebContextLoader test klassining nomiga asoslangan holda standart holatni aniqlaydi. Agar sizning klassingiz com.example.MyTest deb nomlangan bo'lsa, GenericXmlContextLoader test klassingiz uchun ilova kontekstini "classpath:com/example/MyTest-context.xml" dan yuklaydi. Quyidagi misolda, qanday amalga oshirilishi ko'rsatilgan:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "classpath:com/example/MyTest-context.xml" dan yuklanadi
@ContextConfiguration 
class MyTest {
    // klassning tanasi...
}
  1. Standart joylashuvdan konfiguratsiyani yuklash.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "classpath:com/example/MyTest-context.xml" dan yuklanadi
@ContextConfiguration 
class MyTest {
    // klassning tanasi...
}
  1. Standart joylashuvdan konfiguratsiyani yuklash.
Groovy skriptlari yordamida kontekst konfiguratsiyasi

Sizning testlaringiz uchun Groovy Bean Definition DSL dan foydalangan holda Groovy skriptlaridan foydalangan holda ApplicationContext ni yuklash uchun.
Shuningdek, siz o'zingizning test klassingizga @ContextConfiguration annotatsiyasini qo'shishingiz va locations yoki value atributini Groovy skript resurs joylashuvlari bilan to'ldirilgan massiv bilan konfiguratsiya qilishingiz mumkin. Groovy skriptlar uchun resurs qidirish semantikasi XML konfiguratsiya fayllari bilan bir xil.

Groovy skriptlarini qo'llab-quvvatlashni faollashtirish
Spring TestContext Framework-ga ApplicationContext yuklash uchun Groovy skriptlaridan foydalanish avtomatik ravishda faollashadi, agar Groovy classpath-da bo'lsa.

Quyidagi misolda Groovy konfiguratsion fayllarni qanday belgilash ko'rsatilgan:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "/AppConfig.groovy" va
// "/TestConfig.groovy" dan yuklanadi
@ContextConfiguration({"/AppConfig.groovy", "/TestConfig.Groovy"}) 
class MyTest {
    // klassning tanasi...
}
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "/AppConfig.groovy" va
// "/TestConfig.groovy" dan yuklanadi
@ContextConfiguration("/AppConfig.groovy", "/TestConfig.Groovy") 
class MyTest {
    // klassning tanasi...
}
  1. Groovy konfiguratsiya fayllarining joylashuvini belgilash.

Agar siz @ContextConfiguration annotatsiyasida locations va value atributlarini yo'q qilsangiz, TestContext Framework standarti holatda Groovy skriptni aniqlashga harakat qiladi. Maxsus holda, GenericGroovyXmlContextLoader va GenericGroovyXmlWebContextLoader test klassining nomiga asoslangan holda standart holatni aniqlaydi. Agar sizning klassingiz com.example.MyTest deb nomlangan bo'lsa, Groovy kontekst yuklovchisi ilova kontekstini "classpath:com/example/MyTestContext.groovy" dan yuklaydi. Quyidagi misolda, qanday amalga oshirilishi ko'rsatilgan:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "classpath:com/example/MyTestContext.groovy" dan yuklanadi
@ContextConfiguration 
class MyTest {
    // klassning tanasi...
}
  1. Standart joylashuvdan konfiguratsiyani yuklash.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "classpath:com/example/MyTestContext.groovy" dan yuklanadi
@ContextConfiguration 
class MyTest {
    // klassning tanasi...
}
  1. Standart joylashuvdan konfiguratsiyani yuklash.
Bir vaqtning o'zida XML konfiguratsiyasi va Groovy skriptlarini e'lon qilish

Bir vaqtning o'zida konfiguratsiya XML-fayllari va Groovy skriptlarini @ContextConfiguration annotatsiyasida location yoki value atributidan foydalanib e'lon qilishingiz mumkin. Agar konfiguratsiyalangan resurs manzilni belgilashning oxiri .xml bilan tugasa, u XmlBeanDefinitionReader tomonidan yuklanadi. Aks holda, u GroovyBeanDefinitionReader tomonidan yuklanadi.

Quyidagi listingda XML va Groovy-ni birlashtirishning ikkala variantini ham integratsiya testida qanday birlashtirish mumkinligi ko'rsatilgan:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "/app-config.xml" va "/TestConfig.groovy" dan yuklanadi
@ContextConfiguration({ "/app-config.xml", "/TestConfig.groovy" })
class MyTest {
    // klassning tanasi...
}
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "/app-config.xml" va "/TestConfig.groovy" dan yuklanadi
@ContextConfiguration("/app-config.xml", "/TestConfig.groovy")
class MyTest {
    // klassning tanasi...
}
Komponent klasslari yordamida kontekst konfiguratsiyasi

Sizning testlaringiz uchun ApplicationContext ni komponent klasslar yordamida yuklash uchun (qarang "Java asosidagi konteyner konfiguratsiyasi"), siz o'zingizning test klassingizni @ContextConfiguration annotatsiyasi bilan belgilashingiz va classes atributini komponent klasslariga havola bilan to'ldirilgan massiv bilan konfiguratsiya qilishingiz mumkin. Quyidagi misolda, qanday amalga oshirilishi ko'rsatildi:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext AppConfig va TestConfig dan yuklanadi
@ContextConfiguration(classes = {AppConfig.class, TestConfig.class}) 
class MyTest {
    // klassning tanasi...
}
  1. Komponent klasslarni belgilash.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext AppConfig va TestConfig dan yuklanadi
@ContextConfiguration(classes = [AppConfig::class, TestConfig::class]) 
class MyTest {
    // klassning tanasi...
}
  1. Komponent klasslarni belgilash.
Komponent klasslar

"Komponent klass" atamasi quyidagilardan biriga nisbatan qo'llanilishi mumkin:

  • @Configuration bilan belgilangan klass.

  • Komponent (ya'ni @Component, @Service, @Repository yoki boshqa stereotipli annotatsiyalar bilan belgilanadigan klasslar).

  • JSR-330 standarti bo'yicha javax.inject annotatsiyasi bilan belgilanadigan klasslar.

  • @Bean bilan belgilangan metodni o'z ichiga oladigan klasslar.

  • Spring komponenti sifatida ro'yxatdan o'tish (ya'ni, Spring kontekstida Spring beanini) mo'ljallangan har qanday boshqa klass (ya'ni, Spring ichida avtomatik kashf etish va yagona konstruktorni bog'lash afzalliklaridan foydalangan holda).

Spring tomonidan Spring komponenti konfiguratsiyasi va semantikasini to'liqroq tushunish uchun @Configuration va @Bean javadoclarini ko'ring.

Agar siz @ContextConfiguration annotatsiyasida classes atributini yo'q qilsangiz, TestContext Framework standart holda konfiguratsiya klasslari mavjudligini aniqlashga harakat qiladi. Maxsus holda, AnnotationConfigContextLoader va AnnotationConfigWebContextLoader test klassining barcha statik ichki klasslarini kashf etmoqda, ular @Configuration javadocida ko'rsatilganidek, konfiguratsiya klassini amalga oshirish bo'yicha talablariga mos keladi. E'tibor bering, konfiguratsiya klassining nomi ixtiyoriy. Bundan tashqari, istasangiz, test klassi bir nechta statik ichki konfiguratsiya klasslarini o'z ichiga olishi mumkin. Quyidagi misolda OrderServiceTest klassi, testi ApplicationContext ni yuklash uchun avtomatik ravishda ishlatiladigan Config deb nomlangan statik ichki konfiguratsiya klassini e'lon qiladi:

Java
@SpringJUnitConfig 
// ApplicationContext statik ichki klass Config dan yuklanadi
class OrderServiceTest {
    @Configuration
    static class Config {
        // OrderServiceTest klassiga injekt qilinadigan bean
        @Bean
        OrderService orderService() {
            OrderService orderService = new OrderServiceImpl();
            // xususiyatlarni sozlash va h.k.
            return orderService;
        }
    }
    @Autowired
    OrderService orderService;
    @Test
    void testOrderService() {
        // orderService-ni sinash
    }
}
  1. Config ichki klassidan konfiguratsiya ma'lumotlarini yuklash.
Kotlin
@SpringJUnitConfig 
// ApplicationContext statik ichki klass Config dan yuklanadi
class OrderServiceTest {
    @Autowired
    lateinit var orderService: OrderService
    @Configuration
    class Config {
        // OrderServiceTest klassiga injekt qilinadigan bean
        @Bean
        fun orderService(): OrderService {
            // xususiyatlarni sozlash va h.k.
            return OrderServiceImpl()
        }
    }
    @Test
    fun testOrderService() {
        // orderService-ni sinash
    }
}
  1. Config ichki klassidan konfiguratsiya ma'lumotlarini yuklash.
XML, Groovy skriptlar va komponent klasslarni birlashtirish

Ba'zan testlar uchun ApplicationContext ni konfiguratsiya qilish uchun XML konfiguratsion fayllar, Groovy skriptlar va komponent klasslarni (odatda @Configuration annotatsiyali klasslar) birlashtirish talab qilinishi mumkin. Misol uchun, agar siz ishlab chiqarish muhitida XML konfiguratsiyasidan foydalansangiz, sizning testlaringiz uchun ma'lum Spring tomonidan boshqariladigan komponentlarni sozlash uchun @Configuration annotatsiyali klasslardan foydalanishni qaror qilishingiz mumkin yoki aksincha.

Yana bir narsani qo'shish uchun, ba'zi uchinchi tomon ramkalari (masalan, Spring Boot) XML konfiguratsiya fayllari, Groovy skriptlar va @Configuration annotatsiyali klasslardan bir vaqtda ApplicationContext yuklash uchun a'lo qo'llab-quvvatlash vositalarini taqdim etadi. Spring Framework tarixan standart joylashuvlar uchun buni qo'llab-quvvatlamagan. Shuning uchun, spring-test modulida Spring Framework taqdim etadigan SmartContextLoader ning aksariyat amalga oshirilishi har bir test kontekstida bitta resurs turini qo'llab-quvvatlaydi. Ammo, bu ikkala variantni ham ishlatish mumkin emas degani emas. Umumiy qoidadan istisno shundaki, GenericGroovyXmlContextLoader va GenericGroovyXmlWebContextLoader bir vaqtda konfiguratsion XML fayllarini va Groovy skriptlarini qo'llab-quvvatlaydi. Bundan tashqari, uchinchi tomon ramkalari @ContextConfiguration annotatsiyasi orqali locations va classes ni e'lon qilishni qo'llab-quvvatlashi mumkin, TestContext Frameworkda standart testlarni qo'llab-quvvatlashda quyida ta'riflangan imkoniyatlar mavjud.

Agar testlaringizni konfiguratsiya qilish uchun resurs joylashuvlarini (masalan, XML yoki Groovy) va @Configuration annotatsiyali klasslarni ishlatish kerak bo'lsa, ulardan birini kirish nuqtasi sifatida tanlashingiz va bu tanlangan klass yoki joylashuv boshqalarni kiritishi yoki import qilishi kerakligini tanlashingiz kerak. Masalan, XML yoki Groovy skriptlarga komponent klasslarini import qilish uchun komponentni skanerlash yoki ularni oddiy Spring binnariga belgilash orqali kirish mumkin bo'lsada, @Configuration annotatsiyali klassda XML konfiguratsiya fayllarini yoki Groovy skriptlarini import qilish uchun @ImportResource annotatsiyasidan foydalanish mumkin. Diqqat etiboringiz, bunday ishlash semantik jihatdan ishlab chiqarusda sizning ilovangizni konfiguratsiya qilganingiz kabi ekvivalentdir: Ishlab chiqarish konfiguratsiyasida siz ma'lum bir resurs joylashuvlarini yoki @Configuration annotatsiyali klasslarni ishlab chiqarish ApplicationContext yuklash uchun belgilaysiz, ammo sizning borayotganingizdan foydalanishingiz mumkin bo'lgan boshqa konfiguratsiya turini kiritish yoki import qilish imkoniyatingiz hali bor.

Initializatorlar foydalanib kontekstni konfiguratsiyalash

Testlaringiz uchun ApplicationContext ni initializatorlar yordamida sozlash uchun siz o'zingizning test klassingizni @ContextConfiguration annotatsiyasi bilan belgilashingiz va initializers atribti yordamida ApplicationContextInitializer ni amalga oshiruvchi klasslarga ishoratlar bilan to'ldirilgan massivni konfiguratsiya qilishingiz mumkin. Deklaratsiya qilingan kontekst initializatorlari keyinchalik sizning testlaringiz uchun yuklangan ConfigurableApplicationContext ni inizializatsiya qilish uchun ishlatiladi. E'tibor bering, har bir deklaratsiya qilingan inizializator tomonidan qo'llab-quvvatlanadigan ConfigurableApplicationContext ning aniq turi, har safar foydalaniladigan SmartContextLoader tomonidan yaratilgan ApplicationContext turiga mos kelishi kerak (odatda bu GenericApplicationContext). Bundan tashqari, inizializatorlar qo'llaniladigan tartib ularnin Ordered interfeysini amalga oshirishlariga bog'liq yoki ular Springda @Order annotatsiyasi bilan belgilangan yoki standart @Priority annotatsiyasi bilan belgilangani bilan bog'liq. Quyidagi misolda inizializatorlarni qanday ishlatish ko'rsatilgan:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext TestConfig dan yuklanadi
// va TestAppCtxInitializer yordamida inizializatsiya qilinadi
@ContextConfiguration(
    classes = TestConfig.class,
    initializers = TestAppCtxInitializer.class) 
class MyTest {
    // klassning tanasi...
}
  1. Konfiguratsiya klassi va inizializator yordamida konfiguratsiyani tashkil qilish.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext TestConfig dan yuklanadi
// va TestAppCtxInitializer yordamida inizializatsiya qilinadi
@ContextConfiguration(
        classes = [TestConfig::class],
        initializers = [TestAppCtxInitializer::class]) 
class MyTest {
    // klassning tanasi...
}
  1. Konfiguratsiya klassi va inizializator yordamida konfiguratsiyani tashkil qilish.

Shuningdek, siz @ContextConfiguration annotatsiyasida hech qanday resurs joylashuvlarini, Groovy skriptlarini yoki komponent klasslarini e'lon qilishning o'rniga faqat ApplicationContextInitializer klasslarini e'lon qilishingiz mumkin, ular keyinchalik bunca binnarni kontekstdagi ro'yxatga olish uchun javobgar bo'ladi – masalan, XML fayllaridan yoki konfiguratsiya klasslaridan binar ta'riflarini dasturiy yuklash orqali. Quyidagi misolda, qanday amalga oshirilishi ko'rsatildi:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext EntireAppInitializer yordamida inizializatsiya qilinadi
// bu, konteksda binnarni ro'yxatga olish uchun mo'ljallangan
@ContextConfiguration(initializers = EntireAppInitializer.class) 
class MyTest {
    // klassning tanasi...
}
  1. Faqat bitta inizializator orqali konfiguratsiyani tashkil qilish.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext EntireAppInitializer yordamida inizializatsiya qilinadi
// bu, konteksda binnarni ro'yxatga olish uchun mo'ljallangan
@ContextConfiguration(initializers = [EntireAppInitializer::class]) 
class MyTest {
    // klassning tanasi...
}
  1. Faqat bitta inizializator orqali konfiguratsiyani tashkil qilish.
Kontekst konfiguratsiyasini meros qilish

@ContextConfiguration annotatsiyasi inheritLocations va inheritInitializers bul atributlarini qo'llab-quvvatlaydi, bu esa yuqori klasslar tomonidan e'lon qilingan resurs joylashuvlari yoki komponent klasslari va kontekst initializatorlarini meros olish kerakligini ko'rsatadi. Ikkala bayrog'ning standart qiymati true. Bu shuni anglatadiki, test klassi yuqori klasslar tomonidan e'lon qilingan resurs joylashuvlari yoki komponent klasslari va kontekst initializatorlarini meros qiladi. Aniq aytganda, test klassi uchun resurs joylashuvlari yoki komponent klasslari yuqori klasslar tomonidan e'lon qilingan resurs joylashuvlari yoki belgilangan klasslar ro'yxatiga qo'shiladi. Xuddi shunday, berilgan test klassi uchun initializatorlar yuqori klasslar tomonidan aniqlangan initializatorlar to'plamiga qo'shiladi. Shunday qilib, subklasslar resurs joylashuvlarini, komponent klasslarni yoki kontekst initializatorlarini kengaytirishi mumkin.

Agar @ContextConfiguratio.n annotatsiyasida inheritLocations yoki inheritInitializers atribut false deb o'rnatilgan bo'lsa, test klassi uchun, mos ravishda, resurs joylashuvlari yoki komponent klasslari va kontekst initializatorlari yuqori klasslar tomonidan aniqlangan konfiguratsiyani "soya qiladi" va samarali ravishda almashtiradi.

Spring Framework 5.3-dan boshlab, test konfiguratsiyasi ramsuhlarni o'z ichiga olishi mumkin. Batafsil ma'lumot uchun qarang "@Nested annotatsiyasiga ega test klass konfiguratsiyasi".

Quyidagi misol Java resurs manzillari ishlatilgan testlar uchun ApplicationContext base-config.xml va extended-config.xml dan aniq tartibda yuklanishini ko'rsatadi. Shunday qilib, extended-config.xml da aniqlangan binnar chiqarilishi (ya'ni, almashtirilishi) mumkin base-config.xml da aniqlangan binnar bilan. Quyidagi misolda klass bir bo'lib boshqa klassni kengaytiradi va o'z konfiguratsiya faylidan va yuqori klassning konfiguratsiya faylidan foydalanadi:

Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "/base-config.xml" dan yuklanadi
// classpath ildizidan
@ContextConfiguration("/base-config.xml") 
class BaseTest {
    // klassning tanasi...
}
// ApplicationContext "/base-config.xml" va "/extended-config.xml" dan yuklanadi
// classpath ildizidan
@ContextConfiguration("/extended-config.xml") 
class ExtendedTest extends BaseTest {
    // klassning tanasi...
}
  1. Superklassda aniqlangan konfiguratsiya fayli.
  2. Subklassda aniqlangan konfiguratsiya fayli.
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "/base-config.xml" dan yuklanadi
// classpath ildizidan
@ContextConfiguration("/base-config.xml") 
open class BaseTest {
    // klassning tanasi...
}
// ApplicationContext "/base-config.xml" va "/extended-config.xml" dan yuklanadi
// classpath ildizidan
@ContextConfiguration("/extended-config.xml") 
class ExtendedTest : BaseTest() {
    // klassning tanasi...
}
  1. Superklassda aniqlangan konfiguratsiya fayli.
  2. Subklassda aniqlangan konfiguratsiya fayli.

Xuddi shunday, quyidagi misolda komponent klasslar ishlatilgan, ApplicationContext ExtendedTest uchun BaseConfig va ExtendedConfig dan aniq tartibda yuklanadi. Shunday qilib, ExtendedConfig da aniqlangan binnar chiqarilishi (ya'ni, almashtirilishi) mumkin BaseConfig da aniqlangan binnar bilan. Quyidagi misol klass bir bo'lib boshqa klassni kengaytiradi va o'z konfiguratsiya klassidan va yuqori klassning konfiguratsiya klassidan foydalanadi:

Java
// ApplicationContext BaseConfig dan yuklanadi
@SpringJUnitConfig(BaseConfig.class) 
class BaseTest {
    // klassning tanasi...
}
// ApplicationContext BaseConfig va ExtendedConfig dan yuklanadi
@SpringJUnitConfig(ExtendedConfig.class) 
class ExtendedTest extends BaseTest {
    // klassning tanasi...
}
  1. Superklassda aniqlangan konfiguratsiya klassi.
  2. Subklassda aniqlangan konfiguratsiya klassi.
Kotlin
// ApplicationContext BaseConfig dan yuklanadi
@SpringJUnitConfig(BaseConfig::class) 
open class BaseTest {
    // klassning tanasi...
}
// ApplicationContext BaseConfig va ExtendedConfig dan yuklanadi
@SpringJUnitConfig(ExtendedConfig::class) 
class ExtendedTest : BaseTest() {
    // klassning tanasi...
}
  1. Superklassda aniqlangan konfiguratsiya klassi.
  2. Subklassda aniqlangan konfiguratsiya klassi.

Quyidagi misolda kontekst initializatorlari ishlatilgan, ApplicationContext ExtendedTest uchun BaseInitializer va ExtendedInitializer yordamida inizializatsiya qilinadi. Biroq, inizializatorlar qo'llaniladigan tartib ularnin Ordered interfeysini amalga oshirishlariga va Spring dagi @Order annotatsiyasi yoki standart @Priority annotatsiyasi bilan belgilangani bilan bog'liq. Quyidagi misolda klass bir bo'lib boshqa klassni kengaytiradi va o'z inizializatoridan va yuqori klassning inizializatoridan foydalanadi:

Java
// ApplicationContext BaseInitializer bilan inizializatsiya qilinadi
@SpringJUnitConfig(initializers = BaseInitializer.class) 
class BaseTest {
    // klassning tanasi...
}
// ApplicationContext BaseInitializer va ExtendedInitializer bilan inizializatsiya qilinadi
@SpringJUnitConfig(initializers = ExtendedInitializer.class) 
class ExtendedTest extends BaseTest {
    // klassning tanasi...
}
  1. Superklassda aniqlangan inizializator.
  2. Subklassda aniqlangan inizializator.
Kotlin
// ApplicationContext BaseInitializer bilan inizializatsiya qilinadi
@SpringJUnitConfig(initializers = [BaseInitializer::class]) 
open class BaseTest {
    // klassning tanasi...
}
// ApplicationContext BaseInitializer va ExtendedInitializer bilan inizializatsiya qilinadi
@SpringJUnitConfig(initializers = [ExtendedInitializer::class]) 
class ExtendedTest : BaseTest() {
    // klassning tanasi...
}
  1. Superklassda aniqlangan inizializator.
  2. Subklassda aniqlangan inizializator.
Atrof-muhit profillari yordamida kontekstni konfiguratsiya qilish

Spring Framework atrof-muhit va profil tushunchasini (bean ta'rif profillari) birinchi darajali qo'llab-quvvatlashni taklif qiladi, va integratsiya testlarni turli test ssenariylarida ma'lum bean ta'rif profillarini faollashtirish uchun sozlash mumkin. Bu test klassini @ActiveProfiles annotatsiyasi bilan belgilab, test uchun ApplicationContext yuklaganda faollashtirilishi kerak bo'lgan profillar ro'yxatini ta'minlash orqali erishiladi.

@ActiveProfiles annotatsiyasini SmartContextLoader SPI-ning har qanday amalga oshirilishi bilan ishlatishingiz mumkin, ammo @ActiveProfiles annotatsiyasi eski ContextLoader SPI amalga oshirilishi bilan qo'llab-quvvatlanmaydi.

XML konfiguratsiyasi va @Configuration annotatsiyali klasslar bilan ikkita misolni ko'rib chiqing:

<!-- app-config.xml -->
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:jdbc="http://www.springframework.org/schema/jdbc"
    xmlns:jee="http://www.springframework.org/schema/jee"
    xsi:schemaLocation="...">
    <bean id="transferService"
            class="com.bank.service.internal.DefaultTransferService">
        <constructor-arg ref="accountRepository"/>
        <constructor-arg ref="feePolicy"/>
    </bean>
    <bean id="accountRepository"
            class="com.bank.repository.internal.JdbcAccountRepository">
        <constructor-arg ref="dataSource"/>
    </bean>
    <bean id="feePolicy"
        class="com.bank.service.internal.ZeroFeePolicy"/>
    <beans profile="dev">
        <jdbc:embedded-database id="dataSource">
            <jdbc:script
                location="classpath:com/bank/config/sql/schema.sql"/>
            <jdbc:script
                location="classpath:com/bank/config/sql/test-data.sql"/>
        </jdbc:embedded-database>
    </beans>
    <beans profile="production">
        <jee:jndi-lookup id="dataSource" jndi-name="java:comp/env/jdbc/datasource"/>
    </beans>
    <beans profile="default">
        <jdbc:embedded-database id="dataSource">
            <jdbc:script
                location="classpath:com/bank/config/sql/schema.sql"/>
        </jdbc:embedded-database>
    </beans>
</beans>
Java
@ExtendWith(SpringExtension.class)
// ApplicationContext "classpath:/app-config.xml" dan yuklanadi
@ContextConfiguration("/app-config.xml")
@ActiveProfiles("dev")
class TransferServiceTest {
    @Autowired
    TransferService transferService;
    @Test
    void testTransferService() {
        // transferService-ni sinash
    }
}
Kotlin
@ExtendWith(SpringExtension::class)
// ApplicationContext "classpath:/app-config.xml" dan yuklanadi
@ContextConfiguration("/app-config.xml")
@ActiveProfiles("dev")
class TransferServiceTest {
    @Autowired
    lateinit var transferService: TransferService
    @Test
    fun testTransferService() {
        // transferService-ni sinash
    }
}

TransferServiceTest o'rnatilganda, undagi ApplicationContext sinov klassining ildiz yo'lidagi app-config.xml konfiguratsiya faylidan yuklanadi. app-config.xml ni ko'rib chiqish, AccountRepository bean DataSource biniga bog'liqligini ko'rsatadi. Biroq, dataSource yuqori darajali bin sifatida aniqlanmagan. Buning o'rniga dataSource uch marta, production profilida, dev profilida va default profilida aniqlangan.

TransferServiceTest ni @ActiveProfiles("dev") annotatsiyasi bilan belgilash orqali biz Spring TestContext Framework-ga ApplicationContext ni {"dev"} ga o'rnatilgan faol profillar bilan yuklash haqida buyruq beramiz. Natijada, test ma'lumotlari bilan to'ldirilgan ichki ma'lumotlar bazasi hosil qilinadi va accountRepository bini dev DataSource ga havola bilan bog'lanadi. Bu ehtimol, integratsiya testida olishni istagan narsadir.

Ko'pincha default profiliga binlarni tayinlash maqsadga muvofiqdir. Standart profildagi binnar faollashtirilgan profil aniq e'lon qilinganda o'zgarmaydi. Bu to'ldirish uchun binnarni aniqlashni ta'minlaydi, ular odatda ilova uchun standart holatda foydalanganiladi. Masalan, siz dev va production profillari uchun ma'lumotlar manbasini aniq ko'rsatishingiz mumkin, ammo hech biri faol bo'lmasa, ichki xotira ma'lumotlar manbasini sifatida aniqlang.

Quyidagi kod listinglarda, XML o'rniga @Configuration annotatsiyali klasslar bilan bir xil konfiguratsiyani va integratsiya testini qanday amalga oshirishni ko'rsatib beradi:

Java
@Configuration
@Profile("dev")
public class StandaloneDataConfig {
    @Bean
    public DataSource dataSource() {
        return new EmbeddedDatabaseBuilder()
            .setType(EmbeddedDatabaseType.HSQL)
            .addScript("classpath:com/bank/config/sql/schema.sql")
            .addScript("classpath:com/bank/config/sql/test-data.sql")
            .build();
    }
}
Kotlin
@Configuration
@Profile("dev")
class StandaloneDataConfig {
    @Bean
    fun dataSource(): DataSource {
        return EmbeddedDatabaseBuilder()
                .setType(EmbeddedDatabaseType.HSQL)
                .addScript("classpath:com/bank/config/sql/schema.sql")
                .addScript("classpath:com/bank/config/sql/test-data.sql")
                .build()
    }
}
Java
@Configuration
@Profile("production")
public class JndiDataConfig {
    @Bean(destroyMethod="")
    public DataSource dataSource() throws Exception {
        Context ctx = new InitialContext();
        return (DataSource) ctx.lookup("java:comp/env/jdbc/datasource");
    }
}
Kotlin
@Configuration
@Profile("production")
class JndiDataConfig {
    @Bean(destroyMethod = "")
    fun dataSource(): DataSource {
        val ctx = InitialContext()
        return ctx.lookup("java:comp/env/jdbc/datasource") as DataSource
    }
}
Java
@Configuration
@Profile("default")
public class DefaultDataConfig {
    @Bean
    public DataSource dataSource() {
        return new EmbeddedDatabaseBuilder()
            .setType(EmbeddedDatabaseType.HSQL)
            .addScript("classpath:com/bank/config/sql/schema.sql")
            .build();
    }
}
Kotlin
@Configuration
@Profile("default")
class DefaultDataConfig {
    @Bean
    fun dataSource(): DataSource {
        return EmbeddedDatabaseBuilder()
                .setType(EmbeddedDatabaseType.HSQL)
                .addScript("classpath:com/bank/config/sql/schema.sql")
                .build()
    }
}
Java
@Configuration
public class TransferServiceConfig {
    @Autowired DataSource dataSource;
    @Bean
    public TransferService transferService() {
        return new DefaultTransferService(accountRepository(), feePolicy());
    }
    @Bean
    public AccountRepository accountRepository() {
        return new JdbcAccountRepository(dataSource);
    }
    @Bean
    public FeePolicy feePolicy() {
        return new ZeroFeePolicy();
    }
}
Kotlin
@Configuration
class TransferServiceConfig {
    @Autowired
    lateinit var dataSource: DataSource
    @Bean
    fun transferService(): TransferService {
        return DefaultTransferService(accountRepository(), feePolicy())
    }
    @Bean
    fun accountRepository(): AccountRepository {
        return JdbcAccountRepository(dataSource)
    }
    @Bean
    fun feePolicy(): FeePolicy {
        return ZeroFeePolicy()
    }
}
Java
@SpringJUnitConfig({
        TransferServiceConfig.class,
        StandaloneDataConfig.class,
        JndiDataConfig.class,
        DefaultDataConfig.class})
@ActiveProfiles("dev")
class TransferServiceTest {
    @Autowired
    TransferService transferService;
    @Test
    void testTransferService() {
        // transferService-ni sinash
    }
}
Kotlin
@SpringJUnitConfig(
        TransferServiceConfig::class,
        StandaloneDataConfig::class,
        JndiDataConfig::class,
        DefaultDataConfig::class)
@ActiveProfiles("dev")
class TransferServiceTest {
    @Autowired
    lateinit var transferService: TransferService
    @Test
    fun testTransferService() {
        // transferService-ni sinash
    }
}

Bu variantda biz XML konfiguratsiyasini to'rt mustaqil @Configuration annotatsiyali klassga bo'ldik:

  • TransferServiceConfig: dataSource ni @Autowired annotatsiyasi yordamida inj’ektsiya qilish orqali oladi.

  • StandaloneDataConfig: Ichki ma'lumotlar bazasiga ma'lumotlar manbai aniqlaydi, bu ishlab chiquvchi testlari uchun mos keladi.

  • JndiDataConfig: Ishlab chiqarish muhitida JNDI dan chiqarilgan ma'lumotlar manbaini aniqlaydi.

  • DefaultDataConfig: Agar profil faollashtirilmagan bo'lsa, standart ichki xotira ma'lumotlar manbaini aniqlaydi.

XML-ga asoslangan konfiguratsiya misolidagi kabi, biz hali ham TransferServiceTest ni @ActiveProfiles("dev") annotatsiyasi bilan belgilashda, lekin bu safar to'rtta konfiguratsiya klassini @ContextConfiguration bilan belgilaymiz. Test klassining o'zi esa butunlay o'zgarmay qoladi.

Ko'pincha, birinchi marta ma

Izohlar
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION