Projet

Général

Profil

Paste
Télécharger (24,6 ko) Statistiques
| Branche: | Révision:

root / drupal7 / modules / simpletest / tests / upgrade / upgrade.test @ f7a2490e

1
<?php
2

    
3
/**
4
 * Perform end-to-end tests of the upgrade path.
5
 */
6
abstract class UpgradePathTestCase extends DrupalWebTestCase {
7

    
8
  /**
9
   * The file path(s) to the dumped database(s) to load into the child site.
10
   *
11
   * @var array
12
   */
13
  var $databaseDumpFiles = array();
14

    
15
  /**
16
   * Flag that indicates whether the child site has been upgraded.
17
   */
18
  var $upgradedSite = FALSE;
19

    
20
  /**
21
   * Array of errors triggered during the upgrade process.
22
   */
23
  var $upgradeErrors = array();
24

    
25
  /**
26
   * Array of modules loaded when the test starts.
27
   */
28
  var $loadedModules = array();
29

    
30
  /**
31
   * Flag to indicate whether zlib is installed or not.
32
   */
33
  var $zlibInstalled = TRUE;
34

    
35
  /**
36
   * Flag to indicate whether there are pending updates or not.
37
   */
38
  var $pendingUpdates = TRUE;
39

    
40
  /**
41
   * Constructs an UpgradePathTestCase object.
42
   *
43
   * @param $test_id
44
   *   (optional) The ID of the test. Tests with the same id are reported
45
   *   together.
46
   */
47
  function __construct($test_id = NULL) {
48
    parent::__construct($test_id);
49
    $this->zlibInstalled = function_exists('gzopen');
50
  }
51

    
52
  /**
53
   * Prepares the appropriate session for the release of Drupal being upgraded.
54
   */
55
  protected function prepareD7Session() {
56
    // Generate and set a D6-compatible session cookie.
57
    $this->curlInitialize();
58
    $sid = drupal_hash_base64(uniqid(mt_rand(), TRUE) . drupal_random_bytes(55));
59
    $session_name = update_get_d6_session_name();
60
    curl_setopt($this->curlHandle, CURLOPT_COOKIE, rawurlencode($session_name) . '=' . rawurlencode($sid));
61

    
62
    // Force our way into the session of the child site.
63
    drupal_save_session(TRUE);
64
    // A session cannot be written without the ssid column which is missing on
65
    // Drupal 6 sites.
66
    db_add_field('sessions', 'ssid', array('description' => "Secure session ID. The value is generated by Drupal's session handlers.", 'type' => 'varchar', 'length' => 128, 'not null' => TRUE, 'default' => ''));
67
    _drupal_session_write($sid, '');
68
    // Remove the temporarily added ssid column.
69
    db_drop_field('sessions', 'ssid');
70
    drupal_save_session(FALSE);
71
  }
72

    
73
  /**
74
   * Overrides DrupalWebTestCase::setUp() for upgrade testing.
75
   *
76
   * @see DrupalWebTestCase::prepareDatabasePrefix()
77
   * @see DrupalWebTestCase::changeDatabasePrefix()
78
   * @see DrupalWebTestCase::prepareEnvironment()
79
   */
80
  protected function setUp() {
81
    // We are going to set a missing zlib requirement property for usage
82
    // during the performUpgrade() and tearDown() methods. Also set that the
83
    // tests failed.
84
    if (!$this->zlibInstalled) {
85
      parent::setUp();
86
      return;
87
    }
88

    
89
    global $user, $language, $conf;
90

    
91
    // Load the Update API.
92
    require_once DRUPAL_ROOT . '/includes/update.inc';
93

    
94
    // Reset flags.
95
    $this->upgradedSite = FALSE;
96
    $this->upgradeErrors = array();
97

    
98
    $this->loadedModules = module_list();
99

    
100
    // Create the database prefix for this test.
101
    $this->prepareDatabasePrefix();
102

    
103
    // Prepare the environment for running tests.
104
    $this->prepareEnvironment();
105
    if (!$this->setupEnvironment) {
106
      return FALSE;
107
    }
108

    
109
    // Reset all statics and variables to perform tests in a clean environment.
110
    $conf = array();
111
    drupal_static_reset();
112

    
113
    // Change the database prefix.
114
    // All static variables need to be reset before the database prefix is
115
    // changed, since DrupalCacheArray implementations attempt to
116
    // write back to persistent caches when they are destructed.
117
    $this->changeDatabasePrefix();
118
    if (!$this->setupDatabasePrefix) {
119
      return FALSE;
120
    }
121

    
122
    // Unregister the registry.
123
    // This is required to make sure that the database layer works properly.
124
    spl_autoload_unregister('drupal_autoload_class');
125
    spl_autoload_unregister('drupal_autoload_interface');
126

    
127
    // Load the database from the portable PHP dump.
128
    // The files may be gzipped.
129
    foreach ($this->databaseDumpFiles as $file) {
130
      if (substr($file, -3) == '.gz') {
131
        $file = "compress.zlib://$file";
132
      }
133
      require $file;
134
    }
135

    
136
    // Set path variables.
137
    $this->variable_set('file_public_path', $this->public_files_directory);
138
    $this->variable_set('file_private_path', $this->private_files_directory);
139
    $this->variable_set('file_temporary_path', $this->temp_files_directory);
140

    
141
    $this->pass('Finished loading the dump.');
142

    
143
    // Ensure that the session is not written to the new environment and replace
144
    // the global $user session with uid 1 from the new test site.
145
    drupal_save_session(FALSE);
146
    // Login as uid 1.
147
    $user = db_query('SELECT * FROM {users} WHERE uid = :uid', array(':uid' => 1))->fetchObject();
148

    
149
    // Generate and set a D6-compatible session cookie.
150
    $this->prepareD7Session();
151

    
152
    // Restore necessary variables.
153
    $this->variable_set('clean_url', $this->originalCleanUrl);
154
    $this->variable_set('site_mail', 'simpletest@example.com');
155

    
156
    drupal_set_time_limit($this->timeLimit);
157
    $this->setup = TRUE;
158
  }
159

    
160
  /**
161
   * Specialized variable_set() that works even if the child site is not upgraded.
162
   *
163
   * @param $name
164
   *   The name of the variable to set.
165
   * @param $value
166
   *   The value to set. This can be any PHP data type; these functions take care
167
   *   of serialization as necessary.
168
   */
169
  protected function variable_set($name, $value) {
170
    db_delete('variable')
171
      ->condition('name', $name)
172
      ->execute();
173
    db_insert('variable')
174
      ->fields(array(
175
        'name' => $name,
176
        'value' => serialize($value),
177
      ))
178
      ->execute();
179

    
180
    try {
181
      cache_clear_all('variables', 'cache');
182
      cache_clear_all('variables', 'cache_bootstrap');
183
    }
184
    // Since cache_bootstrap won't exist in a Drupal 6 site, ignore the
185
    // exception if the above fails.
186
    catch (Exception $e) {}
187
  }
188

    
189
  /**
190
   * Specialized refreshVariables().
191
   */
192
  protected function refreshVariables() {
193
    // No operation if the child has not been upgraded yet.
194
    if (!$this->upgradedSite) {
195
      return parent::refreshVariables();
196
    }
197
  }
198

    
199
  /**
200
   * Perform the upgrade.
201
   *
202
   * @param $register_errors
203
   *   Register the errors during the upgrade process as failures.
204
   * @return
205
   *   TRUE if the upgrade succeeded, FALSE otherwise.
206
   */
207
  protected function performUpgrade($register_errors = TRUE) {
208
    if (!$this->zlibInstalled) {
209
      $this->fail(t('Missing zlib requirement for upgrade tests.'));
210
      return FALSE;
211
    }
212

    
213
    $update_url = $GLOBALS['base_url'] . '/update.php';
214

    
215
    // Load the first update screen.
216
    $this->drupalGet($update_url, array('external' => TRUE));
217
    if (!$this->assertResponse(200)) {
218
      return FALSE;
219
    }
220

    
221
    // Continue.
222
    $this->drupalPost(NULL, array(), t('Continue'));
223
    if (!$this->assertResponse(200)) {
224
      return FALSE;
225
    }
226

    
227
    // The test should pass if there are no pending updates.
228
    $content = $this->drupalGetContent();
229
    if (strpos($content, t('No pending updates.')) !== FALSE) {
230
      $this->pass(t('No pending updates and therefore no upgrade process to test.'));
231
      $this->pendingUpdates = FALSE;
232
      return TRUE;
233
    }
234

    
235
    // Go!
236
    $this->drupalPost(NULL, array(), t('Apply pending updates'));
237
    if (!$this->assertResponse(200)) {
238
      return FALSE;
239
    }
240

    
241
    // Check for errors during the update process.
242
    foreach ($this->xpath('//li[@class=:class]', array(':class' => 'failure')) as $element) {
243
      $message = strip_tags($element->asXML());
244
      $this->upgradeErrors[] = $message;
245
      if ($register_errors) {
246
        $this->fail($message);
247
      }
248
    }
249

    
250
    if (!empty($this->upgradeErrors)) {
251
      // Upgrade failed, the installation might be in an inconsistent state,
252
      // don't process.
253
      return FALSE;
254
    }
255

    
256
    // Check if there still are pending updates.
257
    $this->drupalGet($update_url, array('external' => TRUE));
258
    $this->drupalPost(NULL, array(), t('Continue'));
259
    if (!$this->assertText(t('No pending updates.'), 'No pending updates at the end of the update process.')) {
260
      return FALSE;
261
    }
262

    
263
    // Upgrade succeed, rebuild the environment so that we can call the API
264
    // of the child site directly from this request.
265
    $this->upgradedSite = TRUE;
266

    
267
    // Reload module list. For modules that are enabled in the test database,
268
    // but not on the test client, we need to load the code here.
269
    $new_modules = array_diff(module_list(TRUE), $this->loadedModules);
270
    foreach ($new_modules as $module) {
271
      drupal_load('module', $module);
272
    }
273

    
274
    // Reload hook implementations
275
    module_implements('', FALSE, TRUE);
276

    
277
    // Rebuild caches.
278
    drupal_static_reset();
279
    drupal_flush_all_caches();
280

    
281
    // Reload global $conf array and permissions.
282
    $this->refreshVariables();
283
    $this->checkPermissions(array(), TRUE);
284

    
285
    return TRUE;
286
  }
287

    
288
  /**
289
   * Force uninstall all modules from a test database, except those listed.
290
   *
291
   * @param $modules
292
   *   The list of modules to keep installed. Required core modules will
293
   *   always be kept.
294
   */
295
  protected function uninstallModulesExcept(array $modules) {
296
    $required_modules = array('block', 'dblog', 'filter', 'node', 'system', 'update', 'user');
297

    
298
    $modules = array_merge($required_modules, $modules);
299

    
300
    db_delete('system')
301
      ->condition('type', 'module')
302
      ->condition('name', $modules, 'NOT IN')
303
      ->execute();
304
  }
305

    
306
}
307

    
308
/**
309
 * Performs end-to-end point test of the release update path.
310
 */
