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

exceptionfactory pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/nifi.git


The following commit(s) were added to refs/heads/main by this push:
     new 1d7ee542b1 NIFI-2161 add option to skip attribute output for unmatched 
JSON path expressions in EvaluateJsonPath
1d7ee542b1 is described below

commit 1d7ee542b121b9ac36412b2a2b3b642d4e0e349c
Author: Chris Sampson <[email protected]>
AuthorDate: Mon Jan 2 10:41:47 2023 +0000

    NIFI-2161 add option to skip attribute output for unmatched JSON path 
expressions in EvaluateJsonPath
    
    This closes #6817
    
    Signed-off-by: David Handermann <[email protected]>
---
 .../nifi/processors/standard/EvaluateJsonPath.java | 102 +++++++++----------
 .../processors/standard/TestEvaluateJsonPath.java  | 109 ++++++++++++---------
 2 files changed, 114 insertions(+), 97 deletions(-)

diff --git 
a/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/main/java/org/apache/nifi/processors/standard/EvaluateJsonPath.java
 
b/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/main/java/org/apache/nifi/processors/standard/EvaluateJsonPath.java
index 0f310d7f96..afdd1b2b35 100644
--- 
a/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/main/java/org/apache/nifi/processors/standard/EvaluateJsonPath.java
+++ 
b/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/main/java/org/apache/nifi/processors/standard/EvaluateJsonPath.java
@@ -16,22 +16,10 @@
  */
 package org.apache.nifi.processors.standard;
 
-import java.io.BufferedOutputStream;
-import java.io.OutputStream;
-import java.nio.charset.StandardCharsets;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Queue;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentLinkedQueue;
-import java.util.concurrent.ConcurrentMap;
-
+import com.jayway.jsonpath.DocumentContext;
+import com.jayway.jsonpath.InvalidJsonException;
+import com.jayway.jsonpath.JsonPath;
+import com.jayway.jsonpath.PathNotFoundException;
 import org.apache.commons.lang3.StringUtils;
 import org.apache.nifi.annotation.behavior.DynamicProperty;
 import org.apache.nifi.annotation.behavior.EventDriven;
@@ -56,11 +44,21 @@ import 
org.apache.nifi.processor.ProcessorInitializationContext;
 import org.apache.nifi.processor.Relationship;
 import org.apache.nifi.processor.exception.ProcessException;
 
-import com.jayway.jsonpath.DocumentContext;
-import com.jayway.jsonpath.InvalidJsonException;
-import com.jayway.jsonpath.JsonPath;
-import com.jayway.jsonpath.PathNotFoundException;
-
+import java.io.BufferedOutputStream;
+import java.io.OutputStream;
+import java.nio.charset.StandardCharsets;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Queue;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.concurrent.ConcurrentMap;
 import java.util.stream.Collectors;
 
 @EventDriven
@@ -80,8 +78,8 @@ import java.util.stream.Collectors;
         + "If the JsonPath evaluates to a JSON array or JSON object and the 
Return Type is set to 'scalar' the FlowFile will be unmodified and will be 
routed to failure. "
         + "A Return Type of JSON can return scalar values if the provided 
JsonPath evaluates to the specified value and will be routed as a match."
         + "If Destination is 'flowfile-content' and the JsonPath does not 
evaluate to a defined path, the FlowFile will be routed to 'unmatched' without 
having its contents modified. "
-        + "If Destination is flowfile-attribute and the expression matches 
nothing, attributes will be created with "
-        + "empty strings as the value, and the FlowFile will always be routed 
to 'matched.'")
+        + "If Destination is 'flowfile-attribute' and the expression matches 
nothing, attributes will be created with "
+        + "empty strings as the value unless 'Path Not Found Behaviour' is set 
to 'skip', and the FlowFile will always be routed to 'matched.'")
 @DynamicProperty(name = "A FlowFile attribute(if <Destination> is set to 
'flowfile-attribute')",
         value = "A JsonPath expression", description = "If 
<Destination>='flowfile-attribute' then that FlowFile attribute "
         + "will be set to any JSON objects that match the JsonPath.  If 
