-
-
Notifications
You must be signed in to change notification settings - Fork 1.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Optimize schema managers' ::listTables() methods #4882
Conversation
Thanks for the patch, @mondrake. I like the idea as such. I've seen a similar approach implemented in a proprietary codebase for exactly the same reason. The patch looks like a good start but it will require some rework before we can accept it:
Please retarget against |
Are you asking for help in implementing this feature or for guidance on what to do? The way I see it is:
|
Thanks for guidance @morozov, I will give this a try. |
@morozov this is going as far as I could get before starting breaking tests that check identicality of SQL strings generated to fetch database assets metadata, for example Can I get feedback whether this is in the right direction and is it OK to break such tests moving on? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It looks like you're moving in the right direction, @mondrake. As for breaking the tests that cover the generated SQL, I'd say that they do more harm than good. It's fine to temporarily remove the failing ones rather than fix them.
If it turns out that those were the only tests that covered some lines, we'll have to think about replacing them with the functional tests that do not test the SQL. This is how such tests should have been written in the first place.
Fixed some points from last review by @morozov. Posted progress. Still to go. |
Also |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@mondrake please rebase on the latest 3.2.x
to address the build issue. I haven't checked the actual new queries in detail but it looks like we're getting somewhere. Great work so far!
@morozov I added conversions for all platforms, I know they're rough around the edges, but I worked by reverse engineering and reimplementing. Reviews welcome. |
@mondrake sorry, I missed your comment. Thanks a lot! I want to go over the resulting changes once again and see if we can/should generalize anything. Specifically:
My idea is to introduce the following family of interfaces: interface TableIntrospector
{
function getTables(string $databaseName, string $tableName): Table;
/**
* @return list<Table>
*/
function getDatabaseTables(string $databaseName): array;
}
interface ColumnIntrospector
{
/**
* @return list<Column>
*/
function getTableColumns(string $databaseName, string $tableName): array;
/**
* @return array<string,list<Column>>
*/
function getDatabaseColumns(string $databaseName): array;
}
// and so on for indexes, foreign keys and options There will be an implementation of all these interfaces for every platform, and the job of each platform-specific schema manager will be just to build a proper introspector. The logic of building the table or a list of tables from parts should be the same for all platforms and could be implemented once in the base class. |
@mondrake I tried to prototype the new API that I had in mind but it looks like implementing it would require some more unforeseen refactoring. I wouldn't like to delay merging this PR any further, so I think the new API could be introduced later. But I believe the issues mentioned above still need to be addressed before this PR can be merged:
I.e. we need to implement some common code in the Additionally, instead of merging the upstream branch into yours, please rebase it. Otherwise, it would have to be rebased before the merge, and the same merge conflicts would have to be addressed again. |
Thanks @morozov, I'll give a try but if you're quicker do not hesitate. Sorry for the mess with branches' merges and rebases, I will git educated one day, eventually :) |
@morozov I changed the listTables() implementation in AbstractSchemaManager to be able to use the new methods and removed the class specific implementations, so to standardize a bit. If this is OK I will follow up with listTableDetails() and finally rebasing. |
@morozov in order to allow BC, I introduced a new abstract class |
* | ||
* @template T of AbstractPlatform | ||
*/ | ||
abstract class AbstractDatabaseIntrospectionSchemaManager extends AbstractSchemaManager |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It looks like the changes I tried to avoid mentioned in #4882 (comment) are inevitable. Instead of introducing a new proper API we have to introduce a temporary API. This temporary API would have to be broken later in order be replaced with the proper one which is unfortunate.
Probably, it makes sense to continue with the introduction of the Introspector API as I tried earlier. See the PoC:
02608ba...morozov:optimize-list-tables
What stopped me there is that I didn't anticipate at that time that the introspectors will have to depend on the platform in order to convert the type introspected from the database (e.g. VARCHAR
) to the DBAL type (e.g. "string").
We have two options here:
- Make them accept a platform in the constructor (sort of okay).
- Or even better, introduce a new interface that would do only the mapping and accept it instead of the platform. For instance:
interface TypeMapper { function mapType(string $type, array $options): Type; } abstract class AbstractPlatform implements TypeMapper { }
This is as much as I've done here. Do you think you could explore this idea further?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@greg0ire if we're taking the route described above, it would be nice to get #5107 wrapped up before we proceed. This would eliminate the need to overhaul the logic of extracting types from the comments.
Do you believe we are in agreement that extraction of types from the comments is no longer necessary?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@morozov honestly I'd rather leave to you to take next steps if you do not mind - this is going so far from the original scope that I am afraid I would rather slow down the process now by reiterating on your input.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do you believe we are in agreement that extraction of types from the comments is no longer necessary?
Yes, but I think we should wait for doctrine/migrations#1227 to be done first, otherwise won't we get a lot of support?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@morozov honestly I'd rather leave to you to take next steps if you do not mind - this is going so far from the original scope that I am afraid I would rather slow down the process now by reiterating on your input.
Sounds fair. I can definitely own it as I see it as an important improvement but I cannot commit to any fixed timeline. I'll take over if it works for you, and thanks for taking it much further than originally planned, @mondrake!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All yours @morozov, and thanks to you for your guidance.
Resolved conficts. |
@mondrake I will close this PR and continue working on the improvement in #5268. Resolving conflicts with the upstream by merging is counterproductive (#4882 (comment)). |
Thanks @morozov. Yes, I have not learnt yet how to rebase properly. I tried but ended up in endless loops of conflicts. Sorry! |
Summary
A new attempt at fixing #2676, which is still an unsolved performance issue for Oracle schema introspection.
Platforms