Ölçeklenebilir ve yan etki ücretsiz entegrasyon testleri nasıl oluşturulur?


14

Mevcut projemde, yan etkisi olmayan ölçeklenebilir entegrasyon testleri oluşturmak için iyi bir çözüm bulmakta zorlanıyorum. Yan etkisi ücretsiz özelliği hakkında biraz açıklama: çoğunlukla veritabanı ile ilgili; testler tamamlandıktan sonra veritabanında herhangi bir değişiklik olmamalıdır (durum korunmalıdır). Belki ölçeklenebilirlik ve devletin korunması bir araya gelmez, ama gerçekten daha iyi bir çözüm bulmak istiyorum.

İşte tipik bir entegrasyon testi (bu testler veritabanı katmanına dokunur):

public class OrderTests {

    List<Order> ordersToDelete = new ArrayList<Order>(); 

    public testOrderCreation() {
        Order order = new Order();
        assertTrue(order.save());
        orderToDelete.add(order);
    }

    public testOrderComparison() {
        Order order = new Order();
        Order order2 = new Order();
        assertFalse(order.isEqual(order2);
        orderToDelete.add(order);
        orderToDelete.add(order2);
    }
    // More tests

    public teardown() {
         for(Order order : ordersToDelete)
             order.delete();
    }
}

Tahmin edebileceğiniz gibi, bu yaklaşım son derece yavaş testler sağlar. Ve tüm entegrasyon testlerine uygulandığında, sistemin sadece küçük bir bölümünü test etmek yaklaşık 5 saniye sürer. Kapsam arttıkça bu sayının arttığını hayal edebiliyorum.

Bu tür testleri yazmak için başka bir yaklaşım ne olabilir? Düşünebileceğim bir alternatif, bir sınıfta küresel değişkenlere sahip olmaktır ve tüm test yöntemleri bu değişkeni paylaşır. Sonuç olarak, yalnızca birkaç sipariş oluşturulur ve silinir; daha hızlı testlerle sonuçlanır. Ancak, bunun daha büyük bir sorun getirdiğini düşünüyorum; testler artık izole edilmedi ve bunları anlamak ve analiz etmek gittikçe zorlaşıyor.

Entegrasyon testlerinin birim testler kadar sık ​​yapılması gerekmiyor olabilir; bu nedenle düşük performans olanlar için kabul edilebilir. Her durumda, birisinin ölçeklenebilirliği geliştirmek için alternatifler bulup bulmadığını bilmek harika olurdu.

Yanıtlar:


6

Birim testi için Hipersonik veya başka bir bellek içi DB kullanmayı düşünün. Testler sadece daha hızlı yürütülmekle kalmaz, aynı zamanda yan etkiler de önemli değildir. (Her testten sonra işlemlerin geri alınması aynı örnek üzerinde birçok testin yapılmasını da mümkün kılar)

Bu aynı zamanda, üretim veritabanında meydana gelen bir şeyin testlerinizi başarısızlıkla başlatamayacağı anlamına gelen iyi bir şey olan IMO veri mockup'ları oluşturmaya zorlar ve size "temiz bir veritabanı yüklemesi" "gibi görünüyor; bu, uygulamanın mevcut üretim sitenizle bağlantısı olmayan yeni bir örneğini birden dağıtmanız gerektiğinde yardımcı olur.

Evet, bu yöntemi kendim kullanıyorum ve evet İLK zamanı ayarlamak için bir PITA'ydı, ancak tamamlanmak üzere olduğum projenin ömrü boyunca kendisi için ödendiğinden fazla. Ayrıca veri maketlerine yardımcı olan bir dizi araç vardır.


Harika bir fikir gibi geliyor. Özellikle tam izolasyon yönünü seviyorum; yeni bir veritabanı kurulumu ile başlayalım. Görünüşe göre biraz çaba gerektirecek, ancak bir kez kurulduktan sonra çok faydalı olacak. Teşekkürler.
Güven

3

Bu, entegrasyon testleri yazarken herkesin karşılaştığı sonsuz sorundur.

İdeal çözüm, özellikle de üretim üzerinde test yapıyorsanız, kurulumda bir işlem açmak ve sökümde geri almaktır. Bunun ihtiyaçlarınızı karşılaması gerektiğini düşünüyorum.

Bunun mümkün olmadığı durumlarda, örneğin uygulamayı istemci katmanından test ettiğinizde, başka bir çözüm sanal makinede bir DB kullanmak ve kurulumda bir anlık görüntü almak ve sökme işlemine geri dönmek ( beklediğiniz sürece).


İşlem geri alımını düşünmediğime inanamıyorum. Bu fikri çözüme hızlı bir çözüm olarak kullanacağım, ancak sonuçta bellek içi DB çok umut verici geliyor.
Güven

3

Entegrasyon testleri her zaman üretim kurulumuna karşı yapılmalıdır. Sizin durumunuzda, aynı veritabanına ve uygulama sunucusuna sahip olmanız gerektiği anlamına gelir. Elbette, performans uğruna bir bellek içi DB kullanmaya karar verebilirsiniz.

Asla yapmamanız gereken şey işlem kapsamınızı genişletmektir. Bazı insanlar işlemin kontrolünü ele geçirmeyi ve testlerden sonra geri almayı önerdi. Bunu yaptığınızda, tüm varlıklar (JPA kullandığınız varsayılarak) , test yürütme boyunca kalıcılık bağlamına bağlı kalacaktır . Bu, bulmak çok zor bazı çok kötü hatalar ile sonuçlanabilir .

Bunun yerine, böyle Kütüphane üzerinden her testten sonra veritabanını el temizlemek gerekir JPAUnit veya benzeri bu yaklaşımın (JDBC kullanarak tüm tabloları temizleyin).

Performans sorunlarınız nedeniyle, tüm yapılarda entegrasyon testlerini yürütmemelisiniz. Sürekli entegrasyon sunucunuzun bunu yapmasına izin verin. Maven kullanıyorsanız, testlerinizi birim ve entegrasyon testlerine ayırmanıza olanak tanıyan güvenli olmayan eklentinin tadını çıkarabilirsiniz .

Ayrıca, hiçbir şeyle alay etmemelisiniz. Unutmayın entegrasyon testi, yani çalışma zamanı yürütme ortamında test davranışı.


İyi cevap. Bir nokta: Bazı dış bağımlılıkları (örneğin e-posta gönderme) taklit etmek kabul edilebilir. Ancak, tam bir sahte hizmet / sunucu kurarak sahte yapmalısınız, Java kodunda alay etmeyin.
sleske

Sleske, sana katılıyorum. Özellikle JPA, EJB, JMS kullanırken veya başka bir spesifikasyona karşı uygularken. Uygulama sunucusunu, kalıcılık sağlayıcısını veya veritabanını değiştirebilirsiniz. Örneğin, hızı ayarlamak ve geliştirmek için gömülü Glassfish ve HSQLDB kullanmak isteyebilirsiniz (elbette başka bir sertifikalı uygulama seçmekte özgürsünüz).
BenR

2

Ölçeklenebilirlik hakkında

Bu sorunu daha önce bir kaç kez yaşadım, entegrasyon testlerinin çalışması çok uzun sürüyordu ve tek bir geliştiricinin sürekli bir değişiklik geri bildirimi döngüsünde çalışması için pratik değildi. Bununla başa çıkmak için bazı stratejiler:

