Tests: Only skip tests related to the temp table reopen issue in MySQL

This is fixed in MariaDB so we can keep it running in majority of our CI
without any issues

Bug: T256006
Change-Id: If68883969f8762c761b152cd18bdeb19d3a6c40d
This commit is contained in:
Amir Sarabadani 2023-06-09 02:03:45 +02:00
parent fec202365f
commit 73e11b8745
4 changed files with 18 additions and 59 deletions

View file

@ -116,18 +116,6 @@ class ChangeTags {
public const DISPLAY_TABLE_ALIAS = 'changetagdisplay';
/**
* If true, this class attempts to avoid reopening database tables within the same query,
* to avoid the "Can't reopen table" error when operating on temporary tables while running
* tests.
*
* @see https://phabricator.wikimedia.org/T256006
* @see 1.35
*
* @var bool
*/
public static $avoidReopeningTablesForTesting = false;
/**
* Loads defined core tags, checks for invalid types (if not array),
* and filters for supported and enabled (if $all is false) tags only.
@ -678,7 +666,6 @@ class ChangeTags {
if ( $filter_tag !== [] && $filter_tag !== '' ) {
// Somebody wants to filter on a tag.
// Add an INNER JOIN on change_tag
$tagTable = self::getDisplayTableName();
$filterTagIds = [];
$changeTagDefStore = MediaWikiServices::getInstance()->getChangeTagDefStore();
foreach ( (array)$filter_tag as $filterTagName ) {
@ -690,7 +677,7 @@ class ChangeTags {
if ( $exclude ) {
if ( $filterTagIds !== [] ) {
$tables[self::DISPLAY_TABLE_ALIAS] = $tagTable;
$tables[self::DISPLAY_TABLE_ALIAS] = self::CHANGE_TAG;
$join_conds[self::DISPLAY_TABLE_ALIAS] = [
'LEFT JOIN',
[ $join_cond, self::DISPLAY_TABLE_ALIAS . '.ct_tag_id' => $filterTagIds ]
@ -698,7 +685,7 @@ class ChangeTags {
$conds[] = self::DISPLAY_TABLE_ALIAS . ".ct_tag_id IS NULL";
}
} else {
$tables[self::DISPLAY_TABLE_ALIAS] = $tagTable;
$tables[self::DISPLAY_TABLE_ALIAS] = self::CHANGE_TAG;
$join_conds[self::DISPLAY_TABLE_ALIAS] = [ 'JOIN', $join_cond ];
if ( $filterTagIds !== [] ) {
$conds[self::DISPLAY_TABLE_ALIAS . '.ct_tag_id'] = $filterTagIds;
@ -721,38 +708,11 @@ class ChangeTags {
* Get the name of the change_tag table to use for modifyDisplayQuery().
* This also does first-call initialisation of the table in testing mode.
*
* @deprecated since 1.41 use ChangeTags::CHANGE_TAG instead
* @return string
*/
public static function getDisplayTableName() {
$tagTable = self::CHANGE_TAG;
if ( self::$avoidReopeningTablesForTesting && defined( 'MW_PHPUNIT_TEST' ) ) {
$db = wfGetDB( DB_REPLICA );
if ( $db->getType() === 'mysql' ) {
// When filtering by tag, we are using the change_tag table twice:
// Once in a join for filtering, and once in a sub-query to list all
// tags for each revision. This does not work with temporary tables
// on some versions of MySQL, which causes phpunit tests to fail.
// As a hacky workaround, we copy the temporary table, and join
// against the copy. It is acknowledged that this is quite horrific.
// Discuss at T256006.
$tagTable = 'change_tag_for_display_query';
if ( !$db->tableExists( $tagTable ) ) {
$db->query(
'CREATE TEMPORARY TABLE IF NOT EXISTS ' . $db->tableName( $tagTable )
. ' LIKE ' . $db->tableName( self::CHANGE_TAG ),
__METHOD__
);
$db->query(
'INSERT IGNORE INTO ' . $db->tableName( $tagTable )
. ' SELECT * FROM ' . $db->tableName( self::CHANGE_TAG ),
__METHOD__
);
}
}
}
return $tagTable;
return self::CHANGE_TAG;
}
/**

View file

@ -56,15 +56,15 @@ class ContributionsLookupTest extends MediaWikiIntegrationTestCase {
protected function setUp(): void {
parent::setUp();
// Work around T256006
ChangeTags::$avoidReopeningTablesForTesting = true;
if ( $this->db->getType() == 'mysql' && strpos( $this->db->getSoftwareLink(), 'MySQL' ) ) {
$this->markTestSkipped( 'See T256006' );
}
// MessageCache needs to be explicitly enabled to load changetag display text.
$this->getServiceContainer()->getMessageCache()->enable();
}
protected function tearDown(): void {
ChangeTags::$avoidReopeningTablesForTesting = false;
$this->getServiceContainer()->getMessageCache()->disable();
parent::tearDown();

View file

@ -25,7 +25,6 @@ class ChangeTagsTest extends MediaWikiIntegrationTestCase {
}
protected function tearDown(): void {
ChangeTags::$avoidReopeningTablesForTesting = false;
parent::tearDown();
}
@ -47,13 +46,14 @@ class ChangeTagsTest extends MediaWikiIntegrationTestCase {
$exclude = false
) {
$this->overrideConfigValue( MainConfigNames::UseTagFilter, $useTags );
if ( $avoidReopeningTables && $this->db->getType() !== 'mysql' ) {
$this->markTestSkipped( 'MySQL only' );
if (
$avoidReopeningTables &&
$this->db->getType() == 'mysql' &&
strpos( $this->db->getSoftwareLink(), 'MySQL' )
) {
$this->markTestSkipped( 'See T256006' );
}
ChangeTags::$avoidReopeningTablesForTesting = $avoidReopeningTables;
$rcId = 123;
ChangeTags::updateTags( [ 'foo', 'bar', '0' ], [], $rcId );
// HACK resolve deferred group concats (see comment in provideModifyDisplayQuery)
@ -279,7 +279,7 @@ class ChangeTagsTest extends MediaWikiIntegrationTestCase {
true, // tag filtering enabled
true, // avoid reopening tables
[
'tables' => [ 'archive', 'changetagdisplay' => 'change_tag_for_display_query' ],
'tables' => [ 'archive', 'changetagdisplay' => 'change_tag' ],
'fields' => [ 'ar_id', 'ar_timestamp', 'ts_tags' => $groupConcats['archive'] ],
'conds' => [ "ar_timestamp > '20170714183203'", 'changetagdisplay.ct_tag_id' => [ 1 ] ],
'join_conds' => [ 'changetagdisplay' => [ 'JOIN', 'changetagdisplay.ct_rev_id=ar_rev_id' ] ],
@ -407,7 +407,7 @@ class ChangeTagsTest extends MediaWikiIntegrationTestCase {
true, // tag filtering enabled
true, // avoid reopening tables
[
'tables' => [ 'recentchanges', 'changetagdisplay' => 'change_tag_for_display_query' ],
'tables' => [ 'recentchanges', 'changetagdisplay' => 'change_tag' ],
'fields' => [ 'rc_id', 'ts_tags' => $groupConcats['recentchanges'] ],
'conds' => [ "rc_timestamp > '20170714183203'", 'changetagdisplay.ct_tag_id' => [ 1, 2 ] ],
'join_conds' => [ 'changetagdisplay' => [ 'JOIN', 'changetagdisplay.ct_rc_id=rc_id' ] ],

View file

@ -54,14 +54,13 @@ class QueryAllSpecialPagesTest extends MediaWikiIntegrationTestCase {
* Test SQL for each of our QueryPages objects
*/
public function testQuerypageSqlQuery() {
global $wgDBtype;
foreach ( $this->queryPages as $page ) {
// With MySQL, skips special pages reopening a temporary table
// See https://bugs.mysql.com/bug.php?id=10327
if (
$wgDBtype === 'mysql'
&& in_array( $page->getName(), $this->reopensTempTable )
$this->db->getType() == 'mysql' &&
strpos( $this->db->getSoftwareLink(), 'MySQL' ) &&
in_array( $page->getName(), $this->reopensTempTable )
) {
$this->markTestSkipped( "SQL query for page {$page->getName()} "
. "can not be tested on MySQL backend (it reopens a temporary table)" );