Jaki problem rozwiązuje automatyczne testowanie interfejsu użytkownika?


23

Obecnie badamy automatyczne testy interfejsu użytkownika (obecnie przeprowadzamy automatyczne testy jednostkowe i integracyjne).

Przyjrzeliśmy się Selenium i Telerik i zdecydowaliśmy się na to drugie jako narzędzie wyboru ze względu na znacznie bardziej elastyczny rejestrator - i tak naprawdę nie chcemy, aby testerzy pisali za dużo kodu.

Staram się jednak zrozumieć ogólną korzyść. Jakie są poglądy ludzi i jakie rzeczy działają dobrze, a co nie?

Nasz system jest stale rozwijany i regularnie publikujemy nowe wersje naszej platformy (internetowej).

Jak dotąd główną korzyścią, jaką widzimy, są testy regresji, szczególnie w przypadku wielu wdrożeń klienckich naszej platformy.

Naprawdę szukam poglądów innych ludzi. „Uważamy”, że jest to słuszne, ale w napiętym już harmonogramie szukamy dodatkowych informacji.


4
Czy termin „automatyczne testowanie” nie oznacza problemu, który próbuje rozwiązać? // OTOH, jeśli pytasz o ROI związane z „automatycznymi testami”, to inne pytanie ...
Jim G.,

Odpowiedzi:


24

Kiedy mój zespół wdrożył automatyczne testowanie interfejsu użytkownika, wydarzyło się wiele wspaniałych rzeczy.

Po pierwsze, zespół QA stał się znacznie bardziej wydajny w testowaniu aplikacji, a także bardziej biegły w aplikacji. Główny QA powiedział, że jest w stanie szybko przyspieszyć nowych członków QA, wprowadzając ich do pakietów testowych interfejsu użytkownika.

Po drugie, jakość biletów QA, które wróciły do ​​zespołu deweloperów, była lepsza. Zamiast „Strona się zepsuła, kiedy kliknąłem przycisk Prześlij”, otrzymaliśmy dokładny przypadek, który nie powiódł się, abyśmy mogli zobaczyć, co zostało wprowadzone do formularza. Zespół kontroli jakości posunął się także o krok dalej, sprawdzając wszystkie przypadki, które zakończyły się niepowodzeniem, i przetestował inne scenariusze na tej stronie, aby uzyskać lepszy obraz tego, co się stało.

Po trzecie, zespół QA miał więcej czasu. Dzięki temu dodatkowemu czasowi mogli zasiąść na kolejnych spotkaniach projektowych. To z kolei pozwoliło im pisać nowe przypadki pakietu testowego w tym samym czasie, gdy deweloperzy kodowali te nowe funkcje.

Warto też podkreślić, że zastosowany przez nas zestaw testów warunków skrajnych był na wagę złota. To szczerze pomogło mi lepiej spać w nocy, wiedząc, że nasza aplikacja może znieść prawie wszystko. Znaleźliśmy sporo stron, które uległy presji, którą udało nam się naprawić przed uruchomieniem. Po prostu perfekcyjnie.

Ostatnią rzeczą, którą odkryliśmy, było to, że z pewnymi poprawkami dokonanymi przez zespół kontroli jakości, moglibyśmy również przeprowadzić testy wstrzykiwania SQL w naszej aplikacji. Znaleźliśmy pewne luki, które udało nam się szybko naprawić.

Instalacja zestawu testów interfejsu użytkownika zajęła sporo czasu. Ale kiedy już tam był, stał się centralną częścią naszego procesu rozwoju.


1
+1 za wyjaśnienie kroków do odtworzenia nieudanego testu będącego nieodłącznym
elementem

Jeden problem: czy testowanie jednostkowe interfejsu użytkownika nie blokuje potencjalnych zmian w interfejsie użytkownika [blokuje cię] ... chociaż głosowałem, ponieważ opisałeś tę korzyść w taki sposób, że ogólny czas działania aplikacji jest monitorowany przez testy jednostkowe, a nie pojedynczy element testowanego systemu.
mnichów,

