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

colegreer pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/tinkerpop.git


The following commit(s) were added to refs/heads/master by this push:
     new b37e35cf47 TINKERPOP-3083 Change SplitGlobalStep and SplitLocalStep to 
use a new StringUtil.split utility method which will split the given string 
into a list of individual string characters if the given separator is an empty 
string. (#2741)
b37e35cf47 is described below

commit b37e35cf478903957e653fb1a6e4b52170ee4c61
Author: andreachild <[email protected]>
AuthorDate: Tue Aug 27 17:01:52 2024 -0700

    TINKERPOP-3083 Change SplitGlobalStep and SplitLocalStep to use a new 
StringUtil.split utility method which will split the given string into a list 
of individual string characters if the given separator is an empty string. 
(#2741)
---
 CHANGELOG.asciidoc                                 |  1 +
 docs/src/dev/provider/gremlin-semantics.asciidoc   |  2 +-
 docs/src/reference/the-traversal.asciidoc          | 10 ++--
 docs/src/upgrade/release-4.x.x.asciidoc            | 16 +++++-
 .../traversal/step/map/SplitGlobalStep.java        |  7 ++-
 .../process/traversal/step/map/SplitLocalStep.java | 11 +---
 .../apache/tinkerpop/gremlin/util/StringUtil.java  | 53 ++++++++++++++++++
 .../traversal/step/map/SplitGlobalStepTest.java    |  2 +-
 .../traversal/step/map/SplitLocalStepTest.java     |  1 +
 .../tinkerpop/gremlin/util/StringUtilTest.java     | 62 ++++++++++++++++++++++
 .../Gremlin.Net.IntegrationTest/Gherkin/Gremlin.cs |  2 +
 gremlin-go/driver/cucumber/gremlin.go              |  2 +
 .../gremlin-javascript/test/cucumber/gremlin.js    |  2 +
 gremlin-python/src/main/python/radish/gremlin.py   |  2 +
 .../gremlin/test/features/map/Split.feature        | 29 ++++++++++
 15 files changed, 182 insertions(+), 20 deletions(-)

diff --git a/CHANGELOG.asciidoc b/CHANGELOG.asciidoc
index c0dafdfb96..8d620a857d 100644
--- a/CHANGELOG.asciidoc
+++ b/CHANGELOG.asciidoc
@@ -46,6 +46,7 @@ 
image::https://raw.githubusercontent.com/apache/tinkerpop/master/docs/static/ima
 * Made `new` keyword optional in the Gremlin grammar.
 * Added TypeScript & ECMAScript module support.
 * Improved graph structures type definitions in TypeScript.
+* Modified the `split()` step to split a string into a list of its characters 
if the given separator is an empty string.
 
 == TinkerPop 3.7.0 (Gremfir Master of the Pan Flute)
 
diff --git a/docs/src/dev/provider/gremlin-semantics.asciidoc 
b/docs/src/dev/provider/gremlin-semantics.asciidoc
index 06c6c35b3e..495235b4db 100644
--- a/docs/src/dev/provider/gremlin-semantics.asciidoc
+++ b/docs/src/dev/provider/gremlin-semantics.asciidoc
@@ -1517,7 +1517,7 @@ 
link:https://tinkerpop.apache.org/docs/x.y.z/reference/#rTrim-step[reference]
 *Arguments:*
 
 * `separator` - The string character(s) used as delimiter to split the input 
string. Nullable, a null separator will split on
-whitespaces.
+whitespaces. An empty string separator will split on each character.
 * `scope` - Determines the type of traverser it operates on. Both scopes will 
operate on the level of individual traversers.
 The `global` scope will operate on individual string traverser. The `local` 
scope will operate on list traverser with string elements inside.
 
diff --git a/docs/src/reference/the-traversal.asciidoc 
b/docs/src/reference/the-traversal.asciidoc
index 0cdfcc51d0..897b7d39f5 100644
--- a/docs/src/reference/the-traversal.asciidoc
+++ b/docs/src/reference/the-traversal.asciidoc
@@ -4455,8 +4455,8 @@ 
link:++https://tinkerpop.apache.org/javadocs/x.y.z/core/org/apache/tinkerpop/gre
 [[split-step]]
 === Split Step
 The `split()`-step (*map*) returns a list of strings created by splitting the 
incoming string traverser around the
-matches of the given separator. A null separator will split the string by 
whitespaces. Null values from the incoming
-traversers are not processed and remain as null when returned. If the incoming 
traverser is a non-String value then an
+matches of the given separator. A null separator will split the string by 
whitespaces. An empty string separator will split on each character.
+Null values from the incoming traversers are not processed and remain as null 
when returned. If the incoming traverser is a non-String value then an
 IllegalArgumentException will be thrown.
 
 [gremlin-groovy,modern]
@@ -4464,12 +4464,14 @@ IllegalArgumentException will be thrown.
 g.inject("that", "this", "test", null).split("h") <1>
 g.V().hasLabel("person").values("name").split("a") <2>
 g.inject("helloworld", "hello world", "hello   world").split(null) <3>
-g.V().hasLabel("person").values("name").fold().split(local, "a") <4>
+g.inject("hello", "world", null).split("") <4>
+g.V().hasLabel("person").values("name").fold().split(local, "a") <5>
 ----
 <1> Split the strings by "h".
 <2> Split person names by "a".
 <3> Splitting by null will split by whitespaces.
-<4> Use `Scope.local` to operate on individual string elements inside incoming 
list, which will return a list of results.
+<4> Splitting by "" will split by each character.
+<5> Use `Scope.local` to operate on individual string elements inside incoming 
list, which will return a list of results.
 
 *Additional References*
 
link:++https://tinkerpop.apache.org/javadocs/x.y.z/core/org/apache/tinkerpop/gremlin/process/traversal/dsl/graph/GraphTraversal.html#split(java.lang.String)++[`split(String)`]
diff --git a/docs/src/upgrade/release-4.x.x.asciidoc 
b/docs/src/upgrade/release-4.x.x.asciidoc
index 1772321f15..7d369ba2a9 100644
--- a/docs/src/upgrade/release-4.x.x.asciidoc
+++ b/docs/src/upgrade/release-4.x.x.asciidoc
@@ -77,7 +77,7 @@ these were deserialized into arrays.
 
 ==== Gremlin Grammar Changes
 
-A number of changes have been introduce to the Gremlin grammar to help make it 
be more consistent and easier to use.
+A number of changes have been introduced to the Gremlin grammar to help make 
it be more consistent and easier to use.
 
 *`new` keyword is now optional*
 
@@ -113,6 +113,20 @@ The `none()` step, which was primarily used by `iterate()` 
to discard traversal
 renamed to `discard()`. In its place is a new list filtering step `none()`, 
which takes a predicate as an argument and
 passes lists with no elements matching the predicate.
 
+==== Splitting a string into characters using split()
+The `split()` step will now split a string into a list of its characters if 
the given separator is an empty string.
+[source,groovy]
+----
+// previous implementation
+g.inject("Hello").split("")
+==>[Hello]
+
+// new implementation
+g.inject("Hello").split("")
+==>[H,e,l,l,o]
+----
+See: link:https://issues.apache.org/jira/browse/TINKERPOP-3083[TINKERPOP-3083]
+
 ==== Improved handling of integer overflows
 
 Integer overflows caused by addition and multiplication operations will throw 
an exception instead of being silently
diff --git 
a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStep.java
 
b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStep.java
index 14e886edfe..fba728a50b 100644
--- 
a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStep.java
+++ 
b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStep.java
@@ -18,15 +18,13 @@
  */
 package org.apache.tinkerpop.gremlin.process.traversal.step.map;
 
-import org.apache.commons.lang3.StringUtils;
 import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
 import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
 import org.apache.tinkerpop.gremlin.process.traversal.step.TraversalParent;
 import 
org.apache.tinkerpop.gremlin.process.traversal.traverser.TraverserRequirement;
+import org.apache.tinkerpop.gremlin.util.StringUtil;
 
-import java.util.Arrays;
 import java.util.Collections;
-import java.util.List;
 import java.util.Set;
 
 /**
@@ -57,7 +55,7 @@ public final class SplitGlobalStep<S, E> extends 
ScalarMapStep<S, E> implements
         }
 
         // we will pass null values to next step
-        return null == item? null : (E) 
Arrays.asList(StringUtils.splitByWholeSeparator((String) item, this.separator));
+        return null == item? null : (E) StringUtil.split((String)item, 
this.separator);
     }
 
     public String getSeparator() {
@@ -75,4 +73,5 @@ public final class SplitGlobalStep<S, E> extends 
ScalarMapStep<S, E> implements
         result = 31 * result + (null != this.separator ? 
this.separator.hashCode() : 0);
         return result;
     }
+
 }
diff --git 
a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStep.java
 
b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStep.java
index 5d638c74ca..9576e22b65 100644
--- 
a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStep.java
+++ 
b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStep.java
@@ -18,17 +18,10 @@
  */
 package org.apache.tinkerpop.gremlin.process.traversal.step.map;
 
-import org.apache.commons.lang3.StringUtils;
 import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
-import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
 import org.apache.tinkerpop.gremlin.process.traversal.step.TraversalParent;
 import 
org.apache.tinkerpop.gremlin.process.traversal.step.util.StringLocalStep;
-import 
org.apache.tinkerpop.gremlin.process.traversal.traverser.TraverserRequirement;
-
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.List;
-import java.util.Set;
+import org.apache.tinkerpop.gremlin.util.StringUtil;
 
 /**
  * Reference implementation for substring step, a mid-traversal step which 
returns a list of strings created by
@@ -50,7 +43,7 @@ public final class SplitLocalStep<S, E> extends 
StringLocalStep<S, E> implements
 
     @Override
     protected E applyStringOperation(String item) {
-        return (E) Arrays.asList((StringUtils.splitByWholeSeparator(item, 
this.separator)));
+        return (E) StringUtil.split(item, this.separator);
     }
 
     @Override
diff --git 
a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/util/StringUtil.java 
b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/util/StringUtil.java
new file mode 100644
index 0000000000..d352a38df4
--- /dev/null
+++ 
b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/util/StringUtil.java
@@ -0,0 +1,53 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.tinkerpop.gremlin.util;
+
+import java.util.Arrays;
+import java.util.List;
+import org.apache.commons.lang3.StringUtils;
+
+/**
+ * Utility class for Strings.
+ *
+ * @author Andrea Child
+ */
+public final class StringUtil {
+
+    private StringUtil() {
+    }
+
+    /**
+     * Splits the provided string into a List of string by the given 
separator, which will not be included in the returned List.
+     *
+     * @param toSplit the string to split
+     * @param separator the separator string to split by - empty will split 
into a List of characters
+     * @return a List of parsed strings, not including the given separator
+     */
+    public static List<String> split(final String toSplit, final String 
separator) {
+        if (toSplit == null) {
+            throw new IllegalArgumentException("toSplit cannot be null");
+        }
+        if (StringUtils.EMPTY.equals(separator)) {
+            // split into a list of character strings
+            // ie. "ab cd" -> ["a","b"," ","c","d"]
+            return Arrays.asList(toSplit.split(StringUtils.EMPTY));
+        }
+        return Arrays.asList(StringUtils.splitByWholeSeparator(toSplit, 
separator));
+    }
+}
diff --git 
a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStepTest.java
 
b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStepTest.java
index 9a442fa5f0..ceb0598ffd 100644
--- 
a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStepTest.java
+++ 
b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitGlobalStepTest.java
@@ -48,7 +48,7 @@ public class SplitGlobalStepTest extends StepTest {
         assertArrayEquals(new String[]{"helloworld"}, 
__.__("helloworld").split(null).next().toArray());
         assertArrayEquals(new String[]{"hello", "world"}, __.__("hello 
world").split(null).next().toArray());
         assertArrayEquals(new String[]{"hello", "world"}, __.__("hello   
world").split(null).next().toArray());
-        assertArrayEquals(new String[]{"hello", "world"}, __.__("hello 
world").split("").next().toArray());
+        assertArrayEquals(new String[]{"h","e","l","l","o"," ", 
"w","o","r","l","d"}, __.__("hello world").split("").next().toArray());
         assertArrayEquals(new String[]{"hello", "world"}, __.__("hello 
world").split(" ").next().toArray());
         assertArrayEquals(new String[]{"hello world"}, __.__("hello 
world").split("  ").next().toArray());
 
diff --git 
a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStepTest.java
 
b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStepTest.java
index b9c792d7d4..cddf7dc4e0 100644
--- 
a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStepTest.java
+++ 
b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/SplitLocalStepTest.java
@@ -42,6 +42,7 @@ public class SplitLocalStepTest extends StepTest {
     public void testReturnTypes() {
         assertArrayEquals(new String[]{"h", "llo"}, 
__.__("hello").split(Scope.local, "e").next().toArray());
         assertArrayEquals(new String[]{"ab", "bc"}, 
__.__("abc|abc").split(Scope.local, "c|a").next().toArray());
+        assertArrayEquals(new String[]{"t","e","s","t"}, 
__.__("test").split(Scope.local, "").next().toArray());
 
         List<List<String>> resList = new ArrayList<>();
         resList.add(Arrays.asList("helloworld"));
diff --git 
a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/util/StringUtilTest.java
 
b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/util/StringUtilTest.java
new file mode 100644
index 0000000000..04e112f92d
--- /dev/null
+++ 
b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/util/StringUtilTest.java
@@ -0,0 +1,62 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.tinkerpop.gremlin.util;
+
+import java.util.Arrays;
+import org.apache.tinkerpop.gremlin.AssertHelper;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+
+/**
+ * @author Andrea Child
+ */
+public class StringUtilTest {
+
+    @Test
+    public void shouldBeUtilityClass() throws Exception {
+        AssertHelper.assertIsUtilityClass(StringUtil.class);
+    }
+
+    @Test
+    public void shouldSplitBySeparatorAndNotContainSeparator() {
+        assertEquals(Arrays.asList("h","llo"), StringUtil.split("hello", "e"));
+    }
+
+    @Test
+    public void shouldNotBeSplitIfSeparatorNotPresentInString() {
+        final String toSplit = "test";
+        assertEquals(Arrays.asList(toSplit), StringUtil.split(toSplit, "x"));
+    }
+
+    @Test
+    public void shouldSplitByCharacterIfSeparatorIsEmpty() {
+        assertEquals(Arrays.asList("t","e","s","t"," ","1","2","3"), 
StringUtil.split("test 123", ""));
+    }
+
+    @Test
+    public void shouldSplitByWhitespaceIfSeparatorIsNull() {
+        assertEquals(Arrays.asList("test","123"), StringUtil.split("test 123", 
null));
+    }
+
+    @Test(expected = IllegalArgumentException.class)
+    public void shouldThrowIfStringToSplitIsNull() {
+        StringUtil.split(null, "test");
+    }
+}
\ No newline at end of file
diff --git a/gremlin-dotnet/test/Gremlin.Net.IntegrationTest/Gherkin/Gremlin.cs 
b/gremlin-dotnet/test/Gremlin.Net.IntegrationTest/Gherkin/Gremlin.cs
index bd0a8e7469..12449a0d9d 100644
--- a/gremlin-dotnet/test/Gremlin.Net.IntegrationTest/Gherkin/Gremlin.cs
+++ b/gremlin-dotnet/test/Gremlin.Net.IntegrationTest/Gherkin/Gremlin.cs
@@ -1204,9 +1204,11 @@ namespace Gremlin.Net.IntegrationTest.Gherkin
                
{"g_V_hasXname_vadasX_shortestPath_distanceXweightX_maxDistanceX1_3X", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.V().Has("name", 
"vadas").ShortestPath().With("~tinkerpop.shortestPath.distance", 
"weight").With("~tinkerpop.shortestPath.maxDistance", 1.3)}}, 
                {"g_injectXthat_this_testX_spiltXhX", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.Inject<object>("that", "this", "test", null).Split("h")}}, 
                {"g_injectXhello_worldX_spiltXnullX", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.Inject<object>("hello world").Split(null)}}, 
+               {"g_injectXthat_this_test_nullX_splitXemptyX", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.Inject<object>("that", "this", "test", null).Split("")}}, 
                {"g_injectXListXa_bXcX_splitXa_bX", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.Inject<object>(p["xx1"]).Split("a")}}, 
                {"g_V_hasLabelXpersonX_valueXnameX_splitXnullX", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.V().HasLabel("person").Values<object>("name").Split(null)}}, 
                
{"g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_aX_unfold", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) 
=>g.V().HasLabel("person").Values<object>("name").Order().Fold().Split<object>(Scope.Local,
 "a").Unfold<object>()}}, 
+               
{"g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_emptyX_unfold", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) 
=>g.V().HasLabel("person").Values<object>("name").Order().Fold().Split<object>(Scope.Local,
 "").Unfold<object>()}}, 
                {"g_injectXthat_this_testX_substringX1_8X", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.Inject<object>("test", "hello world", null).Substring(1, 8)}}, 
                {"g_injectXListXa_bXcX_substringX1_2X", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.Inject<object>(p["xx1"]).Substring(1, 2)}}, 
                {"g_V_hasLabelXpersonX_valueXnameX_substringX2X", new 
List<Func<GraphTraversalSource, IDictionary<string, object>, ITraversal>> 
{(g,p) =>g.V().HasLabel("software").Values<object>("name").Substring(2)}}, 
diff --git a/gremlin-go/driver/cucumber/gremlin.go 
b/gremlin-go/driver/cucumber/gremlin.go
index bcb230d8a3..1097cb2a5d 100644
--- a/gremlin-go/driver/cucumber/gremlin.go
+++ b/gremlin-go/driver/cucumber/gremlin.go
@@ -1175,9 +1175,11 @@ var translationMap = map[string][]func(g 
*gremlingo.GraphTraversalSource, p map[
     "g_V_hasXname_vadasX_shortestPath_distanceXweightX_maxDistanceX1_3X": 
{func(g *gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.V().Has("name", 
"vadas").ShortestPath().With("~tinkerpop.shortestPath.distance", 
"weight").With("~tinkerpop.shortestPath.maxDistance", 1.3)}}, 
     "g_injectXthat_this_testX_spiltXhX": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.Inject("that", "this", "test", 
nil).Split("h")}}, 
     "g_injectXhello_worldX_spiltXnullX": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.Inject("hello world").Split(nil)}}, 
+    "g_injectXthat_this_test_nullX_splitXemptyX": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.Inject("that", "this", "test", 
nil).Split("")}}, 
     "g_injectXListXa_bXcX_splitXa_bX": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.Inject(p["xx1"]).Split("a")}}, 
     "g_V_hasLabelXpersonX_valueXnameX_splitXnullX": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return 
