use of spoon.reflect.code.CtExpression in project spoon by INRIA.
the class CtAnnotationImpl method convertValueToExpression.
private CtExpression convertValueToExpression(Object value) {
CtExpression res;
if (value.getClass().isArray()) {
// Value should be converted to a CtNewArray.
res = getFactory().Core().createNewArray();
Object[] values = (Object[]) value;
res.setType(getFactory().Type().createArrayReference(getFactory().Type().createReference(value.getClass().getComponentType())));
for (Object o : values) {
((CtNewArray) res).addElement(convertValueToExpression(o));
}
} else if (value instanceof Collection) {
// Value should be converted to a CtNewArray.
res = getFactory().Core().createNewArray();
Collection values = (Collection) value;
res.setType(getFactory().Type().createArrayReference(getFactory().Type().createReference(values.toArray()[0].getClass())));
for (Object o : values) {
((CtNewArray) res).addElement(convertValueToExpression(o));
}
} else if (value instanceof Class) {
// Value should be a field access to a .class.
res = getFactory().Code().createClassAccess(getFactory().Type().createReference((Class) value));
} else if (value instanceof Field) {
// Value should be a field access to a field.
CtFieldReference<Object> variable = getFactory().Field().createReference((Field) value);
variable.setStatic(true);
CtTypeAccess target = getFactory().Code().createTypeAccess(getFactory().Type().createReference(((Field) value).getDeclaringClass()));
CtFieldRead fieldRead = getFactory().Core().createFieldRead();
fieldRead.setVariable(variable);
fieldRead.setTarget(target);
fieldRead.setType(target.getAccessedType());
res = fieldRead;
} else if (isPrimitive(value.getClass()) || value instanceof String) {
// Value should be a literal.
res = getFactory().Code().createLiteral(value);
} else if (value.getClass().isEnum()) {
final CtTypeReference declaringClass = getFactory().Type().createReference(((Enum) value).getDeclaringClass());
final CtFieldReference variableRef = getFactory().Field().createReference(declaringClass, declaringClass, ((Enum) value).name());
CtTypeAccess target = getFactory().Code().createTypeAccess(declaringClass);
CtFieldRead fieldRead = getFactory().Core().createFieldRead();
fieldRead.setVariable(variableRef);
fieldRead.setTarget(target);
fieldRead.setType(declaringClass);
res = fieldRead;
} else {
throw new SpoonException("Please, submit a valid value.");
}
return res;
}
use of spoon.reflect.code.CtExpression in project spoon by INRIA.
the class AnnotationTest method testReplaceAnnotationValue.
@Test
public void testReplaceAnnotationValue() throws Exception {
final Launcher launcher = new Launcher();
launcher.addInputResource("./src/test/java/spoon/test/annotation/testclasses/Main.java");
launcher.buildModel();
Factory factory = launcher.getFactory();
CtType<?> type = factory.Type().get("spoon.test.annotation.testclasses.Main");
CtMethod<?> m1 = type.getElements(new NamedElementFilter<>(CtMethod.class, "m1")).get(0);
List<CtAnnotation<? extends Annotation>> annotations = m1.getAnnotations();
assertEquals(1, annotations.size());
CtAnnotation<?> a = annotations.get(0);
AnnotParamTypes annot = (AnnotParamTypes) a.getActualAnnotation();
// contract: test replace of single value
CtExpression integerValue = a.getValue("integer");
assertEquals(42, ((CtLiteral<Integer>) integerValue).getValue().intValue());
assertEquals(42, annot.integer());
integerValue.replace(factory.createLiteral(17));
CtExpression newIntegerValue = a.getValue("integer");
assertEquals(17, ((CtLiteral<Integer>) newIntegerValue).getValue().intValue());
assertEquals(17, annot.integer());
// even if second value is null
try {
a.getValue("integer").replace(Arrays.asList(factory.createLiteral(18), null));
fail();
} catch (SpoonException e) {
// OK
}
// contract: replacing of single value by no value
a.getValue("integer").delete();
assertNull(a.getValue("integer"));
try {
annot.integer();
fail();
} catch (NullPointerException e) {
// OK - fails because int cannot be null
}
// contract: replace with null value means remove
a.getValue("string").replace((CtElement) null);
assertNull(a.getValue("string"));
// contract: check that null value can be returned
assertNull(annot.string());
// contract: replace with null value in collection means remove
a.getValue("clazz").replace(Collections.singletonList(null));
assertNull(a.getValue("clazz"));
// contract: check that null value can be returned
assertNull(annot.clazz());
// contract: test replace of item in collection
assertEquals(1, annot.integers().length);
assertEquals(42, annot.integers()[0]);
CtNewArray<?> integersNewArray = (CtNewArray) a.getValue("integers");
integersNewArray.getElements().get(0).replace(Arrays.asList(null, factory.createLiteral(101), null, factory.createLiteral(102)));
assertEquals(2, annot.integers().length);
assertEquals(101, annot.integers()[0]);
assertEquals(102, annot.integers()[1]);
}
use of spoon.reflect.code.CtExpression in project spoon by INRIA.
the class IntercessionTest method testResetCollectionInSetters.
@Test
// interesting but too fragile with conventions
@Ignore
public void testResetCollectionInSetters() throws Exception {
final Launcher launcher = new Launcher();
launcher.setArgs(new String[] { "--output-type", "nooutput" });
final Factory factory = launcher.getFactory();
launcher.getEnvironment().setNoClasspath(true);
// interfaces.
launcher.addInputResource("./src/main/java/spoon/reflect/code");
launcher.addInputResource("./src/main/java/spoon/reflect/declaration");
launcher.addInputResource("./src/main/java/spoon/reflect/reference");
// implementations.
launcher.addInputResource("./src/main/java/spoon/support/reflect/code");
launcher.addInputResource("./src/main/java/spoon/support/reflect/declaration");
launcher.addInputResource("./src/main/java/spoon/support/reflect/reference");
launcher.buildModel();
new IntercessionScanner(factory) {
@Override
protected boolean isToBeProcessed(CtMethod<?> candidate) {
return //
candidate.getSimpleName().startsWith("set") && //
candidate.hasModifier(ModifierKind.PUBLIC) && //
takeSetterCollection(candidate) && //
avoidInterfaces(candidate) && // && avoidSpecificMethods(candidate) //
avoidThrowUnsupportedOperationException(candidate);
}
private boolean takeSetterCollection(CtMethod<?> candidate) {
final CtTypeReference<?> type = candidate.getParameters().get(0).getType();
final List<CtTypeReference<?>> actualTypeArguments = type.getActualTypeArguments();
return COLLECTIONS.contains(type) && actualTypeArguments.size() == 1 && actualTypeArguments.get(0).isSubtypeOf(CTELEMENT_REFERENCE);
}
@Override
protected void process(CtMethod<?> element) {
if (element.getAnnotation(UnsettableProperty.class) != null) {
// we don't check the contracts for unsettable setters
return;
}
final CtStatement statement = element.getBody().getStatement(0);
if (!(statement instanceof CtIf)) {
fail(log(element, "First statement should be an if to check the parameter of the setter"));
}
final CtIf anIf = (CtIf) statement;
if (!createCheckNull(element.getParameters().get(0)).equals(anIf.getCondition())) {
fail(log(element, "Condition should test if the parameter is null.\nThe condition was " + anIf.getCondition()));
}
if (!(anIf.getThenStatement() instanceof CtBlock)) {
fail(log(element, "Should have a block in the if condition to have the initialization and the return."));
}
if (element.getParameters().get(0).getType().equals(SET_REFERENCE)) {
if (!hasCallEmptyInv(anIf.getThenStatement(), SET_REFERENCE)) {
fail(log(element, "Should initilize the list with CtElementImpl#emptySet()."));
}
} else {
if (!hasCallEmptyInv(anIf.getThenStatement(), LIST_REFERENCE)) {
fail(log(element, "Should initilize the list with CtElementImpl#emptyList()."));
}
}
}
private boolean hasCallEmptyInv(CtBlock thenStatement, CtTypeReference<? extends Collection> collectionReference) {
if (!(thenStatement.getStatement(0) instanceof CtAssignment)) {
return false;
}
final CtExpression assignment = ((CtAssignment) thenStatement.getStatement(0)).getAssignment();
if (!(assignment instanceof CtInvocation)) {
return false;
}
final CtInvocation inv = (CtInvocation) assignment;
if (collectionReference.equals(SET_REFERENCE)) {
if (!inv.getExecutable().getSimpleName().equals("emptySet")) {
return false;
}
} else if (collectionReference.equals(LIST_REFERENCE)) {
if (!inv.getExecutable().getSimpleName().equals("emptyList")) {
return false;
}
}
return true;
}
/**
* Creates <code>list == null && list.isEmpty()</code>.
*
* @param ctParameter <code>list</code>
*/
private CtBinaryOperator<Boolean> createCheckNull(CtParameter<?> ctParameter) {
final CtVariableAccess<?> variableRead = factory.Code().createVariableRead(ctParameter.getReference(), true);
final CtLiteral nullLiteral = factory.Code().createLiteral(null);
nullLiteral.setType(factory.Type().nullType());
final CtBinaryOperator<Boolean> checkNull = factory.Code().createBinaryOperator(variableRead, nullLiteral, BinaryOperatorKind.EQ);
checkNull.setType(factory.Type().BOOLEAN_PRIMITIVE);
final CtMethod<Boolean> isEmptyMethod = ctParameter.getType().getTypeDeclaration().getMethod(factory.Type().booleanPrimitiveType(), "isEmpty");
final CtInvocation<Boolean> isEmpty = factory.Code().createInvocation(variableRead, isEmptyMethod.getReference());
final CtBinaryOperator<Boolean> condition = factory.Code().createBinaryOperator(checkNull, isEmpty, BinaryOperatorKind.OR);
return condition.setType(factory.Type().booleanPrimitiveType());
}
private String log(CtMethod<?> element, String message) {
return message + "\nin " + element.getSignature() + "\ndeclared in " + element.getDeclaringType().getQualifiedName();
}
}.scan(factory.getModel().getUnnamedModule());
}
use of spoon.reflect.code.CtExpression in project spoon by INRIA.
the class TypeReferenceTest method testIgnoreEnclosingClassInActualTypes.
@Test
public void testIgnoreEnclosingClassInActualTypes() throws Exception {
final CtType<Panini> aPanini = buildClass(Panini.class);
final CtStatement ctReturn = aPanini.getMethod("entryIterator").getBody().getStatement(0);
assertTrue(ctReturn instanceof CtReturn);
final CtExpression ctConstructorCall = ((CtReturn) ctReturn).getReturnedExpression();
assertTrue(ctConstructorCall instanceof CtConstructorCall);
assertEquals("spoon.test.reference.testclasses.Panini<K, V>.Itr<java.util.Map.Entry<K, V>>", ctConstructorCall.getType().toString());
}
use of spoon.reflect.code.CtExpression in project dspot by STAMP-project.
the class ConstructorCreator method generateConstructorUsingFactory.
static List<CtExpression<?>> generateConstructorUsingFactory(CtTypeReference type) {
// this method will return an invocation of method that return the given type.
// the usage of Factory classes/methods is well spread
final Factory factory = type.getFactory();
final List<CtMethod<?>> factoryMethod = factory.getModel().getElements(new FILTER_FACTORY_METHOD(type));
return factoryMethod.stream().map(method -> factory.createInvocation(factory.createTypeAccess(method.getParent(CtType.class).getReference(), true), method.getReference(), method.getParameters().stream().map(parameter -> ValueCreator.generateRandomValue(parameter.getType())).collect(Collectors.toList()))).collect(Collectors.toList());
}
Aggregations