diff -u b/core/modules/mysql/mysql.install b/core/modules/mysql/mysql.install --- b/core/modules/mysql/mysql.install +++ b/core/modules/mysql/mysql.install @@ -31,8 +31,7 @@ $query = 'SELECT @@SESSION.transaction_isolation'; } - $tables_missing_key = []; - $missing_primary_key = FALSE; + $tables_missing_primary_key = []; $tables = $connection->schema()->findTables('%'); $isolation_level = $connection->query($query)->fetchField(); $severity_level = REQUIREMENT_INFO; @@ -41,22 +40,21 @@ foreach ($tables as $table) { $primary_key_column = Database::getConnection()->query("SHOW KEYS FROM {" . $table . "} WHERE Key_name = 'PRIMARY'")->fetchAllAssoc('Column_name'); if (empty($primary_key_column)) { - $missing_primary_key = TRUE; - $tables_missing_key[] = $table; + $tables_missing_primary_key[] = $table; } } - $tables_missing_key_text = 'For this to work properly all tables should have a primary key. The following table(s) do no have a primary key: ' . implode(', ', $tables_missing_key); + $tables_missing_primary_key = 'For this to work properly all tables should have a primary key. The following table(s) do no have a primary key: ' . implode(', ', $tables_missing_primary_key); - if ($isolation_level == 'READ-COMMITTED' && $missing_primary_key) { + if ($isolation_level == 'READ-COMMITTED' && !empty($tables_missing_primary_key)) { $severity_level = REQUIREMENT_ERROR; - $description = 'This site is using the database transaction level "READ COMMITTED". ' . $tables_missing_key_text; + $description = 'This site is using the database transaction level "READ COMMITTED". ' . !empty($tables_missing_primary_key); } elseif ($isolation_level == 'REPEATABLE-READ') { $severity_level = REQUIREMENT_WARNING; $description = 'This site is using the database transaction level "REPEATABLE READ". The recommended database transaction level for Drupal is "READ COMMITTED".'; - if ($missing_primary_key) { - $description .= ' ' . $tables_missing_key_text; + if ($tables_missing_primary_key) { + $description .= ' ' . $tables_missing_primary_key; } } elseif ($isolation_level == 'READ-UNCOMMITTED' || $isolation_level == 'SERIALIZED') { diff -u b/core/modules/mysql/src/Driver/Database/mysql/Connection.php b/core/modules/mysql/src/Driver/Database/mysql/Connection.php --- b/core/modules/mysql/src/Driver/Database/mysql/Connection.php +++ b/core/modules/mysql/src/Driver/Database/mysql/Connection.php @@ -205,11 +205,9 @@ ]; // Only set the transaction isolation level when the connection option has // been set to 'READ COMMITTED' or 'REPEATABLE READ'. - if (!empty($connection_options['isolation_level']) && - in_array($connection_options['isolation_level'], - ['READ COMMITTED', 'REPEATABLE READ'], TRUE)) { + if (!empty($connection_options['isolation_level']) && in_array(strtoupper($connection_options['isolation_level']), ['READ COMMITTED', 'REPEATABLE READ'], TRUE)) { $connection_options['init_commands'] += [ - 'isolation_level' => 'SET SESSION TRANSACTION ISOLATION LEVEL ' . $connection_options['isolation_level'], + 'isolation_level' => 'SET SESSION TRANSACTION ISOLATION LEVEL ' . strtoupper($connection_options['isolation_level']), ]; } reverted: --- b/core/modules/mysql/tests/src/Functional/mysql/PrimaryKeyExistsTest.php +++ /dev/null @@ -1,68 +0,0 @@ -drupalCreateUser([ - 'administer site configuration', - 'access site reports', - ]); - $this->drupalLogin($admin_user); - - // Check the message is not a warning. - $this->drupalGet('admin/reports/status'); - $elements = $this->xpath('//details[@class="system-status-report__entry"]//div[contains(text(), :text)]', [ - ':text' => 'To insure correct operation with READ-COMMITTED, ensure all tables have a primary key.', - ]); - $this->assertCount(1, $elements); - $this->assertStringNotContainsString('warning', $elements[0]->getParent()->getParent()->find('css', 'summary')->getAttribute('class')); - - $connection->schema()->createTable('test_primary_key', [ - 'fields' => [ - 'id' => [ - 'type' => 'int', - 'unsigned' => TRUE, - 'not null' => TRUE, - ], - ], - ]); - - $this->assertTrue($connection->schema()->tableExists('test_primary_key')); - - // Check the message is not a warning. - $this->drupalGet('admin/reports/status'); - $elements = $this->xpath('//details[@class="system-status-report__entry"]//div[contains(text(), :text)]', [ - ':text' => 'To insure correct operation with READ-COMMITTED, ensure all tables have a primary key. The following table(s) do not contain a primary key: test_primary_key', - ]); - $this->assertCount(1, $elements); - // Ensure it is a warning. - $this->assertStringContainsString('warning', $elements[0]->getParent()->getParent()->find('css', 'summary')->getAttribute('class')); - - } - -} reverted: --- b/core/phpstan-baseline.neon +++ a/core/phpstan-baseline.neon @@ -2955,6 +2955,11 @@ count: 12 path: tests/Drupal/KernelTests/Core/Cache/GenericCacheBackendUnitTestBase.php + - + message: "#^Variable \\$expected_driver might not be defined\\.$#" + count: 2 + path: tests/Drupal/KernelTests/Core/Database/DriverSpecificKernelTestBase.php + - message: "#^Relying on entity queries to check access by default is deprecated in drupal\\:9\\.2\\.0 and an error will be thrown from drupal\\:10\\.0\\.0\\. Call \\\\Drupal\\\\Core\\\\Entity\\\\Query\\\\QueryInterface\\:\\:accessCheck\\(\\) with TRUE or FALSE to specify whether access should be checked\\.$#" count: 75 reverted: --- b/core/tests/Drupal/FunctionalTests/Core/Database/DriverSpecificBrowserTestBase.php +++ /dev/null @@ -1,21 +0,0 @@ -root = static::getDrupalRoot(); - $expected_driver = ''; $connectionInfo = $this->getDatabaseConnectionInfo(); $test_class_parts = explode('\\', get_class($this)); $expected_provider = $test_class_parts[2] ?? ''; reverted: --- b/core/tests/Drupal/Tests/DriverSpecificTrait.php +++ /dev/null @@ -1,59 +0,0 @@ -root = static::getDrupalRoot(); - $expected_driver = ''; - - if (method_exists($this, 'getDatabaseConnectionInfo')) { - $connectionInfo = $this->getDatabaseConnectionInfo(); - } - else { - $connectionInfo = Database::getConnectionInfo(); - } $test_class_parts = explode('\\', get_class($this)); - $expected_provider = $test_class_parts[2] ?? ''; - for ($i = 3; $i < count($test_class_parts); $i++) { - if (in_array($test_class_parts[$i], ['Kernel', 'Functional'], TRUE)) { - $expected_driver = $test_class_parts[$i + 1] ?? ''; - break; - } - } - if ($connectionInfo['default']['driver'] !== $expected_driver) { - $this->markTestSkipped("This test only runs for the database driver '$expected_driver'. Current database driver is '{$connectionInfo['default']['driver']}'."); - } - - parent::setUp(); - $this->connection = Database::getConnection(); - - // After database initialization, the database driver may be not provided - // by the expected module; skip test in that case. - $running_provider = $this->connection->getProvider(); - $running_driver = $this->connection->driver(); - if ($running_provider !== $expected_provider || $running_driver !== $expected_driver) { - $this->markTestSkipped("This test only runs for the database driver '$expected_driver' provided by the '$expected_provider' module. Connected database driver is '$running_driver' provided by '$running_provider'."); - } - } - -}