Issue #3135629 by alexpott, dww, daffie, jungle, Rkumar, balsama, xjm: Minimum MySQL version requirement is not confirmed when upgrading existing sites from Drupal 8 to Drupal 9

(cherry picked from commit cefc84f9b4)
merge-requests/64/head
catch 2020-05-14 15:25:41 +01:00
parent 0423e3b46a
commit 19e17d5570
8 changed files with 195 additions and 1 deletions

View File

@ -150,6 +150,19 @@ abstract class Tasks {
return $this->results['fail'];
}
/**
* Checks engine version requirements for the status report.
*
* This method is called during runtime and update requirements checks.
*
* @return \Drupal\Core\StringTranslation\TranslatableMarkup[]
* A list of error messages.
*/
final public function engineVersionRequirementsCheck() {
$this->checkEngineVersion();
return $this->results['fail'];
}
/**
* Check if we can connect to the database.
*/

View File

@ -435,9 +435,11 @@ function system_requirements($phase) {
$requirements['database_extensions']['value'] = t('Enabled');
}
}
else {
if ($phase === 'runtime' || $phase === 'update') {
// Database information.
$class = Database::getConnection()->getDriverClass('Install\\Tasks');
/** @var \Drupal\Core\Database\Install\Tasks $tasks */
$tasks = new $class();
$requirements['database_system'] = [
'title' => t('Database system'),
@ -447,6 +449,19 @@ function system_requirements($phase) {
'title' => t('Database system version'),
'value' => Database::getConnection()->version(),
];
$errors = $tasks->engineVersionRequirementsCheck();
$error_count = count($errors);
if ($error_count > 0) {
$error_message = [
'#theme' => 'item_list',
'#items' => $errors,
// Use the comma-list style to display a single error without bullets.
'#context' => ['list_style' => $error_count === 1 ? 'comma-list' : ''],
];
$requirements['database_system_version']['severity'] = REQUIREMENT_ERROR;
$requirements['database_system_version']['description'] = $error_message;
}
}
// Test PHP memory_limit

View File

@ -0,0 +1,49 @@
<?php
namespace Drupal\driver_test\Driver\Database\DrivertestMysqlDeprecatedVersion;
use Drupal\Core\Database\Driver\mysql\Connection as CoreConnection;
/**
* MySQL test implementation of \Drupal\Core\Database\Connection.
*/
class Connection extends CoreConnection {
/**
* Hardcoded database server version.
*
* Faking that we are on a deprecated database.
*
* @var string
*/
protected $databaseVersion = '10.2.31-MariaDB-1:10.2.31+maria~bionic-log';
/**
* {@inheritdoc}
*/
public function driver() {
return 'DrivertestMysqlDeprecatedVersion';
}
/**
* {@inheritdoc}
*/
public function isMariaDb(): bool {
return TRUE;
}
/**
* {@inheritdoc}
*/
public function version() {
return $this->databaseVersion;
}
/**
* {@inheritdoc}
*/
protected function getServerVersion(): string {
return $this->databaseVersion;
}
}

View File

@ -0,0 +1,10 @@
<?php
namespace Drupal\driver_test\Driver\Database\DrivertestMysqlDeprecatedVersion;
use Drupal\Core\Database\Driver\mysql\Insert as CoreInsert;
/**
* MySQL test implementation of \Drupal\Core\Database\Query\Insert.
*/
class Insert extends CoreInsert {}

View File

@ -0,0 +1,19 @@
<?php
namespace Drupal\driver_test\Driver\Database\DrivertestMysqlDeprecatedVersion\Install;
use Drupal\Core\Database\Driver\mysql\Install\Tasks as CoreTasks;
/**
* Specifies installation tasks for MySQL test databases.
*/
class Tasks extends CoreTasks {
/**
* {@inheritdoc}
*/
public function name() {
return t('MySQL deprecated version by the driver_test module');
}
}

View File

@ -0,0 +1,10 @@
<?php
namespace Drupal\driver_test\Driver\Database\DrivertestMysqlDeprecatedVersion;
use Drupal\Core\Database\Driver\mysql\Schema as CoreSchema;
/**
* MySQL test implementation of \Drupal\Core\Database\Schema.
*/
class Schema extends CoreSchema {}

View File

@ -0,0 +1,10 @@
<?php
namespace Drupal\driver_test\Driver\Database\DrivertestMysqlDeprecatedVersion;
use Drupal\Core\Database\Driver\mysql\Upsert as CoreUpsert;
/**
* MySQL test implementation of \Drupal\Core\Database\Query\Upsert.
*/
class Upsert extends CoreUpsert {}

View File

@ -0,0 +1,68 @@
<?php
namespace Drupal\Tests\system\Functional\Update;
use Drupal\Core\Database\Database;
use Drupal\Core\Url;
use Drupal\Tests\BrowserTestBase;
use Drupal\Tests\UpdatePathTestTrait;
/**
* Tests that updates fail if the database does not meet the minimum version.
*
* @group Update
*/
class DatabaseVersionCheckUpdateTest extends BrowserTestBase {
use UpdatePathTestTrait;
/**
* {@inheritdoc}
*/
protected $defaultTheme = 'stark';
/**
* {@inheritdoc}
*/
protected function setUp(): void {
parent::setUp();
$this->ensureUpdatesToRun();
}
/**
* Tests that updates fail if the database does not meet the minimum version.
*/
public function testUpdate() {
if (Database::getConnection()->driver() !== 'mysql') {
$this->markTestSkipped('This test only works with the mysql driver');
}
// Use a database driver that reports a fake database version that does
// not meet requirements. Only change the necessary settings in the database
// settings array so that run-tests.sh continues to work.
$autoload = Database::findDriverAutoloadDirectory('Drupal\driver_test\Driver\Database\DrivertestMysqlDeprecatedVersion', \Drupal::root());
$settings['databases']['default']['default']['driver'] = (object) [
'value' => 'DrivertestMysqlDeprecatedVersion',
'required' => TRUE,
];
$settings['databases']['default']['default']['namespace'] = (object) [
'value' => 'Drupal\\driver_test\\Driver\\Database\\DrivertestMysqlDeprecatedVersion',
'required' => TRUE,
];
$settings['databases']['default']['default']['autoload'] = (object) [
'value' => $autoload,
'required' => TRUE,
];
$settings['settings'] = [
'update_free_access' => (object) [
'value' => TRUE,
'required' => TRUE,
],
];
$this->writeSettings($settings);
$this->drupalGet(Url::fromRoute('system.db_update'));
$this->assertSession()->pageTextContains('Errors found');
$this->assertSession()->pageTextContains('The database server version 10.2.31-MariaDB-1:10.2.31+maria~bionic-log is less than the minimum required version');
}
}