@monksy - Zestaw testowy, którego użyliśmy (nie pamiętam, jak nazywa się moje życie) nie był oparty na współrzędnych. Był wystarczająco inteligentny, aby używać identyfikatorów elementów. Tak długo, jak nadaliśmy nazwy wszystkich elementów interfejsu użytkownika i zachowaliśmy te nazwy poprzez zmiany projektu, przypadki testowe nadal działały. Zapłaciliśmy dość grosza za to oprogramowanie, ale uważaliśmy, że ta funkcja była tego warta.
Tyanna,

1
@Tyanna Zaufaj mi w tym ... to było. Próbowałem zautomatyzować testowanie interfejsu użytkownika [do testów regresywnych] na podstawie lokalizacji. To nie działa i jest dość frustrujące. Btu Miałem na myśli przenoszenie komponentów wokół, zmienianie widoków / interfejsu użytkownika i tematycznych interfejsów użytkownika
monksy,

13

Zautomatyzowane testy interfejsu użytkownika są prawdziwymi testami integracji. Testują cały system w sposób, w jaki jest faktycznie używany, gdy jest aktywny. To sprawia, że ​​są to najbardziej znaczące testy. Jednak są one również najbardziej kruche i najwolniejsze do wykonania.

Miej oko na stosunek kosztów do korzyści (z kruchością będącą częścią kosztów) i nie wahaj się, aby mieć pewne rzeczy, które są testowane tylko ręcznie (ale upewnij się, że testowane). Jeśli to w ogóle możliwe, pozwól programistom na uruchamianie określonych części pakietu testów interfejsu użytkownika na lokalnie działającą wersję aplikacji, aby mogli skorzystać z testów podczas programowania.

Oczywiście testy muszą być uruchamiane automatycznie na serwerze kompilacji (przynajmniej raz dziennie).

tak naprawdę nie chcemy, aby testerzy pisali za dużo kodu.

IMO to marzenie o fajce. Tworzenie testów automatycznych to pisanie kodu. Funkcja nagrywania mogą pomóc napisać trochę tego kodu szybciej i zacząć szybciej z pisania ręcznego (i spowolnić strasznie jeśli pominąć punkt, w którym pisanie kodu ręcznie staje się szybciej), ale ostatecznie pisać kod ręcznie jest to, co będzie skończyć robić dużo. Lepiej mieć nadzieję, że twoja platforma testowa dobrze ją obsługuje i nie koncentrowała się zbytnio na marzeniu (bardzo możliwym do sprzedania), jakim jest umożliwienie osobom, które nie potrafią pisać kodu, tworzyć automatycznych testów.


13

i tak naprawdę nie chcemy, aby testerzy pisali za dużo kodu

Przyjęliśmy odwrotne podejście. Chcieliśmy, aby testerzy pisali kod.

Oto przepływ pracy, który zaczęliśmy stosować. Nie jest to łatwe, ponieważ zarządzanie nie zależy absolutnie od zautomatyzowanych testów interfejsu. Są gotowi zadowolić się „wystarczająco blisko”.

  1. Historie użytkownika.

  2. Koncepcja operacyjna. Jak ta historia prawdopodobnie by działała. Przegląd projektu.

  3. Szkic ekranu: projekt interfejsu użytkownika. Jak by to wyglądało.

  4. Skrypty selenu. Jeśli wszystkie skrypty działają, skończyliśmy z wydaniem.

  5. Kodowanie i testowanie do momentu uruchomienia skryptu.

Zautomatyzowane testowanie jest jedynym sposobem wykazania, że ​​funkcjonalność istnieje.

Testowanie ręczne jest podatne na błędy i podlega obejściu zarządzania: „jest wystarczająco dobry, te nieudane testy nie mają tak wielkiego znaczenia, jak zwolnienie go na czas”.

„Żadna funkcja programu bez automatycznego testu po prostu nie istnieje”.

Prezentacja wizualna to inna historia. Ręczne testowanie układu wizualnego jest wyjątkowym przypadkiem, ponieważ może obejmować ocenę estetyczną lub spojrzenie na konkretne (małe) problemy na bardzo dużym i złożonym ekranie pikseli.


2
„testerzy piszą zautomatyzowane czeki”. W ten sposób testerzy powinni wykonywać swoje zadania. „testerzy kiedykolwiek mają szansę przetestować” nie ma dla mnie większego sensu. Czy możesz wyjaśnić, co to może znaczyć?
S.Lott,

