Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 22
0.00% covered (danger)
0.00%
0 / 2
CRAP
0.00% covered (danger)
0.00%
0 / 1
DisableOATHAuthForUser
0.00% covered (danger)
0.00%
0 / 16
0.00% covered (danger)
0.00%
0 / 2
30
0.00% covered (danger)
0.00%
0 / 1
 __construct
0.00% covered (danger)
0.00%
0 / 4
0.00% covered (danger)
0.00%
0 / 1
2
 execute
0.00% covered (danger)
0.00%
0 / 12
0.00% covered (danger)
0.00%
0 / 1
20
1<?php
2
3use MediaWiki\Extension\OATHAuth\OATHAuthServices;
4use MediaWiki\MediaWikiServices;
5use MediaWiki\Session\SessionManager;
6
7if ( getenv( 'MW_INSTALL_PATH' ) ) {
8    $IP = getenv( 'MW_INSTALL_PATH' );
9} else {
10    $IP = __DIR__ . '/../../..';
11}
12require_once "$IP/maintenance/Maintenance.php";
13
14class DisableOATHAuthForUser extends Maintenance {
15    public function __construct() {
16        parent::__construct();
17        $this->addDescription( 'Remove all two-factor authentication devices from a specific user' );
18        $this->addArg( 'user', 'The username to remove 2FA devices from.' );
19        $this->requireExtension( 'OATHAuth' );
20    }
21
22    public function execute() {
23        $username = $this->getArg( 0 );
24
25        $user = MediaWikiServices::getInstance()->getUserFactory()
26            ->newFromName( $username );
27        if ( $user === null || $user->getId() === 0 ) {
28            $this->fatalError( "User $username doesn't exist!" );
29        }
30
31        $repo = OATHAuthServices::getInstance()->getUserRepository();
32        $oathUser = $repo->findByUser( $user );
33        if ( !$oathUser->isTwoFactorAuthEnabled() ) {
34            $this->fatalError( "User $username does not have two-factor authentication enabled!" );
35        }
36
37        $repo->removeAll( $oathUser, 'Maintenance script', false );
38        // Kill all existing sessions.
39        // If this request to disable 2FA was social-engineered by an attacker,
40        // the legitimate user will hopefully log in again to the wiki, and notice that the second factor
41        // is missing or different, and alert the operators.
42        SessionManager::singleton()->invalidateSessionsForUser( $user );
43
44        $this->output( "Two-factor authentication disabled for $username.\n" );
45    }
46}
47
48$maintClass = DisableOATHAuthForUser::class;
49require_once RUN_MAINTENANCE_IF_MAIN;