/** * Tests imported configuration entities with and without language information. */ function testLanguage() { $this->installModules(['config_test_language']); // Test imported configuration with implicit language code. $storage = new InstallStorage(); $data = $storage->read('config_test.dynamic.dotted.english'); $this->assertTrue(!isset($data['langcode'])); $this->assertEqual($this->config('config_test.dynamic.dotted.english')->get('langcode'), 'en'); // Test imported configuration with explicit language code. $data = $storage->read('config_test.dynamic.dotted.french'); $this->assertEqual($data['langcode'], 'fr'); $this->assertEqual($this->config('config_test.dynamic.dotted.french')->get('langcode'), 'fr'); }
/** * Tests importing configuration. */ function testImport() { $name = 'system.site'; $dynamic_name = 'config_test.dynamic.new'; /** @var \Drupal\Core\Config\StorageInterface $staging */ $staging = $this->container->get('config.storage.staging'); $this->drupalGet('admin/config/development/configuration'); $this->assertText('There are no configuration changes to import.'); $this->assertNoFieldById('edit-submit', t('Import all')); // Create updated configuration object. $new_site_name = 'Config import test ' . $this->randomString(); $this->prepareSiteNameUpdate($new_site_name); $this->assertIdentical($staging->exists($name), TRUE, $name . ' found.'); // Create new config entity. $original_dynamic_data = array('uuid' => '30df59bd-7b03-4cf7-bb35-d42fc49f0651', 'langcode' => \Drupal::languageManager()->getDefaultLanguage()->getId(), 'status' => TRUE, 'dependencies' => array(), 'id' => 'new', 'label' => 'New', 'weight' => 0, 'style' => '', 'size' => '', 'size_value' => '', 'protected_property' => ''); $staging->write($dynamic_name, $original_dynamic_data); $this->assertIdentical($staging->exists($dynamic_name), TRUE, $dynamic_name . ' found.'); // Enable the Action and Ban modules during import. The Ban // module is used because it creates a table during the install. The Action // module is used because it creates a single simple configuration file // during the install. $core_extension = $this->config('core.extension')->get(); $core_extension['module']['action'] = 0; $core_extension['module']['ban'] = 0; $core_extension['module'] = module_config_sort($core_extension['module']); // Bartik is a subtheme of classy so classy must be enabled. $core_extension['theme']['classy'] = 0; $core_extension['theme']['bartik'] = 0; $staging->write('core.extension', $core_extension); // Use the install storage so that we can read configuration from modules // and themes that are not installed. $install_storage = new InstallStorage(); // Set the Bartik theme as default. $system_theme = $this->config('system.theme')->get(); $system_theme['default'] = 'bartik'; $staging->write('system.theme', $system_theme); // Read the action config from module default config folder. $action_settings = $install_storage->read('action.settings'); $action_settings['recursion_limit'] = 50; $staging->write('action.settings', $action_settings); // Uninstall the Options and Text modules to ensure that dependencies are // handled correctly. Options depends on Text so Text should be installed // first. Since they were enabled during the test setup the core.extension // file in staging will already contain them. \Drupal::service('module_installer')->uninstall(array('text', 'options')); // Set the state system to record installations and uninstallations. \Drupal::state()->set('ConfigImportUITest.core.extension.modules_installed', array()); \Drupal::state()->set('ConfigImportUITest.core.extension.modules_uninstalled', array()); // Verify that both appear as ready to import. $this->drupalGet('admin/config/development/configuration'); $this->assertRaw('<td>' . $name); $this->assertRaw('<td>' . $dynamic_name); $this->assertRaw('<td>core.extension'); $this->assertRaw('<td>system.theme'); $this->assertRaw('<td>action.settings'); $this->assertFieldById('edit-submit', t('Import all')); // Import and verify that both do not appear anymore. $this->drupalPostForm(NULL, array(), t('Import all')); $this->assertNoRaw('<td>' . $name); $this->assertNoRaw('<td>' . $dynamic_name); $this->assertNoRaw('<td>core.extension'); $this->assertNoRaw('<td>system.theme'); $this->assertNoRaw('<td>action.settings'); $this->assertNoFieldById('edit-submit', t('Import all')); // Verify that there are no further changes to import. $this->assertText(t('There are no configuration changes to import.')); // Verify site name has changed. $this->assertIdentical($new_site_name, $this->config('system.site')->get('name')); // Verify that new config entity exists. $this->assertIdentical($original_dynamic_data, $this->config($dynamic_name)->get()); // Verify the cache got cleared. $this->assertTrue(isset($GLOBALS['hook_cache_flush'])); $this->rebuildContainer(); $this->assertTrue(\Drupal::moduleHandler()->moduleExists('ban'), 'Ban module installed during import.'); $this->assertTrue(\Drupal::database()->schema()->tableExists('ban_ip'), 'The database table ban_ip exists.'); $this->assertTrue(\Drupal::moduleHandler()->moduleExists('action'), 'Action module installed during import.'); $this->assertTrue(\Drupal::moduleHandler()->moduleExists('options'), 'Options module installed during import.'); $this->assertTrue(\Drupal::moduleHandler()->moduleExists('text'), 'Text module installed during import.'); $theme_info = \Drupal::service('theme_handler')->listInfo(); $this->assertTrue($theme_info['bartik']->status, 'Bartik theme installed during import.'); // Ensure installations and uninstallation occur as expected. $installed = \Drupal::state()->get('ConfigImportUITest.core.extension.modules_installed', array()); $uninstalled = \Drupal::state()->get('ConfigImportUITest.core.extension.modules_uninstalled', array()); $expected = array('action', 'ban', 'text', 'options'); $this->assertIdentical($expected, $installed, 'Action, Ban, Text and Options modules installed in the correct order.'); $this->assertTrue(empty($uninstalled), 'No modules uninstalled during import'); // Verify that the action.settings configuration object was only written // once during the import process and only with the value set in the staged // configuration. This verifies that the module's default configuration is // used during configuration import and, additionally, that after installing // a module, that configuration is not synced twice. $recursion_limit_values = \Drupal::state()->get('ConfigImportUITest.action.settings.recursion_limit', array()); $this->assertIdentical($recursion_limit_values, array(50)); $core_extension = $this->config('core.extension')->get(); unset($core_extension['module']['action']); unset($core_extension['module']['ban']); unset($core_extension['module']['options']); unset($core_extension['module']['text']); unset($core_extension['theme']['bartik']); $staging->write('core.extension', $core_extension); $staging->delete('action.settings'); $staging->delete('text.settings'); $system_theme = $this->config('system.theme')->get(); $system_theme['default'] = 'stark'; $system_theme['admin'] = 'stark'; $staging->write('system.theme', $system_theme); // Set the state system to record installations and uninstallations. \Drupal::state()->set('ConfigImportUITest.core.extension.modules_installed', array()); \Drupal::state()->set('ConfigImportUITest.core.extension.modules_uninstalled', array()); // Verify that both appear as ready to import. $this->drupalGet('admin/config/development/configuration'); $this->assertRaw('<td>core.extension'); $this->assertRaw('<td>system.theme'); $this->assertRaw('<td>action.settings'); // Import and verify that both do not appear anymore. $this->drupalPostForm(NULL, array(), t('Import all')); $this->assertNoRaw('<td>core.extension'); $this->assertNoRaw('<td>system.theme'); $this->assertNoRaw('<td>action.settings'); $this->rebuildContainer(); $this->assertFalse(\Drupal::moduleHandler()->moduleExists('ban'), 'Ban module uninstalled during import.'); $this->assertFalse(\Drupal::database()->schema()->tableExists('ban_ip'), 'The database table ban_ip does not exist.'); $this->assertFalse(\Drupal::moduleHandler()->moduleExists('action'), 'Action module uninstalled during import.'); $this->assertFalse(\Drupal::moduleHandler()->moduleExists('options'), 'Options module uninstalled during import.'); $this->assertFalse(\Drupal::moduleHandler()->moduleExists('text'), 'Text module uninstalled during import.'); // Ensure installations and uninstallation occur as expected. $installed = \Drupal::state()->get('ConfigImportUITest.core.extension.modules_installed', array()); $uninstalled = \Drupal::state()->get('ConfigImportUITest.core.extension.modules_uninstalled', array()); $expected = array('options', 'text', 'ban', 'action'); $this->assertIdentical($expected, $uninstalled, 'Options, Text, Ban and Action modules uninstalled in the correct order.'); $this->assertTrue(empty($installed), 'No modules installed during import'); $theme_info = \Drupal::service('theme_handler')->listInfo(); $this->assertFalse(isset($theme_info['bartik']), 'Bartik theme uninstalled during import.'); // Verify that the action.settings configuration object was only deleted // once during the import process. $delete_called = \Drupal::state()->get('ConfigImportUITest.action.settings.delete', 0); $this->assertIdentical($delete_called, 1, "The action.settings configuration was deleted once during configuration import."); }