3
@ S.Lott: prawdopodobnie testy ręczne. Zautomatyzowane testowanie jest fajne, ale nie wszystko. Nie może wykryć wielu nieoczekiwanych trybów błędów (takich jak problem z układem). Powiedziałbym, że fundamentalizm przedstawiony w dwóch ostatnich zdaniach przynosi efekt przeciwny do zamierzonego.
Michael Borgwardt,

11
Automated testing is the only way to demonstrate that the functionality exists.Nie, nie jest. Testy eksploracyjne lub testy przeprowadzone ręcznie wykazują, że funkcjonalność istnieje. Nie jest tak dobry jak automatyczne testowanie, ale automatyczne testowanie nie jest jedynym sposobem testowania.
StuperUser

1
@ S.Lott - Michael i StuperUser mieli rację. Testy ręczne i najlepiej eksploracyjne.
Lyndon Vrooman,

1
-1 dla fundamentalizmu, jak to ujął Michael. Zobacz joelonsoftware.com/items/2007/12/03.html, aby uzyskać wyjaśnienie, jak absurdalne jest to podejście, jeśli chodzi o jego logiczne zakończenie.
Mason Wheeler,

5

Jak dotąd główną korzyścią, jaką widzimy, są testy regresji, szczególnie w przypadku wielu wdrożeń klienckich naszej platformy.

Zautomatyzowanie testów regresji jest dobrą rzeczą. Dzięki temu testerzy mogą wykonywać ciekawsze prace - dodając więcej automatycznych testów, testując aplikacje pod obciążeniem lub dowolną liczbę innych rzeczy.

Ponadto, czyniąc go zautomatyzowanym, możesz zachęcić programistów do uruchomienia testów, a tym samym zapobiegać problemom wykrywanym dopiero później.


Jakie masz doświadczenie, że utrzymywanie automatycznych testów regresji uwalnia testerów do wykonywania bardziej interesującej pracy? Wiem, że to jest teoria, ale jeśli napisanie lub zmodyfikowanie testów zajmuje kilka dni, a nie tylko wykonanie testów ręcznych, może się nie udać.
IThasTheAnswer

@Tunic - Używamy Silverlight w naszym bieżącym projekcie i piszę teraz kilka testów, które sprawdzają powiązania między XAML a kodem modelu widoku C #. Oznacza to, że nasi testerzy nie muszą sprawdzać, czy wprowadzane przez nich wartości są poprawnie sformatowane itp. Jest jeszcze wcześnie, ale wygląda obiecująco.
ChrisF

5

Przyjrzeliśmy się Selenium i Telerik i zdecydowaliśmy się na to drugie jako narzędzie wyboru ze względu na znacznie bardziej elastyczny rejestrator

Nie jestem pewien, jak bardzo na to spojrzałeś. Z pewnością są też inne opcje. Pan spojrzał na Watir , Watin , Sikuli aby wymienić tylko kilka?

i tak naprawdę nie chcemy, aby testerzy pisali za dużo kodu.

Szkoda mi ludzi, którzy muszą utrzymywać te skrypty. Najczęściej bez kodu, który można łatwo zmodyfikować, skrypty stają się kruche i modyfikowanie skryptu trwa dłużej niż ponowne rejestrowanie, co marnuje jeszcze więcej czasu.

Staram się jednak zrozumieć ogólną korzyść. Jakie są poglądy ludzi i jakie rzeczy działają dobrze, a co nie?

Automatyzacja testów jest piękną rzeczą, jeśli jest wykonana poprawnie. Oszczędza czas na testach / kontrolach regresji, aby dać testerom więcej czasu na robienie tego, co robią najlepiej. Przez chwilę nie wierzcie jednak, że to srebrna kula. Skrypty automatyzacji wymagają dużo czasu, aby opracować, jeśli aplikacja już istnieje, ale testy nie, i wymagają ciągłej aktualizacji z każdą wersją. Zautomatyzowane testy to także świetny sposób dla nowych osób w zespole, aby zobaczyć, jak powinien zachowywać się system. Upewnij się także, że testerzy decydują, co należy zautomatyzować. Jeśli jest to niewielki czek, którego sprawdzenie nie zajmuje dużo, jest bardzo monotonna i łatwa do zautomatyzowania, zacznij od tego. Zawsze zaczynaj od kontroli, które zyskują najwięcej dzięki automatyzacji, i pracuj stamtąd.

