Repository: decorators-squad/eo-yaml
Pull request #462 (2021-06-06 15:03:09)

#457 InlineComment + unit tests
PR for #457 

Fixed printing of mappings (proper print of scalar key and removed printing of key comments);
Introduced InlineComment and used it inside PlainStringScalar;
Unit tests;
Left puzzle to continue work.


Patch:
diff --git a/src/main/java/com/amihaiemil/eoyaml/InlineComment.java b/src/main/java/com/amihaiemil/eoyaml/InlineComment.java
new file mode 100644
index 0000000..3c61bbc
--- /dev/null
+++ b/src/main/java/com/amihaiemil/eoyaml/InlineComment.java
@@ -0,0 +1,66 @@
+/**
+ * Copyright (c) 2016-2021, Mihai Emil Andronache
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ * Redistributions of source code must retain the above copyright notice, this
+ *  list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright notice,
+ *  this list of conditions and the following disclaimer in the documentation
+ *  and/or other materials provided with the distribution.
+ * Neither the name of the copyright holder nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+package com.amihaiemil.eoyaml;
+
+import java.util.Arrays;
+import java.util.stream.Collectors;
+
+/**
+ * Comment decorator which removes the comment's newLines.
+ * Puts the whole comment on one line.
+ * @author Mihai Andronache (amihaiemil@gmail.com)
+ * @version $Id$
+ * @since 5.2.1
+ */
+final class InlineComment implements Comment {
+
+    /**
+     * Original Comment.
+     */
+    private final Comment original;
+
+    /**
+     * Ctor.
+     * @param original Original comment.
+     */
+    InlineComment(final Comment original) {
+        this.original = original;
+    }
+
+    @Override
+    public YamlNode yamlNode() {
+        return this.original.yamlNode();
+    }
+
+    @Override
+    public String value() {
+        return Arrays.stream(
+            this.original.value().split("\\r?\\n")
+        ).collect(Collectors.joining(" "));
+    }
+}
diff --git a/src/main/java/com/amihaiemil/eoyaml/PlainStringScalar.java b/src/main/java/com/amihaiemil/eoyaml/PlainStringScalar.java
index e30e1b2..5332a71 100644
--- a/src/main/java/com/amihaiemil/eoyaml/PlainStringScalar.java
+++ b/src/main/java/com/amihaiemil/eoyaml/PlainStringScalar.java
@@ -66,7 +66,9 @@ final class PlainStringScalar extends BaseScalar {
      */
     PlainStringScalar(final String value, final String comment) {
         this.value = value;
-        this.comment = new BuiltComment(this, comment);
+        this.comment = new InlineComment(
+            new BuiltComment(this, comment)
+        );
     }
 
     /**
diff --git a/src/main/java/com/amihaiemil/eoyaml/RtYamlPrinter.java b/src/main/java/com/amihaiemil/eoyaml/RtYamlPrinter.java
index 69fb26a..b7fb2e4 100644
--- a/src/main/java/com/amihaiemil/eoyaml/RtYamlPrinter.java
+++ b/src/main/java/com/amihaiemil/eoyaml/RtYamlPrinter.java
@@ -132,14 +132,18 @@ final class RtYamlPrinter implements YamlPrinter {
         final Iterator<YamlNode> keysIt = mapping.keys().iterator();
         while(keysIt.hasNext()) {
             final YamlNode key = keysIt.next();
-            this.printPossibleComment(key, alignment.toString());
             final YamlNode value = mapping.value(key);
             if(!(value instanceof Scalar)) {
                 this.printPossibleComment(value, alignment.toString());
             }
             this.writer.append(alignment);
             if(key instanceof Scalar) {
-                this.printScalar((Scalar) key, 0);
+                this.writer.append(
+                    this.indent(
+                        new Escaped((Scalar) key).value(),
+                        0
+                    )
+                );
                 this.writer
                     .append(":");
             } else {


Test patch:
diff --git a/src/test/java/com/amihaiemil/eoyaml/InlineCommentTest.java b/src/test/java/com/amihaiemil/eoyaml/InlineCommentTest.java
new file mode 100644
index 0000000..132766d
--- /dev/null
+++ b/src/test/java/com/amihaiemil/eoyaml/InlineCommentTest.java
@@ -0,0 +1,96 @@
+/**
+ * Copyright (c) 2016-2021, Mihai Emil Andronache
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions are met:
+ * Redistributions of source code must retain the above copyright notice, this
+ *  list of conditions and the following disclaimer.
+ *  Redistributions in binary form must reproduce the above copyright notice,
+ *  this list of conditions and the following disclaimer in the documentation
+ *  and/or other materials provided with the distribution.
+ * Neither the name of the copyright holder nor the names of its
+ *  contributors may be used to endorse or promote products derived from
+ *  this software without specific prior written permission.
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+ * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+ * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+package com.amihaiemil.eoyaml;
+
+import org.hamcrest.MatcherAssert;
+import org.hamcrest.Matchers;
+import org.junit.Test;
+import org.mockito.Mockito;
+
+/**
+ * Unit tests for {@link InlineComment}.
+ * @author Mihai Andronache (amihaiemil@gmail.com)
+ * @version $Id$
+ * @since 5.2.1
+ */
+public final class InlineCommentTest {
+
+    /**
+     * InlineComment can return the parent node from the original Comment.
+     */
+    @Test
+    public void returnsNode() {
+        final YamlNode parent = Mockito.mock(YamlNode.class);
+        final Comment original = Mockito.mock(Comment.class);
+        Mockito.when(original.yamlNode()).thenReturn(parent);
+
+        MatcherAssert.assertThat(
+            new InlineComment(original).yamlNode(),
+            Matchers.is(parent)
+        );
+        Mockito.verify(original, Mockito.times(1)).yamlNode();
+    }
+
+    /**
+     * InlineComment can return the original value if it has no new lines.
+     */
+    @Test
+    public void returnsOriginalValueWithNoNewlines() {
+        final Comment original = Mockito.mock(Comment.class);
+        Mockito.when(original.value()).thenReturn("one line of comment");
+
+        MatcherAssert.assertThat(
+            new InlineComment(original).value(),
+            Matchers.equalTo("one line of comment")
+        );
+        Mockito.verify(original, Mockito.times(1)).value();
+    }
+
+    /**
+     * InlineComment concatenates the lines of the original Comment.
+     */
+    @Test
+    public void returnsConcatenatedLines() {
+        final Comment original = Mockito.mock(Comment.class);
+        Mockito.when(original.value())
+            .thenReturn(
+                "first line" + System.lineSeparator()
+                + "second line" + System.lineSeparator()
+                + "third line"
+            );
+
+        MatcherAssert.assertThat(
+            new InlineComment(original).value(),
+            Matchers.equalTo(
+                "first line second line third line"
+            )
+        );
+        Mockito.verify(original, Mockito.times(1)).value();
+    }
+
+}
diff --git a/src/test/java/com/amihaiemil/eoyaml/YamlMappingCommentsPrintTest.java b/src/test/java/com/amihaiemil/eoyaml/YamlMappingCommentsPrintTest.java
index 472b87d..ebc45ca 100644
--- a/src/test/java/com/amihaiemil/eoyaml/YamlMappingCommentsPrintTest.java
+++ b/src/test/java/com/amihaiemil/eoyaml/YamlMappingCommentsPrintTest.java
@@ -44,9 +44,8 @@ import java.io.IOException;
  * @author Mihai Andronache (amihaiemil@gmail.com)
  * @version $Id$
  * @since 4.2.0
- * @todo #454:60min Modify the printing logic for scalar comments: if the
- *  comment contains line breaks, write it above the scalar. If the comment has
- *  no line breaks, write it inline, after the scalar.
+ * @todo #457:60min Continue modifying the printing logic for scalar comments:
+ *  The above and inline comments should be printed properly.
  */
 public final class YamlMappingCommentsPrintTest {