private static boolean checkOnlyDefaultConstructor(CtClass<?> ctClass) { Set<? extends CtConstructor<?>> constructors = ctClass.getConstructors(); if (constructors.size() > 1) return false; if (constructors.isEmpty()) return true; CtConstructor<?> constructor = constructors.iterator().next(); return constructor.isImplicit(); }
@Test public void testTransformationOnConstructorWithInsertBegin() throws Exception { final CtConstructor<?> ctConstructor = aClass.getElements(new TypeFilter<CtConstructor<?>>(CtConstructor.class)).get(0); ctConstructor.getBody().insertBegin(factory.Code().createCodeSnippetStatement("int i = 0")); assertEquals(2, ctConstructor.getBody().getStatements().size()); assertEquals("super()", ctConstructor.getBody().getStatement(0).toString()); TestUtils.canBeBuilt("./target/spooned/spoon/test/constructor/testclasses/", 8); }
@Test public void callParamConstructor() throws Exception { CtClass<Object> aClass = factory.Class().get(AClass.class); CtConstructor<Object> constructor = aClass.getConstructors().iterator().next(); assertEquals( "{" + System.lineSeparator() + " enclosingInstance.super();" + System.lineSeparator() + "}", constructor.getBody().toString()); }
@Test public void testTransformationOnConstructorWithInsertBefore() throws Exception { final CtConstructor<?> ctConstructor = aClass.getElements(new TypeFilter<CtConstructor<?>>(CtConstructor.class)).get(0); try { ctConstructor .getBody() .getStatement(0) .insertBefore(factory.Code().createCodeSnippetStatement("int i = 0")); fail(); } catch (RuntimeException ignore) { } assertEquals(1, ctConstructor.getBody().getStatements().size()); assertEquals("super()", ctConstructor.getBody().getStatement(0).toString()); }
private static <T> void processConstructor(CtConstructor<T> c, CtClass<T> toMerge) { CtStatement firstStmt = c.getBody().getStatements().get(0); if (firstStmt instanceof CtInvocation) { CtInvocation<?> superConstructorCall = (CtInvocation) firstStmt; if (!(superConstructorCall.getExecutable().getDeclaration() instanceof CtConstructor)) return; CtConstructor superConstructor = (CtConstructor) superConstructorCall.getExecutable().getDeclaration(); if (superConstructor.getDeclaringType() == toMerge) { CtBlock superConstructorBody = c.getFactory().Core().clone(superConstructor.getBody()); superConstructorBody.accept( new CtScanner() { @Override public <T> void visitCtParameterReference(CtParameterReference<T> ref) { int parameterOrder = superConstructor.getParameters().indexOf(ref.getDeclaration()); ref.setDeclaringExecutable(c.getReference()); CtExpression<?> arg = superConstructorCall.getArguments().get(parameterOrder); if (!(arg instanceof CtVariableAccess)) throw sgce("super() should be directly called in " + c); CtVariable param = ((CtVariableAccess) arg).getVariable().getDeclaration(); if (!(param instanceof CtParameter)) throw sgce("super() should be directly called in " + c); ref.setSimpleName(param.getSimpleName()); super.visitCtParameterReference(ref); } }); c.getBody().removeStatement(firstStmt); List<CtStatement> superConstructorBodyStatements = superConstructorBody.getStatements(); for (int i = superConstructorBodyStatements.size() - 1; i >= 0; i--) { c.getBody().insertBegin(superConstructorBodyStatements.get(i)); } } } }
@Override public void process(CtClass<?> cl) { String className = cl.getQualifiedName().replace('.', '_'); try { writer = new PrintWriter( new BufferedWriter(new FileWriter("src/main/resources/alloyGen/gen.als", true))); } catch (IOException e) { e.printStackTrace(); } if (writer != null) { // writer.println("one sig " + className + " extends Type{}\n"); linesToAdd.add(className); for (CtMethod<?> method : cl.getAllMethods()) { if (method.hasModifier(ModifierKind.PUBLIC)) { boolean addMethod = true; final StringBuilder signatureBuilder = new StringBuilder(); String methodName = className + "_" + method.getSimpleName() + "_" + method.getPosition().getLine(); signatureBuilder.append("one sig " + methodName + " extends Method{}\n"); // writer.println("one sig " + methodName + " extends // Method{}"); signatureBuilder.append("fact{\n"); // writer.println("fact{"); signatureBuilder.append( "#" + methodName + ".paramTypes=" + method.getParameters().size() + "\n"); // writer.println("#" + methodName + ".paramTypes=" + // method.getParameters().size()); int i = 0; for (CtParameter<?> param : method.getParameters()) { if (!param.getType().isPrimitive()) { String name = param.getType().toString().replace(".", "_"); if (name.contains("[]") || name.contains("<")) { addMethod = false; } signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=" + name + "\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + // "]=" + name); if (addMethod) { linesToAdd.add(name); } } else { if (param.getType().getQualifiedName().equals(int.class.getName()) | param.getType().getQualifiedName().equals(Integer.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Integer\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Integer"); } else if (param.getType().getQualifiedName().equals(float.class.getName()) | param.getType().getQualifiedName().equals(Float.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Float\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Float"); } else if (param.getType().getQualifiedName().equals(boolean.class.getName()) | param.getType().getQualifiedName().equals(Boolean.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Boolean\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Boolean"); } else if (param.getType().getQualifiedName().equals(byte.class.getName()) | param.getType().getQualifiedName().equals(Byte.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Byte\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Byte"); } else if (param.getType().getQualifiedName().equals(short.class.getName()) | param.getType().getQualifiedName().equals(Short.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Short\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Short"); } else if (param.getType().getQualifiedName().equals(double.class.getName()) | param.getType().getQualifiedName().equals(Double.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Double\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Double"); } else if (param.getType().getQualifiedName().equals(char.class.getName()) | param.getType().getQualifiedName().equals(Character.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Character\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Character"); } else if (param.getType().getQualifiedName().equals(long.class.getName()) | param.getType().getQualifiedName().equals(Long.class.getName())) { signatureBuilder.append(methodName + ".paramTypes[" + (i++) + "]=Gen_Long\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Long"); } else { final String type = param.getType().getQualifiedName().replace('.', '_'); signatureBuilder.append( methodName + ".paramTypes[" + (i++) + "]=Gen_" + type + "\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_" + type); } } } signatureBuilder.append(methodName + ".receiverType=" + className + "\n"); // writer.println(methodName + ".receiverType=" + // className); signatureBuilder.append("}\n\n"); // writer.println("}\n"); if (addMethod) { writer.println(signatureBuilder.toString()); } // writer.flush(); } } int cpt = 1; for (final CtConstructor<?> constructor : cl.getConstructors()) { if (constructor.hasModifier(ModifierKind.PUBLIC)) { String constructorName = className + "_" + constructor.getSimpleName() + "" + (cpt++) + "_" + constructor.getPosition().getLine(); constructorName = constructorName.replace("<", ""); constructorName = constructorName.replace(">", ""); boolean addConstructor = true; final StringBuilder signatureBuilder = new StringBuilder(); signatureBuilder.append("one sig " + constructorName + " extends ConstructorCall{}\n"); // writer.println("one sig " + methodName + " extends // Method{}"); signatureBuilder.append("fact{\n"); // writer.println("fact{"); signatureBuilder.append( "#" + constructorName + ".paramTypes=" + constructor.getParameters().size() + "\n"); // writer.println("#" + methodName + ".paramTypes=" + // method.getParameters().size()); int i = 0; for (CtParameter<?> param : constructor.getParameters()) { if (!param.getType().isPrimitive()) { String name = param.getType().toString().replace(".", "_"); if (name.contains("[]") || name.contains("<")) { addConstructor = false; } signatureBuilder.append( constructorName + ".paramTypes[" + (i++) + "]=" + name + "\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + // "]=" + name); if (addConstructor) { linesToAdd.add(name); } } else { if (param.getType().getQualifiedName().equals(int.class.getName()) | param.getType().getQualifiedName().equals(Integer.class.getName())) { signatureBuilder.append( constructorName + ".paramTypes[" + (i++) + "]=Gen_Integer\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Integer"); } else if (param.getType().getQualifiedName().equals(float.class.getName()) | param.getType().getQualifiedName().equals(Float.class.getName())) { signatureBuilder.append(constructorName + ".paramTypes[" + (i++) + "]=Gen_Float\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Float"); } else if (param.getType().getQualifiedName().equals(boolean.class.getName()) | param.getType().getQualifiedName().equals(Boolean.class.getName())) { signatureBuilder.append( constructorName + ".paramTypes[" + (i++) + "]=Gen_Boolean\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Boolean"); } else if (param.getType().getQualifiedName().equals(byte.class.getName()) | param.getType().getQualifiedName().equals(Byte.class.getName())) { signatureBuilder.append(constructorName + ".paramTypes[" + (i++) + "]=Gen_Byte\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Byte"); } else if (param.getType().getQualifiedName().equals(short.class.getName()) | param.getType().getQualifiedName().equals(Short.class.getName())) { signatureBuilder.append(constructorName + ".paramTypes[" + (i++) + "]=Gen_Short\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Short"); } else if (param.getType().getQualifiedName().equals(double.class.getName()) | param.getType().getQualifiedName().equals(Double.class.getName())) { signatureBuilder.append( constructorName + ".paramTypes[" + (i++) + "]=Gen_Double\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Double"); } else if (param.getType().getQualifiedName().equals(char.class.getName()) | param.getType().getQualifiedName().equals(Character.class.getName())) { signatureBuilder.append( constructorName + ".paramTypes[" + (i++) + "]=Gen_Character\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Character"); } else if (param.getType().getQualifiedName().equals(long.class.getName()) | param.getType().getQualifiedName().equals(Long.class.getName())) { signatureBuilder.append(constructorName + ".paramTypes[" + (i++) + "]=Gen_Long\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_Long"); } else { final String type = param.getType().getQualifiedName().replace('.', '_'); signatureBuilder.append( constructorName + ".paramTypes[" + (i++) + "]=Gen_" + type + "\n"); // writer.println(methodName + ".paramTypes[" + // (i++) + "]=Gen_" + type); } } } // writer.println(methodName + ".receiverType=" + // className); signatureBuilder.append("}\n\n"); // writer.println("}\n"); if (addConstructor) { writer.println(signatureBuilder.toString()); } } } writer.flush(); } }