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 bug where xml:space="preserve" would not preserve XML element whitespace content. #407

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions sorter/src/main/java/sortpom/content/NewlineText.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,11 @@
* in XmlProcessor.PatchedXMLWriter
*/
public class NewlineText extends AbstractText {
public static final NewlineText INSTANCE = new NewlineText();
private static final long serialVersionUID = -7552189498553321263L;

private NewlineText() {}

/**
* This returns a <code>String</code> representation of the <code>NewlineText</code>, suitable for
* debugging.
Expand Down
38 changes: 19 additions & 19 deletions sorter/src/main/java/sortpom/output/PatchedXMLWriter.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,25 @@ public PatchedXMLWriter(
this.endWithNewline = endWithNewline;
}

@Override
public void write(Document doc) throws IOException {
writeDeclaration();

if (doc.getDocType() != null) {
indent();
writeDocType(doc.getDocType());
}

for (int i = 0, size = doc.nodeCount(); i < size; i++) {
var node = doc.node(i);
writeNode(node);
}

if (endWithNewline) {
writePrintln();
}
}

/** Handle spaceBeforeCloseEmptyElement option */
@Override
protected void writeEmptyElementClose(String qualifiedName) throws IOException {
Expand All @@ -62,25 +81,6 @@ protected void writeProcessingInstruction(ProcessingInstruction pi) throws IOExc
lastOutputNodeType = Node.PROCESSING_INSTRUCTION_NODE;
}

@Override
public void write(Document doc) throws IOException {
writeDeclaration();

if (doc.getDocType() != null) {
indent();
writeDocType(doc.getDocType());
}

for (int i = 0, size = doc.nodeCount(); i < size; i++) {
var node = doc.node(i);
writeNode(node);
}

if (endWithNewline) {
writePrintln();
}
}

/** Handle Custom NewLineTest node and potential indent of empty line */
@Override
protected void writeNodeText(Node node) throws IOException {
Expand Down
27 changes: 23 additions & 4 deletions sorter/src/main/java/sortpom/wrapper/TextWrapperCreator.java
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
package sortpom.wrapper;

import java.util.regex.Pattern;
import org.dom4j.Element;
import org.dom4j.Node;
import org.dom4j.Text;
import sortpom.content.NewlineText;
import sortpom.parameter.PluginParameters;
import sortpom.wrapper.content.SingleNewlineInTextWrapper;
import sortpom.wrapper.content.UnsortedWrapper;
Expand All @@ -13,29 +14,47 @@
* @since 2012-05-19
*/
public class TextWrapperCreator {

public static final Pattern REGEX_ONE_NEWLINE =
Pattern.compile("^[\\t ]*(\\r|\\n|\\r\\n)[\\t ]*$");
public static final Pattern REGEX_ONE_OR_MORE_NEWLINE = Pattern.compile("^\\s*?([\\r\\n])\\s*$");
private boolean keepBlankLines;

public void setup(PluginParameters pluginParameters) {
keepBlankLines = pluginParameters.keepBlankLines;
}

Wrapper<Node> createWrapper(Text text) {
if (isElementSpacePreserved(text.getParent())) {
return new UnsortedWrapper<>(text);
}
if (isSingleNewLine(text)) {
return SingleNewlineInTextWrapper.INSTANCE;
} else if (isBlankLineOrLines(text)) {
return new UnsortedWrapper<>(new NewlineText());
return UnsortedWrapper.NEWLINE_TEXT_WRAPPER_INSTANCE;
}
return new UnsortedWrapper<>(text);
}

private boolean isElementSpacePreserved(Element element) {
if (element == null) {
return false;
}
var attr = element.attribute("space");

return attr != null
&& "xml".equals(attr.getNamespacePrefix())
&& "preserve".equals(attr.getText());
}

private boolean isSingleNewLine(Text content) {
return content.getText().matches("[\\t ]*\\r?\\n?[\\t ]*");
return REGEX_ONE_NEWLINE.matcher(content.getText()).matches();
}

boolean isBlankLineOrLines(Text content) {
if (!keepBlankLines) {
return false;
}
return content.getText().matches("^\\s*?([\\r\\n])\\s*$");
return REGEX_ONE_OR_MORE_NEWLINE.matcher(content.getText()).matches();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,12 @@

import org.dom4j.Element;
import org.dom4j.Node;
import sortpom.content.NewlineText;

/** A wrapper that lets is element be unsorted */
public class UnsortedWrapper<T extends Node> implements Wrapper<T> {
public static final UnsortedWrapper<Node> NEWLINE_TEXT_WRAPPER_INSTANCE =
new UnsortedWrapper<>(NewlineText.INSTANCE);

/** The wrapped dom content. */
private final T content;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,23 +68,23 @@ void illegalEncodingWhenSavingPomFileShouldNotWork() throws IOException {
}

@Test
void differentEncodingShouldWork1() throws Exception {
void differentEncodingShouldWork1() {
SortPomImplUtil.create()
.predefinedSortOrder("default_0_4_0")
.encoding("UTF-32BE")
.testFiles("/UTF32Encoding_input.xml", "/UTF32Encoding_expected.xml");
}

@Test
void differentEncodingShouldWork2() throws Exception {
void differentEncodingShouldWork2() {
SortPomImplUtil.create()
.predefinedSortOrder("default_0_4_0")
.encoding("UTF-16")
.testFiles("/UTF16Encoding_input.xml", "/UTF16Encoding_expected.xml");
}

@Test
void differentEncodingShouldWork3() throws Exception {
void differentEncodingShouldWork3() {
SortPomImplUtil.create()
.predefinedSortOrder("default_0_4_0")
.encoding("ISO-8859-1")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,15 +6,15 @@
class IgnoreLineSeparatorsTest {

@Test
void ignoringLineSeparatorsShouldNotSort() throws Exception {
void ignoringLineSeparatorsShouldNotSort() {
SortPomImplUtil.create()
.lineSeparator("\n")
.ignoreLineSeparators(true)
.testNoSorting("/ignore_line_separators_input.xml");
}

@Test
void doNotIgnoreLineSeparatorsShouldSort() throws Exception {
void doNotIgnoreLineSeparatorsShouldSort() {
SortPomImplUtil.create()
.lineSeparator("\n")
.ignoreLineSeparators(false)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
class KeepTimestampParameterTest {

@Test
void whenKeepTimestampNotSetTimestampsShouldDiffer() throws Exception {
void whenKeepTimestampNotSetTimestampsShouldDiffer() {
SortPomImplUtil.create()
.customSortOrderFile("difforder/differentOrder.xml")
.lineSeparator("\n")
Expand All @@ -16,7 +16,7 @@ void whenKeepTimestampNotSetTimestampsShouldDiffer() throws Exception {
}

@Test
void whenKeepTimestampIsSetTimestampsShouldRemain() throws Exception {
void whenKeepTimestampIsSetTimestampsShouldRemain() {
SortPomImplUtil.create()
.customSortOrderFile("difforder/differentOrder.xml")
.lineSeparator("\n")
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@
import static org.hamcrest.core.IsEqual.equalTo;
import static org.junit.jupiter.api.Assertions.assertThrows;

import java.lang.reflect.InvocationTargetException;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.function.Executable;
import sortpom.exception.FailureException;
Expand Down Expand Up @@ -52,11 +51,10 @@ void incorrectCustomSortOrderShouldThrowException2() {
.customSortOrderFile("difforder/VERYdifferentOrder.xml")
.testVerifyXmlIsOrdered("/sortOrderFiles/sorted_differentOrder.xml");

var thrown = assertThrows(InvocationTargetException.class, testMethod);
var thrown = assertThrows(RuntimeException.class, testMethod).getCause().getCause();

var cause = thrown.getTargetException();
assertThat(cause, isA(FailureException.class));
assertThat(cause.getMessage(), endsWith("VERYdifferentOrder.xml in classpath"));
assertThat(thrown, isA(FailureException.class));
assertThat(thrown.getMessage(), endsWith("VERYdifferentOrder.xml in classpath"));
}

@Test
Expand All @@ -68,12 +66,11 @@ void incorrectPredefinedSortOrderShouldThrowException2() {
.lineSeparator("\n")
.testVerifyXmlIsOrdered("/sortOrderFiles/sorted_default_0_4_0.xml");

var thrown = assertThrows(InvocationTargetException.class, testMethod);
var thrown = assertThrows(RuntimeException.class, testMethod).getCause().getCause();

var cause = thrown.getTargetException();
assertThat(cause, isA(IllegalArgumentException.class));
assertThat(thrown, isA(IllegalArgumentException.class));
assertThat(
cause.getMessage(),
thrown.getMessage(),
is(equalTo("Cannot find abbie_normal_brain.xml among the predefined plugin resources")));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ void violationFileShouldBeCreatedOnVerificationStop() {
}

@Test
void violationFileWithParentDirectoryShouldBeCreatedOnVerificationWarn() throws Exception {
void violationFileWithParentDirectoryShouldBeCreatedOnVerificationWarn() {
SortPomImplUtil.create()
.verifyFail("Warn")
.violationFile(FILENAME_WITH_DIRECTORIES)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

class EndWithNewlineTest {
@Test
void endWithNewlineFalseShouldNotOutputFinalNewline() throws Exception {
void endWithNewlineFalseShouldNotOutputFinalNewline() {
XmlProcessorTestUtil.create()
.predefinedSortOrder("default_0_4_0")
.endWithNewlineFalse()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

class IgnoreSectionsTest {
@Test
void forceDependencyToTopTrickShouldWork() throws Exception {
void forceDependencyToTopTrickShouldWork() {
SortPomImplUtil.create()
.sortDependencies("scope,groupId,artifactId")
.lineSeparator("\n")
Expand Down
8 changes: 4 additions & 4 deletions sorter/src/test/java/sortpom/sort/IndentationTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ class IndentationTest {

@ParameterizedTest()
@ValueSource(ints = {0, 1, 4, -1})
void differentIndentsShouldWork(int indent) throws Exception {
void differentIndentsShouldWork(int indent) {
var expectedFile = "/SortModules_expectedIndent" + indent + ".xml";
SortPomImplUtil.create()
.sortProperties()
Expand All @@ -28,7 +28,7 @@ void differentIndentsShouldWork(int indent) throws Exception {

@ParameterizedTest()
@ValueSource(ints = {0, 1, 4, -1})
void indentSchemaLocationShouldBeIndentTimesTwoPlusOne(int indent) throws Exception {
void indentSchemaLocationShouldBeIndentTimesTwoPlusOne(int indent) {
var expectedFile = "/SortModules_expectedSchemaIndent" + indent + ".xml";
SortPomImplUtil.create()
.sortProperties()
Expand Down Expand Up @@ -73,7 +73,7 @@ void indentSchemaLocationShouldAddNewlineAndIndentation(int indent) {
+ lineSeparator
+ indentChars
+ indentChars
+ " xsi:schemaLocation=\"http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd\">"
+ " xsi:schemaLocation=\"http://maven.apache.org/POM/4.0.0 https://maven.apache.org/maven-v4_0_0.xsd\">"
+ lineSeparator
+ indentChars
+ "<Gurka xmlns=\"\"></Gurka>"
Expand Down Expand Up @@ -106,7 +106,7 @@ void otherAttributeShouldNotBeIndented() {
+ lineSeparator
+ indentChars
+ indentChars
+ " xsi:schemaLocation=\"http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd\">"
+ " xsi:schemaLocation=\"http://maven.apache.org/POM/4.0.0 https://maven.apache.org/maven-v4_0_0.xsd\">"
+ lineSeparator
+ indentChars
+ "<Gurka xmlns=\"\" key=\"value\"></Gurka>"
Expand Down
Loading