Problem

  1. Custom database drivers are using a very special and deeply hidden concept right now.

Proposed solution

  1. Turn database drivers into a regular extension type and use the existing ExtensionDiscovery mechanism to locate them:
    $listing = new ExtensionDiscovery();
    $drivers = $listing->scan('driver');
    

    → scans all ./drivers directories in all origins for database driver extensions, and in turn:

    /sites/default/drivers/mssql.info.yml:
    type: driver
    core: 8.x
    name: Microsoft™ SQL Server
    

Comments

tstoeckler’s picture

+++ b/core/includes/install.inc
@@ -136,9 +136,9 @@ function drupal_get_database_types() {
   $files = file_scan_directory(DRUPAL_ROOT . '/core/lib/Drupal/Core/Database/Driver', $mask, array('recurse' => FALSE));
...
+  $listing = new ExtensionDiscovery();
+  $files += $listing->scan('driver');

Shouldn't the core drivers be moved to /core/drivers then?

sun’s picture

Oh hey, I just stumbled over a very old issue :-)

chx’s picture

Assigned: Unassigned » chx

This falls under the must-for-MongoDB umbrella so I will take it on.

Crell’s picture

Status: Needs review » Postponed (maintainer needs more info)

How is this a must for MongoDB? DBTNG is specifically for SQL databases. Using it for a document DB has *never ever* been a supported feature, nor is it now, nor will it be. (That chx was able to do horrible unholy things to it in the past to make it work doesn't change that fact.)

Honestly given how much work we've done to reduce the importance of SQL databases in general (we're close to being able to run SQL-free, I think) I don't see how this is even necessary. There's really only 2 viable contrib drivers that could exist (Oracle and MS SQL).

tstoeckler’s picture

Status: Postponed (maintainer needs more info) » Needs review

With the recent changes to the extension system this is no longer a major rewrite of the entire extension system, as demonstrated by the patch above.

There's really no reason to do this now. Even if there are not as many as there are modules it is so much nicer to drop them into /modules instead of /core/includes/database or wherever. Most sites don't have an awful lot of themes either, but we still treat them equally to modules.

sun’s picture

Interestingly, there is no dedicated drupal.org project type for database drivers: https://drupal.org/project/add

They are registered and listed in the Database driver module category instead.

In there, I see actual database drivers:

https://drupal.org/project/sqlsrv
https://drupal.org/project/oracle

Partial database drivers (PDO):

https://drupal.org/project/doctrine

Entity/field storages:

https://drupal.org/project/riak_field_storage
https://drupal.org/project/mongo_entity

Not database drivers, nor field storage:

https://drupal.org/project/couchdb

Note that https://drupal.org/project/mongodb does not appear in any list (the project is not tagged at all).

Also note that the vast majority of field storage engines are not categorized as database drivers.


The Database subsystem allows to override the drivers that are shipped with core — e.g., when you need to fix problems that either take very long to get addressed in core or won't be addressed in core.

I'm not sure how exactly that works, but if we'd additionally do what @tstoeckler suggested in #1, then overriding a core database driver would work identically to overriding a core profile/module/theme → just copy/paste the directory into a later extension discovery search directory.


Given these findings, I could see the following options:

  1. Move the MSSQL + Oracle implementations into core and drop support for custom database drivers altogether.
  2. Do what is proposed here and give custom database drivers a proper home.
  3. Do 2) and additionally move the built-in core drivers into /core/drivers.

Lastly, I'm a little confused with regard to what happened to field storage engines... the field_sql_storage module no longer exists in D8; the code seems to live elsewhere now, but I'm unable to locate it right now. — I originally wanted to suggest that it might be worth to convert field storage engines into database driver extensions, too...

Crell’s picture

Field storage engines are gone because storage is all handled at the entity level now. They can't be DB drivers anyway because that's a horrid mixing of layers. DB divers are *just* for abstracting differences in SQL servers. That's *it*. Everything else MUST be done at a higher level. (Document DBs, Field storage engines, etc.)

We can't even keep up with supporting SQLite and Postgres in core now; moving MSSQL and Oracle into core would in no way help them get support, and would probably just slow the release of D8 because we'd feel compelled to actually test them, something extremely few people even have the tools to do. (Plus, I am firmly against us including drivers for non-free databases in core.)

tstoeckler’s picture

Do 2) and additionally move the built-in core drivers into /core/drivers.

We should absolutely do this. Not sure if it's easier or harder to do this directly in this issue, but we should definitely do it.

