You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@sling.apache.org by np...@apache.org on 2017/10/20 20:37:13 UTC

[sling-org-apache-sling-pipes] 02/04: SLING-7172 add parent(s) pipes

This is an automated email from the ASF dual-hosted git repository.

npeltier pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/sling-org-apache-sling-pipes.git

commit af8e64ef6c7391490a9df483a58dea1e1ae923b3
Author: npeltier <np...@adobe.com>
AuthorDate: Fri Oct 20 21:23:53 2017 +0200

    SLING-7172 add parent(s) pipes
    
    - move parent pipe to be a sling query pipe,
    - added abstract sling query pipe to avoid duplications,
    - added parents pipe,
    - added unit tests for both parent and parents pipe
---
 .../java/org/apache/sling/pipes/PipeBuilder.java   |  7 ++++
 .../sling/pipes/internal/PipeBuilderImpl.java      |  8 ++++
 .../apache/sling/pipes/internal/PlumberImpl.java   |  6 ++-
 .../sling/pipes/internal/PlumberServlet.java       |  1 +
 .../AbstractExpressionSlingQueryPipe.java}         | 44 +++++++++-------------
 .../AbstractSlingQueryPipe.java}                   | 39 ++++++++++---------
 .../internal/{ => slingQuery}/ChildrenPipe.java    | 29 +++-----------
 .../internal/{ => slingQuery}/ParentPipe.java      | 21 +++++------
 .../ParentsPipe.java}                              | 25 ++++++------
 .../org/apache/sling/pipes/AbstractPipeTest.java   |  2 +
 .../{ => slingQuery}/ChildrenPipeTest.java         |  2 +-
 .../ParentPipeTest.java}                           | 29 ++++++--------
 .../ParentsPipeTest.java}                          | 32 +++++++---------
 .../SLING-INF/jcr_root/content/fruits.json         |  1 +
 14 files changed, 111 insertions(+), 135 deletions(-)

