package fr.inria.diversify.transformation;
import fr.inria.diversify.codeFragment.CodeFragment;
import fr.inria.diversify.transformation.ast.ASTReplace;
import fr.inria.diversify.transformation.ast.exception.BuildTransplantException;
import fr.inria.diversify.util.Log;
import spoon.reflect.code.*;
import spoon.reflect.declaration.CtMethod;
import spoon.reflect.factory.CoreFactory;
import spoon.reflect.reference.CtTypeReference;
/**
* Created by aelie on 03/02/15.
*/
public class SubClassReplaceTransformation extends ASTReplace {
public SubClassReplaceTransformation(CodeFragment transplantationPoint, CodeFragment copyTransplant) {
this.transplantationPoint = transplantationPoint;
this.transplant = copyTransplant;
name = "subClassReplace";
type = "replace";
}
@Override
protected CtCodeElement buildReplacementElement() {
try {
CodeFragment ifStatement = transplant.clone();
if (withVarMapping()) {
if (variableMapping == null) {
variableMapping = transplantationPoint.randomVariableMapping(getTransplant(), subType);
}
}
Log.debug("random variable mapping: {}", variableMapping);
ifStatement.replaceVar(transplantationPoint, variableMapping);
CoreFactory factory = transplant.getCtCodeFragment().getFactory().Core();
CtBlock thenBlock = factory.createBlock();
thenBlock.addStatement((CtStatement) factory.clone(transplantationPoint.getCtCodeFragment()));
((CtIf) ifStatement.getCtCodeFragment()).setThenStatement(thenBlock);
if (((CtIf) ifStatement.getCtCodeFragment()).getElseStatement() == null) {
CtBlock elseBlock = factory.createBlock();
CtCodeSnippetStatement elseSnippet = factory.createCodeSnippetStatement();
elseSnippet.setValue("throw new Exception()");
elseBlock.addStatement(elseSnippet);
((CtIf) ifStatement.getCtCodeFragment()).setElseStatement(elseBlock);
}
return ifStatement.getCtCodeFragment();
} catch (Exception e) {
throw new RuntimeException(new BuildTransplantException("", e));
}
}
@Override
public void apply(String srcDir) throws Exception {
/*CtMethod method = transplantationPoint.getCtCodeFragment().getParent(CtMethod.class);
CoreFactory factory = transplant.getCtCodeFragment().getFactory().Core();
boolean exceptionAlreadyPresent = false;
for(Object thrownTypes : method.getThrownTypes()) {
if(((CtTypeReference)thrownTypes).getQualifiedName().equalsIgnoreCase(exception)) {
exceptionAlreadyPresent = true;
break;
}
}
if(!exceptionAlreadyPresent) {
thrownException = factory.createTypeReference();
thrownException.setSimpleName(exception);
method.addThrownType(thrownException);
}*/
super.apply(srcDir);
}
@Override
public void restore(String srcDir) throws Exception {
/*CtMethod method = transplantationPoint.getCtCodeFragment().getParent(CtMethod.class);
if(thrownException != null) {
method.removeThrownType(thrownException);
}*/
super.restore(srcDir);
}
@Override
protected boolean withVarMapping() {
return true;
}
}