Page MenuHomePhabricator

MediaWiki\Extension\AbuseFilter\Filter\FilterNotFoundException: Filter 222 does not exist
Closed, ResolvedPublicPRODUCTION ERROR

Description

Error
normalized_message
[{reqId}] {exception_url}   MediaWiki\Extension\AbuseFilter\Filter\FilterNotFoundException: Filter 222 does not exist
FrameLocationCall
from/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/FilterLookup.php(114)
#0/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/AbuseLogger.php(312)MediaWiki\Extension\AbuseFilter\FilterLookup->getFilter(int, bool)
#1/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/AbuseLogger.php(223)MediaWiki\Extension\AbuseFilter\AbuseLogger->storeVarDump(int, bool)
#2/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/AbuseLogger.php(148)MediaWiki\Extension\AbuseFilter\AbuseLogger->insertLocalLogEntries(array, Wikimedia\Rdbms\DBConnRef)
#3/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/FilterRunner.php(258)MediaWiki\Extension\AbuseFilter\AbuseLogger->addLogEntries(array)
#4/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/Hooks/Handlers/FilteredActionsHandler.php(159)MediaWiki\Extension\AbuseFilter\FilterRunner->run()
#5/srv/mediawiki/php-1.44.0-wmf.23/extensions/AbuseFilter/includes/Hooks/Handlers/FilteredActionsHandler.php(109)MediaWiki\Extension\AbuseFilter\Hooks\Handlers\FilteredActionsHandler->filterEdit(MediaWiki\Context\DerivativeContext, MediaWiki\User\User, MediaWiki\Content\WikitextContent, string, string, MediaWiki\Status\Status)
#6/srv/mediawiki/php-1.44.0-wmf.23/includes/HookContainer/HookContainer.php(155)MediaWiki\Extension\AbuseFilter\Hooks\Handlers\FilteredActionsHandler->onEditFilterMergedContent(MediaWiki\Context\DerivativeContext, MediaWiki\Content\WikitextContent, MediaWiki\Status\Status, string, MediaWiki\User\User, bool)
#7/srv/mediawiki/php-1.44.0-wmf.23/includes/HookContainer/HookRunner.php(1532)MediaWiki\HookContainer\HookContainer->run(string, array)
#8/srv/mediawiki/php-1.44.0-wmf.23/includes/editpage/Constraint/EditFilterMergedContentHookConstraint.php(88)MediaWiki\HookContainer\HookRunner->onEditFilterMergedContent(MediaWiki\Context\DerivativeContext, MediaWiki\Content\WikitextContent, MediaWiki\Status\Status, string, MediaWiki\User\User, bool)
#9/srv/mediawiki/php-1.44.0-wmf.23/includes/editpage/Constraint/EditConstraintRunner.php(83)MediaWiki\EditPage\Constraint\EditFilterMergedContentHookConstraint->checkConstraint()
#10/srv/mediawiki/php-1.44.0-wmf.23/includes/editpage/EditPage.php(2308)MediaWiki\EditPage\Constraint\EditConstraintRunner->checkConstraints()
#11/srv/mediawiki/php-1.44.0-wmf.23/includes/editpage/EditPage.php(1814)MediaWiki\EditPage\EditPage->internalAttemptSavePrivate(array, bool, bool)
#12/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiEditPage.php(538)MediaWiki\EditPage\EditPage->attemptSave(array)
#13/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiMain.php(2005)MediaWiki\Api\ApiEditPage->execute()
#14/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiMain.php(916)MediaWiki\Api\ApiMain->executeAction()
#15/srv/mediawiki/php-1.44.0-wmf.23/extensions/VisualEditor/includes/ApiVisualEditorEdit.php(139)MediaWiki\Api\ApiMain->execute()
#16/srv/mediawiki/php-1.44.0-wmf.23/extensions/VisualEditor/includes/ApiVisualEditorEdit.php(446)MediaWiki\Extension\VisualEditor\ApiVisualEditorEdit->saveWikitext(MediaWiki\Title\Title, string, array)
#17/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiMain.php(2005)MediaWiki\Extension\VisualEditor\ApiVisualEditorEdit->execute()
#18/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiMain.php(947)MediaWiki\Api\ApiMain->executeAction()
#19/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiMain.php(918)MediaWiki\Api\ApiMain->executeActionWithErrorHandling()
#20/srv/mediawiki/php-1.44.0-wmf.23/includes/api/ApiEntryPoint.php(152)MediaWiki\Api\ApiMain->execute()
#21/srv/mediawiki/php-1.44.0-wmf.23/includes/MediaWikiEntryPoint.php(202)MediaWiki\Api\ApiEntryPoint->execute()
#22/srv/mediawiki/php-1.44.0-wmf.23/api.php(44)MediaWiki\MediaWikiEntryPoint->run()
#23/srv/mediawiki/w/api.php(3)require(string)
#24{main}
Impact
Notes

Event Timeline

I wonder if FilterNotFoundException should be some level of normalized exception, because these were appearing for a variety of numbers...

Let's see:

wikiadmin2023@10.64.131.10(cawiki)> select max(af_id) from abuse_filter;
+------------+
| max(af_id) |
+------------+
|         25 |
+------------+
1 row in set (0.000 sec)

