The documentation for both methods is almost the same and states:
// The information_schema table is very slow to query under MySQL 5.0.
// Instead, we try to select from the table and field in question. If it
// fails, the most likely reason is that it does not exist. That is
// dramatically faster than using information_schema.
// @link http://bugs.mysql.com/bug.php?id=19588
// @todo This override should be removed once we require a version of MySQL
// that has that bug fixed.
The MySQL bug has been fixed on 12 Dec 2007 for versions 5.0 and 5.1. The minimum required version that D8 is currently supporting is version 5.5.
Let us do the todo and remove both override methods.
Comment | File | Size | Author |
---|---|---|---|
#13 | 2797141-13.patch | 1.82 KB | andypost |
Issue fork drupal-2797141
Show commands
Start within a Git clone of the project using the version control instructions.
Or, if you do not have SSH keys set up on git.drupalcode.org:
Comments
Comment #2
daffie CreditAttribution: daffie commentedComment #3
daffie CreditAttribution: daffie commentedFor the testbot.
Comment #4
daffie CreditAttribution: daffie commentedIf I compare the testbot runtimes, the ones with the patch are quicker then the ones from automatic testing:
- PHP5.5: 35 min and 37 min;
- PHP5.5: 33 min and 35 min;
- PHP5.5: 18 min and 19 min.
Comment #6
benjifisherThis issue is basically a follow-up to #748340: MySQL-optimized tableExists() implementation, which added the overrides and the comment, so I am adding that as a related issue. I read the discussion there, and the intention is clearly to do what @daffie suggests here.
The one thing I would like to see is a test on a shared host, like Comment 15 on #748340. The comparison in #4 on this issue is encouraging, but the real test comes from a database server "with 2000ish databases". As @crell put it (Comment 41 on #748340), the criterion for removing these methods is "when MySQL stops sucking," and I am not sure this has been met.
To be clear, the bug filed against MySQL has been closed, and I have no evidence that MySQL "still sucks," so I am marking this issue RTBC.
Comment #7
benjifisherMake the title more DRY. Maybe "the MySQL driver" would be easier to read than the fully qualified class name, but I will leave that as is for now.
Comment #8
alexpottThis change looks sensible but reading the last comments on https://bugs.mysql.com/bug.php?id=19588 gives me pause. Some people are reporting it is not truly fixed :(
Can someone do some more research as to whether this is safe to do?
Comment #13
andypostreroll to test on current mysql versions in CI
Comment #14
Ghost of Drupal PastCheck https://stackoverflow.com/a/38778589/308851 for (surprising) benchmarks.
Comment #15
andypost@chx thanks for link but it using mysql 5.0.77... I used to find fresher ones without success
Exception costs as well so querying information schema looks more predictable
Comment #16
Ghost of Drupal PastYes, it's 5.0.77 but if 5.0.77 was already good with over 11 000 tables then we should be good here.
Comment #22
Driskell CreditAttribution: Driskell as a volunteer and at Other Media commentedI've closed https://www.drupal.org/project/drupal/issues/3267207 as a duplicate of this, and added it as related.
There are further benefits to merging this beyond the performance enhancement as noted in the above. There are cases where tableExists is relied upon to check for database connection failure (see Drupal\Core\Installer\InstallerRedirectTrait::shouldRedirectToInstaller). Because of the exception capture in tableExists here it treats any connection failure as a successful "Table does not exist". This causes a redirect to the installer page if there is any loss of connection within a Drupal page load - which is not ideal - and further compounds with another issue where the redirect can get permanently cached in page_cache....
So yes it would be extremely good, both performance wise, and reliability wise, to proceed with this.
Comment #24
daffie CreditAttribution: daffie commentedWe have the 2 overrides for the MySQL database driver because of a bug in MySQL 5.0.
We have dropped support for that version a very long time ago.
The default has been to use the "information_schema" to test schema data, which the overrides do not do.
Somebody on stackoverflow did in 2016 a performance comparison:
Using
SELECT 1 FROM table
is clearly the slowest and that is what the overriddes are using.See: https://stackoverflow.com/questions/8829102/check-if-mysql-table-exists-...
This issue is "blocking" #3267203: Interruption to the database can cache a redirect to the installer page for all users, #3181013: Faulty permanent config cache has been set to the cache backend on failed sql server connection and #2847855: Incorrect statement class caused by race condition when closing and opening the connection.
The patch was already once RTBC and to me the performance bit has been addressed, therefor changing it back to RTBC.
Comment #25
mondrakeI wonder why are we keeping an abstract implementation for
::tableExists()
and::fieldExists()
.That seems MySql specific. PgSql and Sqlite have their own. Oracle would have it own. Dunno about MSSql.
Comment #26
alexpott@mondrake that's a good point but one that could be addressed in a follow-up in my opinion. It's also a far larger change to make \Drupal\Core\Database\Schema::tableExists() abstract. Let's do this to fix the bugs and consider the API ramifications of #25 - I'd guess \Drupal\Core\Database\Schema::findTables() is another thing where an implementation in the abstract class is driver specific.
Committed and pushed 9e5dd04fac to 10.0.x and 30b2a9daa7 to 9.4.x. Thanks!
As this is helping to fix bugs I re-classified the issue and backported to 9.3.x. Committed 115c991 and pushed to 9.3.x. Thanks!
Comment #30
mondrake#26 sure. Filed #3267759: Move driver-specific Schema methods implemented in the abstract class to the driver modules.