chx’s picture

> How is this a must for MongoDB?

I will be shocked if every SQL query will become, indeed pluggable by the time of the release. One can hope of course, with the recent forumrepository and path patches... we will see. It's Plan B, essentially: revive mongodb_dbtng for the very few remaining queries (and map them by query string to mongodb helper).

tstoeckler’s picture

StatusFileSize
new37.05 KB

Oh just realized now that this is still assigned to you @chx, hope this didn't duplicate any work. Also, I just now realized there's a patch already here, so sorry that there's no interdiff.

This installs on my system. It goes a step further as the original patch in that it also converts the existing driver types to the new system.

I wasn't sure how to do the namespacing of the respective classes, would love some thoughts on that.

We also probably want to move label and description of the database drivers into the YAML files, that is not done so far.

Let's see.

Edit: Also the core: 8.x validation that is mentioned in the IS is missing so far.

Status: Needs review » Needs work

The last submitted patch, 10: 2209307-driver-extension.patch, failed testing.

tstoeckler’s picture

Ahh so I forgot to register the driver namespaces during regular runtime. Not sure where to do that. Also, should we just register all available namespaces (which is what we do now, implicitly) or should there be some sort of installation status for drivers?

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new804 bytes
new37.84 KB

This just hacks the namespace-registering into DrupalKernel::boot(). Let's see if it's green. Not sure if there's a better place.

Status: Needs review » Needs work

The last submitted patch, 13: 2209307-13-driver-extension.patch, failed testing.

sun’s picture

Assigned: chx » Unassigned
Status: Needs work » Needs review
StatusFileSize
new41.21 KB
new7.47 KB

Fixed installer + bootstrap.

I'm able to install locally. Tests may require further tweaks.

We should rename the extension type name "driver" + directory name "drivers", because as @Crell mentioned, it's about SQL databases (RDBMS) only. Since the integrating component is "Database", the most obvious choice would be type: database + ./databases.

tstoeckler’s picture

Awesome, thanks a lot! Makes perfect sense to register the namespace in addConnectionInfo().

+++ b/core/includes/install.inc
@@ -135,9 +135,10 @@ function drupal_detect_database_types() {
+  $discovery->setProfileDirectories(array());

So if I understand this correctly, this will allow selecting database drivers from profiles other than that selected in a previous step during the installation. Is there a specific reason for this?

sun’s picture

Oh, good catch. I added that initially in the hope it would make things work, but it didn't. Instead, the cause was the lack of a filesystem path ('cos database must work before anything else) + the missing namespace/driver-class adjustments.

You're right, drupal_get_profile() uses the already selected installer parameter, so that line should be obsolete.

Next to the potential rename mentioned in #15, we might need to adjust WebTestBase::installParameters().

Status: Needs review » Needs work

The last submitted patch, 15: db.drivers.15.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
Related issues: +#1975220: Allow a Composer user to manage Drupal, modules, and PHP dependencies with a custom root composer.json
StatusFileSize
new906 bytes
new413.67 KB

Reviving this one.

Miraculously, Git was able to merge this without any problems.

This also fixes the MigrateTestCase issues by registering database drivers in unit tests.

tstoeckler’s picture

StatusFileSize
new42.13 KB

Ahh, this is one of those patches where forgetting -C -M is not a good idea. This is the same patch except a teeny-tiny bit more readable.

The last submitted patch, 19: 2209307-19-driver-extension.patch, failed testing.

Status: Needs review » Needs work

The last submitted patch, 20: 2209307-20.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new1.69 KB
new415.45 KB

Interestingly I get completely different fails than the testbot but this let's me install both through the UI and Drush. Let's see.

Status: Needs review » Needs work

The last submitted patch, 23: 2209307-23-driver-extension.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new1.37 KB
new10.74 KB
new43.66 KB

I don't know how I managed to do it, but somehow I switched up the Truncate classes between MySQL and PostreSQL.

While I was at it I changed all the moved @file declarations from "Definition of" to "Contains".

Thus, 2 interdiffs.

And this time with -C -M again. Although beware that for the Merge classes Git will tell you that I moved the MySQL one to SQLite and vice versa. This is because those files are identical but for the namespace, which changes anyway, so that they have the same similarity index.

Status: Needs review » Needs work

The last submitted patch, 25: 2209307-25-driver-extension.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new843 bytes
new44.49 KB

Meh, I have no idea yet how to resolve these hacks properly, but let's see if we can get this green first.