Jak dotąd główną korzyścią, jaką widzimy, są testy regresji, szczególnie w przypadku wielu wdrożeń klienckich naszej platformy.

Jest to główna zaleta, a jeśli zostanie poprawnie skonfigurowana, może przetestować większość przeglądarek, których potrzebujesz przy niewielkiej zmianie konfiguracji.

„Uważamy”, że jest to słuszne, ale w napiętym już harmonogramie szukamy dodatkowych informacji.

Jak wspomniałem wcześniej, automatyzacja testów wymaga znacznych wysiłków, jednak przy prawidłowym wykonaniu nie spotkałem jeszcze zespołu, który powiedziałby „Szkoda, że ​​nie skonfigurowaliśmy naszej automatyzacji testów”.


2
+1 szczególnie za „Źle się czuję z ludźmi, którzy muszą utrzymywać te skrypty”. Dobrze zaprojektowany kod jest kluczową częścią pisania możliwych do utrzymania testów interfejsu użytkownika, szczególnie w przypadku często zmieniającego się interfejsu użytkownika. Jeśli testerzy PO nie mogą korzystać z Obiektów Strony lub ponownie wykorzystywać kodu, radziłbym OP rozważyć automatyzację tylko stabilnego interfejsu użytkownika (jeśli taki istnieje).
Ethel Evans,

3

Masz rację, że regresja jest ogromna. Również -

  • jeśli twoje testy są napisane modułowo, możesz zarobić więcej, mieszając i dopasowując zestawy testów

  • ponownie wykorzystaliśmy automatyczne skrypty testowe do ładowania danych, abyśmy nie musieli blokować bazy danych w celu testowania dużych rozmiarów

  • test wydajności

  • testy wielowątkowe

  • w systemach internetowych - wymiana między przeglądarkami i wymiana między systemami operacyjnymi. W przypadku problemów ze spójnością przeglądarki ogromne znaczenie ma uderzenie w tak szeroką bazę, jak to możliwe.

Rzeczy, które należy pominąć - szczególnie w systemach internetowych, uważaj na przypadki, w których elementy twojego wyświetlacza są tworzone z dynamicznymi, zmieniającymi się identyfikatorami - często automatyczne skrypty testowe nie radzą sobie tak dobrze, a może to wymagać poważnego przeprojektowania, aby to zaktualizować.


+1 za pierwszy punkt. Absolutnie krytyczny dla udanego pakietu automatyzacji testów!
Lyndon Vrooman,

Tak, zgadzam się z pierwszym punktem. Zastanawiałem się właściwie nad drugą i trzecią kwestią, ale myślę, że to tutaj upada Telerik. Skrypty selenowe (w stanie prostych) mogą być używane przez BroswerMob
IThasTheAnswer

3

Tylko jeden przykład: dokładny pomiar czasu renderowania strony internetowej

Korzystając z testów automatyzacji, znacznie łatwiej jest przetestować działanie przeglądarki internetowej. Aby zmierzyć maksymalny czas odpowiedzi, który prawdopodobnie zaakceptujesz, po prostu ustaw stałą w skryptach testowych i / lub przekaż ją jako parametr funkcji, np. W tym pseudokodzie: $ sel-> wait_for_page_to_load ($ mypage, $ maxtime).

Przeprowadzanie testów w różnych przeglądarkach przy niskich wartościach może być całkiem pouczające.

Alternatywą byłoby zlecenie pracownikom pomiaru czasu za pomocą stopera.


3

Zautomatyzowane testowanie interfejsu użytkownika rozwiązuje możliwość:

  • szybko powtarzaj testy dużej liczby komponentów
  • pamiętaj, aby za każdym razem testować dużą liczbę funkcji
  • porównaj przebiegi i czasy uruchamiania zestawów testowych w miarę rozwoju aplikacji
  • skonfigurować przebiegi z setkami różnych danych wejściowych i zmiennych warunków
  • umożliwić osobom, które nie napisały testu, uruchomienie go i dostrzeżenie problemów wizualnych
  • pozwalają użytkownikom końcowym zobaczyć aplikację używaną w szybki i łatwy sposób
  • rozpowszechnianie testów interfejsu użytkownika do sieci, zdalnego serwera lub usługi
  • rozpocząć testowanie objętości przy użyciu maszyn równoległych.

Jednak, jak zauważyli inni:

