Page MenuHomePhabricator

BannerMessageGroup::registerGroupHook of CentralNotice must not query master on GET request (page views)
Open, HighPublicPRODUCTION ERROR

Description

The master DB of the deployment-prep MediaWiki cluster is down but the replicas are up:

tgr@deployment-deploy01:~$ sql metawiki --write
ERROR 2003 (HY000): Can't connect to MySQL server on '172.16.5.23' (113 "No route to host")

tgr@deployment-deploy01:~$ sql metawiki
Welcome to the MariaDB monitor.

Visiting https://meta.wikimedia.beta.wmflabs.org/wiki/Main_Page in an incognito window gives this exception:

Sorry! This site is experiencing technical difficulties.
Try waiting a few minutes and reloading.

(Cannot access the database: Cannot access the database: Unknown error (172.16.5.23:3306))

Backtrace:

#0 /srv/mediawiki/php-master/includes/libs/rdbms/loadbalancer/LoadBalancer.php(751): Wikimedia\Rdbms\LoadBalancer->reportConnectionError()
#1 /srv/mediawiki/php-master/includes/GlobalFunctions.php(2654): Wikimedia\Rdbms\LoadBalancer->getConnection()
#2 /srv/mediawiki/php-master/extensions/CentralNotice/includes/CNDatabase.php(62): wfGetDB()
#3 /srv/mediawiki/php-master/extensions/CentralNotice/includes/BannerMessageGroup.php(230): CNDatabase::getDb()
#4 /srv/mediawiki/php-master/includes/Hooks.php(174): BannerMessageGroup::registerGroupHook()
#5 /srv/mediawiki/php-master/includes/Hooks.php(202): Hooks::callHook()
#6 /srv/mediawiki/php-master/extensions/Translate/MessageGroups.php(62): Hooks::run()
#7 /srv/mediawiki/php-master/includes/libs/objectcache/WANObjectCache.php(1326): Closure$MessageGroups::getCachedGroupDefinitions()
#8 /srv/mediawiki/php-master/includes/libs/objectcache/WANObjectCache.php(1190): WANObjectCache->doGetWithSetCallback()
#9 /srv/mediawiki/php-master/extensions/Translate/MessageGroups.php(92): WANObjectCache->getWithSetCallback()
#10 /srv/mediawiki/php-master/extensions/Translate/MessageGroups.php(42): MessageGroups->getCachedGroupDefinitions()
#11 /srv/mediawiki/php-master/extensions/Translate/MessageGroups.php(586): MessageGroups->init()
#12 /srv/mediawiki/php-master/extensions/Translate/MessageGroups.php(316): MessageGroups->getGroups()
#13 /srv/mediawiki/php-master/extensions/Translate/tag/TranslatablePage.php(209): MessageGroups::getGroup()
#14 /srv/mediawiki/php-master/extensions/Translate/tag/TranslatablePage.php(769): TranslatablePage->getMessageGroup()
#15 /srv/mediawiki/php-master/extensions/Translate/tag/PageTranslationHooks.php(411): TranslatablePage->getTranslationPercentages()
#16 /srv/mediawiki/php-master/extensions/Translate/tag/PageTranslationHooks.php(256): PageTranslationHooks::getTranslatablePageStatus()
#17 /srv/mediawiki/php-master/includes/parser/Parser.php(3987): PageTranslationHooks::languages()
#18 /srv/mediawiki/php-master/includes/parser/Preprocessor_Hash.php(1188): Parser->extensionSubstitution()
#19 /srv/mediawiki/php-master/includes/parser/Parser.php(3036): PPFrame_Hash->expand()
#20 /srv/mediawiki/php-master/includes/parser/Parser.php(1354): Parser->replaceVariables()
#21 /srv/mediawiki/php-master/includes/parser/Parser.php(482): Parser->internalParse()
#22 /srv/mediawiki/php-master/includes/content/WikitextContent.php(369): Parser->parse()
#23 /srv/mediawiki/php-master/includes/content/AbstractContent.php(555): WikitextContent->fillParserOutput()
#24 /srv/mediawiki/php-master/includes/Revision/RenderedRevision.php(266): AbstractContent->getParserOutput()
#25 /srv/mediawiki/php-master/includes/Revision/RenderedRevision.php(234): MediaWiki\Revision\RenderedRevision->getSlotParserOutputUncached()
#26 /srv/mediawiki/php-master/includes/Revision/RevisionRenderer.php(193): MediaWiki\Revision\RenderedRevision->getSlotParserOutput()
#27 /srv/mediawiki/php-master/includes/Revision/RevisionRenderer.php(142): MediaWiki\Revision\RevisionRenderer->combineSlotOutput()
#28 (): Closure$MediaWiki\Revision\RevisionRenderer::getRenderedRevision#2()
#29 /srv/mediawiki/php-master/includes/Revision/RenderedRevision.php(197): call_user_func()
#30 /srv/mediawiki/php-master/includes/poolcounter/PoolWorkArticleView.php(194): MediaWiki\Revision\RenderedRevision->getRevisionParserOutput()
#31 /srv/mediawiki/php-master/includes/poolcounter/PoolCounterWork.php(123): PoolWorkArticleView->doWork()
#32 /srv/mediawiki/php-master/includes/page/Article.php(774): PoolCounterWork->execute()
#33 /srv/mediawiki/php-master/includes/actions/ViewAction.php(68): Article->view()
#34 /srv/mediawiki/php-master/includes/MediaWiki.php(501): ViewAction->show()
#35 /srv/mediawiki/php-master/includes/MediaWiki.php(294): MediaWiki->performAction()
#36 /srv/mediawiki/php-master/includes/MediaWiki.php(867): MediaWiki->performRequest()
#37 /srv/mediawiki/php-master/includes/MediaWiki.php(517): MediaWiki->main()
#38 /srv/mediawiki/php-master/index.php(42): MediaWiki->run()
#39 /srv/mediawiki/w/index.php(3): include()
#40 {main}