<Destination>='flowfile-content' then the FlowFile "
@@ -98,6 +96,8 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
     public static final String PATH_NOT_FOUND_IGNORE = "ignore";
     public static final String PATH_NOT_FOUND_WARN = "warn";
 
+    public static final String PATH_NOT_FOUND_SKIP = "skip";
+
     public static final PropertyDescriptor DESTINATION = new 
PropertyDescriptor.Builder()
             .name("Destination")
             .description("Indicates whether the results of the JsonPath 
evaluation are written to the FlowFile content or a FlowFile attribute; "
@@ -119,9 +119,9 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
     public static final PropertyDescriptor PATH_NOT_FOUND = new 
PropertyDescriptor.Builder()
             .name("Path Not Found Behavior")
             .description("Indicates how to handle missing JSON path 
expressions when destination is set to 'flowfile-attribute'. Selecting 'warn' 
will "
-                    + "generate a warning when a JSON path expression is not 
found.")
+                    + "generate a warning when a JSON path expression is not 
found. Selecting 'skip' will omit attributes for any unmatched JSON path 
expressions.")
             .required(true)
-            .allowableValues(PATH_NOT_FOUND_WARN, PATH_NOT_FOUND_IGNORE)
+            .allowableValues(PATH_NOT_FOUND_WARN, PATH_NOT_FOUND_IGNORE, 
PATH_NOT_FOUND_SKIP)
             .defaultValue(PATH_NOT_FOUND_IGNORE)
             .build();
 
@@ -145,7 +145,6 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
     private final ConcurrentMap<String, JsonPath> cachedJsonPathMap = new 
ConcurrentHashMap<>();
 
     private final Queue<Set<Map.Entry<String, JsonPath>>> 
attributeToJsonPathEntrySetQueue = new ConcurrentLinkedQueue<>();
-    private volatile String representationOption;
     private volatile boolean destinationIsAttribute;
     private volatile String returnType;
     private volatile String pathNotFound;
@@ -153,18 +152,18 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
 
     @Override
     protected void init(final ProcessorInitializationContext context) {
-        final Set<Relationship> relationships = new HashSet<>();
-        relationships.add(REL_MATCH);
-        relationships.add(REL_NO_MATCH);
-        relationships.add(REL_FAILURE);
-        this.relationships = Collections.unmodifiableSet(relationships);
-
-        final List<PropertyDescriptor> properties = new ArrayList<>();
-        properties.add(DESTINATION);
-        properties.add(RETURN_TYPE);
-        properties.add(PATH_NOT_FOUND);
-        properties.add(NULL_VALUE_DEFAULT_REPRESENTATION);
-        this.properties = Collections.unmodifiableList(properties);
+        final Set<Relationship> rels = new HashSet<>();
+        rels.add(REL_MATCH);
+        rels.add(REL_NO_MATCH);
+        rels.add(REL_FAILURE);
+        this.relationships = Collections.unmodifiableSet(rels);
+
+        final List<PropertyDescriptor> props = new ArrayList<>();
+        props.add(DESTINATION);
+        props.add(RETURN_TYPE);
+        props.add(PATH_NOT_FOUND);
+        props.add(NULL_VALUE_DEFAULT_REPRESENTATION);
+        this.properties = Collections.unmodifiableList(props);
     }
 
     @Override
@@ -222,12 +221,8 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
 
     @Override
     public void onPropertyModified(PropertyDescriptor descriptor, String 
oldValue, String newValue) {
-        if (descriptor.isDynamic()) {
-            if (!StringUtils.equals(oldValue, newValue)) {
-                if (oldValue != null) {
-                    cachedJsonPathMap.remove(oldValue);
-                }
-            }
+        if (descriptor.isDynamic() && !StringUtils.equals(oldValue, newValue) 
&& oldValue != null) {
+            cachedJsonPathMap.remove(oldValue);
         }
     }
 
@@ -248,14 +243,13 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
 
     @OnScheduled
     public void onScheduled(ProcessContext processContext) {
-        representationOption = 
processContext.getProperty(NULL_VALUE_DEFAULT_REPRESENTATION).getValue();
         destinationIsAttribute = 
DESTINATION_ATTRIBUTE.equals(processContext.getProperty(DESTINATION).getValue());
         returnType = processContext.getProperty(RETURN_TYPE).getValue();
         if (returnType.equals(RETURN_TYPE_AUTO)) {
             returnType = destinationIsAttribute ? RETURN_TYPE_SCALAR : 
RETURN_TYPE_JSON;
         }
         pathNotFound = processContext.getProperty(PATH_NOT_FOUND).getValue();
-        nullDefaultValue = NULL_REPRESENTATION_MAP.get(representationOption);
+        nullDefaultValue = 
NULL_REPRESENTATION_MAP.get(processContext.getProperty(NULL_VALUE_DEFAULT_REPRESENTATION).getValue());
     }
 
     @OnUnscheduled
@@ -276,7 +270,7 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
         try {
             documentContext = validateAndEstablishJsonContext(processSession, 
flowFile);
         } catch (InvalidJsonException e) {
-            logger.error("FlowFile {} did not have valid JSON content.", new 
Object[]{flowFile});
+            logger.error("FlowFile {} did not have valid JSON content.", 
flowFile);
             processSession.transfer(flowFile, REL_FAILURE);
             return;
         }
@@ -291,7 +285,7 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
 
         try {
             // We'll only be using this map if destinationIsAttribute == true
-            final Map<String, String> jsonPathResults = destinationIsAttribute 
? new HashMap<>(attributeJsonPathEntries.size()) : Collections.EMPTY_MAP;
+            final Map<String, String> jsonPathResults = destinationIsAttribute 
? new HashMap<>(attributeJsonPathEntries.size()) : Collections.emptyMap();
 
             for (final Map.Entry<String, JsonPath> attributeJsonPathEntry : 
attributeJsonPathEntries) {
                 final String jsonPathAttrKey = attributeJsonPathEntry.getKey();
@@ -299,22 +293,24 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
 
                 Object result;
                 try {
-                    Object potentialResult = documentContext.read(jsonPathExp);
+                    final Object potentialResult = 
documentContext.read(jsonPathExp);
                     if (returnType.equals(RETURN_TYPE_SCALAR) && 
!isJsonScalar(potentialResult)) {
                         logger.error("Unable to return a scalar value for the 
expression {} for FlowFile {}. Evaluated value was {}. Transferring to {}.",
-                                new Object[]{jsonPathExp.getPath(), 
flowFile.getId(), potentialResult.toString(), REL_FAILURE.getName()});
+                                jsonPathExp.getPath(), flowFile.getId(), 
potentialResult.toString(), REL_FAILURE.getName());
                         processSession.transfer(flowFile, REL_FAILURE);
                         return;
                     }
                     result = potentialResult;
-                } catch (PathNotFoundException e) {
+                } catch (final PathNotFoundException e) {
                     if (pathNotFound.equals(PATH_NOT_FOUND_WARN)) {
                         logger.warn("FlowFile {} could not find path {} for 
attribute key {}.",
                                 new Object[]{flowFile.getId(), 
jsonPathExp.getPath(), jsonPathAttrKey}, e);
                     }
 
                     if (destinationIsAttribute) {
-                        jsonPathResults.put(jsonPathAttrKey, 
StringUtils.EMPTY);
+                        if (!pathNotFound.equals(PATH_NOT_FOUND_SKIP)) {
+                            jsonPathResults.put(jsonPathAttrKey, 
StringUtils.EMPTY);
+                        }
                         continue;
                     } else {
                         processSession.transfer(flowFile, REL_NO_MATCH);
@@ -336,7 +332,7 @@ public class EvaluateJsonPath extends 
AbstractJsonPathProcessor {
             }
 
             // jsonPathResults map will be empty if this is false
-            if (destinationIsAttribute) {
+            if (destinationIsAttribute && !jsonPathResults.isEmpty()) {
                 flowFile = processSession.putAllAttributes(flowFile, 
jsonPathResults);
             }
             processSession.transfer(flowFile, REL_MATCH);
diff --git 
a/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/test/java/org/apache/nifi/processors/standard/TestEvaluateJsonPath.java
 
b/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/test/java/org/apache/nifi/processors/standard/TestEvaluateJsonPath.java
index 79a07a8c5b..6620c25141 100644
--- 
a/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/test/java/org/apache/nifi/processors/standard/TestEvaluateJsonPath.java
+++ 
b/nifi-nar-bundles/nifi-standard-bundle/nifi-standard-processors/src/test/java/org/apache/nifi/processors/standard/TestEvaluateJsonPath.java
@@ -16,34 +16,33 @@
  */
 package org.apache.nifi.processors.standard;
 
-import java.io.BufferedOutputStream;
-import java.io.IOException;
-import java.io.OutputStream;
-import java.nio.charset.StandardCharsets;
-import java.nio.file.Path;
-import java.nio.file.Paths;
-import java.util.Arrays;
-import java.util.List;
 import org.apache.nifi.flowfile.FlowFile;
 import org.apache.nifi.processor.ProcessSession;
 import org.apache.nifi.processor.Relationship;
-import org.apache.nifi.processor.io.OutputStreamCallback;
 import org.apache.nifi.util.MockFlowFile;
 import org.apache.nifi.util.StringUtils;
 import org.apache.nifi.util.TestRunner;
 import org.apache.nifi.util.TestRunners;
 import org.junit.jupiter.api.Test;
 
+import java.io.BufferedOutputStream;
+import java.io.OutputStream;
+import java.nio.charset.StandardCharsets;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.Arrays;
+import java.util.List;
+
 import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.junit.jupiter.api.Assertions.assertNotNull;
 
-public class TestEvaluateJsonPath {
+class TestEvaluateJsonPath {
 
     private static final Path JSON_SNIPPET = 
Paths.get("src/test/resources/TestJson/json-sample.json");
     private static final Path XML_SNIPPET = 
Paths.get("src/test/resources/TestXml/xml-snippet.xml");
 
     @Test
-    public void testInvalidJsonPath() {
+    void testInvalidJsonPath() {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
         testRunner.setProperty("invalid.jsonPath", "$..");
@@ -52,7 +51,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testUpgradeToJsonPath24() throws Exception {
+    void testUpgradeToJsonPath24() throws Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
         List<String> badInputs = Arrays.asList("LoremIpsum []", 
"LoremIpsum[]", "$..", "$.xyz.");
@@ -90,7 +89,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testInvalidJsonDocument() throws Exception {
+    void testInvalidJsonDocument() throws Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
 
@@ -98,11 +97,10 @@ public class TestEvaluateJsonPath {
         testRunner.run();
 
         testRunner.assertAllFlowFilesTransferred(EvaluateJsonPath.REL_FAILURE, 
1);
-        final MockFlowFile out = 
testRunner.getFlowFilesForRelationship(EvaluateJsonPath.REL_FAILURE).get(0);
     }
 
     @Test
-    public void testInvalidConfiguration_destinationContent_twoPaths() throws 
Exception {
+    void testInvalidConfiguration_destinationContent_twoPaths() {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_CONTENT);
         testRunner.setProperty("JsonPath1", "$[0]._id");
@@ -112,7 +110,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testInvalidConfiguration_invalidJsonPath_space() throws 
Exception {
+    void testInvalidConfiguration_invalidJsonPath_space() {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_CONTENT);
         testRunner.setProperty("JsonPath1", "$[0]. _id");
@@ -120,18 +118,22 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testConfiguration_destinationAttributes_twoPaths() throws 
Exception {
+    void testConfiguration_destinationAttributes_twoPaths() throws Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
         testRunner.setProperty("JsonPath1", "$[0]._id");
-        testRunner.setProperty("JsonPath2", "$[0].name");
+        testRunner.setProperty("JsonPath2", "$[0].name"); // cannot be 
converted to scalar
 
         testRunner.enqueue(JSON_SNIPPET);
         testRunner.run();
+
+        Relationship expectedRel = EvaluateJsonPath.REL_FAILURE;
+
+        testRunner.assertAllFlowFilesTransferred(expectedRel, 1);
     }
 
     @Test
-    public void testExtractPath_destinationAttribute() throws Exception {
+    void testExtractPath_destinationAttribute() throws Exception {
         String jsonPathAttrKey = "JsonPath";
 
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
@@ -149,7 +151,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testExtractPath_destinationAttributes_twoPaths() throws 
Exception {
+    void testExtractPath_destinationAttributes_twoPaths() throws Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
         testRunner.setProperty(EvaluateJsonPath.RETURN_TYPE, 
EvaluateJsonPath.RETURN_TYPE_JSON);
@@ -172,9 +174,10 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testExtractPath_destinationAttributes_twoPaths_notFound() 
throws Exception {
+    void testExtractPath_destinationAttributes_twoPaths_notFound() throws 
Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
+        testRunner.setProperty(EvaluateJsonPath.PATH_NOT_FOUND, 
EvaluateJsonPath.PATH_NOT_FOUND_WARN);
 
         String jsonPathIdAttrKey = "evaluatejson.id";
         String jsonPathNameAttrKey = "evaluatejson.name";
@@ -189,14 +192,15 @@ public class TestEvaluateJsonPath {
 
         testRunner.assertAllFlowFilesTransferred(expectedRel, 1);
         final MockFlowFile out = 
testRunner.getFlowFilesForRelationship(expectedRel).get(0);
-        assertEquals("", out.getAttribute(jsonPathIdAttrKey), "Transferred 
flow file did not have the correct result for id attribute");
-        assertEquals("", out.getAttribute(jsonPathNameAttrKey), "Transferred 
flow file did not have the correct result for name attribute");
+        assertEquals(StringUtils.EMPTY, out.getAttribute(jsonPathIdAttrKey), 
"Transferred flow file did not have the correct result for id attribute");
+        assertEquals(StringUtils.EMPTY, out.getAttribute(jsonPathNameAttrKey), 
"Transferred flow file did not have the correct result for name attribute");
     }
 
     @Test
-    public void testExtractPath_destinationAttributes_twoPaths_oneFound() 
throws Exception {
+    void testExtractPath_destinationAttributes_twoPaths_oneFound() throws 
Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
+        testRunner.setProperty(EvaluateJsonPath.PATH_NOT_FOUND, 
EvaluateJsonPath.PATH_NOT_FOUND_IGNORE);
 
         String jsonPathIdAttrKey = "evaluatejson.id";
         String jsonPathNameAttrKey = "evaluatejson.name";
@@ -216,7 +220,30 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testExtractPath_destinationContent() throws Exception {
+    void testExtractPath_destinationAttributes_twoPaths_oneFound_skipMissing() 
throws Exception {
+        final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
+        testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
+        testRunner.setProperty(EvaluateJsonPath.PATH_NOT_FOUND, 
EvaluateJsonPath.PATH_NOT_FOUND_SKIP);
+
+        String jsonPathIdAttrKey = "evaluatejson.id";
+        String jsonPathNameAttrKey = "evaluatejson.name";
+
+        testRunner.setProperty(jsonPathIdAttrKey, "$[0]._id");
+        testRunner.setProperty(jsonPathNameAttrKey, "$[0].name.nonexistent");
+
+        testRunner.enqueue(JSON_SNIPPET);
+        testRunner.run();
+
+        Relationship expectedRel = EvaluateJsonPath.REL_MATCH;
+
+        testRunner.assertAllFlowFilesTransferred(expectedRel, 1);
+        final MockFlowFile out = 
testRunner.getFlowFilesForRelationship(expectedRel).get(0);
+        assertEquals("54df94072d5dbf7dc6340cc5", 
out.getAttribute(jsonPathIdAttrKey), "Transferred flow file did not have the 
correct result for id attribute");
+        out.assertAttributeNotExists(jsonPathNameAttrKey);
+    }
+
+    @Test
+    void testExtractPath_destinationContent() throws Exception {
         String jsonPathAttrKey = "JsonPath";
 
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
@@ -233,7 +260,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testExtractPath_destinationContent_indefiniteResult() throws 
Exception {
+    void testExtractPath_destinationContent_indefiniteResult() throws 
Exception {
         String jsonPathAttrKey = "friends.indefinite.id.list";
 
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
@@ -250,7 +277,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void 
testExtractPath_destinationContent_indefiniteResult_operators() throws 
Exception {
+    void testExtractPath_destinationContent_indefiniteResult_operators() 
throws Exception {
         String jsonPathAttrKey = "friends.indefinite.id.list";
 
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
@@ -267,7 +294,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testRouteUnmatched_destinationContent_noMatch() throws 
Exception {
+    void testRouteUnmatched_destinationContent_noMatch() throws Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_CONTENT);
         testRunner.setProperty("jsonPath", "$[0].nonexistent.key");
@@ -282,7 +309,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testRouteFailure_returnTypeScalar_resultArray() throws 
Exception {
+    void testRouteFailure_returnTypeScalar_resultArray() throws Exception {
         String jsonPathAttrKey = "friends.indefinite.id.list";
 
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
@@ -300,7 +327,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testNullInput() throws Exception {
+    void testNullInput() {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.RETURN_TYPE, 
EvaluateJsonPath.RETURN_TYPE_JSON);
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
@@ -311,12 +338,9 @@ public class TestEvaluateJsonPath {
         ProcessSession session = 
testRunner.getProcessSessionFactory().createSession();
         FlowFile ff = session.create();
 
-        ff = session.write(ff, new OutputStreamCallback() {
-            @Override
-            public void process(OutputStream out) throws IOException {
-                try (OutputStream outputStream = new 
BufferedOutputStream(out)) {
-                    outputStream.write("{\"stringField\": \"String Value\", 
\"nullField\": null}".getBytes(StandardCharsets.UTF_8));
-                }
+        ff = session.write(ff, out -> {
+            try (OutputStream outputStream = new BufferedOutputStream(out)) {
+                outputStream.write("{\"stringField\": \"String Value\", 
\"nullField\": null}".getBytes(StandardCharsets.UTF_8));
             }
         });
 
@@ -338,7 +362,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testNullInput_nullStringRepresentation() throws Exception {
+    void testNullInput_nullStringRepresentation() {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.RETURN_TYPE, 
EvaluateJsonPath.RETURN_TYPE_JSON);
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
@@ -350,12 +374,9 @@ public class TestEvaluateJsonPath {
         ProcessSession session = 
testRunner.getProcessSessionFactory().createSession();
         FlowFile ff = session.create();
 
-        ff = session.write(ff, new OutputStreamCallback() {
-            @Override
-            public void process(OutputStream out) throws IOException {
-                try (OutputStream outputStream = new 
BufferedOutputStream(out)) {
-                    outputStream.write("{\"stringField\": \"String Value\", 
\"nullField\": null}".getBytes(StandardCharsets.UTF_8));
-                }
+        ff = session.write(ff, out -> {
+            try (OutputStream outputStream = new BufferedOutputStream(out)) {
+                outputStream.write("{\"stringField\": \"String Value\", 
\"nullField\": null}".getBytes(StandardCharsets.UTF_8));
             }
         });
 
@@ -377,7 +398,7 @@ public class TestEvaluateJsonPath {
     }
 
     @Test
-    public void testHandleAsciiControlCharacters() throws Exception {
+    void testHandleAsciiControlCharacters() throws Exception {
         final TestRunner testRunner = TestRunners.newTestRunner(new 
EvaluateJsonPath());
         testRunner.setProperty(EvaluateJsonPath.DESTINATION, 
EvaluateJsonPath.DESTINATION_ATTRIBUTE);
         testRunner.setProperty(EvaluateJsonPath.RETURN_TYPE, 
EvaluateJsonPath.RETURN_TYPE_JSON);

Reply via email to