Remove uses of deprecated TestUser properties
[lhc/web/wiklou.git] / tests / phpunit / includes / api / ApiLoginTest.php
1 <?php
2
3 /**
4 * @group API
5 * @group Database
6 * @group medium
7 *
8 * @covers ApiLogin
9 */
10 class ApiLoginTest extends ApiTestCase {
11
12 /**
13 * Test result of attempted login with an empty username
14 */
15 public function testApiLoginNoName() {
16 global $wgDisableAuthManager;
17
18 $session = [
19 'wsTokenSecrets' => [ 'login' => 'foobar' ],
20 ];
21 $data = $this->doApiRequest( [ 'action' => 'login',
22 'lgname' => '', 'lgpassword' => self::$users['sysop']->getPassword(),
23 'lgtoken' => (string)( new MediaWiki\Session\Token( 'foobar', '' ) )
24 ], $session );
25 $this->assertEquals( $wgDisableAuthManager ? 'NoName' : 'Failed', $data[0]['login']['result'] );
26 }
27
28 public function testApiLoginBadPass() {
29 global $wgServer, $wgDisableAuthManager;
30
31 $user = self::$users['sysop'];
32 $userName = $user->getUser()->getName();
33 $user->getUser()->logout();
34
35 if ( !isset( $wgServer ) ) {
36 $this->markTestIncomplete( 'This test needs $wgServer to be set in LocalSettings.php' );
37 }
38 $ret = $this->doApiRequest( [
39 "action" => "login",
40 "lgname" => $userName,
41 "lgpassword" => "bad",
42 ] );
43
44 $result = $ret[0];
45
46 $this->assertNotInternalType( "bool", $result );
47 $a = $result["login"]["result"];
48 $this->assertEquals( "NeedToken", $a );
49
50 $token = $result["login"]["token"];
51
52 $ret = $this->doApiRequest(
53 [
54 "action" => "login",
55 "lgtoken" => $token,
56 "lgname" => $userName,
57 "lgpassword" => "badnowayinhell",
58 ],
59 $ret[2]
60 );
61
62 $result = $ret[0];
63
64 $this->assertNotInternalType( "bool", $result );
65 $a = $result["login"]["result"];
66
67 $this->assertEquals( $wgDisableAuthManager ? 'WrongPass' : 'Failed', $a );
68 }
69
70 public function testApiLoginGoodPass() {
71 global $wgServer;
72
73 if ( !isset( $wgServer ) ) {
74 $this->markTestIncomplete( 'This test needs $wgServer to be set in LocalSettings.php' );
75 }
76
77 $user = self::$users['sysop'];
78 $userName = $user->getUser()->getName();
79 $password = $user->getPassword();
80 $user->getUser()->logout();
81
82 $ret = $this->doApiRequest( [
83 "action" => "login",
84 "lgname" => $userName,
85 "lgpassword" => $password,
86 ]
87 );
88
89 $result = $ret[0];
90 $this->assertNotInternalType( "bool", $result );
91 $this->assertNotInternalType( "null", $result["login"] );
92
93 $a = $result["login"]["result"];
94 $this->assertEquals( "NeedToken", $a );
95 $token = $result["login"]["token"];
96
97 $ret = $this->doApiRequest(
98 [
99 "action" => "login",
100 "lgtoken" => $token,
101 "lgname" => $userName,
102 "lgpassword" => $password,
103 ],
104 $ret[2]
105 );
106
107 $result = $ret[0];
108
109 $this->assertNotInternalType( "bool", $result );
110 $a = $result["login"]["result"];
111
112 $this->assertEquals( "Success", $a );
113 }
114
115 /**
116 * @group Broken
117 */
118 public function testApiLoginGotCookie() {
119 $this->markTestIncomplete( "The server can't do external HTTP requests, "
120 . "and the internal one won't give cookies" );
121
122 global $wgServer, $wgScriptPath;
123
124 if ( !isset( $wgServer ) ) {
125 $this->markTestIncomplete( 'This test needs $wgServer to be set in LocalSettings.php' );
126 }
127 $user = self::$users['sysop'];
128 $userName = $user->getUser()->getName();
129 $password = $user->getPassword();
130
131 $req = MWHttpRequest::factory( self::$apiUrl . "?action=login&format=xml",
132 [ "method" => "POST",
133 "postData" => [
134 "lgname" => $userName,
135 "lgpassword" => $password
136 ]
137 ],
138 __METHOD__
139 );
140 $req->execute();
141
142 libxml_use_internal_errors( true );
143 $sxe = simplexml_load_string( $req->getContent() );
144 $this->assertNotInternalType( "bool", $sxe );
145 $this->assertThat( $sxe, $this->isInstanceOf( "SimpleXMLElement" ) );
146 $this->assertNotInternalType( "null", $sxe->login[0] );
147
148 $a = $sxe->login[0]->attributes()->result[0];
149 $this->assertEquals( ' result="NeedToken"', $a->asXML() );
150 $token = (string)$sxe->login[0]->attributes()->token;
151
152 $req->setData( [
153 "lgtoken" => $token,
154 "lgname" => $userName,
155 "lgpassword" => $password ] );
156 $req->execute();
157
158 $cj = $req->getCookieJar();
159 $serverName = parse_url( $wgServer, PHP_URL_HOST );
160 $this->assertNotEquals( false, $serverName );
161 $serializedCookie = $cj->serializeToHttpRequest( $wgScriptPath, $serverName );
162 $this->assertNotEquals( '', $serializedCookie );
163 $this->assertRegExp(
164 '/_session=[^;]*; .*UserID=[0-9]*; .*UserName=' . $user->userName . '; .*Token=/',
165 $serializedCookie
166 );
167 }
168
169 public function testRunLogin() {
170 $user = self::$users['sysop'];
171 $userName = $user->getUser()->getName();
172 $password = $user->getPassword();
173
174 $data = $this->doApiRequest( [
175 'action' => 'login',
176 'lgname' => $userName,
177 'lgpassword' => $password ] );
178
179 $this->assertArrayHasKey( "login", $data[0] );
180 $this->assertArrayHasKey( "result", $data[0]['login'] );
181 $this->assertEquals( "NeedToken", $data[0]['login']['result'] );
182 $token = $data[0]['login']['token'];
183
184 $data = $this->doApiRequest( [
185 'action' => 'login',
186 "lgtoken" => $token,
187 "lgname" => $userName,
188 "lgpassword" => $password ], $data[2] );
189
190 $this->assertArrayHasKey( "login", $data[0] );
191 $this->assertArrayHasKey( "result", $data[0]['login'] );
192 $this->assertEquals( "Success", $data[0]['login']['result'] );
193 $this->assertArrayHasKey( 'lgtoken', $data[0]['login'] );
194 }
195
196 public function testBotPassword() {
197 global $wgServer, $wgSessionProviders;
198
199 if ( !isset( $wgServer ) ) {
200 $this->markTestIncomplete( 'This test needs $wgServer to be set in LocalSettings.php' );
201 }
202
203 $this->setMwGlobals( [
204 'wgSessionProviders' => array_merge( $wgSessionProviders, [
205 [
206 'class' => MediaWiki\Session\BotPasswordSessionProvider::class,
207 'args' => [ [ 'priority' => 40 ] ],
208 ]
209 ] ),
210 'wgEnableBotPasswords' => true,
211 'wgBotPasswordsDatabase' => false,
212 'wgCentralIdLookupProvider' => 'local',
213 'wgGrantPermissions' => [
214 'test' => [ 'read' => true ],
215 ],
216 ] );
217
218 // Make sure our session provider is present
219 $manager = TestingAccessWrapper::newFromObject( MediaWiki\Session\SessionManager::singleton() );
220 if ( !isset( $manager->sessionProviders[MediaWiki\Session\BotPasswordSessionProvider::class] ) ) {
221 $tmp = $manager->sessionProviders;
222 $manager->sessionProviders = null;
223 $manager->sessionProviders = $tmp + $manager->getProviders();
224 }
225 $this->assertNotNull(
226 MediaWiki\Session\SessionManager::singleton()->getProvider(
227 MediaWiki\Session\BotPasswordSessionProvider::class
228 ),
229 'sanity check'
230 );
231
232 $user = self::$users['sysop'];
233 $centralId = CentralIdLookup::factory()->centralIdFromLocalUser( $user->getUser() );
234 $this->assertNotEquals( 0, $centralId, 'sanity check' );
235
236 $passwordFactory = new PasswordFactory();
237 $passwordFactory->init( RequestContext::getMain()->getConfig() );
238 // A is unsalted MD5 (thus fast) ... we don't care about security here, this is test only
239 $passwordHash = $passwordFactory->newFromPlaintext( 'foobaz' );
240
241 $dbw = wfGetDB( DB_MASTER );
242 $dbw->insert(
243 'bot_passwords',
244 [
245 'bp_user' => $centralId,
246 'bp_app_id' => 'foo',
247 'bp_password' => $passwordHash->toString(),
248 'bp_token' => '',
249 'bp_restrictions' => MWRestrictions::newDefault()->toJson(),
250 'bp_grants' => '["test"]',
251 ],
252 __METHOD__
253 );
254
255 $lgName = $user->getUser()->getName() . BotPassword::getSeparator() . 'foo';
256
257 $ret = $this->doApiRequest( [
258 'action' => 'login',
259 'lgname' => $lgName,
260 'lgpassword' => 'foobaz',
261 ] );
262
263 $result = $ret[0];
264 $this->assertNotInternalType( 'bool', $result );
265 $this->assertNotInternalType( 'null', $result['login'] );
266
267 $a = $result['login']['result'];
268 $this->assertEquals( 'NeedToken', $a );
269 $token = $result['login']['token'];
270
271 $ret = $this->doApiRequest( [
272 'action' => 'login',
273 'lgtoken' => $token,
274 'lgname' => $lgName,
275 'lgpassword' => 'foobaz',
276 ], $ret[2] );
277
278 $result = $ret[0];
279 $this->assertNotInternalType( 'bool', $result );
280 $a = $result['login']['result'];
281
282 $this->assertEquals( 'Success', $a );
283 }
284
285 }