New Major Release: Doctrine DBAL 3.0

Posted on November 17, 2020 by Benjamin Eberlei


We have released a new major version of Doctrine DBAL, version 3.0.0. This new major version comes almost 10 years after DBAL 2.0 was released on December 2010, then coupled into the ORM 2.0.

Today Doctrine DBAL is released independent of the ORM, thanks to Composer and sees its new major version before the ORM.

This release was made possible foremost by Sergei Morozov, our primary DBAL maintainer, who has spent countless hours working on the package since 2016. Thank you!

See the Release Notes for a detailed list of changes.

This blog post covers a few of the major changes in a bit more detail to give you an idea of what DBAL 3.0 looks like.

Decouple DBAL from PDO

The major theme of DBAL 3.0 is the decoupling from PDO. Instead of copying the API verbatim like DBAL 2.0 did, DBAL 3.0 grows it into a better, more usable direction.

We extract all fetch-methods from the Statement class and moved them to a new Result class that is returned from Statement::execute.

Old code:

$statement = $connection->prepare('SELECT * FROM tbl WHERE col = ?');
$statement->bindParam(1, $value);
$statement->execute();

while ($row = $statement->fetch()) {
}

New Code:

$statement = $connection->prepare('SELECT * FROM tbl WHERE col = ?');
$statement->bindParam(1, $value);
$result = $statement->execute();

while ($row = $result->fetchAssociative()) {
}

The Result Fetching API was improved to use more human-readable names:

// Old
$stmt->fetch();
$stmt->fetch(PDO::FETCH_ARRAY);
$stmt->fetchColumn();
$stmt->fetchAll();

// New
$stmt->fetchAssociative();
$stmt->fetchNumeric();
$stmt->fetchOne();
$stmt->fetchAllAssociative();

Many more changes have been made on the public API and also for the internals, but these are the most visible ones.

Upgrading to DBAL 3 from 2

DBAL 3 is a real new major release with significant changes to the public API. Depending on your codebase a migration could require non-trivial work. However we do not intend to leave you hanging with DBAL 2 and a future migration:

  1. We intend to support DBAL 2.12 a while longer, including support for the upcoming PHP 8.0, so that there is no rush for you to upgrade to DBAL 3.

  2. DBAL 2.12 already includes forwards compatible API changes for all the new APIs, so that you can migrate your code step by step to the new APIs already.

  3. Deprecated methods in DBAL 2.12 are tagged with the @deprecated doc-block and static analysis tools such as Psalm, PHPStan and Phan can already help you detect using or calling this deprecated code in your application.

  4. We intend to release another version of DBAL 2 which includes optional triggering of deprecation messages at runtime similar to how Symfony deals with deprecations.

As you can see, with these approaches it will be possible for you to smoothly migrate your application from DBAL 2 to 3.

As a note to libraries and frameworks that need to support multiple versions of Doctrine DBAL: We recommend you start out with DBAL 2.12 and migrate all usages of deprecated APIs to their newer counterparts. Then once you have managed this, you can allow 3.0 and try to get your code working with both versions. Unfortunately this may not be possible for all cases, because we could not provide replacement APIs for everything and some features have been dropped between DBAL 2 and 3.

Outlook

DBAL 3 is a huge first step towards a modern database abstraction layer, independent from the legacy of PHP and PDO API design. In the future we plan to improve DBAL in other ways that we haven't gotten around yet, such as more API modernization, increased safety with use of strict scalar types in the code base, better error handling and more.