Status: Needs review » Needs work

The last submitted patch, 27: 2209307-27-driver-extension.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new2.21 KB
new47.44 KB

This should fix the remaining test failures except the one that caused the fatal, which I didn't figure out which one it was.

I've added some debug code (not in the interdiff, to avoid confusion) to help sort that out. Let's see.

Status: Needs review » Needs work

The last submitted patch, 29: 2209307-29-driver-extension.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new47.45 KB

Meh, so much for that debug code. Next try.

Status: Needs review » Needs work

The last submitted patch, 31: 2209307-31-driver-extension.patch, failed testing.

tstoeckler’s picture

Status: Needs work » Needs review
StatusFileSize
new5.47 KB
new0 bytes

Let's see.

tstoeckler’s picture

StatusFileSize
new51.4 KB

Yeah...

Status: Needs review » Needs work

The last submitted patch, 34: 2209307-34-driver-extension.patch, failed testing.

andypost’s picture

Issue tags: +Needs reroll
druprad’s picture

Status: Needs work » Needs review
Issue tags: -Needs reroll
StatusFileSize
new423.49 KB

Updated patch re-rolled for comment #34

Status: Needs review » Needs work

The last submitted patch, 38: driver-extension-2209307-38.patch, failed testing.

The last submitted patch, 38: driver-extension-2209307-38.patch, failed testing.

andypost’s picture

Issue tags: +Needs reroll

wrong merge

andypost’s picture

Version: 8.0.x-dev » 8.1.x-dev

Version: 8.1.x-dev » 8.2.x-dev

Drupal 8.1.0-beta1 was released on March 2, 2016, which means new developments and disruptive changes should now be targeted against the 8.2.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

rteijeiro’s picture

Status: Needs work » Closed (outdated)
Issue tags: -Needs reroll

I think this issue needs new patch, not a re-roll. I checked the patch code and there is no core/lib/Drupal/Core/Database/Driver/fake folder.

Closed it as outdated but feel free to reopen it.

andypost’s picture

Status: Closed (outdated) » Needs work

I still sure that db drivers should be extensions, there's more then "fake" in last patch

andypost’s picture

daffie’s picture

@tstoeckler: I have tried to reroll your patch and I am doing something wrong, because I am unable to do a complete run of the install process. Can you reroll your own patch? I think this is a important issue and I will do reviews to get the issue fixed.

I think this is an important issue, because I want to make Drupal better. Lets look at Drupal with a outside-in approach from the viewpoint of contrib database driver creator and its user.

Creating a contrib database driver is not an easy task. Finding what to do and how to do it is not easy. An extra problem is that it is not only the driver any more. There are also services that need to be overridden. Which services that need to be overridden and which ones aren’t is also not easy to determine.
As contrib database driver developer you want your driver to pass all the core tests. Only there is no way to make minor changes to those test because they are in core. The by core supported database drivers do make minor changes to core tests because they can and they are needed. Contrib database drivers should be able to do the same.

The next problem is that you should not hack Drupal core in production site. A contrib database driver needs to place their contrib database driver files in DRUPAL_ROOT/core/lib/Drupal/Core/Database/Driver. For me this is hacking core and we should never have to do that.

If I where to create a contrib database driver I would use the by Drupal core supported drivers as my main example. And those drivers are completely integrated in core. The different parts are hidden/scattered in the Drupal core. The driver is easily found, but the overridden services are not and the same for the driver changed tests. A contrib database driver developer should not be searching the whole of Drupal core to find out how to make his/her contrib database driver.

How to make it better.

Move the Drupal core database drivers to DRUPAL_ROOT/core/databases directory and the contrib ones should live in DRUPAL_ROOT/databases. First: the directory name “databases” is more easily understood then “drivers”. Second: There is more in the directory then the driver alone.
The location for the for the driver should be DRUPAL_ROOT/core/databases/mysql/src/Driver for the MySQL driver and DRUPAL_ROOT/databases/oracle/src/Driver for the Oracle driver. The specific overridden services go to DRUPAL_ROOT/core/databases/mysql/src and DRUPAL_ROOT/databases/oracle/src. The overridden tests should go to DRUPAL_ROOT/core/databases/mysql/tests and DRUPAL_ROOT/databases/oracle/tests.
Now the database drivers for MySQL, PostgreSQL and SQLite have become the examples for the contrib ones. Those are not only Oracle and MS-SQL but also other RDBD’s as DB2, Teradata, SAP-server etc. There are also cloud based databases as Amazon Redshift, AzureSQL etc. In the future we should start supporting NoSQL databases as MongoDB, Cassandra and others.