  • Daha az entegrasyon testi yazın - sistemdeki birim testleri ile iyi bir kapsama sahipseniz, entegrasyon testleri farklı bileşenlerin birlikte nasıl çalıştığına daha fazla (ahem) entegrasyon konularına odaklanmalıdır. Duman testlerine daha benzerler, sadece sistemin hala bir bütün olarak çalışıp çalışmadığını görmeye çalışırlar. İdeal olarak, birim testleriniz uygulamanın fonksiyonel bölümlerinin çoğunu kapsar ve entegrasyon testleri bu parçaların birbirleriyle nasıl etkileştiğini kontrol eder. Burada mantıksal yolların kapsamlı bir şekilde kapsanmasına gerek yoktur, sadece sistemdeki bazı kritik yollar.
  • Bir seferde sadece testlerin bir alt kümesini çalıştırın - bazı işlevler üzerinde çalışan tek bir geliştirici olarak, normalde bu işlevselliği kapsamak için hangi testlerin gerekli olduğunu hissedersiniz. Yalnızca değişikliklerinizi kapsamak için anlamlı olan testleri yapın. JUnit gibi çerçeveler , bir kategorideki fikstürleri gruplandırmanıza izin verir . Sahip olduğunuz her özellik için en iyi kapsamı sağlayan gruplamaları oluşturun. Tabii ki, hala tüm entegrasyon testlerini bir noktada, belki de kaynak kontrol sistemine geçmeden önce ve kesinlikle sürekli entegrasyon sunucusunda çalıştırmak istiyorsunuz.
  • Sistemi optimize edin - Bazı performans testleriyle birleştirilmiş entegrasyon testleri , sistemin yavaş parçalarını ayarlamak için gerekli girişi sağlayabilir, böylece testler daha sonra daha hızlı çalışır. Bu, veritabanında gerekli dizinlerin, alt sistemler arasındaki konuşkan arayüzlerin veya adreslenmesi gereken diğer performans darboğazlarının ortaya çıkarılmasına yardımcı olabilir.
  • Testlerinizi paralel olarak gerçekleştirin - İyi bir ortogonal test grubunuz varsa, paralel olarak çalıştırmayı deneyebilirsiniz . Özenli olun dik olsa söz gereksinimi, sen birbirlerinin ayak adım Testlerinizi istemiyoruz.

Daha fazla etki için bu teknikleri birleştirmeyi deneyin.


1
Gerçekten iyi yönergeler; daha az entegrasyon testi yazmak en iyi tavsiyedir. Ayrıca, bunları paralel olarak çalıştırmak çok iyi bir alternatif olacaktır; Testlerimi doğrudan izolasyon açısından alıp almadığımı kontrol etmek için mükemmel bir "test".
Güven

2

Test amacıyla, bir SQLite veritabanının dosya tabanlı dağıtımını kullandık (sadece bir kaynağı kopyalayın). Bu, şema geçişlerini de test edebilmemiz için yapıldı. Bildiğim kadarıyla, şema değişiklikleri işlemsel değildir, bu nedenle bir işlem iptal edildikten sonra geri alınmaz. Ayrıca test kurulumu için işlem desteğine güvenmek zorunda kalmamak, işlemlerinizin davranışını uygulamanızdan düzgün bir şekilde test etmenizi sağlar.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.