Chris@0
|
1 <?php
|
Chris@0
|
2
|
Chris@0
|
3 /**
|
Chris@0
|
4 * @file
|
Chris@0
|
5 * Post update functions for Views.
|
Chris@0
|
6 */
|
Chris@0
|
7
|
Chris@0
|
8 use Drupal\Core\StringTranslation\TranslatableMarkup;
|
Chris@0
|
9 use Drupal\views\Entity\View;
|
Chris@0
|
10 use Drupal\views\Views;
|
Chris@0
|
11
|
Chris@0
|
12 /**
|
Chris@0
|
13 * Update the cacheability metadata for all views.
|
Chris@0
|
14 */
|
Chris@0
|
15 function views_post_update_update_cacheability_metadata() {
|
Chris@0
|
16 // Load all views.
|
Chris@0
|
17 $views = \Drupal::entityManager()->getStorage('view')->loadMultiple();
|
Chris@0
|
18
|
Chris@0
|
19 /* @var \Drupal\views\Entity\View[] $views */
|
Chris@0
|
20 foreach ($views as $view) {
|
Chris@0
|
21 $displays = $view->get('display');
|
Chris@0
|
22 foreach (array_keys($displays) as $display_id) {
|
Chris@0
|
23 $display =& $view->getDisplay($display_id);
|
Chris@0
|
24 // Unset the cache_metadata key, so all cacheability metadata for the
|
Chris@0
|
25 // display is recalculated.
|
Chris@0
|
26 unset($display['cache_metadata']);
|
Chris@0
|
27 }
|
Chris@0
|
28 $view->save();
|
Chris@0
|
29 }
|
Chris@0
|
30
|
Chris@0
|
31 }
|
Chris@0
|
32
|
Chris@0
|
33 /**
|
Chris@0
|
34 * Update some views fields that were previously duplicated.
|
Chris@0
|
35 */
|
Chris@0
|
36 function views_post_update_cleanup_duplicate_views_data() {
|
Chris@0
|
37 $config_factory = \Drupal::configFactory();
|
Chris@0
|
38 $ids = [];
|
Chris@0
|
39 $message = NULL;
|
Chris@0
|
40 $data_tables = [];
|
Chris@0
|
41 $base_tables = [];
|
Chris@0
|
42 $revision_tables = [];
|
Chris@0
|
43 $entities_by_table = [];
|
Chris@0
|
44 $duplicate_fields = [];
|
Chris@0
|
45 $handler_types = Views::getHandlerTypes();
|
Chris@0
|
46
|
Chris@0
|
47 /** @var \Drupal\Core\Entity\EntityTypeManagerInterface $entity_type_manager */
|
Chris@0
|
48 $entity_type_manager = \Drupal::service('entity_type.manager');
|
Chris@0
|
49 // This will allow us to create an index of all entity types of the site.
|
Chris@0
|
50 foreach ($entity_type_manager->getDefinitions() as $entity_type_id => $entity_type) {
|
Chris@0
|
51 // Store the entity keyed by base table. If it has a data table, use that as
|
Chris@0
|
52 // well.
|
Chris@0
|
53 if ($data_table = $entity_type->getDataTable()) {
|
Chris@0
|
54 $entities_by_table[$data_table] = $entity_type;
|
Chris@0
|
55 }
|
Chris@0
|
56 if ($base_table = $entity_type->getBaseTable()) {
|
Chris@0
|
57 $entities_by_table[$base_table] = $entity_type;
|
Chris@0
|
58 }
|
Chris@0
|
59
|
Chris@0
|
60 // The following code basically contains the same kind of logic as
|
Chris@0
|
61 // \Drupal\Core\Entity\Sql\SqlContentEntityStorage::initTableLayout() to
|
Chris@0
|
62 // prefetch all tables (base, data, revision, and revision data).
|
Chris@0
|
63 $base_tables[$entity_type_id] = $entity_type->getBaseTable() ?: $entity_type->id();
|
Chris@0
|
64 $revisionable = $entity_type->isRevisionable();
|
Chris@0
|
65
|
Chris@0
|
66 $revision_table = '';
|
Chris@0
|
67 if ($revisionable) {
|
Chris@0
|
68 $revision_table = $entity_type->getRevisionTable() ?: $entity_type->id() . '_revision';
|
Chris@0
|
69 }
|
Chris@0
|
70 $revision_tables[$entity_type_id] = $revision_table;
|
Chris@0
|
71
|
Chris@0
|
72 $translatable = $entity_type->isTranslatable();
|
Chris@0
|
73 $data_table = '';
|
Chris@0
|
74 // For example the data table just exists, when the entity type is
|
Chris@0
|
75 // translatable.
|
Chris@0
|
76 if ($translatable) {
|
Chris@0
|
77 $data_table = $entity_type->getDataTable() ?: $entity_type->id() . '_field_data';
|
Chris@0
|
78 }
|
Chris@0
|
79 $data_tables[$entity_type_id] = $data_table;
|
Chris@0
|
80
|
Chris@0
|
81 $duplicate_fields[$entity_type_id] = array_intersect_key($entity_type->getKeys(), array_flip(['id', 'revision', 'bundle']));
|
Chris@0
|
82 }
|
Chris@0
|
83
|
Chris@0
|
84 foreach ($config_factory->listAll('views.view.') as $view_config_name) {
|
Chris@0
|
85 $changed = FALSE;
|
Chris@0
|
86 $view = $config_factory->getEditable($view_config_name);
|
Chris@0
|
87
|
Chris@0
|
88 $displays = $view->get('display');
|
Chris@0
|
89 if (isset($entities_by_table[$view->get('base_table')])) {
|
Chris@0
|
90 $entity_type = $entities_by_table[$view->get('base_table')];
|
Chris@0
|
91 $entity_type_id = $entity_type->id();
|
Chris@0
|
92 $data_table = $data_tables[$entity_type_id];
|
Chris@0
|
93 $base_table = $base_tables[$entity_type_id];
|
Chris@0
|
94 $revision_table = $revision_tables[$entity_type_id];
|
Chris@0
|
95
|
Chris@0
|
96 if ($data_table) {
|
Chris@0
|
97 foreach ($displays as $display_name => &$display) {
|
Chris@0
|
98 foreach ($handler_types as $handler_type) {
|
Chris@0
|
99 if (!empty($display['display_options'][$handler_type['plural']])) {
|
Chris@0
|
100 foreach ($display['display_options'][$handler_type['plural']] as $field_name => &$field) {
|
Chris@0
|
101 $table = $field['table'];
|
Chris@0
|
102 if (($table === $base_table || $table === $revision_table) && in_array($field_name, $duplicate_fields[$entity_type_id])) {
|
Chris@0
|
103 $field['table'] = $data_table;
|
Chris@0
|
104 $changed = TRUE;
|
Chris@0
|
105 }
|
Chris@0
|
106 }
|
Chris@0
|
107 }
|
Chris@0
|
108 }
|
Chris@0
|
109 }
|
Chris@0
|
110 }
|
Chris@0
|
111 }
|
Chris@0
|
112
|
Chris@0
|
113 if ($changed) {
|
Chris@0
|
114 $view->set('display', $displays);
|
Chris@0
|
115 $view->save();
|
Chris@0
|
116 $ids[] = $view->get('id');
|
Chris@0
|
117 }
|
Chris@0
|
118 }
|
Chris@0
|
119 if (!empty($ids)) {
|
Chris@0
|
120 $message = new TranslatableMarkup('Updated tables for field handlers for views: @ids', ['@ids' => implode(', ', array_unique($ids))]);
|
Chris@0
|
121 }
|
Chris@0
|
122
|
Chris@0
|
123 return $message;
|
Chris@0
|
124 }
|
Chris@0
|
125
|
Chris@0
|
126 /**
|
Chris@0
|
127 * Include field formatter dependencies in a view when the formatter is used.
|
Chris@0
|
128 */
|
Chris@0
|
129 function views_post_update_field_formatter_dependencies() {
|
Chris@0
|
130 $views = View::loadMultiple();
|
Chris@0
|
131 array_walk($views, function (View $view) {
|
Chris@0
|
132 $view->save();
|
Chris@0
|
133 });
|
Chris@0
|
134 }
|
Chris@0
|
135
|
Chris@0
|
136 /**
|
Chris@0
|
137 * Fix views with dependencies on taxonomy terms that don't exist.
|
Chris@0
|
138 */
|
Chris@0
|
139 function views_post_update_taxonomy_index_tid() {
|
Chris@0
|
140 $views = View::loadMultiple();
|
Chris@0
|
141 array_walk($views, function (View $view) {
|
Chris@0
|
142 $old_dependencies = $view->getDependencies();
|
Chris@0
|
143 $new_dependencies = $view->calculateDependencies()->getDependencies();
|
Chris@0
|
144 if ($old_dependencies !== $new_dependencies) {
|
Chris@0
|
145 $view->save();
|
Chris@0
|
146 }
|
Chris@0
|
147 });
|
Chris@0
|
148 }
|
Chris@0
|
149
|
Chris@0
|
150 /**
|
Chris@0
|
151 * Fix views with serializer dependencies.
|
Chris@0
|
152 */
|
Chris@0
|
153 function views_post_update_serializer_dependencies() {
|
Chris@0
|
154 $views = View::loadMultiple();
|
Chris@0
|
155 array_walk($views, function (View $view) {
|
Chris@0
|
156 $old_dependencies = $view->getDependencies();
|
Chris@0
|
157 $new_dependencies = $view->calculateDependencies()->getDependencies();
|
Chris@0
|
158 if ($old_dependencies !== $new_dependencies) {
|
Chris@0
|
159 $view->save();
|
Chris@0
|
160 }
|
Chris@0
|
161 });
|
Chris@0
|
162 }
|
Chris@0
|
163
|
Chris@0
|
164 /**
|
Chris@0
|
165 * Set all boolean filter values to strings.
|
Chris@0
|
166 */
|
Chris@0
|
167 function views_post_update_boolean_filter_values() {
|
Chris@0
|
168 $config_factory = \Drupal::configFactory();
|
Chris@0
|
169 foreach ($config_factory->listAll('views.view.') as $view_config_name) {
|
Chris@0
|
170 $view = $config_factory->getEditable($view_config_name);
|
Chris@0
|
171 $save = FALSE;
|
Chris@0
|
172 foreach ($view->get('display') as $display_name => $display) {
|
Chris@0
|
173 if (isset($display['display_options']['filters'])) {
|
Chris@0
|
174 foreach ($display['display_options']['filters'] as $filter_name => $filter) {
|
Chris@0
|
175 if (isset($filter['plugin_id']) && $filter['plugin_id'] === 'boolean') {
|
Chris@0
|
176 $new_value = FALSE;
|
Chris@0
|
177 // Update all boolean and integer values to strings.
|
Chris@0
|
178 if ($filter['value'] === TRUE || $filter['value'] === 1) {
|
Chris@0
|
179 $new_value = '1';
|
Chris@0
|
180 }
|
Chris@0
|
181 elseif ($filter['value'] === FALSE || $filter['value'] === 0) {
|
Chris@0
|
182 $new_value = '0';
|
Chris@0
|
183 }
|
Chris@0
|
184 if ($new_value !== FALSE) {
|
Chris@0
|
185 $view->set("display.$display_name.display_options.filters.$filter_name.value", $new_value);
|
Chris@0
|
186 $save = TRUE;
|
Chris@0
|
187 }
|
Chris@0
|
188 }
|
Chris@0
|
189 }
|
Chris@0
|
190 }
|
Chris@0
|
191 }
|
Chris@0
|
192 if ($save) {
|
Chris@0
|
193 $view->save();
|
Chris@0
|
194 }
|
Chris@0
|
195 }
|
Chris@0
|
196 }
|
Chris@0
|
197
|
Chris@0
|
198 /**
|
Chris@0
|
199 * Rebuild caches to ensure schema changes are read in.
|
Chris@0
|
200 */
|
Chris@0
|
201 function views_post_update_grouped_filters() {
|
Chris@0
|
202 // Empty update to cause a cache rebuild so that the schema changes are read.
|
Chris@0
|
203 }
|
Chris@0
|
204
|
Chris@0
|
205 /**
|
Chris@0
|
206 * Fix table names for revision metadata fields.
|
Chris@0
|
207 */
|
Chris@0
|
208 function views_post_update_revision_metadata_fields() {
|
Chris@0
|
209 // The table names are fixed automatically in
|
Chris@0
|
210 // \Drupal\views\Entity\View::preSave(), so we just need to re-save all views.
|
Chris@0
|
211 $views = View::loadMultiple();
|
Chris@0
|
212 array_walk($views, function (View $view) {
|
Chris@0
|
213 $view->save();
|
Chris@0
|
214 });
|
Chris@0
|
215 }
|