diff --git a/app/code/Magento/Catalog/Test/Unit/Controller/Adminhtml/Product/Initialization/HelperTest.php b/app/code/Magento/Catalog/Test/Unit/Controller/Adminhtml/Product/Initialization/HelperTest.php
index edd654a7393126c61b877d35b36de9077316ec4d..a4218e92b3486db76afc61254553b914610d99c3 100644
--- a/app/code/Magento/Catalog/Test/Unit/Controller/Adminhtml/Product/Initialization/HelperTest.php
+++ b/app/code/Magento/Catalog/Test/Unit/Controller/Adminhtml/Product/Initialization/HelperTest.php
@@ -278,15 +278,19 @@ class HelperTest extends \PHPUnit_Framework_TestCase
             ->method('getOptionsReadOnly')
             ->willReturn(false);
 
+        $firstExpectedCustomOption = clone $this->customOptionMock;
+        $firstExpectedCustomOption->setData($optionsData['option2']);
+        $secondExpectedCustomOption = clone $this->customOptionMock;
+        $secondExpectedCustomOption->setData($optionsData['option3']);
         $this->customOptionFactoryMock->expects($this->any())
             ->method('create')
             ->willReturnMap([
                 [
                     ['data' => $optionsData['option2']],
-                    (clone $this->customOptionMock)->setData($optionsData['option2'])
+                    $firstExpectedCustomOption
                 ], [
                     ['data' => $optionsData['option3']],
-                    (clone $this->customOptionMock)->setData($optionsData['option3'])
+                    $secondExpectedCustomOption
                 ]
             ]);
 
diff --git a/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php b/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php
index 74a6cc7d2cd923e46b80f39c2645c5cef2ba421a..d714caa1724f07c3aab05de714048e8ec72a6a80 100644
--- a/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php
+++ b/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php
@@ -54,25 +54,70 @@ class ArrayType implements InterpreterInterface
      */
     private function sortItems($items)
     {
-        uasort(
-            $items,
-            function ($firstItem, $secondItem) {
-                $firstValue = 0;
-                $secondValue = 0;
-                if (isset($firstItem['sortOrder'])) {
-                    $firstValue = intval($firstItem['sortOrder']);
+        $sortOrderDefined = $this->isSortOrderDefined($items);
+        if ($sortOrderDefined) {
+            $indexedItems = [];
+            foreach ($items as $key => $item) {
+                $indexedItems[] = ['key' => $key, 'item' => $item];
+            }
+            uksort(
+                $indexedItems,
+                function ($firstItemKey, $secondItemKey) use ($indexedItems) {
+                    return $this->compareItems($firstItemKey, $secondItemKey, $indexedItems);
                 }
+            );
+            // Convert array of sorted items back to initial format
+            $items = [];
+            foreach ($indexedItems as $indexedItem) {
+                $items[$indexedItem['key']] = $indexedItem['item'];
+            }
+        }
+        return $items;
+    }
 
-                if (isset($secondItem['sortOrder'])) {
-                    $secondValue = intval($secondItem['sortOrder']);
-                }
+    /**
+     * Compare sortOrder of item
+     *
+     * @param mixed $firstItemKey
+     * @param mixed $secondItemKey
+     * @param array $indexedItems
+     * @return int
+     */
+    private function compareItems($firstItemKey, $secondItemKey, $indexedItems)
+    {
+        $firstItem = $indexedItems[$firstItemKey]['item'];
+        $secondItem = $indexedItems[$secondItemKey]['item'];
+        $firstValue = 0;
+        $secondValue = 0;
+        if (isset($firstItem['sortOrder'])) {
+            $firstValue = intval($firstItem['sortOrder']);
+        }
 
-                if ($firstValue == $secondValue) {
-                    return 0;
-                }
-                return $firstValue < $secondValue ? -1 : 1;
+        if (isset($secondItem['sortOrder'])) {
+            $secondValue = intval($secondItem['sortOrder']);
+        }
+
+        if ($firstValue == $secondValue) {
+            // These keys reflect initial relative position of items.
+            // Allows stable sort for items with equal 'sortOrder'
+            return $firstItemKey < $secondItemKey ? -1 : 1;
+        }
+        return $firstValue < $secondValue ? -1 : 1;
+    }
+
+    /**
+     * Determine if a sort order exists for any of the items.
+     *
+     * @param array $items
+     * @return bool
+     */
+    private function isSortOrderDefined($items)
+    {
+        foreach ($items as $itemData) {
+            if (isset($itemData['sortOrder'])) {
+                return true;
             }
-        );
-        return $items;
+        }
+        return false;
     }
 }
diff --git a/lib/internal/Magento/Framework/Data/Test/Unit/Argument/Interpreter/ArrayTypeTest.php b/lib/internal/Magento/Framework/Data/Test/Unit/Argument/Interpreter/ArrayTypeTest.php
index 7d3c21ba271cecf75a83d4bc9aa5923ce1920337..e1bc7528cbe1a00a0d5abebb2739cf9a83c7f43a 100644
--- a/lib/internal/Magento/Framework/Data/Test/Unit/Argument/Interpreter/ArrayTypeTest.php
+++ b/lib/internal/Magento/Framework/Data/Test/Unit/Argument/Interpreter/ArrayTypeTest.php
@@ -103,6 +103,40 @@ class ArrayTypeTest extends \PHPUnit_Framework_TestCase
                     'key1' => '-value 1-',
                 ],
             ],
+            'pre-sorted array items' => [
+                [
+                    'item' => [
+                        'key1' => ['value' => 'value 1'],
+                        'key4' => ['value' => 'value 4'],
+                        'key2' => ['value' => 'value 2', 'sortOrder' => 10],
+                        'key3' => ['value' => 'value 3'],
+                    ],
+                ],
+                [
+                    'key1' => '-value 1-',
+                    'key4' => '-value 4-',
+                    'key3' => '-value 3-',
+                    'key2' => '-value 2-',
+                ],
+            ],
+            'sort order edge case values' => [
+                [
+                    'item' => [
+                        'key1' => ['value' => 'value 1', 'sortOrder' => 101],
+                        'key4' => ['value' => 'value 4'],
+                        'key2' => ['value' => 'value 2', 'sortOrder' => -10],
+                        'key3' => ['value' => 'value 3'],
+                        'key5' => ['value' => 'value 5', 'sortOrder' => 20],
+                    ],
+                ],
+                [
+                    'key2' => '-value 2-',
+                    'key4' => '-value 4-',
+                    'key3' => '-value 3-',
+                    'key5' => '-value 5-',
+                    'key1' => '-value 1-',
+                ],
+            ],
         ];
     }
 }