*/
use MediaWiki\MediaWikiServices;
+use MediaWiki\Storage\NameTableAccessException;
use Wikimedia\Rdbms\Database;
class ChangeTags {
* @return array Array with two items: (html, classes)
* - html: String: HTML for displaying the tags (empty string when param $tags is empty)
* - classes: Array of strings: CSS classes used in the generated html, one class for each tag
+ * @return-taint onlysafefor_htmlnoent
*/
public static function formatSummaryRow( $tags, $page, IContextSource $context = null ) {
if ( !$tags ) {
throw new MWException( 'Unable to determine appropriate JOIN condition for tagging.' );
}
+ $tagTables[] = 'change_tag';
if ( $wgChangeTagsSchemaMigrationStage > MIGRATION_WRITE_BOTH ) {
- $tables[] = 'change_tag_def';
- $join_cond = [ $join_cond, 'ct_tag_id=ctd_id' ];
+ $tagTables[] = 'change_tag_def';
+ $join_cond_ts_tags = [ $join_cond, 'ct_tag_id=ctd_id' ];
$field = 'ctd_name';
} else {
$field = 'ct_tag';
+ $join_cond_ts_tags = $join_cond;
}
$fields['ts_tags'] = wfGetDB( DB_REPLICA )->buildGroupConcatField(
- ',', 'change_tag', $field, $join_cond
+ ',', $tagTables, $field, $join_cond_ts_tags
);
if ( $wgUseTagFilter && $filter_tag ) {
$tables[] = 'change_tag';
$join_conds['change_tag'] = [ 'INNER JOIN', $join_cond ];
if ( $wgChangeTagsSchemaMigrationStage > MIGRATION_WRITE_BOTH ) {
- $tables[] = 'change_tag_def';
- $join_conds['change_tag_def'] = [ 'INNER JOIN', 'ct_tag_id=ctd_id' ];
- $conds['ctd_name'] = $filter_tag;
+ $filterTagIds = [];
+ $changeTagDefStore = MediaWikiServices::getInstance()->getChangeTagDefStore();
+ foreach ( (array)$filter_tag as $filterTagName ) {
+ try {
+ $filterTagIds[] = $changeTagDefStore->getId( $filterTagName );
+ } catch ( NameTableAccessException $exception ) {
+ // Return nothing.
+ $conds[] = '0';
+ break;
+ };
+ }
+ $conds['ct_tag_id'] = $filterTagIds;
} else {
$conds['ct_tag'] = $filter_tag;
}
);
}
- $dbw->replace(
- 'valid_tag',
- [ 'vt_tag' ],
- [ 'vt_tag' => $tag ],
- __METHOD__
- );
-
+ if ( $wgChangeTagsSchemaMigrationStage < MIGRATION_NEW ) {
+ $dbw->replace(
+ 'valid_tag',
+ [ 'vt_tag' ],
+ [ 'vt_tag' => $tag ],
+ __METHOD__
+ );
+ }
// clear the memcache of defined tags
self::purgeTagCacheAll();
}
);
}
- $dbw->delete( 'valid_tag', [ 'vt_tag' => $tag ], __METHOD__ );
+ if ( $wgChangeTagsSchemaMigrationStage < MIGRATION_NEW ) {
+ $dbw->delete( 'valid_tag', [ 'vt_tag' => $tag ], __METHOD__ );
+ }
// clear the memcache of defined tags
self::purgeTagCacheAll();
/**
* Lists tags explicitly defined in the `valid_tag` table of the database.
* Tags in table 'change_tag' which are not in table 'valid_tag' are not
- * included.
+ * included. In case of new backend loads the data from `change_tag_def` table.
*
* Tries memcached first.
*
$cache->makeKey( 'valid-tags-db' ),
WANObjectCache::TTL_MINUTE * 5,
function ( $oldValue, &$ttl, array &$setOpts ) use ( $fname ) {
+ global $wgChangeTagsSchemaMigrationStage;
$dbr = wfGetDB( DB_REPLICA );
$setOpts += Database::getCacheSetOptions( $dbr );
- $tags = $dbr->selectFieldValues( 'valid_tag', 'vt_tag', [], $fname );
+ if ( $wgChangeTagsSchemaMigrationStage > MIGRATION_WRITE_BOTH ) {
+ $tags = self::listExplicitlyDefinedTagsNewBackend();
+ } else {
+ $tags = $dbr->selectFieldValues( 'valid_tag', 'vt_tag', [], $fname );
+ }
return array_filter( array_unique( $tags ) );
},
);
}
+ /**
+ * Lists tags explicitly user defined tags. When ctd_user_defined is true.
+ *
+ * @return string[] Array of strings: tags
+ * @since 1.25
+ */
+ private static function listExplicitlyDefinedTagsNewBackend() {
+ $dbr = wfGetDB( DB_REPLICA );
+ return $dbr->selectFieldValues(
+ 'change_tag_def',
+ 'ctd_name',
+ [ 'ctd_user_defined' => 1 ],
+ __METHOD__
+ );
+ }
+
/**
* Lists tags defined by core or extensions using the ListDefinedTags hook.
* Extensions need only define those tags they deem to be in active use.