diff --git a/core/includes/install.core.inc b/core/includes/install.core.inc
index 8f8ba759f4..9e66bae456 100644
--- a/core/includes/install.core.inc
+++ b/core/includes/install.core.inc
@@ -1104,14 +1104,6 @@ function install_base_system(&$install_state) {
   // system.module in order to work.
   \Drupal::service('file.htaccess_writer')->ensure();
 
-  // Prime the module list static cache with the user module's exact location.
-  // @todo Remove as part of https://www.drupal.org/node/2186491
-  \Drupal::service('extension.list.module')->setPathname('user', 'core/modules/user/user.info.yml');
-
-  // Install the User module so that installing from configuration works and to
-  // ensure the anonymous user is created with a langcode of 'en'.
-  \Drupal::service('module_installer')->install(['user'], FALSE);
-
   $install_state['base_system_verified'] = TRUE;
 }
 
@@ -1580,9 +1572,8 @@ function install_profile_modules(&$install_state) {
       $modules = array_merge($modules, array_keys($files[$module]->requires));
     }
   }
-  // The System and User modules have already been installed by
-  // install_base_system().
-  $modules = array_diff(array_unique($modules), ['system', 'user']);
+  // The System module has already been installed by install_base_system().
+  $modules = array_diff(array_unique($modules), ['system']);
   foreach ($modules as $module) {
     if (!empty($files[$module]->info['required'])) {
       $required[$module] = $files[$module]->sort;
diff --git a/core/lib/Drupal/Core/Config/ConfigImporter.php b/core/lib/Drupal/Core/Config/ConfigImporter.php
index 68b1f7cf33..dc31ee5f9f 100644
--- a/core/lib/Drupal/Core/Config/ConfigImporter.php
+++ b/core/lib/Drupal/Core/Config/ConfigImporter.php
@@ -415,11 +415,30 @@ protected function createExtensionChangelist() {
 
     // Determine which modules to install.
     $install = array_keys(array_diff_key($new_extensions['module'], $current_extensions['module']));
+    // Always install required modules first. Respect the dependencies between
+    // the modules.
+    $install_required = [];
+    $install_non_required = [];
+    foreach ($install as $module) {
+      if (!isset($module_data[$module])) {
+        // The module doesn't exist. This is handled in
+        // \Drupal\Core\EventSubscriber\ConfigImportSubscriber::validateModules().
+        continue;
+      }
+      if (!empty($module_data[$module]->info['required'])) {
+        $install_required[$module] = $module_data[$module]->sort;
+      }
+      else {
+        $install_non_required[$module] = $module_data[$module]->sort;
+      }
+    }
     // Ensure that installed modules are sorted in exactly the reverse order
     // (with dependencies installed first, and modules of the same weight sorted
     // in alphabetical order).
-    $module_list = array_reverse($module_list);
-    $this->extensionChangelist['module']['install'] = array_intersect(array_keys($module_list), $install);
+    arsort($install_required);
+    arsort($install_non_required);
+
+    $this->extensionChangelist['module']['install'] = array_keys($install_required + $install_non_required);
 
     // If we're installing the install profile ensure it comes last. This will
     // occur when installing a site from configuration.
