Two new exceptions have been added to the Drupal\Core\Database\Exception namespace:
- SchemaTableDoesNotExistException extends SchemaObjectDoesNotExistException.
- SchemaTableAlreadyExistsException extends SchemaObjectExistsException.
The MySQL, PostgreSQL and SQLite drivers throw them when a query fails because a table is missing or already exists. Core will later rely on these exceptions to create tables on demand.
ExceptionHandler has a new protected method, rethrowNormalizedException(). The base handleStatementException() and handleExecutionException() call it for every \PDOException. A driver maps its native error codes by overriding this method. For example, the PostgreSQL driver does this:
protected function rethrowNormalizedException(
\Exception $exception,
int|string $sqlState,
?int $errorCode,
string $queryString,
array $arguments,
array $options = [],
): never {
$info = new SqlExecutionInfo($queryString, $arguments, $options);
$message = $info->appendToMessage($exception->getMessage());
match ($sqlState) {
'42P01' => throw new SchemaTableDoesNotExistException($message, (int) $sqlState, $exception, $info),
'42P07' => throw new SchemaTableAlreadyExistsException($message, (int) $sqlState, $exception, $info),
default => parent::rethrowNormalizedException($exception, $sqlState, $errorCode, $queryString, $arguments, $options),
};
}
DatabaseExceptionWrapper has a new optional fourth constructor argument, ?SqlExecutionInfo $info.