88d9bb5d62abe02e5364cd75b446c5311754861c
[yaffs-website] / web / core / modules / system / tests / src / Functional / Entity / ConfigEntityImportTest.php
1 <?php
2
3 namespace Drupal\Tests\system\Functional\Entity;
4
5 use Drupal\Core\Entity\EntityWithPluginCollectionInterface;
6 use Drupal\filter\Entity\FilterFormat;
7 use Drupal\image\Entity\ImageStyle;
8 use Drupal\search\Entity\SearchPage;
9 use Drupal\Tests\BrowserTestBase;
10 use Drupal\system\Entity\Action;
11
12 /**
13  * Tests ConfigEntity importing.
14  *
15  * @group Entity
16  */
17 class ConfigEntityImportTest extends BrowserTestBase {
18
19   /**
20    * Modules to enable.
21    *
22    * @var array
23    */
24   public static $modules = ['action', 'block', 'filter', 'image', 'search', 'search_extra_type', 'config_test'];
25
26   /**
27    * {@inheritdoc}
28    */
29   protected function setUp() {
30     parent::setUp();
31
32     $this->copyConfig($this->container->get('config.storage'), $this->container->get('config.storage.sync'));
33   }
34
35   /**
36    * Runs test methods for each module within a single test run.
37    */
38   public function testConfigUpdateImport() {
39     $this->doActionUpdate();
40     $this->doBlockUpdate();
41     $this->doFilterFormatUpdate();
42     $this->doImageStyleUpdate();
43     $this->doSearchPageUpdate();
44     $this->doThirdPartySettingsUpdate();
45   }
46
47   /**
48    * Tests updating a action during import.
49    */
50   protected function doActionUpdate() {
51     // Create a test action with a known label.
52     $name = 'system.action.apple';
53     $entity = Action::create([
54       'id' => 'apple',
55       'plugin' => 'action_message_action',
56     ]);
57     $entity->save();
58
59     $this->checkSinglePluginConfigSync($entity, 'configuration', 'message', '');
60
61     // Read the existing data, and prepare an altered version in sync.
62     $custom_data = $original_data = $this->container->get('config.storage')->read($name);
63     $custom_data['configuration']['message'] = 'Granny Smith';
64     $this->assertConfigUpdateImport($name, $original_data, $custom_data);
65
66   }
67
68   /**
69    * Tests updating a block during import.
70    */
71   protected function doBlockUpdate() {
72     // Create a test block with a known label.
73     $name = 'block.block.apple';
74     $block = $this->drupalPlaceBlock('system_powered_by_block', [
75       'id' => 'apple',
76       'label' => 'Red Delicious',
77     ]);
78
79     $this->checkSinglePluginConfigSync($block, 'settings', 'label', 'Red Delicious');
80
81     // Read the existing data, and prepare an altered version in sync.
82     $custom_data = $original_data = $this->container->get('config.storage')->read($name);
83     $custom_data['settings']['label'] = 'Granny Smith';
84     $this->assertConfigUpdateImport($name, $original_data, $custom_data);
85   }
86
87   /**
88    * Tests updating a filter format during import.
89    */
90   protected function doFilterFormatUpdate() {
91     // Create a test filter format with a known label.
92     $name = 'filter.format.plain_text';
93
94     /** @var $entity \Drupal\filter\Entity\FilterFormat */
95     $entity = FilterFormat::load('plain_text');
96     $plugin_collection = $entity->getPluginCollections()['filters'];
97
98     $filters = $entity->get('filters');
99     $this->assertIdentical(72, $filters['filter_url']['settings']['filter_url_length']);
100
101     $filters['filter_url']['settings']['filter_url_length'] = 100;
102     $entity->set('filters', $filters);
103     $entity->save();
104     $this->assertIdentical($filters, $entity->get('filters'));
105     $this->assertIdentical($filters, $plugin_collection->getConfiguration());
106
107     $filters['filter_url']['settings']['filter_url_length'] = -100;
108     $entity->getPluginCollections()['filters']->setConfiguration($filters);
109     $entity->save();
110     $this->assertIdentical($filters, $entity->get('filters'));
111     $this->assertIdentical($filters, $plugin_collection->getConfiguration());
112
113     // Read the existing data, and prepare an altered version in sync.
114     $custom_data = $original_data = $this->container->get('config.storage')->read($name);
115     $custom_data['filters']['filter_url']['settings']['filter_url_length'] = 100;
116     $this->assertConfigUpdateImport($name, $original_data, $custom_data);
117   }
118
119   /**
120    * Tests updating an image style during import.
121    */
122   protected function doImageStyleUpdate() {
123     // Create a test image style with a known label.
124     $name = 'image.style.thumbnail';
125
126     /** @var $entity \Drupal\image\Entity\ImageStyle */
127     $entity = ImageStyle::load('thumbnail');
128     $plugin_collection = $entity->getPluginCollections()['effects'];
129
130     $effects = $entity->get('effects');
131     $effect_id = key($effects);
132     $this->assertIdentical(100, $effects[$effect_id]['data']['height']);
133
134     $effects[$effect_id]['data']['height'] = 50;
135     $entity->set('effects', $effects);
136     $entity->save();
137     // Ensure the entity and plugin have the correct configuration.
138     $this->assertIdentical($effects, $entity->get('effects'));
139     $this->assertIdentical($effects, $plugin_collection->getConfiguration());
140
141     $effects[$effect_id]['data']['height'] = -50;
142     $entity->getPluginCollections()['effects']->setConfiguration($effects);
143     $entity->save();
144     // Ensure the entity and plugin have the correct configuration.
145     $this->assertIdentical($effects, $entity->get('effects'));
146     $this->assertIdentical($effects, $plugin_collection->getConfiguration());
147
148     // Read the existing data, and prepare an altered version in sync.
149     $custom_data = $original_data = $this->container->get('config.storage')->read($name);
150     $effect_name = key($original_data['effects']);
151
152     $custom_data['effects'][$effect_name]['data']['upscale'] = FALSE;
153     $this->assertConfigUpdateImport($name, $original_data, $custom_data);
154   }
155
156   /**
157    * Tests updating a search page during import.
158    */
159   protected function doSearchPageUpdate() {
160     // Create a test search page with a known label.
161     $name = 'search.page.apple';
162     $entity = SearchPage::create([
163       'id' => 'apple',
164       'plugin' => 'search_extra_type_search',
165     ]);
166     $entity->save();
167
168     $this->checkSinglePluginConfigSync($entity, 'configuration', 'boost', 'bi');
169
170     // Read the existing data, and prepare an altered version in sync.
171     $custom_data = $original_data = $this->container->get('config.storage')->read($name);
172     $custom_data['configuration']['boost'] = 'asdf';
173     $this->assertConfigUpdateImport($name, $original_data, $custom_data);
174   }
175
176   /**
177    * Tests updating of third party settings.
178    */
179   protected function doThirdPartySettingsUpdate() {
180     // Create a test action with a known label.
181     $name = 'system.action.third_party_settings_test';
182
183     /** @var \Drupal\config_test\Entity\ConfigTest $entity */
184     $entity = Action::create([
185       'id' => 'third_party_settings_test',
186       'plugin' => 'action_message_action',
187     ]);
188     $entity->save();
189
190     $this->assertIdentical([], $entity->getThirdPartyProviders());
191     // Get a copy of the configuration before the third party setting is added.
192     $no_third_part_setting_config = $this->container->get('config.storage')->read($name);
193
194     // Add a third party setting.
195     $entity->setThirdPartySetting('config_test', 'integer', 1);
196     $entity->save();
197     $this->assertIdentical(1, $entity->getThirdPartySetting('config_test', 'integer'));
198     $has_third_part_setting_config = $this->container->get('config.storage')->read($name);
199
200     // Ensure configuration imports can completely remove third party settings.
201     $this->assertConfigUpdateImport($name, $has_third_part_setting_config, $no_third_part_setting_config);
202   }
203
204   /**
205    * Tests that a single set of plugin config stays in sync.
206    *
207    * @param \Drupal\Core\Entity\EntityWithPluginCollectionInterface $entity
208    *   The entity.
209    * @param string $config_key
210    *   Where the plugin config is stored.
211    * @param string $setting_key
212    *   The setting within the plugin config to change.
213    * @param mixed $expected
214    *   The expected default value of the plugin config setting.
215    */
216   protected function checkSinglePluginConfigSync(EntityWithPluginCollectionInterface $entity, $config_key, $setting_key, $expected) {
217     $plugin_collection = $entity->getPluginCollections()[$config_key];
218     $settings = $entity->get($config_key);
219
220     // Ensure the default config exists.
221     $this->assertIdentical($expected, $settings[$setting_key]);
222
223     // Change the plugin config by setting it on the entity.
224     $settings[$setting_key] = $this->randomString();
225     $entity->set($config_key, $settings);
226     $entity->save();
227     $this->assertIdentical($settings, $entity->get($config_key));
228     $this->assertIdentical($settings, $plugin_collection->getConfiguration());
229
230     // Change the plugin config by setting it on the plugin.
231     $settings[$setting_key] = $this->randomString();
232     $plugin_collection->setConfiguration($settings);
233     $entity->save();
234     $this->assertIdentical($settings, $entity->get($config_key));
235     $this->assertIdentical($settings, $plugin_collection->getConfiguration());
236   }
237
238   /**
239    * Asserts that config entities are updated during import.
240    *
241    * @param string $name
242    *   The name of the config object.
243    * @param array $original_data
244    *   The original data stored in the config object.
245    * @param array $custom_data
246    *   The new data to store in the config object.
247    */
248   public function assertConfigUpdateImport($name, $original_data, $custom_data) {
249     $this->container->get('config.storage.sync')->write($name, $custom_data);
250
251     // Verify the active configuration still returns the default values.
252     $config = $this->config($name);
253     $this->assertIdentical($config->get(), $original_data);
254
255     // Import.
256     $this->configImporter()->import();
257
258     // Verify the values were updated.
259     $this->container->get('config.factory')->reset($name);
260     $config = $this->config($name);
261     $this->assertIdentical($config->get(), $custom_data);
262   }
263
264 }