Telerik ...

narzędzie wyboru ze względu na znacznie bardziej elastyczny rejestrator

jest czerwoną flagą dla wielu z nas.

Skrypty zarejestrowane w ten sposób zwykle nie są rozwiązaniem długoterminowym, ponieważ:

  • identyfikator bazy danych / obiektu może się zmieniać w zależności od przypadku
  • ręcznie nagrane skrypty często polegają na często zmieniających się znacznikach układu strony
  • wspólne działania będą musiały być zapisywane w kółko zamiast zezwalać na ponowne użycie (patrz podejście SitePrism i PageObject)
  • czasem trzeba użyć narzędzi takich jak xpath, aby uzyskać dodatkowe informacje na podstawie bieżących informacji o stronie. Prosty nagrany skrypt tego nie zrobi.
  • programiści i testerzy, którzy piszą kod, nie będą zachęcani do korzystania z klas CSS, identyfikatorów i atrybutów danych HTML5, które są praktykami prowadzącymi do bardziej niezawodnych, łatwych w utrzymaniu testów.

Telerik ma jednak pewne zalety, które należy wziąć pod uwagę:

  • skierowany do klientów mobilnych
  • wbudowane narzędzia do zarządzania wzrostem
  • obsługuje Android, iOS i Windows Phone

Podejście, które może pomóc w uzupełnieniu braków, polega na zarejestrowaniu początkowego skryptu za pomocą narzędzia do rejestrowania stron narzędzi, a następnie zmianie skryptu na używanie identyfikatorów, klas i atrybutów danych, aby trwał on z czasem. Jest to podejście, którego faktycznie użyłem z wtyczką selenu firefox.


2

Dzięki temu „Testowanie eksperckie” (podobne do „Testów eksploracyjnych”, ale przeprowadzane przez użytkowników końcowych lub członków zespołu z dużą wiedzą biznesową) jest łatwiejsze do przeprowadzenia, rejestrowania wyników, pomiaru i automatyzacji.


2

Przychodzę do tego z innego tła. U moich byłych pracodawców opracowaliśmy komercyjne narzędzia do automatycznego testowania (QALoad, QARun, TestPartner, SilkTest, SilkPerfomer).

Zauważyliśmy automatyczne testowanie interfejsu użytkownika jako wypełniające dwie role:

  1. Pełne testy regresji

  2. Zautomatyzowana konfiguracja środowisk testowych

Mocno oparliśmy się na narzędziach do przeprowadzania testów regresji w nocy. Po prostu nie mieliśmy siły człowieka do przetestowania wszystkich przycisków i okien dialogowych, aby sprawdzić, czy nie zepsuliśmy niczego między interfejsem użytkownika a logiką biznesową.

W przypadku ważniejszych testów stwierdziliśmy, że jedna osoba może rozpędzić kilka maszyn wirtualnych i użyć skryptów, aby przejść do prawdziwego testu. Pozwala im skupić się na ważnych elementach i nie próbuje wykonywać 24-etapowych przypadków testowych.

Jedynym problemem związanym z automatycznymi testami był zwyczaj zrzucania zbyt wielu testów do pudełka bez jakiegokolwiek nadzoru, aby wyeliminować duplikaty lub niepotrzebne testy. Co jakiś czas musieliśmy wchodzić i przycinać rzeczy, aby apartament mógł zostać ukończony w mniej niż 12 godzin.


2

Zautomatyzowane testowanie dowolnego rodzaju zapewnia testy regresyjne; uruchamiając test, który kiedyś działał, upewniasz się, że nadal działa (lub nie działa) bez względu na to, co dodałeś. Dzieje się tak niezależnie od tego, czy test jest testem integracji (który zwykle nie dotyka interfejsu użytkownika), czy AAT (który zwykle wymaga interfejsu użytkownika).

Zautomatyzowane testowanie interfejsu użytkownika umożliwia testowanie systemu tak, jakby użytkownik klikał przyciski. Takie testy można zatem wykorzystać do zweryfikowania nawigacji w systemie, poprawności etykiet i / lub komunikatów, wydajności i / lub czasów ładowania w określonym środowisku testowym itp. Podstawowym celem jest ograniczenie czasu spędzanego przez pracownika działu jakości na klikaniu przycisków, podobnie jak integracja i testy jednostkowe dla programisty. Może raz skonfigurować jeden test (zwykle poprzez rejestrowanie własnych kliknięć myszką i wpisów danych w skrypcie), a gdy test zadziała prawidłowo, wszystko, co powinien zrobić, aby sprawdzić poprawność testowanego systemu, uruchom go ponownie. Niektóre frameworki, takie jak Selenium, pozwalają na migrację testów między przeglądarkami, umożliwiając testowanie kilku środowisk, w których strona powinna działać poprawnie.

