Skip to content
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

Generate a table hash that take account of the AUTO_INCREMENT changes #10

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

nojimage
Copy link

@nojimage nojimage commented Dec 20, 2017

CHECKSUM TABLE calculates a hash value for the current table record.

This hash value does not include the value of AUTO_INCREMENT, it is not possible to track changes when only the value of AUTO_INCREMENT changes.
For example, if you add a record in a test case and delete that record.

If do not check the change of AUTO_INCREMENT, it will be occurred mismatch problem when assert the record id in the test case.

@ravage84 ravage84 added this to the 1.0 milestone Aug 25, 2023
@ravage84
Copy link
Collaborator

Even though this is probably mostly an edge case, it could be useful.

@nojimage can you please rebase your PR?

@krugerman007
Copy link
Contributor

I confirm that the issue is relevant!

Case: The empty table hash has not changed, but the autoincrement has already changed. In this case, the table is not cleared.

Please accept this request.

P.S. If necessary, I can do a rebase.

@ravage84
Copy link
Collaborator

ravage84 commented Aug 9, 2024

@krugerman007 yes, please re-create this PR (with proper CS) based on your other PR, once they are merged.

@ravage84
Copy link
Collaborator

ravage84 commented Aug 9, 2024

@krugerman007 can you please also check what a difference in speed peformance this change means?
Because with this, for each table, an additional SQL query needs to be executed.

@krugerman007
Copy link
Contributor

krugerman007 commented Aug 9, 2024

@krugerman007 can you please also check what a difference in speed peformance this change means? Because with this, for each table, an additional SQL query needs to be executed.

Sure:

Original for 1372 Tests:

2024-08-09 12_10_51

With this fix:

image

The difference is 4:27 - 3:32 = 0:55. It is 25% slower...

@ravage84 ravage84 modified the milestones: 1.x, 3.0.2 Aug 9, 2024
Comment on lines +133 to +139
$autoIncrementSth = $db->execute('SELECT `AUTO_INCREMENT` FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA=:schema AND TABLE_NAME=:table;', [
'schema' => $db->config()['database'],
'table' => $this->table,
]);
$autoIncrementResult = $autoIncrementSth->fetch('assoc');

return (string) $autoIncrementResult['AUTO_INCREMENT'];
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To prevent performance degredation, we could try to execute both queries in one go.

  1. Getting the table checksum
  2. Fetching the AUTO_INCREMENT info

Because apart from the additional queries to execute, the biggest part of the performance degredation of this change comes most likely from the PHP side.

And since it sems it not possible to query the table checksum as a sub query, we can only try the idea above.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you mean with "both queries in one go"? We cannot combine it like this:

SELECT 
  (SELECT `AUTO_INCREMENT` ...) as auto_increment,
  (CHECKSUM TABLE ...) as checksum;

Because the second query is not a select.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I tried that already.

But can we execute two queries with one execute() call by splitting them like SELECT ...;CHECKSUM TABLE;?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unfortunately I didn't find any way to get the result from the second query. Only the first query is returned:

// Debugging
$sth = $db->execute(
  "CHECKSUM TABLE " . $this->table . ';' .
  'SELECT `AUTO_INCREMENT` FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_SCHEMA=:schema AND TABLE_NAME=:table;',
  [
    'schema' => $db->config()['database'],
    'table' => $this->table,
  ]
);

// How to get the result of the second query?
// $sth->fetch('assoc'); returns the result of the first one.

@ravage84
Copy link
Collaborator

ravage84 commented Aug 9, 2024

Another idea to prevent performance degredation is to add a configuration setting which enables/disables the additoinal query for either the whole plugin (all fixtures), for each fixture individually or even fo each test class individually.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants