Hva er mutasjonstesting? (Eksempel)
โก Smart oppsummering
Mutasjonstesting introduserer bevisst smรฅ feil i kildekoden og kjรธrer deretter den eksisterende testsuiten mot hver feilaktige versjon, for รฅ mรฅle om disse testene er sterke nok til รฅ oppdage endringen.
Hva er mutasjonstesting?
Mutasjonstesting er en type programvaretesting der visse utsagn i kildekoden endres eller muteres for รฅ sjekke om testtilfellene er i stand til รฅ finne feil i kildekoden. Mรฅlet med mutasjonstesting er รฅ sikre kvaliteten pรฅ testtilfellene nรฅr det gjelder robusthet, slik at de ikke klarer รฅ motstรฅ den muterte kildekoden.
Endringen som gjรธres i et mutantprogram mรฅ holdes ekstremt liten, slik at den ikke pรฅvirker programmets overordnede mรฅl. Mutasjonstesting kalles ogsรฅ en feilbasert teststrategi, fordi den innebรฆrer รฅ bevisst lage en feil i programmet. Det er en form for Hvit Box Testing som hovedsakelig brukes under Enhetstesting.
Mutasjonstesting ble foreslรฅtt i 1971 i en studentartikkel av Richard Lipton og formalisert i artikkelen ยซHints on Test Data Selectionยป fra 1978 av DeMillo, Lipton og Sayward. Den mistet momentum pรฅ grunn av datidens datakostnad og har siden gjenvunnet terreng for sprรฅk som Java, C#, Python, JavaSkript og XML.
Hvordan utfรธre mutasjonstesting?
Fรธlgende er trinnene for รฅ utfรธre mutasjonstesting, ogsรฅ kjent som mutasjonsanalyse:
Trinn 1: Feil introduseres i programmets kildekode ved รฅ opprette mange versjoner kalt mutanter. Hver mutant skal inneholde รฉn enkelt feil, og mรฅlet er รฅ forรฅrsake at mutantversjonen feiler, noe som demonstrerer effektiviteten til testtilfellene.
Trinn 2: Testtilfeller brukes pรฅ det opprinnelige programmet og ogsรฅ pรฅ mutantprogrammet. Testsak skal vรฆre tilstrekkelig, og den er tilpasset for รฅ oppdage feil i et program.
Trinn 3: Sammenlign resultatene fra det opprinnelige og mutantprogrammet.
Trinn 4: Hvis det originale programmet og mutantprogrammet genererer ulik utdata, blir mutanten drept av testtilfellet. Derfor er testtilfellet godt nok til รฅ oppdage endringen mellom det originale og mutantprogrammet.
Trinn 5: Hvis det opprinnelige programmet og mutantprogrammet genererer samme utdata, holdes mutanten i live. I slike tilfeller mรฅ det lages mer effektive testtilfeller som dreper alle mutantene.
Diagrammet nedenfor tracfรธlger de samme fem trinnene, fra det opprinnelige programmet gjennom mutantgenerering til den drepte eller overlevende dommen.
Hvordan lage mutantprogrammer?
En mutasjon er ikke annet enn en enkelt syntaktisk endring som gjรธres i en programsetning. Hvert mutantprogram skal avvike fra det opprinnelige programmet med nรธyaktig รฉn mutasjon.
| Originalt program | Mutant program |
| Hvis (x>y) Skriv ut "Hei" Else Skriv ut "Hei" |
Hvis (x Skriv ut "Hei" Else Skriv ut "Hei" |
I paret ovenfor er bare sammenligningsoperatoren endret, men et testtilfelle der x er stรธrre enn y skriver nรฅ ut ยซHeiยป i stedet for ยซHalloยป. Illustrasjonen viser den ene syntaktiske redigeringen.
Hva skal endres i et mutantprogram?
Det finnes flere teknikker som kan brukes til รฅ generere mutantprogrammer. De tre familiene nedenfor dekker de fleste mutasjonsoperatorene som verktรธy leveres med.
| Operand erstatningsoperatรธrer | Operatorer for modifisering av uttrykk | Operatorer for modifisering av setninger |
| Erstatt operanden med en annen operand (x med y, eller y med x) eller med en konstant verdi. | Erstatt en operator, eller sett inn en ny operator, i en programsetning. | Programmatiske utsagn er modifisert for รฅ lage mutante programmer. |
| Eksempel: If(x>y) erstatte x- og y-verdier If(5>y) erstatt x med konstant 5 |
Eksempel: Hvis(x==y) Vi kan erstatte == med >= og fรฅ mutantprogrammet som If(x>=y) og sette inn ++ i setningen If(x==++y) |
Eksempel: Slett den andre delen i en if-else-setning Slett hele if-else-setningen for รฅ sjekke hvordan programmet oppfรธrer seg |
Noen eksempler pรฅ mutasjonsoperatorer:
- GOTO etiketterstatning
- Returerklรฆringserstatning
- Sletting av erklรฆring
- Innsetting av unรฆr operator (som โ og ++)
- Utskifting av logisk kontakt
- Sammenlignbar erstatning for arraynavn
- Fjerne else-delen av en if-else-setning
- Legge til eller erstatte operatorer
- Erstatning av erklรฆring ved รฅ endre dataene
- Datamodifisering for variablene
- Endring av datatyper i programmet
OperaTorer som berรธrer en grensebetingelse overlever oftest, sรฅ mutasjonsresultater peker ofte tilbake pรฅ hull i grenseverdianalyse.
Typer mutasjonstesting
In Engineering programvareMutasjonstesting er grunnleggende kategorisert i tre typer โ utsagnsmutasjon, verdimutasjon og beslutningsmutasjon.
- Uttalelsesmutasjon โ en setning klippes ut, limes inn eller slettes, sรฅ resultatet kan bli at noen linjer med kode fjernes.
- Verdimutasjon โ verdiene til primรฆre parametere og konstanter endres, for eksempel endring av en lรธkkegrense eller en terskel.
- Beslutningsmutasjon โ kontrollsetninger endres, for eksempel flipping en relasjonsoperator eller negerer en betingelse.
Verktรธy grupperer operatorene sine under disse tre overskriftene, slik at familien som produserte en overlevende mutant forteller testeren hvilken type pรฅstand som mangler. En overlevende beslutningsmutant markerer vanligvis en uprรธvd gren, som overlapper med lรธkketesting.
Automatisering av mutasjonstesting
Mutasjonstesting er ekstremt tidkrevende og komplisert รฅ utfรธre manuelt, sรฅ det anbefales รฅ bruke automatiseringsverktรธy, som ogsรฅ reduserer kostnadene. Et mutasjonsverktรธy samler mutantene, planlegger kjรธringene, registrerer hvilken mutant hver mislykkede test drepte, og rapporterer poengsummen.
Liste over tilgjengelige verktรธy:
- Stryker โ et rammeverk for mutasjonstesting med รฅpen kildekode med utgaver for JavaManus og TypeScript (StrykerJS), C# og .NET (Stryker.NET), og Scala (Stryker4s).
- PIT, ogsรฅ skrevet PITest โ et mutasjonstestingssystem for Java og JVM-en som muterer kompilert bytekode og kobles til Maven og Gradle bygger ved siden av JUnit.
Begge kjรธrer som et byggesteg, sรฅ de hรธrer hjemme i samme kontinuerlig integrering rรธrledningen som resten av automatiseringstesting pรฅ.
Mutasjonspoeng
Mutasjonsskรฅren er definert som prosentandelen drepte mutanter av det totale antallet mutanter.
Mutasjonspoeng = (drepte mutanter / totalt antall mutanter) * 100
Formelen vises nedenfor i den formen de fleste verktรธy rapporterer den.
Testtilfeller beskrives som mutasjonstilstrekkelige nรฅr poengsummen nรฅr 100 prosent. I praksis mรฅ nevneren ekskludere ekvivalente mutanter โ mutanter hvis endrede syntaks oppfรธrer seg nรธyaktig som originalen, slik at ingen test kan drepe dem. Verktรธy rapporterer derfor drepte mutanter delt pรฅ drepte pluss overlevende ikke-ekvivalente mutanter, og lar testeren flagge ekvivalenter.
Eksperimentelle resultater har vist at mutasjonstesting er en effektiv mรฅte รฅ mรฅle tilstrekkeligheten av testtilfeller. Den stรธrste ulempen er kostnaden ved รฅ generere mutantene og utfรธre hvert testtilfelle mot hver enkelt.
Mutasjonstesting vs. Code Dekning
Hรธyt testdekning beviser ikke sterke tester. Linje- og grendekning registrerer hvilke utsagn som ble kjรธrt, ikke om noe ble verifisert etterpรฅ, sรฅ en test som kaller en metode og ikke hevder noe teller fortsatt som dekket. Mutasjonstesting tetter dette gapet, fordi en mutant bare dรธr nรฅr en pรฅstand faktisk mislykkes.
| Aspekt | Code dekning | Mutasjonspoengsum |
| Hva den mรฅler | Hvilke linjer eller grener testene ble utfรธrt | Hvilke injiserte feil testene oppdaget |
| Fรธlsom for pรฅstander | Nei โ en test med null pรฅstander gir fortsatt dekning | Ja โ en mutant overlever nรฅr ingen pรฅstand feiler |
| Kostnaden for en lรธpetur | รn instrumentert testkjรธring | รn testkjรธring per overlevende mutant, sรฅ langt tregere |
| Typisk bruk | En rask gate pรฅ hver commit | En grundigere periodisk kontroll av kritiske moduler |
| Feil modus | 100 prosent dekning uten reell verifisering | Ekvivalente mutanter som aldri kan drepes |
De to mรฅlingene er komplementรฆre. Dekningen navngir koden som aldri ble nรฅdd; mutasjonspoengsummen navngir den nรฅdde koden som aldri ble sjekket. Begge gir samme informasjon. prosess for feilhรฅndtering, sammen med tiltak som defekttetthet.
Fordeler med mutasjonstesting
Fรธlgende er fordelene med mutasjonstesting:
- Det er en kraftig tilnรฆrming for รฅ oppnรฅ hรธy dekning av kildeprogrammet.
- Den tester selve testsuiten, noe ingen andre teknikk for programvaretesting gjรธr direkte.
- Mutasjonstesting gir programvareutvikleren et godt nivรฅ av feildeteksjon.
- Metoden avdekker uklarheter i kildekoden og har kapasitet til รฅ avdekke feil som vanlige kjรธringer aldri nรฅr.
- Overlevende mutanter er handlingsrettede: hver av dem navngir en spesifikk linje og en spesifikk endring som suiten ikke la merke til.
- Kunder drar nytte av denne testingen ved รฅ motta et mer pรฅlitelig og stabilt system.
Ulemper med mutasjonstesting
Pรฅ den annen side er fรธlgende ulemper med mutasjonstesting:
- Mutasjonstesting er ekstremt kostbart og tidkrevende, fordi et stort antall mutantprogrammer mรฅ genereres og kompileres.
- Siden det er tidkrevende, er det rimelig รฅ si at denne testingen ikke kan gjรธres uten et automatiseringsverktรธy.
- Hver mutant utรธves av samme antall testtilfeller som det opprinnelige programmet, sรฅ en stor mutantpopulasjon mรฅ kjรธres mot hele testsuiten.
- Ekvivalente mutanter kan ikke drepes av noen test, og รฅ skille dem fra ekte overlevende krever vanligvis manuell gjennomgang.
- Fordi metoden endrer kildekoden, er den ikke anvendelig for Svart Box Testing.
Nรฅr man skal bruke mutasjonstesting
Kostnadsprofilen ovenfor betyr at mutasjonstesting sjelden kjรธres over en hel kodebase pรฅ hver commit. Det betaler seg selv der en uoppdaget feil er dyr og koden som testes er liten nok til รฅ mutere raskt.
- Sikkerhetskritisk eller รธkonomisk logikk โ betalingsberegning, skatteregler og autorisasjonskontroller, der et stille feil svar er verre enn et krasj.
- Suiter med mistenkelig hรธy dekning โ nรฅr dekningen er nรฆr 100 prosent, men feilene fortsatt slippes unna.
- Eldre kode blir refaktorert โ mutasjonsresultater avslรธrer om de eksisterende testene ville fange opp en regresjon.
- Biblioteker og delte komponenter โ en feil i en gjenbrukt komponent multipliseres pรฅ tvers av hver innringer.
- Lag som รธver testdrevet utvikling โ poengsummen kontrollerer at testene som ble skrevet fรธrst gjรธr et ordentlig arbeid.
Det er vanligvis ikke verdt รฅ kjรธre pรฅ engangsprototyper, pรฅ tynt lim eller generert kode uten forgreningslogikk, eller pรฅ pakker dominert av trege integrasjonstester som allerede tar timer for รฉn passering.
De fleste teamene skal derfor avgrense kjรธringen til endrede filer, sette en terskel for modulene som er viktige, og la det bredere Regresjonstesting suiten bรฆrer resten av livssyklus for programvaretesting.