311
abstract class UpdatePathTestCase extends UpgradePathTestCase {
312
  /**
313
   * Overrides UpgradePathTestCase::prepareD7Session().
314
   */
315
  protected function prepareD7Session() {
316
    // Generate and set a D7-compatible session cookie.
317
    $this->curlInitialize();
318
    $sid = drupal_hash_base64(uniqid(mt_rand(), TRUE) . drupal_random_bytes(55));
319
    curl_setopt($this->curlHandle, CURLOPT_COOKIE, rawurlencode(session_name()) . '=' . rawurlencode($sid));
320

    
321
    // Force our way into the session of the child site.
322
    drupal_save_session(TRUE);
323
    _drupal_session_write($sid, '');
324
    drupal_save_session(FALSE);
325
  }
326
}
327

    
328
/**
329
 * Perform basic upgrade tests.
330
 *
331
 * Load a bare installation of Drupal 6 and run the upgrade process on it.
332
 *
333
 * The install only contains dblog (although it's optional, it's only so that
334
 * another hook_watchdog module can take its place, the site is not functional
335
 * without watchdog) and update.
336
 */
337
class BasicUpgradePath extends UpgradePathTestCase {
338
  public static function getInfo() {
339
    return array(
340
      'name'  => 'Basic upgrade path',
341
      'description'  => 'Basic upgrade path tests.',
342
      'group' => 'Upgrade path',
343
    );
344
  }
345

    
346
  public function setUp() {
347
    // Path to the database dump files.
348
    $this->databaseDumpFiles = array(
349
      drupal_get_path('module', 'simpletest') . '/tests/upgrade/drupal-6.bare.database.php',
350
    );
351
    parent::setUp();
352
  }
353

    
354
  /**
355
   * Test a failed upgrade, and verify that the failure is reported.
356
   */
357
  public function testFailedUpgrade() {
358
    // Destroy a table that the upgrade process needs.
359
    db_drop_table('access');
360
    // Assert that the upgrade fails.
361
    $this->assertFalse($this->performUpgrade(FALSE) && $this->pendingUpdates, 'A failed upgrade should return messages.');
362
  }
363

    
364
  /**
365
   * Test a successful upgrade.
366
   */
367
  public function testBasicUpgrade() {
368
    $this->assertTrue($this->performUpgrade(), 'The upgrade was completed successfully.');
369

    
370
    // Hit the frontpage.
371
    $this->drupalGet('');
372
    $this->assertResponse(200);
373

    
374
    // Verify that we are still logged in.
375
    $this->drupalGet('user');
376
    $this->clickLink(t('Edit'));
377
    $this->assertEqual($this->getUrl(), url('user/1/edit', array('absolute' => TRUE)), 'We are still logged in as admin at the end of the upgrade.');
378

    
379
    // Logout and verify that we can login back in with our initial password.
380
    $this->drupalLogout();
381
    $this->drupalLogin((object) array(
382
      'uid' => 1,
383
      'name' => 'admin',
384
      'pass_raw' => 'admin',
385
    ));
386

    
387
    // The previous login should've triggered a password rehash, so login one
388
    // more time to make sure the new hash is readable.
389
    $this->drupalLogout();
390
    $this->drupalLogin((object) array(
391
      'uid' => 1,
392
      'name' => 'admin',
393
      'pass_raw' => 'admin',
394
    ));
395

    
396
    // Test that the site name is correctly displayed.
397
    $this->assertText('Drupal 6', 'The site name is correctly displayed.');
398

    
399
    // Verify that the main admin sections are available.
400
    $this->drupalGet('admin');
401
    $this->assertText(t('Content'));
402
    $this->assertText(t('Appearance'));
403
    $this->assertText(t('People'));
404
    $this->assertText(t('Configuration'));
405
    $this->assertText(t('Reports'));
406
    $this->assertText(t('Structure'));
407
    $this->assertText(t('Modules'));
408

    
409
    // Confirm that no {menu_links} entry exists for user/autocomplete.
410
    $result = db_query('SELECT COUNT(*) FROM {menu_links} WHERE link_path = :user_autocomplete', array(':user_autocomplete' => 'user/autocomplete'))->fetchField();
411
    $this->assertFalse($result, 'No {menu_links} entry exists for user/autocomplete');
412

    
413
    // Test that the environment after the upgrade is in a consistent status.
414
    $update_d6 = variable_get('update_d6', FALSE);
415
    $this->assertFalse($update_d6, 'The D6 upgrade flag variable has been correctly disabled.');
416
  }
417
}
418

    
419
/**
420
 * Performs point release update tests on a bare database.
421
 *
422
 * Loads an installation of Drupal 7.0 and runs the update process on it.
423
 *
424
 * The install contains the standard profile (plus all optional) modules
425
 * without any content so that an update from any of the modules under this
426
 * profile installation can be wholly tested.
427
 */