diff --git a/src/main/java/org/apache/sling/pipes/PipeBuilder.java b/src/main/java/org/apache/sling/pipes/PipeBuilder.java
index 2082f23..3fe25c2 100644
--- a/src/main/java/org/apache/sling/pipes/PipeBuilder.java
+++ b/src/main/java/org/apache/sling/pipes/PipeBuilder.java
@@ -126,6 +126,13 @@ public interface PipeBuilder {
      */
     PipeBuilder parent();
 
+    /**
+     * attach a parents pipe to the current context
+     * @param expr expression
+     * @return updated instance of PipeBuilder
+     * @throws IllegalAccessException in case it's called with wrong # of arguments
+     */
+    PipeBuilder parents(String expr) throws IllegalAccessException;
 
     /**
      * attach a reference pipe to the current context
diff --git a/src/main/java/org/apache/sling/pipes/internal/PipeBuilderImpl.java b/src/main/java/org/apache/sling/pipes/internal/PipeBuilderImpl.java
index 15e70f2..85e78e5 100644
--- a/src/main/java/org/apache/sling/pipes/internal/PipeBuilderImpl.java
+++ b/src/main/java/org/apache/sling/pipes/internal/PipeBuilderImpl.java
@@ -23,6 +23,9 @@ import org.apache.sling.api.resource.ResourceResolver;
 import org.apache.sling.api.resource.ResourceUtil;
 import org.apache.sling.event.jobs.Job;
 import org.apache.sling.pipes.*;
+import org.apache.sling.pipes.internal.slingQuery.ChildrenPipe;
+import org.apache.sling.pipes.internal.slingQuery.ParentPipe;
+import org.apache.sling.pipes.internal.slingQuery.ParentsPipe;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -162,6 +165,11 @@ public class PipeBuilderImpl implements PipeBuilder {
     }
 
     @Override
+    public PipeBuilder parents(String expr) throws IllegalAccessException {
+        return pipe(ParentsPipe.RESOURCE_TYPE).expr(expr);
+    }
+
+    @Override
     public PipeBuilder ref(String expr) throws IllegalAccessException {
         return pipe(ReferencePipe.RESOURCE_TYPE).expr(expr);
     }
diff --git a/src/main/java/org/apache/sling/pipes/internal/PlumberImpl.java b/src/main/java/org/apache/sling/pipes/internal/PlumberImpl.java
index c6002fc..31d4840 100644
--- a/src/main/java/org/apache/sling/pipes/internal/PlumberImpl.java
+++ b/src/main/java/org/apache/sling/pipes/internal/PlumberImpl.java
@@ -53,6 +53,9 @@ import org.apache.sling.event.jobs.Job;
 import org.apache.sling.event.jobs.JobManager;
 import org.apache.sling.event.jobs.consumer.JobConsumer;
 import org.apache.sling.pipes.*;
+import org.apache.sling.pipes.internal.slingQuery.ChildrenPipe;
+import org.apache.sling.pipes.internal.slingQuery.ParentPipe;
+import org.apache.sling.pipes.internal.slingQuery.ParentsPipe;
 import org.osgi.service.component.annotations.Activate;
 import org.osgi.service.component.annotations.Component;
 import org.osgi.service.component.annotations.Reference;
@@ -113,13 +116,14 @@ public class PlumberImpl implements Plumber, JobConsumer {
         registerPipe(XPathPipe.RESOURCE_TYPE, XPathPipe.class);
         registerPipe(ReferencePipe.RESOURCE_TYPE, ReferencePipe.class);
         registerPipe(RemovePipe.RESOURCE_TYPE, RemovePipe.class);
-        registerPipe(ParentPipe.RESOURCE_TYPE, ParentPipe.class);
+        registerPipe(ParentsPipe.RESOURCE_TYPE, ParentsPipe.class);
         registerPipe(MovePipe.RESOURCE_TYPE, MovePipe.class);
         registerPipe(PathPipe.RESOURCE_TYPE, PathPipe.class);
         registerPipe(FilterPipe.RESOURCE_TYPE, FilterPipe.class);
         registerPipe(NotPipe.RESOURCE_TYPE, NotPipe.class);
         registerPipe(TraversePipe.RESOURCE_TYPE, TraversePipe.class);
         registerPipe(CsvPipe.RESOURCE_TYPE, CsvPipe.class);
+        registerPipe(ParentPipe.RESOURCE_TYPE, ParentPipe.class);
     }
 
     @Reference(policy= ReferencePolicy.DYNAMIC, cardinality= ReferenceCardinality.OPTIONAL)
diff --git a/src/main/java/org/apache/sling/pipes/internal/PlumberServlet.java b/src/main/java/org/apache/sling/pipes/internal/PlumberServlet.java
index 7449d71..a95c5cb 100644
--- a/src/main/java/org/apache/sling/pipes/internal/PlumberServlet.java
+++ b/src/main/java/org/apache/sling/pipes/internal/PlumberServlet.java
@@ -37,6 +37,7 @@ import org.apache.sling.pipes.BasePipe;
 import org.apache.sling.pipes.ContainerPipe;
 import org.apache.sling.pipes.OutputWriter;
 import org.apache.sling.pipes.Plumber;
+import org.apache.sling.pipes.internal.slingQuery.ChildrenPipe;
 import org.osgi.service.component.annotations.Component;
 import org.osgi.service.component.annotations.Reference;
 import org.slf4j.Logger;
diff --git a/src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java b/src/main/java/org/apache/sling/pipes/internal/slingQuery/AbstractExpressionSlingQueryPipe.java
similarity index 50%
copy from src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java
copy to src/main/java/org/apache/sling/pipes/internal/slingQuery/AbstractExpressionSlingQueryPipe.java
index 02916b6..2189801 100644
--- a/src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java
+++ b/src/main/java/org/apache/sling/pipes/internal/slingQuery/AbstractExpressionSlingQueryPipe.java
@@ -14,45 +14,35 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
-
-import static org.apache.sling.query.SlingQuery.$;
-
-import java.util.Iterator;
+package org.apache.sling.pipes.internal.slingQuery;
 
 import org.apache.sling.api.resource.Resource;
-import org.apache.sling.pipes.BasePipe;
 import org.apache.sling.pipes.Plumber;
 import org.apache.sling.query.SlingQuery;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
 /**
- * this pipe uses SlingQuery to filters children (filter defined in expr property) of
- * a resource (defined in the path property)
+ * deals with sling query pipe code that takes an expression as input
  */
-public class ChildrenPipe extends BasePipe {
-    private static Logger logger = LoggerFactory.getLogger(ChildrenPipe.class);
-
-    public final static String RESOURCE_TYPE = RT_PREFIX + "children";
-
-    public ChildrenPipe(Plumber plumber, Resource resource) throws Exception {
+public abstract class AbstractExpressionSlingQueryPipe extends AbstractSlingQueryPipe {
+    Logger logger = LoggerFactory.getLogger(AbstractExpressionSlingQueryPipe.class);
+    public AbstractExpressionSlingQueryPipe(Plumber plumber, Resource resource) throws Exception {
         super(plumber, resource);
     }
 
-    @Override
-    public boolean modifiesContent() {
-        return false;
-    }
+    /**
+     * generates a sling query object out of a resource and an expression
+     * @param resource input resource
+     * @param expression pipe's expression configuration
+     * @return SlingQuery object
+     */
+    protected abstract SlingQuery getQuery(Resource resource, String expression);
 
-    public Iterator<Resource> getOutput() {
-        Resource resource = getInput();
-        if (resource != null) {
-            String queryExpression = getExpr();
-            SlingQuery query = $(resource).children(getExpr());
-            logger.info("[sling query][children]: executing $({}).children({})", resource.getPath(), queryExpression);
-            return query.iterator();
-        }
-        return EMPTY_ITERATOR;
+    @Override
+    protected SlingQuery getQuery(Resource resource) {
+        String expression = getExpr();
+        logger.debug("executing sling query pipe with expression {}", expression);
+        return getQuery(resource, expression);
     }
 }
diff --git a/src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java b/src/main/java/org/apache/sling/pipes/internal/slingQuery/AbstractSlingQueryPipe.java
similarity index 62%
copy from src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java
copy to src/main/java/org/apache/sling/pipes/internal/slingQuery/AbstractSlingQueryPipe.java
index 02916b6..2827046 100644
--- a/src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java
+++ b/src/main/java/org/apache/sling/pipes/internal/slingQuery/AbstractSlingQueryPipe.java
@@ -14,45 +14,44 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
-
-import static org.apache.sling.query.SlingQuery.$;
-
-import java.util.Iterator;
+package org.apache.sling.pipes.internal.slingQuery;
 
 import org.apache.sling.api.resource.Resource;
 import org.apache.sling.pipes.BasePipe;
 import org.apache.sling.pipes.Plumber;
 import org.apache.sling.query.SlingQuery;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
+
+import java.util.Iterator;
 
 /**
- * this pipe uses SlingQuery to filters children (filter defined in expr property) of
- * a resource (defined in the path property)
+ * deals with common sling query pipe code
  */
-public class ChildrenPipe extends BasePipe {
-    private static Logger logger = LoggerFactory.getLogger(ChildrenPipe.class);
-
-    public final static String RESOURCE_TYPE = RT_PREFIX + "children";
-
-    public ChildrenPipe(Plumber plumber, Resource resource) throws Exception {
+public abstract class AbstractSlingQueryPipe extends BasePipe {
+    public AbstractSlingQueryPipe(Plumber plumber, Resource resource) throws Exception {
         super(plumber, resource);
     }
-
     @Override
     public boolean modifiesContent() {
         return false;
     }
 
+    /**
+     * generates a sling query object out of a resource
+     * @param resource input resource
+     * @return SlingQuery object
+     */
+    protected abstract SlingQuery getQuery(Resource resource);
+
+    /**
+     * generate outputs out of input resource and abstract query
+     * @return output's resource iterator, empty in case input is null
+     */
     public Iterator<Resource> getOutput() {
         Resource resource = getInput();
         if (resource != null) {
-            String queryExpression = getExpr();
-            SlingQuery query = $(resource).children(getExpr());
-            logger.info("[sling query][children]: executing $({}).children({})", resource.getPath(), queryExpression);
+            SlingQuery query = getQuery(resource);
             return query.iterator();
         }
         return EMPTY_ITERATOR;
     }
-}
+}
\ No newline at end of file
diff --git a/src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java b/src/main/java/org/apache/sling/pipes/internal/slingQuery/ChildrenPipe.java
similarity index 62%
rename from src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java
rename to src/main/java/org/apache/sling/pipes/internal/slingQuery/ChildrenPipe.java
index 02916b6..df9e299 100644
--- a/src/main/java/org/apache/sling/pipes/internal/ChildrenPipe.java
+++ b/src/main/java/org/apache/sling/pipes/internal/slingQuery/ChildrenPipe.java
@@ -14,26 +14,18 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
+package org.apache.sling.pipes.internal.slingQuery;
 
 import static org.apache.sling.query.SlingQuery.$;
 
-import java.util.Iterator;
-
 import org.apache.sling.api.resource.Resource;
-import org.apache.sling.pipes.BasePipe;
 import org.apache.sling.pipes.Plumber;
 import org.apache.sling.query.SlingQuery;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
 /**
  * this pipe uses SlingQuery to filters children (filter defined in expr property) of
  * a resource (defined in the path property)
  */
-public class ChildrenPipe extends BasePipe {
-    private static Logger logger = LoggerFactory.getLogger(ChildrenPipe.class);
-
+public class ChildrenPipe extends AbstractExpressionSlingQueryPipe {
     public final static String RESOURCE_TYPE = RT_PREFIX + "children";
 
     public ChildrenPipe(Plumber plumber, Resource resource) throws Exception {
@@ -41,18 +33,7 @@ public class ChildrenPipe extends BasePipe {
     }
 
     @Override
-    public boolean modifiesContent() {
-        return false;
-    }
-
-    public Iterator<Resource> getOutput() {
-        Resource resource = getInput();
-        if (resource != null) {
-            String queryExpression = getExpr();
-            SlingQuery query = $(resource).children(getExpr());
-            logger.info("[sling query][children]: executing $({}).children({})", resource.getPath(), queryExpression);
-            return query.iterator();
-        }
-        return EMPTY_ITERATOR;
+    protected SlingQuery getQuery(Resource resource, String expression) {
+        return $(resource).children(expression);
     }
-}
+}
\ No newline at end of file
diff --git a/src/main/java/org/apache/sling/pipes/internal/ParentPipe.java b/src/main/java/org/apache/sling/pipes/internal/slingQuery/ParentPipe.java
similarity index 73%
copy from src/main/java/org/apache/sling/pipes/internal/ParentPipe.java
copy to src/main/java/org/apache/sling/pipes/internal/slingQuery/ParentPipe.java
index 6939f05..359799a 100644
--- a/src/main/java/org/apache/sling/pipes/internal/ParentPipe.java
+++ b/src/main/java/org/apache/sling/pipes/internal/slingQuery/ParentPipe.java
@@ -14,20 +14,18 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
-
-import java.util.Collections;
-import java.util.Iterator;
+package org.apache.sling.pipes.internal.slingQuery;
 
 import org.apache.sling.api.resource.Resource;
-import org.apache.sling.pipes.BasePipe;
 import org.apache.sling.pipes.Plumber;
+import org.apache.sling.query.SlingQuery;
+
+import static org.apache.sling.query.SlingQuery.$;
 
 /**
- * very simple pipe, returning parent resource of input resource
+ * returns sling query parents resources of input resource
  */
-public class ParentPipe extends BasePipe {
-
+public class ParentPipe extends AbstractSlingQueryPipe {
     public static final String RESOURCE_TYPE = RT_PREFIX + "parent";
 
     public ParentPipe(Plumber plumber, Resource resource) throws Exception {
@@ -35,8 +33,7 @@ public class ParentPipe extends BasePipe {
     }
 
     @Override
-    public Iterator<Resource> getOutput() {
-        Resource resource = getInput();
-        return Collections.singleton(resource.getParent()).iterator();
+    protected SlingQuery getQuery(Resource resource) {
+        return $(resource).parent();
     }
-}
+}
\ No newline at end of file
diff --git a/src/main/java/org/apache/sling/pipes/internal/ParentPipe.java b/src/main/java/org/apache/sling/pipes/internal/slingQuery/ParentsPipe.java
similarity index 67%
rename from src/main/java/org/apache/sling/pipes/internal/ParentPipe.java
rename to src/main/java/org/apache/sling/pipes/internal/slingQuery/ParentsPipe.java
index 6939f05..297182b 100644
--- a/src/main/java/org/apache/sling/pipes/internal/ParentPipe.java
+++ b/src/main/java/org/apache/sling/pipes/internal/slingQuery/ParentsPipe.java
@@ -14,29 +14,26 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
-
-import java.util.Collections;
-import java.util.Iterator;
+package org.apache.sling.pipes.internal.slingQuery;
 
 import org.apache.sling.api.resource.Resource;
-import org.apache.sling.pipes.BasePipe;
 import org.apache.sling.pipes.Plumber;
+import org.apache.sling.query.SlingQuery;
+
+import static org.apache.sling.query.SlingQuery.$;
 
 /**
- * very simple pipe, returning parent resource of input resource
+ * returns sling query parents resources of input resource
  */
-public class ParentPipe extends BasePipe {
-
-    public static final String RESOURCE_TYPE = RT_PREFIX + "parent";
+public class ParentsPipe extends AbstractExpressionSlingQueryPipe {
+    public static final String RESOURCE_TYPE = RT_PREFIX + "parents";
 
-    public ParentPipe(Plumber plumber, Resource resource) throws Exception {
+    public ParentsPipe(Plumber plumber, Resource resource) throws Exception {
         super(plumber, resource);
     }
 
     @Override
-    public Iterator<Resource> getOutput() {
-        Resource resource = getInput();
-        return Collections.singleton(resource.getParent()).iterator();
+    protected SlingQuery getQuery(Resource resource, String expression) {
+        return $(resource).parents(expression);
     }
-}
+}
\ No newline at end of file
diff --git a/src/test/java/org/apache/sling/pipes/AbstractPipeTest.java b/src/test/java/org/apache/sling/pipes/AbstractPipeTest.java
index 3d2c799..0b8d99a 100644
--- a/src/test/java/org/apache/sling/pipes/AbstractPipeTest.java
+++ b/src/test/java/org/apache/sling/pipes/AbstractPipeTest.java
@@ -44,6 +44,8 @@ public class AbstractPipeTest {
     protected static final String PATH_FRUITS = "/content/fruits";
     protected static final String PATH_BANANA = PATH_FRUITS + "/banana";
     protected static final String PATH_APPLE = PATH_FRUITS + "/apple";
+    protected static final String PATH_PEA = PATH_APPLE + "/isnota/pea";
+    protected static final String SAME_COLOR = PATH_PEA + "/buttheyhavesamecolor";
     protected static final String NN_SIMPLE = "simple";
     protected static final String NN_COMPLEX = "complex";
     protected static final String PN_INDEX = "/index";
diff --git a/src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java b/src/test/java/org/apache/sling/pipes/internal/slingQuery/ChildrenPipeTest.java
similarity index 96%
copy from src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java
copy to src/test/java/org/apache/sling/pipes/internal/slingQuery/ChildrenPipeTest.java
index c0be002..fa6fa1d 100644
--- a/src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java
+++ b/src/test/java/org/apache/sling/pipes/internal/slingQuery/ChildrenPipeTest.java
@@ -14,7 +14,7 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
+package org.apache.sling.pipes.internal.slingQuery;
 
 import static org.junit.Assert.assertTrue;
 
diff --git a/src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java b/src/test/java/org/apache/sling/pipes/internal/slingQuery/ParentPipeTest.java
similarity index 58%
copy from src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java
copy to src/test/java/org/apache/sling/pipes/internal/slingQuery/ParentPipeTest.java
index c0be002..492cf0a 100644
--- a/src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java
+++ b/src/test/java/org/apache/sling/pipes/internal/slingQuery/ParentPipeTest.java
@@ -14,29 +14,22 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
+package org.apache.sling.pipes.internal.slingQuery;
 
-import static org.junit.Assert.assertTrue;
-
-import org.apache.sling.api.resource.PersistenceException;
 import org.apache.sling.pipes.AbstractPipeTest;
-import org.junit.Before;
 import org.junit.Test;
 
-/**
- * test the sling query pipe
- */
-public class ChildrenPipeTest extends AbstractPipeTest {
+import java.util.Set;
 
-    @Before
-    public void setup() throws PersistenceException {
-        super.setup();
-        context.load().json("/users.json", "/content/users");
-        context.load().json("/children.json", PATH_PIPE);
-    }
+import static org.junit.Assert.*;
 
+public class ParentPipeTest extends AbstractPipeTest {
     @Test
-    public void testChildren() throws Exception {
-        assertTrue("this pipe should have an output", getOutput(PATH_PIPE + "/" + NN_SIMPLE).hasNext());
+    public void testParent() throws Exception {
+        Set<String> outputs = plumber.newPipe(context.resourceResolver())
+                .echo(SAME_COLOR)
+                .parent().run();
+        assertEquals("there should be 1 outputs", 1, outputs.size());
+        assertTrue("there should be pea", outputs.contains(PATH_PEA));
     }
-}
+}
\ No newline at end of file
diff --git a/src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java b/src/test/java/org/apache/sling/pipes/internal/slingQuery/ParentsPipeTest.java
similarity index 61%
rename from src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java
rename to src/test/java/org/apache/sling/pipes/internal/slingQuery/ParentsPipeTest.java
index c0be002..7d5c71c 100644
--- a/src/test/java/org/apache/sling/pipes/internal/ChildrenPipeTest.java
+++ b/src/test/java/org/apache/sling/pipes/internal/slingQuery/ParentsPipeTest.java
@@ -14,29 +14,25 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.apache.sling.pipes.internal;
+package org.apache.sling.pipes.internal.slingQuery;
 
-import static org.junit.Assert.assertTrue;
-
-import org.apache.sling.api.resource.PersistenceException;
 import org.apache.sling.pipes.AbstractPipeTest;
-import org.junit.Before;
 import org.junit.Test;
 
-/**
- * test the sling query pipe
- */
-public class ChildrenPipeTest extends AbstractPipeTest {
+import java.util.Set;
 
-    @Before
-    public void setup() throws PersistenceException {
-        super.setup();
-        context.load().json("/users.json", "/content/users");
-        context.load().json("/children.json", PATH_PIPE);
-    }
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+public class ParentsPipeTest extends AbstractPipeTest {
 
     @Test
-    public void testChildren() throws Exception {
-        assertTrue("this pipe should have an output", getOutput(PATH_PIPE + "/" + NN_SIMPLE).hasNext());
+    public void testParents() throws Exception {
+        Set<String> outputs = plumber.newPipe(context.resourceResolver())
+                .echo(SAME_COLOR)
+                .parents("[color=green]").run();
+        assertEquals("there should be 2 outputs", 2, outputs.size());
+        assertTrue("there should be apple", outputs.contains(PATH_APPLE));
+        assertTrue("there should be pea", outputs.contains(PATH_PEA));
     }
-}
+}
\ No newline at end of file
diff --git a/src/test/resources/SLING-INF/jcr_root/content/fruits.json b/src/test/resources/SLING-INF/jcr_root/content/fruits.json
index 617999e..0817134 100644
--- a/src/test/resources/SLING-INF/jcr_root/content/fruits.json
+++ b/src/test/resources/SLING-INF/jcr_root/content/fruits.json
@@ -5,6 +5,7 @@
     "jcr:primaryType":"nt:unstructured",
     "sling:resourceType":"/apps/pipes-it/fruit",
     "jcr:title":"Apple",
+    "color":"green",
     "worm": true,
     "isnota":{
       "jcr:primaryType":"nt:unstructured",

-- 
To stop receiving notification emails like this one, please contact
"commits@sling.apache.org" <co...@sling.apache.org>.