Pull merge.
[yaffs-website] / web / core / modules / migrate / tests / src / Kernel / HighWaterTest.php
1 <?php
2
3 namespace Drupal\Tests\migrate\Kernel;
4
5 /**
6  * Tests migration high water property.
7  *
8  * @group migrate
9  */
10 class HighWaterTest extends MigrateTestBase {
11
12   /**
13    * {@inheritdoc}
14    */
15   public static $modules = [
16     'system',
17     'user',
18     'node',
19     'migrate',
20     'migrate_high_water_test',
21     'field',
22   ];
23
24   /**
25    * {@inheritdoc}
26    */
27   protected function setUp() {
28     parent::setUp();
29     // Create source test table.
30     $this->sourceDatabase->schema()->createTable('high_water_node', [
31       'fields' => [
32         'id' => [
33           'description' => 'Serial',
34           'type' => 'serial',
35           'unsigned' => TRUE,
36           'not null' => TRUE,
37         ],
38         'changed' => [
39           'description' => 'Highwater',
40           'type' => 'int',
41           'unsigned' => TRUE,
42         ],
43         'title' => [
44           'description' => 'Title',
45           'type' => 'varchar',
46           'length' => 128,
47           'not null' => TRUE,
48           'default' => '',
49         ],
50       ],
51       'primary key' => [
52         'id',
53       ],
54       'description' => 'Contains nodes to import',
55     ]);
56
57     // Add 3 items to source table.
58     $this->sourceDatabase->insert('high_water_node')
59       ->fields([
60         'title',
61         'changed',
62       ])
63       ->values([
64         'title' => 'Item 1',
65         'changed' => 1,
66       ])
67       ->values([
68         'title' => 'Item 2',
69         'changed' => 2,
70       ])
71       ->values([
72         'title' => 'Item 3',
73         'changed' => 3,
74       ])
75       ->execute();
76
77     $this->installEntitySchema('node');
78     $this->installEntitySchema('user');
79     $this->installSchema('node', 'node_access');
80
81     $this->executeMigration('high_water_test');
82   }
83
84   /**
85    * Tests high water property of SqlBase.
86    */
87   public function testHighWater() {
88     // Assert all of the nodes have been imported.
89     $this->assertNodeExists('Item 1');
90     $this->assertNodeExists('Item 2');
91     $this->assertNodeExists('Item 3');
92
93     // Update Item 1 setting its high_water_property to value that is below
94     // current high water mark.
95     $this->sourceDatabase->update('high_water_node')
96       ->fields([
97         'title' => 'Item 1 updated',
98         'changed' => 2,
99       ])
100       ->condition('title', 'Item 1')
101       ->execute();
102
103     // Update Item 2 setting its high_water_property to value equal to
104     // current high water mark.
105     $this->sourceDatabase->update('high_water_node')
106       ->fields([
107         'title' => 'Item 2 updated',
108         'changed' => 3,
109       ])
110       ->condition('title', 'Item 2')
111       ->execute();
112
113     // Update Item 3 setting its high_water_property to value that is above
114     // current high water mark.
115     $this->sourceDatabase->update('high_water_node')
116       ->fields([
117         'title' => 'Item 3 updated',
118         'changed' => 4,
119       ])
120       ->condition('title', 'Item 3')
121       ->execute();
122
123     // Execute migration again.
124     $this->executeMigration('high_water_test');
125
126     // Item with lower highwater should not be updated.
127     $this->assertNodeExists('Item 1');
128     $this->assertNodeDoesNotExist('Item 1 updated');
129
130     // Item with equal highwater should not be updated.
131     $this->assertNodeExists('Item 2');
132     $this->assertNodeDoesNotExist('Item 2 updated');
133
134     // Item with greater highwater should be updated.
135     $this->assertNodeExists('Item 3 updated');
136     $this->assertNodeDoesNotExist('Item 3');
137   }
138
139   /**
140    * Tests that the high water value can be 0.
141    */
142   public function testZeroHighwater() {
143     // Assert all of the nodes have been imported.
144     $this->assertNodeExists('Item 1');
145     $this->assertNodeExists('Item 2');
146     $this->assertNodeExists('Item 3');
147     $migration = $this->container->get('plugin.manager.migration')->CreateInstance('high_water_test', []);
148     $source = $migration->getSourcePlugin();
149     $source->rewind();
150     $count = 0;
151     while ($source->valid()) {
152       $count++;
153       $source->next();
154     }
155
156     // Expect no rows as everything is below the high water mark.
157     $this->assertSame(0, $count);
158
159     // Test resetting the high water mark to 0.
160     $this->container->get('keyvalue')->get('migrate:high_water')->set('high_water_test', 0);
161     $migration = $this->container->get('plugin.manager.migration')->CreateInstance('high_water_test', []);
162     $source = $migration->getSourcePlugin();
163     $source->rewind();
164     $count = 0;
165     while ($source->valid()) {
166       $count++;
167       $source->next();
168     }
169     $this->assertSame(3, $count);
170   }
171
172   /**
173    * Tests that deleting the high water value causes all rows to be reimported.
174    */
175   public function testNullHighwater() {
176     // Assert all of the nodes have been imported.
177     $this->assertNodeExists('Item 1');
178     $this->assertNodeExists('Item 2');
179     $this->assertNodeExists('Item 3');
180     $migration = $this->container->get('plugin.manager.migration')->CreateInstance('high_water_test', []);
181     $source = $migration->getSourcePlugin();
182     $source->rewind();
183     $count = 0;
184     while ($source->valid()) {
185       $count++;
186       $source->next();
187     }
188
189     // Expect no rows as everything is below the high water mark.
190     $this->assertSame(0, $count);
191
192     // Test resetting the high water mark.
193     $this->container->get('keyvalue')->get('migrate:high_water')->delete('high_water_test');
194     $migration = $this->container->get('plugin.manager.migration')->CreateInstance('high_water_test', []);
195     $source = $migration->getSourcePlugin();
196     $source->rewind();
197     $count = 0;
198     while ($source->valid()) {
199       $count++;
200       $source->next();
201     }
202     $this->assertSame(3, $count);
203   }
204
205   /**
206    * Tests high water property of SqlBase when rows marked for update.
207    */
208   public function testHighWaterUpdate() {
209     // Assert all of the nodes have been imported.
210     $this->assertNodeExists('Item 1');
211     $this->assertNodeExists('Item 2');
212     $this->assertNodeExists('Item 3');
213
214     // Update Item 1 setting its high_water_property to value that is below
215     // current high water mark.
216     $this->sourceDatabase->update('high_water_node')
217       ->fields([
218         'title' => 'Item 1 updated',
219         'changed' => 2,
220       ])
221       ->condition('title', 'Item 1')
222       ->execute();
223
224     // Update Item 2 setting its high_water_property to value equal to
225     // current high water mark.
226     $this->sourceDatabase->update('high_water_node')
227       ->fields([
228         'title' => 'Item 2 updated',
229         'changed' => 3,
230       ])
231       ->condition('title', 'Item 2')
232       ->execute();
233
234     // Update Item 3 setting its high_water_property to value that is above
235     // current high water mark.
236     $this->sourceDatabase->update('high_water_node')
237       ->fields([
238         'title' => 'Item 3 updated',
239         'changed' => 4,
240       ])
241       ->condition('title', 'Item 3')
242       ->execute();
243
244     // Set all rows as needing an update.
245     $id_map = $this->getMigration('high_water_test')->getIdMap();
246     $id_map->prepareUpdate();
247
248     $this->executeMigration('high_water_test');
249
250     // Item with lower highwater should be updated.
251     $this->assertNodeExists('Item 1 updated');
252     $this->assertNodeDoesNotExist('Item 1');
253
254     // Item with equal highwater should be updated.
255     $this->assertNodeExists('Item 2 updated');
256     $this->assertNodeDoesNotExist('Item 2');
257
258     // Item with greater highwater should be updated.
259     $this->assertNodeExists('Item 3 updated');
260     $this->assertNodeDoesNotExist('Item 3');
261   }
262
263   /**
264    * Assert that node with given title exists.
265    *
266    * @param string $title
267    *   Title of the node.
268    */
269   protected function assertNodeExists($title) {
270     self::assertTrue($this->nodeExists($title));
271   }
272
273   /**
274    * Assert that node with given title does not exist.
275    *
276    * @param string $title
277    *   Title of the node.
278    */
279   protected function assertNodeDoesNotExist($title) {
280     self::assertFalse($this->nodeExists($title));
281   }
282
283   /**
284    * Checks if node with given title exists.
285    *
286    * @param string $title
287    *   Title of the node.
288    *
289    * @return bool
290    */
291   protected function nodeExists($title) {
292     $query = \Drupal::entityQuery('node');
293     $result = $query
294       ->condition('title', $title)
295       ->range(0, 1)
296       ->execute();
297
298     return !empty($result);
299   }
300
301 }