428
class BasicStandardUpdatePath extends UpdatePathTestCase {
429
  public static function getInfo() {
430
    return array(
431
      'name'  => 'Basic standard + all profile update path',
432
      'description'  => 'Basic update path tests for a standard profile install with all enabled modules.',
433
      'group' => 'Upgrade path',
434
    );
435
  }
436

    
437
  public function setUp() {
438
    // Path to the database dump files.
439
    $this->databaseDumpFiles = array(
440
      drupal_get_path('module', 'simpletest') . '/tests/upgrade/drupal-7.bare.standard_all.database.php.gz',
441
    );
442
    parent::setUp();
443
  }
444

    
445
  /**
446
   * Tests a successful point release update.
447
   */
448
  public function testBasicStandardUpdate() {
449
    $this->assertTrue($this->performUpgrade(), 'The upgrade was completed successfully.');
450

    
451
    // Hit the frontpage.
452
    $this->drupalGet('');
453
    $this->assertResponse(200);
454

    
455
    // Verify that we are still logged in.
456
    $this->drupalGet('user');
457
    $this->clickLink(t('Edit'));
458
    $this->assertEqual($this->getUrl(), url('user/1/edit', array('absolute' => TRUE)), 'We are still logged in as admin at the end of the upgrade.');
459

    
460
    // Logout and verify that we can login back in with our initial password.
461
    $this->drupalLogout();
462
    $this->drupalLogin((object) array(
463
      'uid' => 1,
464
      'name' => 'admin',
465
      'pass_raw' => 'admin',
466
    ));
467

    
468
    // The previous login should've triggered a password rehash, so login one
469
    // more time to make sure the new hash is readable.
470
    $this->drupalLogout();
471
    $this->drupalLogin((object) array(
472
      'uid' => 1,
473
      'name' => 'admin',
474
      'pass_raw' => 'admin',
475
    ));
476

    
477
    // Test that the site name is correctly displayed.
478
    $this->assertText('Drupal', 'The site name is correctly displayed.');
479

    
480
    // Verify that the main admin sections are available.
481
    $this->drupalGet('admin');
482
    $this->assertText(t('Content'));
483
    $this->assertText(t('Appearance'));
484
    $this->assertText(t('People'));
485
    $this->assertText(t('Configuration'));
486
    $this->assertText(t('Reports'));
487
    $this->assertText(t('Structure'));
488
    $this->assertText(t('Modules'));
489

    
490
    // Confirm that no {menu_links} entry exists for user/autocomplete.
491
    $result = db_query('SELECT COUNT(*) FROM {menu_links} WHERE link_path = :user_autocomplete', array(':user_autocomplete' => 'user/autocomplete'))->fetchField();
492
    $this->assertFalse($result, 'No {menu_links} entry exists for user/autocomplete');
493
  }
494
}
495

    
496
/**
497
 * Performs point release update tests on a bare database.
498
 *
499
 * Loads an installation of Drupal 7.0 and runs the update process on it.
500
 *
501
 * The install contains the minimal profile modules (without any generated
502
 * content) so that an update from of a site under this profile may be tested.
503
 */
