Mercurial > hg > cmmr2012-drupal-site
comparison core/modules/user/src/Tests/UserRegistrationTest.php @ 0:c75dbcec494b
Initial commit from drush-created site
author | Chris Cannam |
---|---|
date | Thu, 05 Jul 2018 14:24:15 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:c75dbcec494b |
---|---|
1 <?php | |
2 | |
3 namespace Drupal\user\Tests; | |
4 | |
5 use Drupal\Core\Entity\Entity\EntityFormDisplay; | |
6 use Drupal\Component\Utility\SafeMarkup; | |
7 use Drupal\Core\Field\FieldStorageDefinitionInterface; | |
8 use Drupal\field\Entity\FieldConfig; | |
9 use Drupal\field\Entity\FieldStorageConfig; | |
10 use Drupal\simpletest\WebTestBase; | |
11 | |
12 /** | |
13 * Tests registration of user under different configurations. | |
14 * | |
15 * @group user | |
16 */ | |
17 class UserRegistrationTest extends WebTestBase { | |
18 | |
19 /** | |
20 * Modules to enable. | |
21 * | |
22 * @var array | |
23 */ | |
24 public static $modules = ['field_test']; | |
25 | |
26 public function testRegistrationWithEmailVerification() { | |
27 $config = $this->config('user.settings'); | |
28 // Require email verification. | |
29 $config->set('verify_mail', TRUE)->save(); | |
30 | |
31 // Set registration to administrator only. | |
32 $config->set('register', USER_REGISTER_ADMINISTRATORS_ONLY)->save(); | |
33 $this->drupalGet('user/register'); | |
34 $this->assertResponse(403, 'Registration page is inaccessible when only administrators can create accounts.'); | |
35 | |
36 // Allow registration by site visitors without administrator approval. | |
37 $config->set('register', USER_REGISTER_VISITORS)->save(); | |
38 $edit = []; | |
39 $edit['name'] = $name = $this->randomMachineName(); | |
40 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
41 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
42 $this->assertText(t('A welcome message with further instructions has been sent to your email address.'), 'User registered successfully.'); | |
43 | |
44 /** @var EntityStorageInterface $storage */ | |
45 $storage = $this->container->get('entity_type.manager')->getStorage('user'); | |
46 $accounts = $storage->loadByProperties(['name' => $name, 'mail' => $mail]); | |
47 $new_user = reset($accounts); | |
48 $this->assertTrue($new_user->isActive(), 'New account is active after registration.'); | |
49 $resetURL = user_pass_reset_url($new_user); | |
50 $this->drupalGet($resetURL); | |
51 $this->assertTitle(t('Set password | Drupal'), 'Page title is "Set password".'); | |
52 | |
53 // Allow registration by site visitors, but require administrator approval. | |
54 $config->set('register', USER_REGISTER_VISITORS_ADMINISTRATIVE_APPROVAL)->save(); | |
55 $edit = []; | |
56 $edit['name'] = $name = $this->randomMachineName(); | |
57 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
58 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
59 $this->container->get('entity.manager')->getStorage('user')->resetCache(); | |
60 $accounts = $storage->loadByProperties(['name' => $name, 'mail' => $mail]); | |
61 $new_user = reset($accounts); | |
62 $this->assertFalse($new_user->isActive(), 'New account is blocked until approved by an administrator.'); | |
63 } | |
64 | |
65 public function testRegistrationWithoutEmailVerification() { | |
66 $config = $this->config('user.settings'); | |
67 // Don't require email verification and allow registration by site visitors | |
68 // without administrator approval. | |
69 $config | |
70 ->set('verify_mail', FALSE) | |
71 ->set('register', USER_REGISTER_VISITORS) | |
72 ->save(); | |
73 | |
74 $edit = []; | |
75 $edit['name'] = $name = $this->randomMachineName(); | |
76 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
77 | |
78 // Try entering a mismatching password. | |
79 $edit['pass[pass1]'] = '99999.0'; | |
80 $edit['pass[pass2]'] = '99999'; | |
81 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
82 $this->assertText(t('The specified passwords do not match.'), 'Typing mismatched passwords displays an error message.'); | |
83 | |
84 // Enter a correct password. | |
85 $edit['pass[pass1]'] = $new_pass = $this->randomMachineName(); | |
86 $edit['pass[pass2]'] = $new_pass; | |
87 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
88 $this->container->get('entity.manager')->getStorage('user')->resetCache(); | |
89 $accounts = $this->container->get('entity_type.manager')->getStorage('user') | |
90 ->loadByProperties(['name' => $name, 'mail' => $mail]); | |
91 $new_user = reset($accounts); | |
92 $this->assertNotNull($new_user, 'New account successfully created with matching passwords.'); | |
93 $this->assertText(t('Registration successful. You are now logged in.'), 'Users are logged in after registering.'); | |
94 $this->drupalLogout(); | |
95 | |
96 // Allow registration by site visitors, but require administrator approval. | |
97 $config->set('register', USER_REGISTER_VISITORS_ADMINISTRATIVE_APPROVAL)->save(); | |
98 $edit = []; | |
99 $edit['name'] = $name = $this->randomMachineName(); | |
100 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
101 $edit['pass[pass1]'] = $pass = $this->randomMachineName(); | |
102 $edit['pass[pass2]'] = $pass; | |
103 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
104 $this->assertText(t('Thank you for applying for an account. Your account is currently pending approval by the site administrator.'), 'Users are notified of pending approval'); | |
105 | |
106 // Try to log in before administrator approval. | |
107 $auth = [ | |
108 'name' => $name, | |
109 'pass' => $pass, | |
110 ]; | |
111 $this->drupalPostForm('user/login', $auth, t('Log in')); | |
112 $this->assertText(t('The username @name has not been activated or is blocked.', ['@name' => $name]), 'User cannot log in yet.'); | |
113 | |
114 // Activate the new account. | |
115 $accounts = $this->container->get('entity_type.manager')->getStorage('user') | |
116 ->loadByProperties(['name' => $name, 'mail' => $mail]); | |
117 $new_user = reset($accounts); | |
118 $admin_user = $this->drupalCreateUser(['administer users']); | |
119 $this->drupalLogin($admin_user); | |
120 $edit = [ | |
121 'status' => 1, | |
122 ]; | |
123 $this->drupalPostForm('user/' . $new_user->id() . '/edit', $edit, t('Save')); | |
124 $this->drupalLogout(); | |
125 | |
126 // Log in after administrator approval. | |
127 $this->drupalPostForm('user/login', $auth, t('Log in')); | |
128 $this->assertText(t('Member for'), 'User can log in after administrator approval.'); | |
129 } | |
130 | |
131 public function testRegistrationEmailDuplicates() { | |
132 // Don't require email verification and allow registration by site visitors | |
133 // without administrator approval. | |
134 $this->config('user.settings') | |
135 ->set('verify_mail', FALSE) | |
136 ->set('register', USER_REGISTER_VISITORS) | |
137 ->save(); | |
138 | |
139 // Set up a user to check for duplicates. | |
140 $duplicate_user = $this->drupalCreateUser(); | |
141 | |
142 $edit = []; | |
143 $edit['name'] = $this->randomMachineName(); | |
144 $edit['mail'] = $duplicate_user->getEmail(); | |
145 | |
146 // Attempt to create a new account using an existing email address. | |
147 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
148 $this->assertText(t('The email address @email is already taken.', ['@email' => $duplicate_user->getEmail()]), 'Supplying an exact duplicate email address displays an error message'); | |
149 | |
150 // Attempt to bypass duplicate email registration validation by adding spaces. | |
151 $edit['mail'] = ' ' . $duplicate_user->getEmail() . ' '; | |
152 | |
153 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
154 $this->assertText(t('The email address @email is already taken.', ['@email' => $duplicate_user->getEmail()]), 'Supplying a duplicate email address with added whitespace displays an error message'); | |
155 } | |
156 | |
157 /** | |
158 * Tests that UUID isn't cached in form state on register form. | |
159 * | |
160 * This is a regression test for https://www.drupal.org/node/2500527 to ensure | |
161 * that the form is not cached on GET requests. | |
162 */ | |
163 public function testUuidFormState() { | |
164 \Drupal::service('module_installer')->install(['image']); | |
165 \Drupal::service('router.builder')->rebuild(); | |
166 | |
167 // Add a picture field in order to ensure that no form cache is written, | |
168 // which breaks registration of more than 1 user every 6 hours. | |
169 $field_storage = FieldStorageConfig::create([ | |
170 'field_name' => 'user_picture', | |
171 'entity_type' => 'user', | |
172 'type' => 'image', | |
173 ]); | |
174 $field_storage->save(); | |
175 | |
176 $field = FieldConfig::create([ | |
177 'field_name' => 'user_picture', | |
178 'entity_type' => 'user', | |
179 'bundle' => 'user', | |
180 ]); | |
181 $field->save(); | |
182 | |
183 $form_display = EntityFormDisplay::create([ | |
184 'targetEntityType' => 'user', | |
185 'bundle' => 'user', | |
186 'mode' => 'default', | |
187 'status' => TRUE, | |
188 ]); | |
189 $form_display->setComponent('user_picture', [ | |
190 'type' => 'image_image', | |
191 ]); | |
192 $form_display->save(); | |
193 | |
194 // Don't require email verification and allow registration by site visitors | |
195 // without administrator approval. | |
196 $this->config('user.settings') | |
197 ->set('verify_mail', FALSE) | |
198 ->set('register', USER_REGISTER_VISITORS) | |
199 ->save(); | |
200 | |
201 $edit = []; | |
202 $edit['name'] = $this->randomMachineName(); | |
203 $edit['mail'] = $edit['name'] . '@example.com'; | |
204 $edit['pass[pass2]'] = $edit['pass[pass1]'] = $this->randomMachineName(); | |
205 | |
206 // Create one account. | |
207 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
208 $this->assertResponse(200); | |
209 | |
210 $user_storage = \Drupal::entityManager()->getStorage('user'); | |
211 | |
212 $this->assertTrue($user_storage->loadByProperties(['name' => $edit['name']])); | |
213 $this->drupalLogout(); | |
214 | |
215 // Create a second account. | |
216 $edit['name'] = $this->randomMachineName(); | |
217 $edit['mail'] = $edit['name'] . '@example.com'; | |
218 $edit['pass[pass2]'] = $edit['pass[pass1]'] = $this->randomMachineName(); | |
219 | |
220 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
221 $this->assertResponse(200); | |
222 | |
223 $this->assertTrue($user_storage->loadByProperties(['name' => $edit['name']])); | |
224 } | |
225 | |
226 public function testRegistrationDefaultValues() { | |
227 // Don't require email verification and allow registration by site visitors | |
228 // without administrator approval. | |
229 $config_user_settings = $this->config('user.settings') | |
230 ->set('verify_mail', FALSE) | |
231 ->set('register', USER_REGISTER_VISITORS) | |
232 ->save(); | |
233 | |
234 // Set the default timezone to Brussels. | |
235 $config_system_date = $this->config('system.date') | |
236 ->set('timezone.user.configurable', 1) | |
237 ->set('timezone.default', 'Europe/Brussels') | |
238 ->save(); | |
239 | |
240 // Check the presence of expected cache tags. | |
241 $this->drupalGet('user/register'); | |
242 $this->assertCacheTag('config:user.settings'); | |
243 | |
244 $edit = []; | |
245 $edit['name'] = $name = $this->randomMachineName(); | |
246 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
247 $edit['pass[pass1]'] = $new_pass = $this->randomMachineName(); | |
248 $edit['pass[pass2]'] = $new_pass; | |
249 $this->drupalPostForm(NULL, $edit, t('Create new account')); | |
250 | |
251 // Check user fields. | |
252 $accounts = $this->container->get('entity_type.manager')->getStorage('user') | |
253 ->loadByProperties(['name' => $name, 'mail' => $mail]); | |
254 $new_user = reset($accounts); | |
255 $this->assertEqual($new_user->getUsername(), $name, 'Username matches.'); | |
256 $this->assertEqual($new_user->getEmail(), $mail, 'Email address matches.'); | |
257 $this->assertTrue(($new_user->getCreatedTime() > REQUEST_TIME - 20), 'Correct creation time.'); | |
258 $this->assertEqual($new_user->isActive(), $config_user_settings->get('register') == USER_REGISTER_VISITORS ? 1 : 0, 'Correct status field.'); | |
259 $this->assertEqual($new_user->getTimezone(), $config_system_date->get('timezone.default'), 'Correct time zone field.'); | |
260 $this->assertEqual($new_user->langcode->value, \Drupal::languageManager()->getDefaultLanguage()->getId(), 'Correct language field.'); | |
261 $this->assertEqual($new_user->preferred_langcode->value, \Drupal::languageManager()->getDefaultLanguage()->getId(), 'Correct preferred language field.'); | |
262 $this->assertEqual($new_user->init->value, $mail, 'Correct init field.'); | |
263 } | |
264 | |
265 /** | |
266 * Tests username and email field constraints on user registration. | |
267 * | |
268 * @see \Drupal\user\Plugin\Validation\Constraint\UserNameUnique | |
269 * @see \Drupal\user\Plugin\Validation\Constraint\UserMailUnique | |
270 */ | |
271 public function testUniqueFields() { | |
272 $account = $this->drupalCreateUser(); | |
273 | |
274 $edit = ['mail' => 'test@example.com', 'name' => $account->getUsername()]; | |
275 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
276 $this->assertRaw(SafeMarkup::format('The username %value is already taken.', ['%value' => $account->getUsername()])); | |
277 | |
278 $edit = ['mail' => $account->getEmail(), 'name' => $this->randomString()]; | |
279 $this->drupalPostForm('user/register', $edit, t('Create new account')); | |
280 $this->assertRaw(SafeMarkup::format('The email address %value is already taken.', ['%value' => $account->getEmail()])); | |
281 } | |
282 | |
283 /** | |
284 * Tests Field API fields on user registration forms. | |
285 */ | |
286 public function testRegistrationWithUserFields() { | |
287 // Create a field on 'user' entity type. | |
288 $field_storage = FieldStorageConfig::create([ | |
289 'field_name' => 'test_user_field', | |
290 'entity_type' => 'user', | |
291 'type' => 'test_field', | |
292 'cardinality' => 1, | |
293 ]); | |
294 $field_storage->save(); | |
295 $field = FieldConfig::create([ | |
296 'field_storage' => $field_storage, | |
297 'label' => 'Some user field', | |
298 'bundle' => 'user', | |
299 'required' => TRUE, | |
300 ]); | |
301 $field->save(); | |
302 entity_get_form_display('user', 'user', 'default') | |
303 ->setComponent('test_user_field', ['type' => 'test_field_widget']) | |
304 ->save(); | |
305 entity_get_form_display('user', 'user', 'register') | |
306 ->save(); | |
307 | |
308 // Check that the field does not appear on the registration form. | |
309 $this->drupalGet('user/register'); | |
310 $this->assertNoText($field->label(), 'The field does not appear on user registration form'); | |
311 $this->assertCacheTag('config:core.entity_form_display.user.user.register'); | |
312 $this->assertCacheTag('config:user.settings'); | |
313 | |
314 // Have the field appear on the registration form. | |
315 entity_get_form_display('user', 'user', 'register') | |
316 ->setComponent('test_user_field', ['type' => 'test_field_widget']) | |
317 ->save(); | |
318 | |
319 $this->drupalGet('user/register'); | |
320 $this->assertText($field->label(), 'The field appears on user registration form'); | |
321 $this->assertRegistrationFormCacheTagsWithUserFields(); | |
322 | |
323 // Check that validation errors are correctly reported. | |
324 $edit = []; | |
325 $edit['name'] = $name = $this->randomMachineName(); | |
326 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
327 // Missing input in required field. | |
328 $edit['test_user_field[0][value]'] = ''; | |
329 $this->drupalPostForm(NULL, $edit, t('Create new account')); | |
330 $this->assertRegistrationFormCacheTagsWithUserFields(); | |
331 $this->assertRaw(t('@name field is required.', ['@name' => $field->label()]), 'Field validation error was correctly reported.'); | |
332 // Invalid input. | |
333 $edit['test_user_field[0][value]'] = '-1'; | |
334 $this->drupalPostForm(NULL, $edit, t('Create new account')); | |
335 $this->assertRegistrationFormCacheTagsWithUserFields(); | |
336 $this->assertRaw(t('%name does not accept the value -1.', ['%name' => $field->label()]), 'Field validation error was correctly reported.'); | |
337 | |
338 // Submit with valid data. | |
339 $value = rand(1, 255); | |
340 $edit['test_user_field[0][value]'] = $value; | |
341 $this->drupalPostForm(NULL, $edit, t('Create new account')); | |
342 // Check user fields. | |
343 $accounts = $this->container->get('entity_type.manager')->getStorage('user') | |
344 ->loadByProperties(['name' => $name, 'mail' => $mail]); | |
345 $new_user = reset($accounts); | |
346 $this->assertEqual($new_user->test_user_field->value, $value, 'The field value was correctly saved.'); | |
347 | |
348 // Check that the 'add more' button works. | |
349 $field_storage->setCardinality(FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED); | |
350 $field_storage->save(); | |
351 foreach (['js', 'nojs'] as $js) { | |
352 $this->drupalGet('user/register'); | |
353 $this->assertRegistrationFormCacheTagsWithUserFields(); | |
354 // Add two inputs. | |
355 $value = rand(1, 255); | |
356 $edit = []; | |
357 $edit['test_user_field[0][value]'] = $value; | |
358 if ($js == 'js') { | |
359 $this->drupalPostAjaxForm(NULL, $edit, 'test_user_field_add_more'); | |
360 $this->drupalPostAjaxForm(NULL, $edit, 'test_user_field_add_more'); | |
361 } | |
362 else { | |
363 $this->drupalPostForm(NULL, $edit, t('Add another item')); | |
364 $this->drupalPostForm(NULL, $edit, t('Add another item')); | |
365 } | |
366 // Submit with three values. | |
367 $edit['test_user_field[1][value]'] = $value + 1; | |
368 $edit['test_user_field[2][value]'] = $value + 2; | |
369 $edit['name'] = $name = $this->randomMachineName(); | |
370 $edit['mail'] = $mail = $edit['name'] . '@example.com'; | |
371 $this->drupalPostForm(NULL, $edit, t('Create new account')); | |
372 // Check user fields. | |
373 $accounts = $this->container->get('entity_type.manager')->getStorage('user') | |
374 ->loadByProperties(['name' => $name, 'mail' => $mail]); | |
375 $new_user = reset($accounts); | |
376 $this->assertEqual($new_user->test_user_field[0]->value, $value, format_string('@js : The field value was correctly saved.', ['@js' => $js])); | |
377 $this->assertEqual($new_user->test_user_field[1]->value, $value + 1, format_string('@js : The field value was correctly saved.', ['@js' => $js])); | |
378 $this->assertEqual($new_user->test_user_field[2]->value, $value + 2, format_string('@js : The field value was correctly saved.', ['@js' => $js])); | |
379 } | |
380 } | |
381 | |
382 /** | |
383 * Asserts the presence of cache tags on registration form with user fields. | |
384 */ | |
385 protected function assertRegistrationFormCacheTagsWithUserFields() { | |
386 $this->assertCacheTag('config:core.entity_form_display.user.user.register'); | |
387 $this->assertCacheTag('config:field.field.user.user.test_user_field'); | |
388 $this->assertCacheTag('config:field.storage.user.test_user_field'); | |
389 $this->assertCacheTag('config:user.settings'); | |
390 } | |
391 | |
392 } |