str.partition and str.rpartition return tuples instead of lists

--
PiperOrigin-RevId: 148281228
MOS_MIGRATED_REVID=148281228
diff --git a/src/main/java/com/google/devtools/build/lib/syntax/MethodLibrary.java b/src/main/java/com/google/devtools/build/lib/syntax/MethodLibrary.java
index 3a01f76..3dd3fcd 100644
--- a/src/main/java/com/google/devtools/build/lib/syntax/MethodLibrary.java
+++ b/src/main/java/com/google/devtools/build/lib/syntax/MethodLibrary.java
@@ -398,10 +398,10 @@
   }
 
   @SkylarkSignature(name = "partition", objectType = StringModule.class,
-      returnType = MutableList.class,
+      returnType = Tuple.class,
       doc = "Splits the input string at the first occurrence of the separator "
           + "<code>sep</code> and returns the resulting partition as a three-element "
-          + "list of the form [substring_before, separator, substring_after].",
+          + "tuple of the form (substring_before, separator, substring_after).",
       parameters = {
         @Param(name = "self", type = String.class, doc = "This string."),
         @Param(name = "sep", type = String.class,
@@ -410,17 +410,17 @@
       useLocation = true)
   private static final BuiltinFunction partition = new BuiltinFunction("partition") {
     @SuppressWarnings("unused")
-    public MutableList<String> invoke(String self, String sep, Location loc, Environment env)
+    public Tuple<String> invoke(String self, String sep, Location loc, Environment env)
         throws EvalException {
-      return partitionWrapper(self, sep, true, env, loc);
+      return partitionWrapper(self, sep, true, loc);
     }
   };
 
   @SkylarkSignature(name = "rpartition", objectType = StringModule.class,
-      returnType = MutableList.class,
+      returnType = Tuple.class,
       doc = "Splits the input string at the last occurrence of the separator "
           + "<code>sep</code> and returns the resulting partition as a three-element "
-          + "list of the form [substring_before, separator, substring_after].",
+          + "tuple of the form (substring_before, separator, substring_after).",
       parameters = {
         @Param(name = "self", type = String.class, doc = "This string."),
         @Param(name = "sep", type = String.class,
@@ -429,9 +429,9 @@
       useLocation = true)
   private static final BuiltinFunction rpartition = new BuiltinFunction("rpartition") {
     @SuppressWarnings("unused")
-    public MutableList<String> invoke(String self, String sep, Location loc, Environment env)
+    public Tuple<String> invoke(String self, String sep, Location loc, Environment env)
         throws EvalException {
-      return partitionWrapper(self, sep, false, env, loc);
+      return partitionWrapper(self, sep, false, loc);
     }
   };
 
@@ -443,15 +443,13 @@
    * @param separator The string to split on
    * @param forward A flag that controls whether the input string is split around
    *    the first ({@code true}) or last ({@code false}) occurrence of the separator.
-   * @param env The current environment
    * @param loc The location that is used for potential exceptions
    * @return A list with three elements
    */
-  private static MutableList<String> partitionWrapper(
-      String self, String separator, boolean forward,
-      Environment env, Location loc) throws EvalException {
+  private static Tuple<String> partitionWrapper(
+      String self, String separator, boolean forward, Location loc) throws EvalException {
     try {
-      return new MutableList(stringPartition(self, separator, forward), env);
+      return Tuple.copyOf(stringPartition(self, separator, forward));
     } catch (IllegalArgumentException ex) {
       throw new EvalException(loc, ex);
     }
diff --git a/src/test/java/com/google/devtools/build/lib/syntax/MethodLibraryTest.java b/src/test/java/com/google/devtools/build/lib/syntax/MethodLibraryTest.java
index 55867c6..fb9c5cc 100644
--- a/src/test/java/com/google/devtools/build/lib/syntax/MethodLibraryTest.java
+++ b/src/test/java/com/google/devtools/build/lib/syntax/MethodLibraryTest.java
@@ -628,24 +628,24 @@
   @Test
   public void testPyStringPartitionEasy() throws Exception {
     new BothModesTest()
-        .testEval("'lawl'.partition('a')", "['l', 'a', 'wl']")
-        .testEval("'lawl'.rpartition('a')", "['l', 'a', 'wl']");
+        .testEval("'lawl'.partition('a')", "('l', 'a', 'wl')")
+        .testEval("'lawl'.rpartition('a')", "('l', 'a', 'wl')");
   }
 
   @Test
   public void testPyStringPartitionMultipleSep() throws Exception {
     new BothModesTest()
-        .testEval("'google'.partition('o')", "['g', 'o', 'ogle']")
-        .testEval("'google'.rpartition('o')", "['go', 'o', 'gle']")
-        .testEval("'xxx'.partition('x')", "['', 'x', 'xx']")
-        .testEval("'xxx'.rpartition('x')", "['xx', 'x', '']");
+        .testEval("'google'.partition('o')", "('g', 'o', 'ogle')")
+        .testEval("'google'.rpartition('o')", "('go', 'o', 'gle')")
+        .testEval("'xxx'.partition('x')", "('', 'x', 'xx')")
+        .testEval("'xxx'.rpartition('x')", "('xx', 'x', '')");
   }
 
   @Test
   public void testPyStringPartitionEmptyInput() throws Exception {
     new BothModesTest()
-        .testEval("''.partition('a')", "['', '', '']")
-        .testEval("''.rpartition('a')", "['', '', '']");
+        .testEval("''.partition('a')", "('', '', '')")
+        .testEval("''.rpartition('a')", "('', '', '')");
   }
 
   @Test
@@ -658,47 +658,47 @@
   @Test
   public void testPyStringPartitionDefaultSep() throws Exception {
     new BothModesTest()
-        .testEval("'hi this is a test'.partition()", "['hi', ' ', 'this is a test']")
-        .testEval("'hi this is a test'.rpartition()", "['hi this is a', ' ', 'test']")
-        .testEval("'google'.partition()", "['google', '', '']")
-        .testEval("'google'.rpartition()", "['', '', 'google']");
+        .testEval("'hi this is a test'.partition()", "('hi', ' ', 'this is a test')")
+        .testEval("'hi this is a test'.rpartition()", "('hi this is a', ' ', 'test')")
+        .testEval("'google'.partition()", "('google', '', '')")
+        .testEval("'google'.rpartition()", "('', '', 'google')");
   }
 
   @Test
   public void testPyStringPartitionNoMatch() throws Exception {
     new BothModesTest()
-        .testEval("'google'.partition('x')", "['google', '', '']")
-        .testEval("'google'.rpartition('x')", "['', '', 'google']");
+        .testEval("'google'.partition('x')", "('google', '', '')")
+        .testEval("'google'.rpartition('x')", "('', '', 'google')");
   }
 
   @Test
   public void testPyStringPartitionWordBoundaries() throws Exception {
     new BothModesTest()
-        .testEval("'goog'.partition('g')", "['', 'g', 'oog']")
-        .testEval("'goog'.rpartition('g')", "['goo', 'g', '']")
-        .testEval("'plex'.partition('p')", "['', 'p', 'lex']")
-        .testEval("'plex'.rpartition('p')", "['', 'p', 'lex']")
-        .testEval("'plex'.partition('x')", "['ple', 'x', '']")
-        .testEval("'plex'.rpartition('x')", "['ple', 'x', '']");
+        .testEval("'goog'.partition('g')", "('', 'g', 'oog')")
+        .testEval("'goog'.rpartition('g')", "('goo', 'g', '')")
+        .testEval("'plex'.partition('p')", "('', 'p', 'lex')")
+        .testEval("'plex'.rpartition('p')", "('', 'p', 'lex')")
+        .testEval("'plex'.partition('x')", "('ple', 'x', '')")
+        .testEval("'plex'.rpartition('x')", "('ple', 'x', '')");
   }
 
   @Test
   public void testPyStringPartitionLongSep() throws Exception {
     new BothModesTest()
-        .testEval("'google'.partition('oog')", "['g', 'oog', 'le']")
-        .testEval("'google'.rpartition('oog')", "['g', 'oog', 'le']")
+        .testEval("'google'.partition('oog')", "('g', 'oog', 'le')")
+        .testEval("'google'.rpartition('oog')", "('g', 'oog', 'le')")
         .testEval(
-            "'lolgooglolgooglolgooglol'.partition('goog')", "['lol', 'goog', 'lolgooglolgooglol']")
+            "'lolgooglolgooglolgooglol'.partition('goog')", "('lol', 'goog', 'lolgooglolgooglol')")
         .testEval(
             "'lolgooglolgooglolgooglol'.rpartition('goog')",
-            "['lolgooglolgooglol', 'goog', 'lol']");
+            "('lolgooglolgooglol', 'goog', 'lol')");
   }
 
   @Test
   public void testPyStringPartitionCompleteString() throws Exception {
     new BothModesTest()
-        .testEval("'google'.partition('google')", "['', 'google', '']")
-        .testEval("'google'.rpartition('google')", "['', 'google', '']");
+        .testEval("'google'.partition('google')", "('', 'google', '')")
+        .testEval("'google'.rpartition('google')", "('', 'google', '')");
   }
 
   @Test