504
class BasicMinimalUpdatePath extends UpdatePathTestCase {
505
  public static function getInfo() {
506
    return array(
507
      'name'  => 'Basic minimal profile update path',
508
      'description'  => 'Basic update path tests for a minimal profile install.',
509
      'group' => 'Upgrade path',
510
    );
511
  }
512

    
513
  public function setUp() {
514
    // Path to the database dump files.
515
    $this->databaseDumpFiles = array(
516
      drupal_get_path('module', 'simpletest') . '/tests/upgrade/drupal-7.bare.minimal.database.php.gz',
517
    );
518
    parent::setUp();
519
  }
520

    
521
  /**
522
   * Tests a successful point release update.
523
   */
524
  public function testBasicMinimalUpdate() {
525
    $this->assertTrue($this->performUpgrade(), 'The upgrade was completed successfully.');
526

    
527
    // Hit the frontpage.
528
    $this->drupalGet('');
529
    $this->assertResponse(200);
530

    
531
    // Verify that we are still logged in.
532
    $this->drupalGet('user');
533
    $this->clickLink(t('Edit'));
534
    $this->assertEqual($this->getUrl(), url('user/1/edit', array('absolute' => TRUE)), 'We are still logged in as admin at the end of the upgrade.');
535

    
536
    // Logout and verify that we can login back in with our initial password.
537
    $this->drupalLogout();
538
    $this->drupalLogin((object) array(
539
      'uid' => 1,
540
      'name' => 'admin',
541
      'pass_raw' => 'admin',
542
    ));
543

    
544
    // The previous login should've triggered a password rehash, so login one
545
    // more time to make sure the new hash is readable.
546
    $this->drupalLogout();
547
    $this->drupalLogin((object) array(
548
      'uid' => 1,
549
      'name' => 'admin',
550
      'pass_raw' => 'admin',
551
    ));
552

    
553
    // Test that the site name is correctly displayed.
554
    $this->assertText('Drupal', 'The site name is correctly displayed.');
555

    
556
    // Verify that the main admin sections are available.
557
    $this->drupalGet('admin');
558
    $this->assertText(t('Content'));
559
    $this->assertText(t('Appearance'));
560
    $this->assertText(t('People'));
561
    $this->assertText(t('Configuration'));
562
    $this->assertText(t('Reports'));
563
    $this->assertText(t('Structure'));
564
    $this->assertText(t('Modules'));
565

    
566
    // Confirm that no {menu_links} entry exists for user/autocomplete.
567
    $result = db_query('SELECT COUNT(*) FROM {menu_links} WHERE link_path = :user_autocomplete', array(':user_autocomplete' => 'user/autocomplete'))->fetchField();
568
    $this->assertFalse($result, 'No {menu_links} entry exists for user/autocomplete');
569

    
570
    // Confirm that a date format that just differs in the case can be added.
571
    $admin_date_format = 'j M y';
572
    $edit = array('date_format' => $admin_date_format);
573
    $this->drupalPost('admin/config/regional/date-time/formats/add', $edit, t('Add format'));
574

    
575
    // Add a new date format which just differs in the case.
576
    $admin_date_format_uppercase = 'j M Y';
577
    $edit = array('date_format' => $admin_date_format_uppercase);
578
    $this->drupalPost('admin/config/regional/date-time/formats/add', $edit, t('Add format'));
579
    $this->assertText(t('Custom date format added.'));
580

    
581
    // Verify that the unique key on {date_formats}.format still exists.
582
    $this->assertTrue(db_index_exists('date_formats', 'formats'), 'Unique key on {date_formats} exists');
583
  }
584
}
585

    
586
/**
587
 * Performs point release update tests on a 'filled' database.
588
 *
589
 * Loads an installation of Drupal 7.0 and runs the update process on it.
590
 *
591
 * The install contains the standard profile (plus all optional) modules
592
 * with generated content so that an update from any of the modules under this
593
 * profile installation can be wholly tested.
594
 */