g.V().HasLabel("person").Values("name").Split(nil)}}, 
     "g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_aX_unfold": 
{func(g *gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return 
g.V().HasLabel("person").Values("name").Order().Fold().Split(gremlingo.Scope.Local,
 "a").Unfold()}}, 
+    "g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_emptyX_unfold": 
{func(g *gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return 
g.V().HasLabel("person").Values("name").Order().Fold().Split(gremlingo.Scope.Local,
 "").Unfold()}}, 
     "g_injectXthat_this_testX_substringX1_8X": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.Inject("test", "hello world", 
nil).Substring(1, 8)}}, 
     "g_injectXListXa_bXcX_substringX1_2X": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return g.Inject(p["xx1"]).Substring(1, 2)}}, 
     "g_V_hasLabelXpersonX_valueXnameX_substringX2X": {func(g 
*gremlingo.GraphTraversalSource, p map[string]interface{}) 
*gremlingo.GraphTraversal {return 
g.V().HasLabel("software").Values("name").Substring(2)}}, 
diff --git 
a/gremlin-javascript/src/main/javascript/gremlin-javascript/test/cucumber/gremlin.js
 
b/gremlin-javascript/src/main/javascript/gremlin-javascript/test/cucumber/gremlin.js
index 8e0a3c8598..2303335aae 100644
--- 
a/gremlin-javascript/src/main/javascript/gremlin-javascript/test/cucumber/gremlin.js
+++ 
b/gremlin-javascript/src/main/javascript/gremlin-javascript/test/cucumber/gremlin.js
@@ -1196,9 +1196,11 @@ const gremlins = {
     g_V_hasXname_vadasX_shortestPath_distanceXweightX_maxDistanceX1_3X: 
[function({g}) { return g.V().has("name", 
"vadas").shortestPath().with_("~tinkerpop.shortestPath.distance", 
"weight").with_("~tinkerpop.shortestPath.maxDistance", 1.3) }], 
     g_injectXthat_this_testX_spiltXhX: [function({g}) { return 
g.inject("that", "this", "test", null).split("h") }], 
     g_injectXhello_worldX_spiltXnullX: [function({g}) { return g.inject("hello 
world").split(null) }], 
+    g_injectXthat_this_test_nullX_splitXemptyX: [function({g}) { return 
g.inject("that", "this", "test", null).split("") }], 
     g_injectXListXa_bXcX_splitXa_bX: [function({g, xx1}) { return 
g.inject(xx1).split("a") }], 
     g_V_hasLabelXpersonX_valueXnameX_splitXnullX: [function({g}) { return 
g.V().hasLabel("person").values("name").split(null) }], 
     g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_aX_unfold: 
[function({g}) { return 
g.V().hasLabel("person").values("name").order().fold().split(Scope.local, 
"a").unfold() }], 
+    g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_emptyX_unfold: 
[function({g}) { return 
g.V().hasLabel("person").values("name").order().fold().split(Scope.local, 
"").unfold() }], 
     g_injectXthat_this_testX_substringX1_8X: [function({g}) { return 
g.inject("test", "hello world", null).substring(1, 8) }], 
     g_injectXListXa_bXcX_substringX1_2X: [function({g, xx1}) { return 
g.inject(xx1).substring(1, 2) }], 
     g_V_hasLabelXpersonX_valueXnameX_substringX2X: [function({g}) { return 
g.V().hasLabel("software").values("name").substring(2) }], 
diff --git a/gremlin-python/src/main/python/radish/gremlin.py 
b/gremlin-python/src/main/python/radish/gremlin.py
index 95114c84d3..b3b4abadc1 100644
--- a/gremlin-python/src/main/python/radish/gremlin.py
+++ b/gremlin-python/src/main/python/radish/gremlin.py
@@ -1178,9 +1178,11 @@ world.gremlins = {
     'g_V_hasXname_vadasX_shortestPath_distanceXweightX_maxDistanceX1_3X': 
[(lambda g:g.V().has('name', 
'vadas').shortest_path().with_('~tinkerpop.shortestPath.distance', 
'weight').with_('~tinkerpop.shortestPath.maxDistance', 1.3))], 
     'g_injectXthat_this_testX_spiltXhX': [(lambda g:g.inject('that', 'this', 
'test', None).split('h'))], 
     'g_injectXhello_worldX_spiltXnullX': [(lambda g:g.inject('hello 
world').split(None))], 
+    'g_injectXthat_this_test_nullX_splitXemptyX': [(lambda g:g.inject('that', 
'this', 'test', None).split(''))], 
     'g_injectXListXa_bXcX_splitXa_bX': [(lambda g, 
xx1=None:g.inject(xx1).split('a'))], 
     'g_V_hasLabelXpersonX_valueXnameX_splitXnullX': [(lambda 
g:g.V().has_label('person').values('name').split(None))], 
     'g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_aX_unfold': 
[(lambda 
g:g.V().has_label('person').values('name').order().fold().split(Scope.local, 
'a').unfold())], 
+    'g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_emptyX_unfold': 
[(lambda 
g:g.V().has_label('person').values('name').order().fold().split(Scope.local, 
'').unfold())], 
     'g_injectXthat_this_testX_substringX1_8X': [(lambda g:g.inject('test', 
'hello world', None).substring(1, 8))], 
     'g_injectXListXa_bXcX_substringX1_2X': [(lambda g, 
xx1=None:g.inject(xx1).substring(1, 2))], 
     'g_V_hasLabelXpersonX_valueXnameX_substringX2X': [(lambda 
g:g.V().has_label('software').values('name').substring(2))], 
diff --git 
a/gremlin-test/src/main/resources/org/apache/tinkerpop/gremlin/test/features/map/Split.feature
 
b/gremlin-test/src/main/resources/org/apache/tinkerpop/gremlin/test/features/map/Split.feature
index 54e04f14ba..3fa024adcd 100644
--- 
a/gremlin-test/src/main/resources/org/apache/tinkerpop/gremlin/test/features/map/Split.feature
+++ 
b/gremlin-test/src/main/resources/org/apache/tinkerpop/gremlin/test/features/map/Split.feature
@@ -45,6 +45,21 @@ Feature: Step - split()
       | result |
       | l[hello,world] |
 
+  @GraphComputerVerificationInjectionNotSupported
+  Scenario: g_injectXthat_this_test_nullX_splitXemptyX
+    Given the empty graph
+    And the traversal of
+      """
+      g.inject("that", "this", "test", null).split("")
+      """
+    When iterated to list
+    Then the result should be unordered
+      | result |
+      | l[t,h,a,t] |
+      | l[t,h,i,s] |
+      | l[t,e,s,t] |
+      | null |
+
   @GraphComputerVerificationInjectionNotSupported
   Scenario: g_injectXListXa_bXcX_splitXa_bX
     Given the empty graph
@@ -83,3 +98,17 @@ Feature: Step - split()
       | l[m,rko] |
       | l[peter] |
       | l[v,d,s] |
+
+  Scenario: 
g_V_hasLabelXpersonX_valueXnameX_order_fold_splitXlocal_emptyX_unfold
+    Given the modern graph
+    And the traversal of
+      """
+      
g.V().hasLabel("person").values("name").order().fold().split(Scope.local, 
"").unfold()
+      """
+    When iterated to list
+    Then the result should be unordered
+      | result |
+      | l[j,o,s,h] |
+      | l[m,a,r,k,o] |
+      | l[p,e,t,e,r] |
+      | l[v,a,d,a,s] |
\ No newline at end of file

Reply via email to