Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
84.29% covered (warning)
84.29%
59 / 70
69.23% covered (warning)
69.23%
9 / 13
CRAP
0.00% covered (danger)
0.00%
0 / 1
SpecialUserLogout
85.51% covered (warning)
85.51%
59 / 69
69.23% covered (warning)
69.23%
9 / 13
24.61
0.00% covered (danger)
0.00%
0 / 1
 __construct
100.00% covered (success)
100.00%
2 / 2
100.00% covered (success)
100.00%
1 / 1
1
 doesWrites
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 isListed
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 getGroupName
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 getFormFields
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 getDisplayFormat
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 execute
100.00% covered (success)
100.00%
7 / 7
100.00% covered (success)
100.00%
1 / 1
2
 alterForm
100.00% covered (success)
100.00%
23 / 23
100.00% covered (success)
100.00%
1 / 1
2
 onSubmit
41.67% covered (danger)
41.67%
5 / 12
0.00% covered (danger)
0.00%
0 / 1
2.79
 onSuccess
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
1 / 1
1
 showSuccess
100.00% covered (success)
100.00%
9 / 9
100.00% covered (success)
100.00%
1 / 1
4
 requiresUnblock
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 getDescription
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
1 / 1
5
1<?php
2/**
3 * @license GPL-2.0-or-later
4 * @file
5 */
6
7namespace MediaWiki\Specials;
8
9use MediaWiki\Exception\ErrorPageError;
10use MediaWiki\Html\Html;
11use MediaWiki\HTMLForm\HTMLForm;
12use MediaWiki\SpecialPage\FormSpecialPage;
13use MediaWiki\SpecialPage\SpecialPage;
14use MediaWiki\Status\Status;
15use MediaWiki\User\TempUser\TempUserConfig;
16use OOUI\HtmlSnippet;
17use OOUI\MessageWidget;
18
19/**
20 * Implements Special:Userlogout
21 *
22 * @ingroup SpecialPage
23 * @ingroup Auth
24 */
25class SpecialUserLogout extends FormSpecialPage {
26    /**
27     * @var string|null
28     */
29    private $oldUserName;
30
31    private TempUserConfig $tempUserConfig;
32
33    public function __construct( TempUserConfig $tempUserConfig ) {
34        parent::__construct( 'Userlogout' );
35        $this->tempUserConfig = $tempUserConfig;
36    }
37
38    /** @inheritDoc */
39    public function doesWrites() {
40        return true;
41    }
42
43    /** @inheritDoc */
44    public function isListed() {
45        return $this->getAuthManager()->canAuthenticateNow();
46    }
47
48    /** @inheritDoc */
49    protected function getGroupName() {
50        return 'login';
51    }
52
53    /** @inheritDoc */
54    protected function getFormFields() {
55        return [];
56    }
57
58    /** @inheritDoc */
59    protected function getDisplayFormat() {
60        return 'ooui';
61    }
62
63    /** @inheritDoc */
64    public function execute( $par ) {
65        $user = $this->getUser();
66        if ( $user->isAnon() ) {
67            $this->setHeaders();
68            $this->showSuccess();
69            return;
70        }
71        $this->oldUserName = $user->getName();
72
73        parent::execute( $par );
74    }
75
76    public function alterForm( HTMLForm $form ) {
77        $form->setTokenSalt( 'logoutToken' );
78        $form->setSubmitTextMsg( 'userlogout-submit' );
79        if ( $this->getUser()->isTemp() ) {
80            $form->addHeaderHtml(
81                // Keep in sync with mediawiki.page.ready/ready.js
82                Html::rawElement( 'p', [], $this->msg( 'userlogout-temp' )->parse() ) .
83                Html::rawElement( 'p', [], $this->msg( 'userlogout-temp-moreinfo' )->parse() ) .
84                ( new MessageWidget( [
85                    'type' => 'notice',
86                    'label' => new HtmlSnippet(
87                        Html::element(
88                            'strong',
89                            [],
90                            $this->msg( 'userlogout-temp-messagebox-title' )->text()
91                        ) .
92                        Html::element( 'br' ) .
93                        $this->msg( 'userlogout-temp-messagebox-body' )->parse()
94                    ),
95                ] ) )->toString()
96            );
97        } else {
98            $form->addHeaderHtml(
99                Html::element( 'p', [], $this->msg( 'userlogout-continue' )->text() )
100            );
101        }
102
103        $form->addHiddenFields( $this->getRequest()->getValues( 'returnto', 'returntoquery' ) );
104    }
105
106    /**
107     * Process the form.  At this point we know that the user passes all the criteria in
108     * userCanExecute(), and if the data array contains 'Username', etc, then Username
109     * resets are allowed.
110     * @param array $data
111     * @return Status
112     */
113    public function onSubmit( array $data ) {
114        // Make sure it's possible to log out
115        $session = $this->getRequest()->getSession();
116        if ( !$session->canSetUser() ) {
117            throw new ErrorPageError(
118                'cannotlogoutnow-title',
119                'cannotlogoutnow-text',
120                [
121                    $session->getProvider()->describe( $this->getLanguage() )
122                ]
123            );
124        }
125
126        $user = $this->getUser();
127
128        $user->logout();
129        return new Status();
130    }
131
132    public function onSuccess() {
133        $this->showSuccess();
134
135        $out = $this->getOutput();
136        // Hook.
137        $injected_html = '';
138        $this->getHookRunner()->onUserLogoutComplete( $this->getUser(), $injected_html, $this->oldUserName );
139        $out->addHTML( $injected_html );
140    }
141
142    private function showSuccess() {
143        $loginURL = SpecialPage::getTitleFor( 'Userlogin' )->getFullURL(
144            $this->getRequest()->getValues( 'returnto', 'returntoquery' ) );
145
146        $out = $this->getOutput();
147
148        $messageKey = 'logouttext';
149        if (
150            ( $this->oldUserName !== null && $this->tempUserConfig->isTempName( $this->oldUserName ) ) ||
151            $this->getRequest()->getCheck( 'wasTempUser' )
152        ) {
153            // Generates the message key logouttext-for-temporary-account which is used to customise the success
154            // message for a temporary account.
155            $messageKey .= '-for-temporary-account';
156        }
157        $out->addWikiMsg( $messageKey, $loginURL );
158
159        $out->returnToMain();
160    }
161
162    /**
163     * Let blocked users to log out and come back with their sockpuppets
164     * @return bool
165     */
166    public function requiresUnblock() {
167        return false;
168    }
169
170    /** @inheritDoc */
171    public function getDescription() {
172        // Set the page title as "templogout" if the user is (or just was) logged in to a temporary account
173        if (
174            $this->getUser()->isTemp() ||
175            ( $this->oldUserName !== null && $this->tempUserConfig->isTempName( $this->oldUserName ) ) ||
176            $this->getRequest()->getCheck( 'wasTempUser' )
177        ) {
178            return $this->msg( 'templogout' );
179        }
180        return parent::getDescription();
181    }
182}
183
184/**
185 * Retain the old class name for backwards compatibility.
186 * @deprecated since 1.41
187 */
188class_alias( SpecialUserLogout::class, 'SpecialUserLogout' );