595
class FilledStandardUpdatePath extends UpdatePathTestCase {
596
  public static function getInfo() {
597
    return array(
598
      'name'  => 'Basic standard + all profile update path, populated database',
599
      'description'  => 'Basic update path tests for a standard profile install with all enabled modules and a populated database.',
600
      'group' => 'Upgrade path',
601
    );
602
  }
603

    
604
  public function setUp() {
605
    // Path to the database dump files.
606
    $this->databaseDumpFiles = array(
607
      drupal_get_path('module', 'simpletest') . '/tests/upgrade/drupal-7.filled.standard_all.database.php.gz',
608
    );
609
    parent::setUp();
610
  }
611

    
612
  /**
613
   * Tests a successful point release update.
614
   */
615
  public function testFilledStandardUpdate() {
616
    $this->assertTrue($this->performUpgrade(), 'The upgrade was completed successfully.');
617

    
618
    // Hit the frontpage.
619
    $this->drupalGet('');
620
    $this->assertResponse(200);
621

    
622
    // Verify that we are still logged in.
623
    $this->drupalGet('user');
624
    $this->clickLink(t('Edit'));
625
    $this->assertEqual($this->getUrl(), url('user/1/edit', array('absolute' => TRUE)), 'We are still logged in as admin at the end of the upgrade.');
626

    
627
    // Logout and verify that we can login back in with our initial password.
628
    $this->drupalLogout();
629
    $this->drupalLogin((object) array(
630
      'uid' => 1,
631
      'name' => 'admin',
632
      'pass_raw' => 'admin',
633
    ));
634

    
635
    // The previous login should've triggered a password rehash, so login one
636
    // more time to make sure the new hash is readable.
637
    $this->drupalLogout();
638
    $this->drupalLogin((object) array(
639
      'uid' => 1,
640
      'name' => 'admin',
641
      'pass_raw' => 'admin',
642
    ));
643

    
644
    // Test that the site name is correctly displayed.
645
    $this->assertText('Drupal', 'The site name is correctly displayed.');
646

    
647
    // Verify that the main admin sections are available.
648
    $this->drupalGet('admin');
649
    $this->assertText(t('Content'));
650
    $this->assertText(t('Appearance'));
651
    $this->assertText(t('People'));
652
    $this->assertText(t('Configuration'));
653
    $this->assertText(t('Reports'));
654
    $this->assertText(t('Structure'));
655
    $this->assertText(t('Modules'));
656

    
657
    // Confirm that no {menu_links} entry exists for user/autocomplete.
658
    $result = db_query('SELECT COUNT(*) FROM {menu_links} WHERE link_path = :user_autocomplete', array(':user_autocomplete' => 'user/autocomplete'))->fetchField();
659
    $this->assertFalse($result, 'No {menu_links} entry exists for user/autocomplete');
660
  }
661
}
662

    
663
/**
664
 * Performs point release update tests on a populated database.
665
 *
666
 * Loads an installation of Drupal 7.0 and runs the update process on it.
667
 *
668
 * The install contains the minimal profile modules (along with generated
669
 * content) so that an update from of a site under this profile may be tested.
670
 */