That's not great error recovery. MediaWiki should not need master reads just to show the main page, but if it does, it should at least resume in readonly mode on error. (Also, what's up with the error message?)

Event Timeline

Krinkle subscribed.

MediaWiki should not need master reads just to show the main page, but if it does, it should at least resume in readonly mode on error.

It doesn't. The error comes from CentralNotice via Translate, and are from rare code paths (various levels of cache miss). If they happen in prod (not seen recently), they'd emit DBPerformance warnings and prioritised as a Wikimedia-production-error.

Krinkle renamed this task from MediaWiki should work in readonly mode when the master is down to CentralNotice must not query master on GET request (page views).Feb 19 2019, 12:31 AM
Krinkle updated the task description. (Show Details)
CentralNotice/includes/BannerMessageGroup.php
	/**
	 * TranslatePostInitGroups hook handler
	 *
	 * Add banner message groups to the list of message groups that should be
	 * translated through the Translate extension.
	 *
	 * @param array &$list
	 * @return bool
	 */
	public static function registerGroupHook( &$list ) {
		$dbr = CNDatabase::getDb( DB_MASTER );
		                        # ^^^^^^^^^

Source

(Tagging as Meta for now, as only seen in beta, but no reason to believe it is limited to that.)

Quennlatifa0303 set Due Date to Feb 19 2019, 12:00 AM.
Restricted Application changed the subtype of this task from "Task" to "Deadline". · View Herald TranscriptFeb 19 2019, 4:01 AM
Krinkle raised the priority of this task from Medium to Needs Triage.Feb 19 2019, 4:11 AM
Krinkle removed Due Date.
Restricted Application changed the subtype of this task from "Deadline" to "Task". · View Herald TranscriptFeb 19 2019, 4:11 AM

This looks like it should use DB_REPLICA.

This looks like it should use DB_REPLICA.

	public static function registerGroupHook( &$list ) {
		// Must be explicitly master for runs under a jobqueue
		$dbr = CNDatabase::getDb( DB_MASTER );

If it's not actually part of a job, it should be DB_REPLICA. Also, even when it should use DB_MASTER it should not be using getCachedGroupDefinitions() since it should skip the cache.

mmodell changed the subtype of this task from "Task" to "Production Error".Aug 28 2019, 11:07 PM
Krinkle triaged this task as High priority.Jul 2 2020, 4:03 PM
Krinkle moved this task from Later to Current: Other on the Sustainability (MediaWiki-MultiDC) board.

BannerMessageGroup::registerGroupHook is triggering master queries (a) on HTTP GET requests and also (b) inside of a getWithSetCallback() call, which should use DB_REPLICA data.

aaron renamed this task from CentralNotice must not query master on GET request (page views) to BannerMessageGroup::registerGroupHook of CentralNotice must not query master on GET request (page views).Jul 16 2020, 8:19 PM

Still seen:

  • Request: GET meta.wikimedia.org /wiki/<some page name>/cs
  • reqId: YEfCorGzrOfMwJS5Kr-RUQAAAIs
Expectation (masterConns <= 0) by MediaWiki::main not met (actual: 1):
trace
from /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/rdbms/TransactionProfiler.php(378)
#0 /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/rdbms/TransactionProfiler.php(189): Wikimedia\Rdbms\TransactionProfiler->reportExpectationViolated(string, string, integer)
#1 /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/rdbms/loadbalancer/LoadBalancer.php(1006): Wikimedia\Rdbms\TransactionProfiler->recordConnection(string, string, boolean)
#2 /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/rdbms/loadbalancer/LoadBalancer.php(960): Wikimedia\Rdbms\LoadBalancer->getServerConnection(integer, string, integer)
#3 /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/rdbms/loadbalancer/LoadBalancer.php(1126): Wikimedia\Rdbms\LoadBalancer->getConnection(integer, array, string, integer)
#4 /srv/mediawiki/php-1.36.0-wmf.33/includes/GlobalFunctions.php(2468): Wikimedia\Rdbms\LoadBalancer->getMaintenanceConnectionRef(integer, array, string)
#5 /srv/mediawiki/php-1.36.0-wmf.33/extensions/CentralNotice/includes/CNDatabase.php(63): wfGetDB(integer)
#6 /srv/mediawiki/php-1.36.0-wmf.33/extensions/CentralNotice/includes/BannerMessageGroup.php(235): CNDatabase::getDb(integer)
#7 /srv/mediawiki/php-1.36.0-wmf.33/includes/HookContainer/HookContainer.php(333): BannerMessageGroup::registerGroupHook(array, array, array)
#8 /srv/mediawiki/php-1.36.0-wmf.33/includes/HookContainer/HookContainer.php(140): MediaWiki\HookContainer\HookContainer->callLegacyHook(string, array, array, array)
#9 /srv/mediawiki/php-1.36.0-wmf.33/includes/Hooks.php(137): MediaWiki\HookContainer\HookContainer->run(string, array, array)
#10 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/MessageGroups.php(68): Hooks::run(string, array)
#11 /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/objectcache/wancache/WANObjectCache.php(1604): MessageGroups->{closure}(DependencyWrapper, integer, array, double, array)
#12 /srv/mediawiki/php-1.36.0-wmf.33/includes/libs/objectcache/wancache/WANObjectCache.php(1432): WANObjectCache->fetchOrRegenerate(string, integer, Closure, array, array)
#13 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/MessageGroups.php(97): WANObjectCache->getWithSetCallback(string, integer, Closure, array)
#14 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/MessageGroups.php(44): MessageGroups->getCachedGroupDefinitions()
#15 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/MessageGroups.php(559): MessageGroups->init()
#16 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/MessageGroups.php(293): MessageGroups->getGroups()
#17 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/tag/TranslatablePage.php(187): MessageGroups::getGroup(string)
#18 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/tag/TranslatablePage.php(586): TranslatablePage->getMessageGroup()
#19 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/tag/PageTranslationHooks.php(1167): TranslatablePage->getTranslationPercentages()
#20 /srv/mediawiki/php-1.36.0-wmf.33/extensions/Translate/tag/PageTranslationHooks.php(1075): PageTranslationHooks::translationPageHeader(RequestContext, TranslatablePage)
#21 /srv/mediawiki/php-1.36.0-wmf.33/includes/HookContainer/HookContainer.php(333): PageTranslationHooks::translatablePageHeader(Article, NULL, boolean)
#22 /srv/mediawiki/php-1.36.0-wmf.33/includes/HookContainer/HookContainer.php(140): MediaWiki\HookContainer\HookContainer->callLegacyHook(string, array, array, array)
#23 /srv/mediawiki/php-1.36.0-wmf.33/includes/HookContainer/HookRunner.php(902): MediaWiki\HookContainer\HookContainer->run(string, array)
#24 /srv/mediawiki/php-1.36.0-wmf.33/includes/page/Article.php(633): MediaWiki\HookContainer\HookRunner->onArticleViewHeader(Article, NULL, boolean)
#25 /srv/mediawiki/php-1.36.0-wmf.33/includes/page/Article.php(571): Article->generateContentOutput(User, ParserOptions, integer, OutputPage, array)
#26 /srv/mediawiki/php-1.36.0-wmf.33/includes/actions/ViewAction.php(74): Article->view()
#27 /srv/mediawiki/php-1.36.0-wmf.33/includes/MediaWiki.php(531): ViewAction->show()
#28 /srv/mediawiki/php-1.36.0-wmf.33/includes/MediaWiki.php(315): MediaWiki->performAction(Article, Title)
#29 /srv/mediawiki/php-1.36.0-wmf.33/includes/MediaWiki.php(925): MediaWiki->performRequest()
#30 /srv/mediawiki/php-1.36.0-wmf.33/includes/MediaWiki.php(547): MediaWiki->main()
#31 /srv/mediawiki/php-1.36.0-wmf.33/index.php(53): MediaWiki->run()
#32 /srv/mediawiki/php-1.36.0-wmf.33/index.php(46): wfIndexMain()
#33 /srv/mediawiki/w/index.php(3): require(string)
#34 {main}