Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: Fix Sniper printer failing to put added import statement on separate line #3702

37 changes: 24 additions & 13 deletions src/test/java/spoon/test/prettyprinter/TestSniperPrinter.java
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
import org.junit.rules.TemporaryFolder;
import spoon.Launcher;
import spoon.SpoonException;
import spoon.processing.Processor;
import spoon.refactoring.Refactoring;
import spoon.reflect.CtModel;
import spoon.reflect.code.CtConstructorCall;
Expand All @@ -23,6 +22,7 @@
import spoon.reflect.code.CtStatement;
import spoon.reflect.code.CtThrow;
import spoon.reflect.declaration.CtClass;
import spoon.reflect.declaration.CtCompilationUnit;
import spoon.reflect.declaration.CtElement;
import spoon.reflect.declaration.CtField;
import spoon.reflect.declaration.CtMethod;
Expand All @@ -33,8 +33,6 @@
import spoon.reflect.reference.CtExecutableReference;
import spoon.reflect.reference.CtReference;
import spoon.reflect.reference.CtTypeReference;
import spoon.reflect.visitor.ImportCleaner;
import spoon.reflect.visitor.ImportConflictDetector;
import spoon.reflect.visitor.filter.TypeFilter;
import spoon.support.modelobs.ChangeCollector;
import spoon.support.modelobs.SourceFragmentCreator;
Expand All @@ -59,6 +57,9 @@
import java.util.function.BiConsumer;
import java.util.function.Consumer;

import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.anyOf;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
Expand Down Expand Up @@ -369,6 +370,25 @@ public void testPrintTypesThrowsWhenPassedTypesFromMultipleCompilationUnits() {
}
}

@Test
public void testAddedImportStatementPlacedOnSeparateLine() {
// contract: newline must be inserted between import statements when a new one is added

Consumer<CtType<?>> addArrayListImport = type -> {
Factory factory = type.getFactory();
CtCompilationUnit cu = factory.CompilationUnit().getOrCreate(type);
CtTypeReference<?> arrayListRef = factory.Type().get(java.util.ArrayList.class).getReference();
cu.getImports().add(factory.createImport(arrayListRef));
};
BiConsumer<CtType<?>, String> assertImportsPrintedCorrectly = (type, result) -> {
assertThat(result, anyOf(
containsString("import java.util.Set;\nimport java.util.ArrayList;\n"),
containsString("import java.util.ArrayList;\nimport java.util.Set;\n")));
};

testSniper("ClassWithSingleImport", addArrayListImport, assertImportsPrintedCorrectly);
}

/**
* 1) Runs spoon using sniper mode,
* 2) runs `typeChanger` to modify the code,
Expand Down Expand Up @@ -398,16 +418,7 @@ private void testSniper(String testClass, Consumer<CtType<?>> transformation, Bi
private static Launcher createLauncherWithSniperPrinter() {
Launcher launcher = new Launcher();
launcher.getEnvironment().setPrettyPrinterCreator(() -> {
SniperJavaPrettyPrinter printer = new SniperJavaPrettyPrinter(launcher.getEnvironment());
printer.setPreprocessors(Collections.unmodifiableList(Arrays.<Processor<CtElement>>asList(
//remove unused imports first. Do not add new imports at time when conflicts are not resolved
new ImportCleaner().setCanAddImports(false),
//solve conflicts, the current imports are relevant too
new ImportConflictDetector(),
//compute final imports
new ImportCleaner()
)));
return printer;
Comment on lines -401 to -410
Copy link
Collaborator Author

@slarse slarse Nov 17, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Removed as it interfered with my test case (removed unused imports), and no other test cases actually rely on this functionality. Very unclear why it's here.

return new SniperJavaPrettyPrinter(launcher.getEnvironment());
});
return launcher;
}
Expand Down
4 changes: 4 additions & 0 deletions src/test/resources/ClassWithSingleImport.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
import java.util.Set;

public class ClassWithSingleImport {
}