Bez testów automatycznych jesteś ograniczony liczbą i szybkością testerów kontroli jakości; muszą mieć dosłownie praktyczny system, testując, czy nowa funkcja spełnia wymagania i (co równie ważne), czy nie zepsułeś niczego, co już tam było.


0

Testowanie determinuje wiele różnych rzeczy. Wiele z tych testów można zautomatyzować, aby umożliwić usunięcie znoju i zrobić więcej. Aby ustalić, czy testy można zautomatyzować, najpierw musisz sprawdzić, czy zadane przez nich pytanie jest odpowiednie.

  • Czy określasz, czy komponent działa zgodnie ze specyfikacją?
  • Czy chcesz przetestować wszystkie możliwe wejścia i wyjścia?
  • test warunków skrajnych składnik?
  • A może próbujesz sprawdzić, czy „to działa”?

Większość z nich można zautomatyzować, ponieważ mają one charakter mechaniczny. Nowa funkcja akceptuje dane wejściowe, więc co się stanie, gdy wyrzucimy na nią losowe dane? Ale niektóre, takie jak testowanie, czy system działa, wymaga od kogoś faktycznego korzystania z niego. Jeśli nie, nigdy nie będziesz wiedzieć, czy oczekiwania użytkowników są takie same jak oczekiwania programu. Dopóki system się nie „zepsuje”.


-1

Z mojego doświadczenia wynika, że ​​automatyczne testowanie interfejsu użytkownika obejmuje wiele luk, w tym:

  • Brak dokumentacji (przykład: użycie automatycznego testera do demonstracji istniejącej funkcjonalności)
  • Nieaktualne wymagania z powodu pełzania zakresu (przykład: identyfikowanie luki między wymaganiami a kodem poprzez przechwytywanie ekranu podczas testów)
  • Wysokie obroty programistów i testerów (przykład: wsteczna starsza inżynieria JavaScript poprzez przechwytywanie ekranu podczas testów z otwartym narzędziem programisty)
  • Identyfikacja naruszeń standardowych konwencji nazewnictwa za pomocą testów regresji XPath (przykład: przeszukiwanie wszystkich węzłów atrybutów DOM w poszukiwaniu nazw wielbłądów)
  • Rozpoznawanie luk w zabezpieczeniach, które może wykryć tylko komputer (na przykład: wyloguj się z jednej karty, jednocześnie przesyłając formularz w drugiej)

1
Jak to pomaga w tych sprawach? Byłoby miło, gdybyś mógł trochę rozwinąć.
Hulk,

-1

Chciałbym podzielić się doświadczeniem naszego zespołu. Używamy własnego narzędzia do testowania interfejsu użytkownika, Screenster, do testowania aplikacji internetowych naszych i naszych klientów. Sprawdził się jako pomocna alternatywa dla Selenium do zadań testowania wizualnego / CSS. Screenster to narzędzie do automatyzacji testów, które dokonuje porównania różnych wersji stron na podstawie zrzutów ekranu. Najpierw tworzy wizualną linię bazową strony, wykonując zrzut ekranu dla każdej akcji użytkownika. Podczas następnego uruchomienia na każdym kroku wykonuje nowy zrzut ekranu, porównuje go z tym z linii bazowej i podkreśla różnice.

Podsumowując, Screenster ma następujące zalety: Wizualna linia bazowa: zrzuty ekranu są przechwytywane dla każdego kroku użytkownika podczas nagrywania testowego Porównanie oparte na zrzutach ekranu: Screenster porównuje obrazy przechwycone podczas odtwarzania z obrazami od linii podstawowej i podkreśla wszystkie różnice Inteligentne selektory CSS: tester może wybrać Elementy CSS na zrzutach ekranu i wykonuj z nimi działania - np. Oznacz je jako regiony ignorowania, aby wykluczyć z dalszego porównania

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.