SlideShare a Scribd company logo
Mutation Testing
  Hernán Wilkinson             Nicolás Chillo     Gabriel Brunstein
     UBA - 10Pines                  UBA                 UBA
hernan.wilkinson@gmail.com
                             nchillo@gmail.com   gaboto@gmail.com
What is Mutation Testing?



Technique to verify the quality of the tests
What is Mutation Testing?

        Verify Quality of…           Verify Quality of…




Source Code                  Tests                   Mutation
                                                     Testing
How does it work?
     1st Step: Create the Mutant

                    Mutation
                    Process




The Source
   Code                                The “Mutant”




             The Mutation “Operator”
Examples
DebitCard>>= anotherDebitCard
 ^(type = anotherDebitCard type)
  and: [ number = anotherDebitCard number ]



                   Operator: Change #and: by #or:




CreditCard>>= anotherDebitCard
 ^(type = anotherDebitCard type)
   or: [ number = anotherDebitCard number ]
Examples
Purchase>>netPaid
 ^self totalPaid – self totalRefunded



                       Change #- with #+



Purchase>>netPaid
 ^self totalPaid + self totalRefunded
Why?
How does it help?
How does it work?
  2nd Step: Try to Kill the Mutant




                                  A Killer
  The “Mutant”           tries to kill the Mutant!


All tests run  The Mutant Survives!!!
                                                     The Test Suite
A test fails or errors  The Mutant Dies
Meaning…


The Mutant Survives  The case generated by the mutant
                     is not tested



The Mutant Dies  The case generated by the mutant is
                       tested
Example: The mutant survives
DebitCard>>= anotherDebitCard
 ^(type = anotherDebitCard type) and: [ number = anotherDebitCard number ]


                                             Operator: Change #and: by #or:

DebitCard>>= anotherDebitCard
 ^(type = anotherDebitCard type) or: [ number = anotherDebitCard number ]




DebitCardTest>>testDebitCardWithSameNumberShouldBeEqual
    self assert: (DebitCard visaNumbered: 123) = (DebitCard visaNumbered: 123).
Example: The mutant dies
DebitCard>>= anotherDebitCard
 ^(type = anotherDebitCard type) and: [ number = anotherDebitCard number ]


                                             Operator: Change #and: by #or:

DebitCard>>= anotherDebitCard
 ^(type = anotherDebitCard type) or: [ number = anotherDebitCard number ]




DebitCardTest>>testDebitCardWithSameNumberShouldBeEqual
    self assert: (DebitCard visaNumbered: 123) = (DebitCard visaNumbered: 123).


DebitCardTest >>testDebitCardWithDifferentNumberShouldBeDifferent
    self deny: (DebitCard visaNumbered: 123) = (DebitCard visaNumbered: 789).
Example: The mutant survives
Purchase>>netPaid
 ^self totalPaid – self totalRefunded

                                           Change #- with #+
Purchase>>netPaid
 ^self totalPaid + self totalRefunded


Purchase>>testNetPaid
   | purchase |
   purchase := Purchase for: 20 * euros.
   self assert: purchase netPaid = (purchase totalPaid – purchase totalRefunded)
Example: The mutant dies
Purchase>>netPaid
 ^self totalPaid – self totalRefunded

                                        Change #- with #+
Purchase>>netPaid
 ^self totalPaid + self totalRefunded


Purchase>>testNetPaidWithOutRefunds  Renamed!
   | purchase |
   purchase := Purchase for: 20 * euros.
   self assert: purchase netPaid = (purchase totalPaid – purchase totalRefunded)

Purchase>>testNetPaidWithRefunds
   | purchase |
   purchase := Purchase for: 20 * euros.
   purchase addRefundFor: 10 * euros.
   self assert: purchase netPaid = (purchase totalPaid – purchase totalRefunded)
How does it work? - Summary
• Changes the original source code with
  special “operators” to generate “Mutants”
• Run the test suite related to the changed
  code
  • If a test errors or fails  Kills the mutant
  • If all tests run  The Mutant survives
• Surviving Mutants show not tested cases


                 The Important Thing!
MuTalk



Mutation Testing Tool for Smalltalk (Pharo
              and Squeak)