671
class FilledMinimalUpdatePath extends UpdatePathTestCase {
672
  public static function getInfo() {
673
    return array(
674
      'name'  => 'Basic minimal profile update path, populated database',
675
      'description'  => 'Basic update path tests for a minimal profile install with a populated database.',
676
      'group' => 'Upgrade path',
677
    );
678
  }
679

    
680
  public function setUp() {
681
    // Path to the database dump files.
682
    $this->databaseDumpFiles = array(
683
      drupal_get_path('module', 'simpletest') . '/tests/upgrade/drupal-7.filled.minimal.database.php.gz',
684
    );
685
    parent::setUp();
686
  }
687

    
688
  /**
689
   * Tests a successful point release update.
690
   */
691
  public function testFilledStandardUpdate() {
692
    $this->assertTrue($this->performUpgrade(), 'The upgrade was completed successfully.');
693

    
694
    // Hit the frontpage.
695
    $this->drupalGet('');
696
    $this->assertResponse(200);
697

    
698
    // Verify that we are still logged in.
699
    $this->drupalGet('user');
700
    $this->clickLink(t('Edit'));
701
    $this->assertEqual($this->getUrl(), url('user/1/edit', array('absolute' => TRUE)), 'We are still logged in as admin at the end of the upgrade.');
702

    
703
    // Logout and verify that we can login back in with our initial password.
704
    $this->drupalLogout();
705
    $this->drupalLogin((object) array(
706
      'uid' => 1,
707
      'name' => 'admin',
708
      'pass_raw' => 'admin',
709
    ));
710

    
711
    // The previous login should've triggered a password rehash, so login one
712
    // more time to make sure the new hash is readable.
713
    $this->drupalLogout();
714
    $this->drupalLogin((object) array(
715
      'uid' => 1,
716
      'name' => 'admin',
717
      'pass_raw' => 'admin',
718
    ));
719

    
720
    // Test that the site name is correctly displayed.
721
    $this->assertText('Drupal', 'The site name is correctly displayed.');
722

    
723
    // Verify that the main admin sections are available.
724
    $this->drupalGet('admin');
725
    $this->assertText(t('Content'));
726
    $this->assertText(t('Appearance'));
727
    $this->assertText(t('People'));
728
    $this->assertText(t('Configuration'));
729
    $this->assertText(t('Reports'));
730
    $this->assertText(t('Structure'));
731
    $this->assertText(t('Modules'));
732

    
733
    // Confirm that no {menu_links} entry exists for user/autocomplete.
734
    $result = db_query('SELECT COUNT(*) FROM {menu_links} WHERE link_path = :user_autocomplete', array(':user_autocomplete' => 'user/autocomplete'))->fetchField();
735
    $this->assertFalse($result, 'No {menu_links} entry exists for user/autocomplete');
736
  }
737
}