meaning it definitely does not exist. Where does the 222 ID come from? Following the trace, the integer is extracted in AbuseLogger.php#118. I don't see anything in GlobalNameUtils::splitGlobalName() that might go wrong, hence following $filter. But that in turn comes from FilterRunner, so I'm still not sure how it could've ended up there.

Also, considering that global filter 222 does exist, presumably this is a regression where something is not passing the appropriate flag for global filters.

I wonder if FilterNotFoundException should be some level of normalized exception, because these were appearing for a variety of numbers...

Yeah, I think it should. It should be a simple change and I can review, otherwise I'll make a patch but first I want to find where the regression is.

OK yeah, I see. This is a regression from r1131341, where all log entries on the local wiki are treated as entries from local filters. It's a subtle mistake and it took me a couple passes to spot it.

The terminology here is a bit confusing, because local logs can be for both local and global filter hits; whereas foreign logs can only be for local filters (in the context of that foreign wiki). I'll make a patch.

Daimona triaged this task as Unbreak Now! priority.Apr 2 2025, 7:54 PM

Making this a train blocker because every hit of a global filter will result in uncaught exceptions or wrong entries in the DB.

Change #1133524 had a related patch set uploaded (by Daimona Eaytoy; author: Daimona Eaytoy):

[mediawiki/extensions/AbuseFilter@master] AbuseLogger: use the correct `global` flag for filter entries

https://gerrit.wikimedia.org/r/1133524

Change #1133524 had a related patch set uploaded (by Daimona Eaytoy; author: Daimona Eaytoy):

[mediawiki/extensions/AbuseFilter@master] AbuseLogger: use the correct `global` flag for filter entries

https://gerrit.wikimedia.org/r/1133524

Thanks. Taking a look at the patch.

Change #1133538 had a related patch set uploaded (by Dreamy Jazz; author: Daimona Eaytoy):

[mediawiki/extensions/AbuseFilter@wmf/1.44.0-wmf.23] AbuseLogger: properly distinguish between global filters and central DB

https://gerrit.wikimedia.org/r/1133538

Change #1133524 merged by jenkins-bot:

[mediawiki/extensions/AbuseFilter@master] AbuseLogger: properly distinguish between global filters and central DB

https://gerrit.wikimedia.org/r/1133524

Change #1133538 merged by jenkins-bot:

[mediawiki/extensions/AbuseFilter@wmf/1.44.0-wmf.23] AbuseLogger: properly distinguish between global filters and central DB

https://gerrit.wikimedia.org/r/1133538

Mentioned in SAL (#wikimedia-operations) [2025-04-02T21:35:02Z] <dreamyjazz@deploy1003> Started scap sync-world: Backport for [[gerrit:1133538|AbuseLogger: properly distinguish between global filters and central DB (T390904)]]

Mentioned in SAL (#wikimedia-operations) [2025-04-02T21:41:34Z] <dreamyjazz@deploy1003> dreamyjazz: Backport for [[gerrit:1133538|AbuseLogger: properly distinguish between global filters and central DB (T390904)]] synced to the testservers (https://wikitech.wikimedia.org/wiki/Mwdebug)

Mentioned in SAL (#wikimedia-operations) [2025-04-02T22:00:21Z] <dreamyjazz@deploy1003> Finished scap sync-world: Backport for [[gerrit:1133538|AbuseLogger: properly distinguish between global filters and central DB (T390904)]] (duration: 25m 19s)

I wonder if FilterNotFoundException should be some level of normalized exception, because these were appearing for a variety of numbers...

Want to do that in a different task? :)

To clarify on the risk of data corruption, me and @Daimona found that for local log entries (coped from etherpad):

  • If the ID of the global filter does not exist as a local filter, we get an uncaught exception (T390904), so no log entry is written and that's good.
  • If the ID of the global filter also exists as a local filter, the variable dump is unaffected unless:
    • The local filter was not protected and the global filter was protected. In this case, the variable dump will have no "user_unnamed_ip" variable included.
      • There is only one protected global filter. The only log entries in the last couple days are for a group2 wiki, so no entries affected.
    • The local filter was protected and the global filter was not protected. In this case, if the action also matched any protected filter the "user_unnamed_ip" variable will be present in the variable dump. This is the status quo (i.e. behaviour before the problem patch)
    • The "user_unnamed_ip" variable value is expired after 90 days and can be looked up separately (private details for an AbuseFilter log).
  • In all cases, any problems would either be the status quo before the patch or can be worked around as needed. We hide the value of protected variables in public logs, so there is no risk of showing private data to those who cannot see it.

Global log entries were unaffected by any issues.

Change #1133561 had a related patch set uploaded (by Daimona Eaytoy; author: Daimona Eaytoy):

[mediawiki/extensions/AbuseFilter@master] Make FilterNotFoundException a NormalizedException

https://gerrit.wikimedia.org/r/1133561

To clarify on the risk of data corruption, me and @Daimona found that for local log entries (coped from etherpad):

Yup, and for the papertrail, I later verified that no filter is affected in production (group0 and group1 only).

Change #1133561 merged by jenkins-bot:

[mediawiki/extensions/AbuseFilter@master] Make FilterNotFoundException a NormalizedException

https://gerrit.wikimedia.org/r/1133561