The class ConfiguredMutagen allows to easilly generate mutants using a configuration file specifying the mutation operators configuration:
import static be.unamur.transitionsystem.dsl.TransitionSystemXmlLoaders.*; import static be.unamur.transitionsystem.dsl.test.mutation.ConfiguredMutagen.*; public Main{ public static void main(String[] args){ LabelledTransitionSystem lts = new MyLTS().getTransitionSystem(); // Loads the mutation operators configuration // E.g., ennumerative mutants generation configure("operatorsConfig.xml") .outputDir("mutants/") // Generates mutants in the given folder .mutate(lts); // E.g., FMM generation configure("operatorsConfig.xml") .ftsMutant("fmm.fts") // Generates FMM's FTS with given name .tvlMutant("fmm.tvl") // Generates FMM's FD in TVL format .mutate(lts); // E.g., ennumerative and FMM generation (will generate the same mutants) configure("operatorsConfig.xml") .outputDir("mutants/") // Generates mutants in the given folder .ftsMutant("fmm.fts") // Generates FMM's FTS with given name .tvlMutant("fmm.tvl") // Generates FMM's FD in TVL format .mutate(lts); } }
Here is a exemple of configuration file (in XML):
<?xml version="1.0" encoding="UTF-8"?> <config> <mutantsSize>200</mutantsSize> <!-- Default mutant size (may be redefined) --> <!-- Default selection strategies for each operator (may be redefined) --> <actionSelection>be.unamur.transitionsystem.test.mutation.RandomSelectionStrategy</actionSelection> <stateSelection>be.unamur.transitionsystem.test.mutation.RandomSelectionStrategy</stateSelection> <transitionSelection>be.unamur.transitionsystem.test.mutation.RandomSelectionStrategy</transitionSelection> <unique>true</unique> <!-- Default uniqueness of each mutant (may be redefined) --> <!-- Operators --> <operators> <operator> <class>be.unamur.transitionsystem.test.mutation.ActionExchange</class> </operator> <operator> <class>be.unamur.transitionsystem.test.mutation.ActionMissing</class> </operator> <operator> <class>be.unamur.transitionsystem.test.mutation.StateMissing</class> </operator> <operator> <class>be.unamur.transitionsystem.test.mutation.TransitionAdd</class> </operator> <operator> <class>be.unamur.transitionsystem.test.mutation.TransitionDestinationExchange</class> </operator> <operator> <class>be.unamur.transitionsystem.test.mutation.TransitionMissing</class> </operator> <operator> <class>be.unamur.transitionsystem.test.mutation.WrongInitialState</class> <mutantsSize>100</mutantsSize> <actionSelection>be.unamur.transitionsystem.test.mutation.RandomSelectionStrategy</actionSelection> <stateSelection>be.unamur.transitionsystem.test.mutation.RandomSelectionStrategy</stateSelection> <transitionSelection>be.unamur.transitionsystem.test.mutation.RandomSelectionStrategy</transitionSelection> <unique>false</unique> </operator> </operators> </config>
It is also possible to configure a particular mutation operator for a given transition system using the Mutagen class:
import static be.unamur.transitionsystem.dsl.TransitionSystemXmlLoaders.*; import static be.unamur.transitionsystem.dsl.test.mutation.Mutagen.*; import be.unamur.transitionsystem.test.mutation.*; public Main{ public static void main(String[] args){ LabelledTransitionSystem lts = new MyLTS().getTransitionSystem(); FeaturedTransitionSystem fts = new FeaturedTransitionSystem(lts); // Initialise the operator for the given transition system MutationOperator op = transitionMissing(lts) .transitionSelectionStrategy(new RandomSelectionStrategy()) .done(); // Apply the operator op.apply(); // Get the mutant transition system (enumerative version) LabelledTransitionSystem mutant = (LabelledTransitionSystem) op.result(); // Enrich the FMM's FTS with the new mutant op.transpose(fts); // Get the feature ID used in the FMM's FTS (should be added to the used feature diagram) String mutantFeatureId = op.getFeatureId(); } }
The FeaturedMutantsModel class in the be.unamur.transitionsystem.test.mutation package allows to compactly represent a set of mutants using a FMM. It may be build using mutation operators or using a mutation configuration.
import be.unamur.transitionsystem.test.mutation.FeaturedMutantsModel; import be.unamur.transitionsystem.test.mutation.MutationConfiguration; import be.unamur.fts.fexpression.configuration.Configuration; public static void main(String[] args){ LabelledTransitionSystem lts = new MyLTS().getTransitionSystem(); // Initialise the FMM FeaturedMutantsModel fmm = new FeaturedMutantsModel(lts); // Initialise the operatro for the given transition system MutationOperator op = transitionMissing(lts) .transitionSelectionStrategy(new RandomSelectionStrategy()) .done(); // Apply the operator fmm.mutate(op); // Apply mutations from a configuration file fmm.mutate(new MutationConfiguration("mutations.xml")); // Iterate over 2nd order mutants Iterator<Configuration> it = fmm.getMutantsConfigs(2); while(it.hasNext()){ LabelledTransitionSystem mutant = fmm.getMutant(it.next()); // ... } } }
To execute a test case on a FMM, one may use one of the several static methods defined in FeaturedMutantsModels in package be.unamur.transitionsystem.dsl.test.mutation.
import be.unamur.transitionsystem.test.mutation.FeaturedMutantsModel; import be.unamur.transitionsystem.test.mutation.MutationConfiguration; import static be.unamur.transitionsystem.dsl.test.mutation.FeaturedMutantsModels.*; import static be.unamur.transitionsystem.dsl.test.TestCaseXmlLoader.*; public static void main(String[] args){ LabelledTransitionSystem lts = new MyLTS().getTransitionSystem(); // Initialise the FMM FeaturedMutantsModel fmm = new FeaturedMutantsModel(system); fmm.mutate(new MutationConfiguration("mutations.xml")); // Load set of test cases Iterator<TestCase> it = loadLtsTestCases("mytests.xml"); while(it.hasNext(){ // Get the alive mutants FExpression alive = getAliveMutants(it.next(), fmm); } } }