Demo
MuTalk – How does it work?
•       Runs the test to be sure that all run
•       For each method m
    •       For each operator o
        •     Changes m AST using o
        •     Compiles mutated code
        •     Changes method dictionary
        •     Run the tests
MuTalk – Operators
•       Boolean messages
    •    Remove #not
    •    Replace #and: with #eqv:
    •    Replace #and: with #nand:
    •    Replace #and: with #or:
    •    Replace #and: with #secondArgResult:
    •    Replace #and: with false
    •    Replace #or: First Condition with false
    •    Replace #or: Second Condition with false
    •    Replace #or: with #and:
    •    Replace #or: with #xor:
MuTalk – Operators
•       Magnitude messages
    •    Replace #'<=' with #<
    •    Replace #'<=' with #=
    •    Replace #'<=' with #>
    •    Replace #'>=' with #=
    •    Replace #'>=' with #>
    •    Replace #'~=' with #=
    •    Replace #< with #>
    •    Replace #= with #'~='
    •    Replace #> with #<
    •    Replace #max: with #min:
    •    Replace #min: with #max:
MuTalk – Operators
•       Collection messages
    •     Remove at:ifAbsent:
    •     Replace #reject: with #select:
    •     Replace #select: with #reject:
    •     Replace Reject block with [:each | false]
    •     Replace Reject block with [:each | true]
    •     Replace Select block with [:each | false]
    •     Replace Select block with [:each | true]
    •     Replace detect: block with [:each | false] when #detect:ifNone:
    •     Replace detect: block with [:each | true] when #detect:ifNone:
    •     Replace do block with [:each |]
    •     Replace ifNone: block with [] when #detect:ifNone:
    •     Replace inject:aValue into:aBlock with aValue
    •     Replace sortBlock:aBlock with sortBlock:[:a :b| true]
MuTalk – Operators
•       Number messages
    •    Replace #* with #/
    •    Replace #+ with #-
    •    Replace #- with #+
    •    Replace #/ with #*
MuTalk – Operators
•       Flow control messages
    •     Remove Exception Handler Operator
    •     Replace #ifFalse: receiver with false
    •     Replace #ifFalse: receiver with true
    •     Replace #ifFalse: with #ifTrue:
    •     Replace #ifFalse:IfTrue: receiver with false
    •     Replace #ifFalse:IfTrue: receiver with true
    •     Replace #ifTrue: receiver with false
    •     Replace #ifTrue: receiver with true
    •     Replace #ifTrue: with #ifFalse:
    •     Replace #ifTrue:ifFalse: receiver with false
    •     Replace #ifTrue:ifFalse: receiver with true
Why is not widely used?
Is not new … - History

Begins in 1971, R. Lipton, “Fault Diagnosis of
            Computer Programs”

 Generally accepted in 1978, R. Lipton et al,
  “Hints on test data selection: Help for the
           practicing programmer”
Why is not widely used?


Maturity Problem: Because Testing is not
            widely used YET!
        (Although it is increasing)
Why is not widely used?


Integration Problem: Inability to successfully
  integrate it into the software development
                     process
         (TDD plays a key role now)
Why is not widely used?



Technical Problem: It is a Brute Force
             technique!
Technical Problems
• Brute force technique



                   NxM
      N = number of tests
      M = number of mutants
Aconcagua
•   Number of Tests: 666
•   Number of Mutants: 1005
•   Time to create a mutant/compile/link/run:
    10 secs. each aprox.?
•   Total time:
     –   6693300 seconds
     –   1859 hours, 15 minutes
Another way of doing it…
CreditCard>>= anotherCreditCard
 ^(anotherCreditCard isKindOf: self class) and: [ number =
  anotherCreditCard number ]