It is not that I personally would like to add as many databases as possible to Drupal for the fun of it, but I think that the usage of Drupal will grow much by supporting many more databases. One of the great strengths of Linux is that it will run almost anywhere. Lets do the same with Drupal. That does not mean that we should add more databases in Drupal core. A better option is it to make easier for others to add their own contrib database driver.

Version: 8.2.x-dev » 8.3.x-dev

Drupal 8.2.0-beta1 was released on August 3, 2016, which means new developments and disruptive changes should now be targeted against the 8.3.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

ankitadmane’s picture

Hi daffie

how can i connect to redshift database as earlier you mention we need an connection with AWS redshift as well

daffie’s picture

@ankit: The AWS Redshift database is based on the Postgres 8 database and we have a Drupal driver for Postgres 9. So what I would do is to use our Postgres 9 driver and test how well that does. If you find any problem, then please report them by creating bug reports.

david_garcia’s picture

From #47:

The next problem is that you should not hack Drupal core in production site. A contrib database driver needs to place their contrib database driver files in DRUPAL_ROOT/core/lib/Drupal/Core/Database/Driver. For me this is hacking core and we should never have to do that.

Actually you do not need to "hack" core, contrib database driver are supposed to be sitting in a "\drivers\lib\Drupal\Driver\Database" directory, which is out of core.

Database access is isolated and easy to plug into (I can tell that from being the MS SQL Server driver maintainer), but it's true that to get it running the first time you need a lot of reverse engineering. But for anyone that wants to write a new database driver they could easily take a look at one of the current contrib implementations and elaborate on top of that.

It is true that some parts of core have specific database logic (such as doing one thing for SQLite and other stuff for the rest of drivers) but there is no approach I can think of to deal with that, except for overriding whatever part of core is doing that (which should by the way be easier now in Drupal 8 as overriding core code/services is much much much more easier than it was in Drupal 7).

What I really miss the ability for the driver to tell the testing framework to skip some tests (or to override them with custom implementations).

daffie’s picture

Actually you do not need to "hack" core, contrib database driver are supposed to be sitting in a "\drivers\lib\Drupal\Driver\Database" directory, which is out of core.

@david_garcia: I did not know there is a specific location for contrib database drivers. Thank you for the info!

What I really miss the ability for the driver to tell the testing framework to skip some tests (or to override them with custom implementations).

@david_garcia: If you want to work on that, create an issue for it and I will help by doing the reviewing.

Version: 8.3.x-dev » 8.4.x-dev

Drupal 8.3.0-alpha1 will be released the week of January 30, 2017, which means new developments and disruptive changes should now be targeted against the 8.4.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.4.x-dev » 8.5.x-dev

Drupal 8.4.0-alpha1 will be released the week of July 31, 2017, which means new developments and disruptive changes should now be targeted against the 8.5.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.5.x-dev » 8.6.x-dev

Drupal 8.5.0-alpha1 will be released the week of January 17, 2018, which means new developments and disruptive changes should now be targeted against the 8.6.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.6.x-dev » 8.7.x-dev

Drupal 8.6.0-alpha1 will be released the week of July 16, 2018, which means new developments and disruptive changes should now be targeted against the 8.7.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.7.x-dev » 8.8.x-dev

Drupal 8.7.0-alpha1 will be released the week of March 11, 2019, which means new developments and disruptive changes should now be targeted against the 8.8.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

Version: 8.8.x-dev » 8.9.x-dev

Drupal 8.8.0-alpha1 will be released the week of October 14th, 2019, which means new developments and disruptive changes should now be targeted against the 8.9.x-dev branch. (Any changes to 8.9.x will also be committed to 9.0.x in preparation for Drupal 9’s release, but some changes like significant feature additions will be deferred to 9.1.x.). For more information see the Drupal 8 and 9 minor version schedule and the Allowed changes during the Drupal 8 and 9 release cycles.

Version: 8.9.x-dev » 9.1.x-dev

Drupal 8.9.0-beta1 was released on March 20, 2020. 8.9.x is the final, long-term support (LTS) minor release of Drupal 8, which means new developments and disruptive changes should now be targeted against the 9.1.x-dev branch. For more information see the Drupal 8 and 9 minor version schedule and the Allowed changes during the Drupal 8 and 9 release cycles.