CreditCard>>= anotherCreditCard
 MutantId = 12 ifTrue: [ ^(anotherCreditCard isKindOf: self class) or: [
  number = anotherCreditCard number ].
 MutantId = 13 ifTrue: [ ^(anotherCreditCard isKindOf: self class)
  nand: [ number = anotherCreditCard number ].
 MutantId = 14 ifTrue: [ ^(anotherCreditCard isKindOf: self class) eqv: [
  number = anotherCreditCard number ].
Aconcagua
•   Number of Tests: 666
•   Number of Mutants: 1005
•   Time to create the
    metamutant/compile/link: 2 minutes?
•   Time to run the tests per mutant: 1 sec
•   Total time:
     –   1125 seconds
     –   18 minutes 45 seconds
MuTalk Optimizations
              Running Strategies
Mutate all methods, run all tests per       Mutate covered methods, run all
     mutant                                      tests per mutant
    –    Create a mutant for each method         –      Takes coverage running all tests
    –    Run all the test for each mutant        –      Mutate only covered methods
    –    Disadvantage: Slower strategy           –      Run all methods per mutant
                                                 –      Relies on coverage

Mutate all methods, run only test           Mutate covered methods, run only test
     that cover mutated method                    that covered mutated methods
    –    Run coverage keeping for each       –       Run coverage keeping for each
         method the tests that covered it            method the tests that covered it
    –    Create a mutant for each method     –       Create a mutant for only covered
    –    For each mutant, run only the               methods
         tests that covered the original     –       For each mutant, run only the tests
         method                                      that covered the original method
MuTalk - Aconcagua Statistics
•       Mutate All, Run All: 1 minute, 6 seconds
•       Mutate Covered, Run Covering: 36
        seconds
•       Result:
    •     545 Killed
    •     6 Terminated
    •     83 Survived
More Statistics
MuTalk Optimizations
Terminated Mutants




       Try to kill the Mutant!

       The killer has to be
       “Terminated”

                                 The Test Suite
MuTalk - Terminated Mutants


• Take the time it runs each test the first
  time
• If the test takes more thant 3 times,
  terminate it
Let’s redefine MuTalk as…

  Mutation Testing Tool for Smalltalk (Pharo
  and Squeak) that uses meta-facilities to
run faster and provide inmediate feedback
Work in progress


• Operators Categorization based on how
  useful they are to detect errors
• Filter Operators on View
• Cancel process
Future work

• Make Operators more “inteligent”
  • a = b ifTrue: [ … ]
    • a = b ifFalse: [] is equivalent to a ~= b ifTrue: []
• Suggest tests using not killed mutants
• Use MuTalk to test MuTalk?
Why does it work?


 “Complex faults are coupled to simple faults
in such a way that a test data set that detects
all simple faults in a program will detect most
       complex faults” (Coupling effect)
    Demonstrated in 1995, K. Wah, “Fault coupling in finite
                                      bijective functions”
Why does it work?


 “In practice, if the software contains a fault,
there will usually be a set of mutants that can
only be killed by a test case that also detects
                     that fault”
     Geist et al, “Estimation and enhancement of real-time
      software reliability through mutation analysis”, 1992
More Statistics…
How does it compare to
               coverage?
•       Does not replaces coverage because
        some methods do not generate mutants
•       But:
    •     Mutants on not covered methods will survive
    •     It provides better insight than coverage
    •     Method Coverage fails with long
          methods/conditions/loops/etc.
Questions?
MuTalk - Mutation
    Testing for Smalltalk

  Hernán Wilkinson             Nicolás Chillo     Gabriel Brunstein
     UBA - 10Pines                  UBA                 UBA
hernan.wilkinson@gmail.com
                             nchillo@gmail.com   gaboto@gmail.com

More Related Content

PPT
Domain Driven Design (DDD)
PPTX
Java virtual machine
PPTX
Domain Driven Design(DDD) Presentation
PPTX
Regression testing
PPTX
Java History
PPTX
Diabetes Mellitus
PPTX
Hypertension
PPTX
Republic Act No. 11313 Safe Spaces Act (Bawal Bastos Law).pptx
Domain Driven Design (DDD)
Java virtual machine
Domain Driven Design(DDD) Presentation
Regression testing
Java History
Diabetes Mellitus
Hypertension
Republic Act No. 11313 Safe Spaces Act (Bawal Bastos Law).pptx

What's hot (20)

PPTX
Mutation Testing: Testing your tests
PDF
An introduction to unit testing
PPSX
PPSX
Principles of Software testing
PPTX
JUNit Presentation
PDF
Mutation testing
PPTX
JUnit- A Unit Testing Framework
PDF
JUnit & Mockito, first steps
PPTX
PPTX
Unit Testing And Mocking
PPTX
An Introduction to Unit Testing
PPTX
Unit Testing Concepts and Best Practices
PDF
An Introduction to Test Driven Development
PPTX
Unit testing
PDF
Testing with Spring: An Introduction
PPTX
UNIT TESTING PPT
PPTX
Java Unit Testing
PPTX
Understanding Unit Testing
PPTX
Unit test
PPTX
Combinatorial testing ppt
Mutation Testing: Testing your tests
An introduction to unit testing
Principles of Software testing
JUNit Presentation
Mutation testing
JUnit- A Unit Testing Framework
JUnit & Mockito, first steps
Unit Testing And Mocking
An Introduction to Unit Testing
Unit Testing Concepts and Best Practices
An Introduction to Test Driven Development
Unit testing
Testing with Spring: An Introduction
UNIT TESTING PPT
Java Unit Testing
Understanding Unit Testing
Unit test
Combinatorial testing ppt
Ad

Viewers also liked (20)

PDF
Kill the mutants - A better way to test your tests
PPT
Mutation testing
PDF
Mutation testing (OOP 2012, 2012-JAN-24)
PPTX
Mutation Testing
PPTX
Mutation testing
PPTX
Kill the mutants and test your tests - Roy van Rijn
PDF
Mutation Testing: Leaving the Stone Age. FOSDEM 2017
KEY
An introduction to mutation testing
PPTX
Mutagens
 
PPTX
Black box
PPT
Black Box Testing
PPTX
Test corner第三回, Charles 的使用經驗分享。
PPTX
Mutation Testing
PDF
Mutation testing in Java
PPTX
Exploratory Testing Explained (Tampere Goes Agile - 2013)
PPTX
Exploratory Testing Explained and Experienced
PDF
A Taste of Exploratory Testing
PPTX
Random testing
PDF
xUnit Test Patterns - Chapter11
PPTX
Atm reconciliation manual
Kill the mutants - A better way to test your tests
Mutation testing
Mutation testing (OOP 2012, 2012-JAN-24)
Mutation Testing
Mutation testing
Kill the mutants and test your tests - Roy van Rijn
Mutation Testing: Leaving the Stone Age. FOSDEM 2017
An introduction to mutation testing
Mutagens
 
Black box
Black Box Testing
Test corner第三回, Charles 的使用經驗分享。
Mutation Testing
Mutation testing in Java
Exploratory Testing Explained (Tampere Goes Agile - 2013)
Exploratory Testing Explained and Experienced
A Taste of Exploratory Testing
Random testing
xUnit Test Patterns - Chapter11
Atm reconciliation manual
Ad

Similar to Mutation Testing (20)

PDF
des mutants dans le code.pdf
PDF
Benchmarking and PHPBench
PDF
The Most Important Thing: How Mozilla Does Security and What You Can Steal
PDF
Mutation Testing.pdf
PPTX
PHX Session #3 - "It Works on My Machine!" Closing the Loop Between Developme...
PDF
EvoRobocode Competition @ GECCO-2013
PDF
Procedures, the Pop-11 stack and debugging
PPTX
Mutation-Testing mit PIT
PPT
UNIT 3.ppt
PDF
Test Automation Day 2018
PPTX
Tech Days 2015: Dynamic Analysis
PDF
Web 2.0 Performance and Reliability: How to Run Large Web Apps
PPTX
Session #3: "It Works on My Machine!" Closing the Loop Between Development & ...
PDF
TDD, BDD and mocks
PDF
The Unicorn's Travel to the Microcosm
PPT
Verilog Lecture3 hust 2014
PDF
Beijing Perl Workshop 2008 Hiveminder Secret Sauce
PDF
Must.kill.mutants. TopConf Tallinn 2016
PDF
Stop Flying Blind! Quantifying Risk with Monte Carlo Simulation
PPTX
Joker - Improve your tests with mutation testing
des mutants dans le code.pdf
Benchmarking and PHPBench
The Most Important Thing: How Mozilla Does Security and What You Can Steal
Mutation Testing.pdf
PHX Session #3 - "It Works on My Machine!" Closing the Loop Between Developme...
EvoRobocode Competition @ GECCO-2013
Procedures, the Pop-11 stack and debugging
Mutation-Testing mit PIT
UNIT 3.ppt
Test Automation Day 2018
Tech Days 2015: Dynamic Analysis
Web 2.0 Performance and Reliability: How to Run Large Web Apps
Session #3: "It Works on My Machine!" Closing the Loop Between Development & ...
TDD, BDD and mocks
The Unicorn's Travel to the Microcosm
Verilog Lecture3 hust 2014
Beijing Perl Workshop 2008 Hiveminder Secret Sauce
Must.kill.mutants. TopConf Tallinn 2016
Stop Flying Blind! Quantifying Risk with Monte Carlo Simulation
Joker - Improve your tests with mutation testing

More from ESUG (20)

PDF
ShowUs: Pharo Stream Deck (ESUG 2025, Gdansk)
PDF
Micromaid: A simple Mermaid-like chart generator for Pharo
PDF
Directing Generative AI for Pharo Documentation
PDF
Even Lighter Than Lightweiht: Augmenting Type Inference with Primitive Heuris...
PDF
Composing and Performing Electronic Music on-the-Fly with Pharo and Coypu
PDF
Gamifying Agent-Based Models in Cormas: Towards the Playable Architecture for...
PDF
Analysing Python Machine Learning Notebooks with Moose
PDF
FASTTypeScript metamodel generation using FAST traits and TreeSitter project
PDF
Migrating Katalon Studio Tests to Playwright with Model Driven Engineering
PDF
Package-Aware Approach for Repository-Level Code Completion in Pharo
PDF
Evaluating Benchmark Quality: a Mutation-Testing- Based Methodology
PDF
An Analysis of Inline Method Refactoring
PDF
Identification of unnecessary object allocations using static escape analysis
PDF
Control flow-sensitive optimizations In the Druid Meta-Compiler
PDF
Clean Blocks (IWST 2025, Gdansk, Poland)
PDF
Encoding for Objects Matters (IWST 2025)
PDF
Challenges of Transpiling Smalltalk to JavaScript
PDF
Immersive experiences: what Pharo users do!
PDF
ChatPharo: an Open Architecture for Understanding How to Talk Live to LLMs
PDF
Cavrois - an Organic Window Management (ESUG 2025)
ShowUs: Pharo Stream Deck (ESUG 2025, Gdansk)
Micromaid: A simple Mermaid-like chart generator for Pharo
Directing Generative AI for Pharo Documentation
Even Lighter Than Lightweiht: Augmenting Type Inference with Primitive Heuris...
Composing and Performing Electronic Music on-the-Fly with Pharo and Coypu
Gamifying Agent-Based Models in Cormas: Towards the Playable Architecture for...
Analysing Python Machine Learning Notebooks with Moose
FASTTypeScript metamodel generation using FAST traits and TreeSitter project
Migrating Katalon Studio Tests to Playwright with Model Driven Engineering
Package-Aware Approach for Repository-Level Code Completion in Pharo
Evaluating Benchmark Quality: a Mutation-Testing- Based Methodology
An Analysis of Inline Method Refactoring
Identification of unnecessary object allocations using static escape analysis
Control flow-sensitive optimizations In the Druid Meta-Compiler
Clean Blocks (IWST 2025, Gdansk, Poland)
Encoding for Objects Matters (IWST 2025)
Challenges of Transpiling Smalltalk to JavaScript
Immersive experiences: what Pharo users do!
ChatPharo: an Open Architecture for Understanding How to Talk Live to LLMs
Cavrois - an Organic Window Management (ESUG 2025)

Recently uploaded (20)

PDF
Mobile App Security Testing_ A Comprehensive Guide.pdf
PDF
Agricultural_Statistics_at_a_Glance_2022_0.pdf
PDF
How UI/UX Design Impacts User Retention in Mobile Apps.pdf
PPTX
Big Data Technologies - Introduction.pptx
PDF
cuic standard and advanced reporting.pdf
PPTX
Detection-First SIEM: Rule Types, Dashboards, and Threat-Informed Strategy
PDF
Profit Center Accounting in SAP S/4HANA, S4F28 Col11
PPTX
Programs and apps: productivity, graphics, security and other tools
PDF
Diabetes mellitus diagnosis method based random forest with bat algorithm
PPTX
ACSFv1EN-58255 AWS Academy Cloud Security Foundations.pptx
PPTX
VMware vSphere Foundation How to Sell Presentation-Ver1.4-2-14-2024.pptx
PDF
Advanced methodologies resolving dimensionality complications for autism neur...
PDF
Machine learning based COVID-19 study performance prediction
PDF
Peak of Data & AI Encore- AI for Metadata and Smarter Workflows
PDF
Unlocking AI with Model Context Protocol (MCP)
PDF
Build a system with the filesystem maintained by OSTree @ COSCUP 2025
PDF
Dropbox Q2 2025 Financial Results & Investor Presentation
PPTX
Digital-Transformation-Roadmap-for-Companies.pptx
PDF
Empathic Computing: Creating Shared Understanding
PDF
Encapsulation_ Review paper, used for researhc scholars
Mobile App Security Testing_ A Comprehensive Guide.pdf
Agricultural_Statistics_at_a_Glance_2022_0.pdf
How UI/UX Design Impacts User Retention in Mobile Apps.pdf
Big Data Technologies - Introduction.pptx
cuic standard and advanced reporting.pdf
Detection-First SIEM: Rule Types, Dashboards, and Threat-Informed Strategy
Profit Center Accounting in SAP S/4HANA, S4F28 Col11
Programs and apps: productivity, graphics, security and other tools
Diabetes mellitus diagnosis method based random forest with bat algorithm
ACSFv1EN-58255 AWS Academy Cloud Security Foundations.pptx
VMware vSphere Foundation How to Sell Presentation-Ver1.4-2-14-2024.pptx
Advanced methodologies resolving dimensionality complications for autism neur...
Machine learning based COVID-19 study performance prediction
Peak of Data & AI Encore- AI for Metadata and Smarter Workflows
Unlocking AI with Model Context Protocol (MCP)
Build a system with the filesystem maintained by OSTree @ COSCUP 2025
Dropbox Q2 2025 Financial Results & Investor Presentation
Digital-Transformation-Roadmap-for-Companies.pptx
Empathic Computing: Creating Shared Understanding
Encapsulation_ Review paper, used for researhc scholars

Mutation Testing

  • 1. Mutation Testing Hernán Wilkinson Nicolás Chillo Gabriel Brunstein UBA - 10Pines UBA UBA hernan.wilkinson@gmail.com nchillo@gmail.com gaboto@gmail.com
  • 2. What is Mutation Testing? Technique to verify the quality of the tests
  • 3. What is Mutation Testing? Verify Quality of… Verify Quality of… Source Code Tests Mutation Testing
  • 4. How does it work? 1st Step: Create the Mutant Mutation Process The Source Code The “Mutant” The Mutation “Operator”
  • 5. Examples DebitCard>>= anotherDebitCard ^(type = anotherDebitCard type) and: [ number = anotherDebitCard number ] Operator: Change #and: by #or: CreditCard>>= anotherDebitCard ^(type = anotherDebitCard type) or: [ number = anotherDebitCard number ]
  • 6. Examples Purchase>>netPaid ^self totalPaid – self totalRefunded Change #- with #+ Purchase>>netPaid ^self totalPaid + self totalRefunded
  • 8. How does it work? 2nd Step: Try to Kill the Mutant A Killer The “Mutant” tries to kill the Mutant! All tests run  The Mutant Survives!!! The Test Suite A test fails or errors  The Mutant Dies
  • 9. Meaning… The Mutant Survives  The case generated by the mutant is not tested The Mutant Dies  The case generated by the mutant is tested
  • 10. Example: The mutant survives DebitCard>>= anotherDebitCard ^(type = anotherDebitCard type) and: [ number = anotherDebitCard number ] Operator: Change #and: by #or: DebitCard>>= anotherDebitCard ^(type = anotherDebitCard type) or: [ number = anotherDebitCard number ] DebitCardTest>>testDebitCardWithSameNumberShouldBeEqual self assert: (DebitCard visaNumbered: 123) = (DebitCard visaNumbered: 123).
  • 11. Example: The mutant dies DebitCard>>= anotherDebitCard ^(type = anotherDebitCard type) and: [ number = anotherDebitCard number ] Operator: Change #and: by #or: DebitCard>>= anotherDebitCard ^(type = anotherDebitCard type) or: [ number = anotherDebitCard number ] DebitCardTest>>testDebitCardWithSameNumberShouldBeEqual self assert: (DebitCard visaNumbered: 123) = (DebitCard visaNumbered: 123). DebitCardTest >>testDebitCardWithDifferentNumberShouldBeDifferent self deny: (DebitCard visaNumbered: 123) = (DebitCard visaNumbered: 789).
  • 12. Example: The mutant survives Purchase>>netPaid ^self totalPaid – self totalRefunded Change #- with #+ Purchase>>netPaid ^self totalPaid + self totalRefunded Purchase>>testNetPaid | purchase | purchase := Purchase for: 20 * euros. self assert: purchase netPaid = (purchase totalPaid – purchase totalRefunded)
  • 13. Example: The mutant dies Purchase>>netPaid ^self totalPaid – self totalRefunded Change #- with #+ Purchase>>netPaid ^self totalPaid + self totalRefunded Purchase>>testNetPaidWithOutRefunds  Renamed! | purchase | purchase := Purchase for: 20 * euros. self assert: purchase netPaid = (purchase totalPaid – purchase totalRefunded) Purchase>>testNetPaidWithRefunds | purchase | purchase := Purchase for: 20 * euros. purchase addRefundFor: 10 * euros. self assert: purchase netPaid = (purchase totalPaid – purchase totalRefunded)
  • 14. How does it work? - Summary • Changes the original source code with special “operators” to generate “Mutants” • Run the test suite related to the changed code • If a test errors or fails  Kills the mutant • If all tests run  The Mutant survives • Surviving Mutants show not tested cases The Important Thing!
  • 15. MuTalk Mutation Testing Tool for Smalltalk (Pharo and Squeak)
  • 16. Demo
  • 17. MuTalk – How does it work? • Runs the test to be sure that all run • For each method m • For each operator o • Changes m AST using o • Compiles mutated code • Changes method dictionary • Run the tests
  • 18. MuTalk – Operators • Boolean messages • Remove #not • Replace #and: with #eqv: • Replace #and: with #nand: • Replace #and: with #or: • Replace #and: with #secondArgResult: • Replace #and: with false • Replace #or: First Condition with false • Replace #or: Second Condition with false • Replace #or: with #and: • Replace #or: with #xor:
  • 19. MuTalk – Operators • Magnitude messages • Replace #'<=' with #< • Replace #'<=' with #= • Replace #'<=' with #> • Replace #'>=' with #= • Replace #'>=' with #> • Replace #'~=' with #= • Replace #< with #> • Replace #= with #'~=' • Replace #> with #< • Replace #max: with #min: • Replace #min: with #max:
  • 20. MuTalk – Operators • Collection messages • Remove at:ifAbsent: • Replace #reject: with #select: • Replace #select: with #reject: • Replace Reject block with [:each | false] • Replace Reject block with [:each | true] • Replace Select block with [:each | false] • Replace Select block with [:each | true] • Replace detect: block with [:each | false] when #detect:ifNone: • Replace detect: block with [:each | true] when #detect:ifNone: • Replace do block with [:each |] • Replace ifNone: block with [] when #detect:ifNone: • Replace inject:aValue into:aBlock with aValue • Replace sortBlock:aBlock with sortBlock:[:a :b| true]
  • 21. MuTalk – Operators • Number messages • Replace #* with #/ • Replace #+ with #- • Replace #- with #+ • Replace #/ with #*
  • 22. MuTalk – Operators • Flow control messages • Remove Exception Handler Operator • Replace #ifFalse: receiver with false • Replace #ifFalse: receiver with true • Replace #ifFalse: with #ifTrue: • Replace #ifFalse:IfTrue: receiver with false • Replace #ifFalse:IfTrue: receiver with true • Replace #ifTrue: receiver with false • Replace #ifTrue: receiver with true • Replace #ifTrue: with #ifFalse: • Replace #ifTrue:ifFalse: receiver with false • Replace #ifTrue:ifFalse: receiver with true
  • 23. Why is not widely used?
  • 24. Is not new … - History Begins in 1971, R. Lipton, “Fault Diagnosis of Computer Programs” Generally accepted in 1978, R. Lipton et al, “Hints on test data selection: Help for the practicing programmer”
  • 25. Why is not widely used? Maturity Problem: Because Testing is not widely used YET! (Although it is increasing)
  • 26. Why is not widely used? Integration Problem: Inability to successfully integrate it into the software development process (TDD plays a key role now)
  • 27. Why is not widely used? Technical Problem: It is a Brute Force technique!
  • 28. Technical Problems • Brute force technique NxM N = number of tests M = number of mutants
  • 29. Aconcagua • Number of Tests: 666 • Number of Mutants: 1005 • Time to create a mutant/compile/link/run: 10 secs. each aprox.? • Total time: – 6693300 seconds – 1859 hours, 15 minutes
  • 30. Another way of doing it… CreditCard>>= anotherCreditCard ^(anotherCreditCard isKindOf: self class) and: [ number = anotherCreditCard number ] CreditCard>>= anotherCreditCard MutantId = 12 ifTrue: [ ^(anotherCreditCard isKindOf: self class) or: [ number = anotherCreditCard number ]. MutantId = 13 ifTrue: [ ^(anotherCreditCard isKindOf: self class) nand: [ number = anotherCreditCard number ]. MutantId = 14 ifTrue: [ ^(anotherCreditCard isKindOf: self class) eqv: [ number = anotherCreditCard number ].
  • 31. Aconcagua • Number of Tests: 666 • Number of Mutants: 1005 • Time to create the metamutant/compile/link: 2 minutes? • Time to run the tests per mutant: 1 sec • Total time: – 1125 seconds – 18 minutes 45 seconds
  • 32. MuTalk Optimizations Running Strategies Mutate all methods, run all tests per Mutate covered methods, run all mutant tests per mutant – Create a mutant for each method – Takes coverage running all tests – Run all the test for each mutant – Mutate only covered methods – Disadvantage: Slower strategy – Run all methods per mutant – Relies on coverage Mutate all methods, run only test Mutate covered methods, run only test that cover mutated method that covered mutated methods – Run coverage keeping for each – Run coverage keeping for each method the tests that covered it method the tests that covered it – Create a mutant for each method – Create a mutant for only covered – For each mutant, run only the methods tests that covered the original – For each mutant, run only the tests method that covered the original method
  • 33. MuTalk - Aconcagua Statistics • Mutate All, Run All: 1 minute, 6 seconds • Mutate Covered, Run Covering: 36 seconds • Result: • 545 Killed • 6 Terminated • 83 Survived
  • 35. MuTalk Optimizations Terminated Mutants Try to kill the Mutant! The killer has to be “Terminated” The Test Suite
  • 36. MuTalk - Terminated Mutants • Take the time it runs each test the first time • If the test takes more thant 3 times, terminate it
  • 37. Let’s redefine MuTalk as… Mutation Testing Tool for Smalltalk (Pharo and Squeak) that uses meta-facilities to run faster and provide inmediate feedback
  • 38. Work in progress • Operators Categorization based on how useful they are to detect errors • Filter Operators on View • Cancel process
  • 39. Future work • Make Operators more “inteligent” • a = b ifTrue: [ … ] • a = b ifFalse: [] is equivalent to a ~= b ifTrue: [] • Suggest tests using not killed mutants • Use MuTalk to test MuTalk?
  • 40. Why does it work? “Complex faults are coupled to simple faults in such a way that a test data set that detects all simple faults in a program will detect most complex faults” (Coupling effect) Demonstrated in 1995, K. Wah, “Fault coupling in finite bijective functions”
  • 41. Why does it work? “In practice, if the software contains a fault, there will usually be a set of mutants that can only be killed by a test case that also detects that fault” Geist et al, “Estimation and enhancement of real-time software reliability through mutation analysis”, 1992
  • 43. How does it compare to coverage? • Does not replaces coverage because some methods do not generate mutants • But: • Mutants on not covered methods will survive • It provides better insight than coverage • Method Coverage fails with long methods/conditions/loops/etc.
  • 45. MuTalk - Mutation Testing for Smalltalk Hernán Wilkinson Nicolás Chillo Gabriel Brunstein UBA - 10Pines UBA UBA hernan.wilkinson@gmail.com nchillo@gmail.com gaboto@gmail.com