View source
<?php
namespace Drupal\Tests\user\Functional;
use Drupal\comment\CommentInterface;
use Drupal\comment\Entity\Comment;
use Drupal\comment\Tests\CommentTestTrait;
use Drupal\node\Entity\Node;
use Drupal\Tests\BrowserTestBase;
use Drupal\user\Entity\User;
class UserCancelTest extends BrowserTestBase {
use CommentTestTrait;
public static $modules = [
'node',
'comment',
];
protected $defaultTheme = 'stark';
protected function setUp() {
parent::setUp();
$this
->drupalCreateContentType([
'type' => 'page',
'name' => 'Basic page',
]);
}
public function testUserCancelWithoutPermission() {
$node_storage = $this->container
->get('entity_type.manager')
->getStorage('node');
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$account = $this
->drupalCreateUser([]);
$this
->drupalLogin($account);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->assertNoRaw(t('Cancel account'), 'No cancel account button displayed.');
$timestamp = $account
->getLastLoginTime();
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$timestamp}/" . user_pass_rehash($account, $timestamp));
$this
->assertSession()
->statusCodeEquals(403);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$this
->assertTrue($account
->isActive(), 'User account was not canceled.');
$node_storage
->resetCache([
$node
->id(),
]);
$test_node = $node_storage
->load($node
->id());
$this
->assertTrue($test_node
->getOwnerId() == $account
->id() && $test_node
->isPublished(), 'Node of the user has not been altered.');
}
public function testUserCancelChangePermission() {
\Drupal::service('module_installer')
->install([
'user_form_test',
]);
\Drupal::service('router.builder')
->rebuild();
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$account = $this
->drupalCreateUser([]);
$admin_user = $this
->drupalCreateUser([
'cancel other accounts',
]);
$this
->drupalLogin($admin_user);
$this
->drupalPostForm('user_form_test_cancel/' . $account
->id(), [], t('Cancel account'));
$this
->assertRaw(t('%name has been deleted.', [
'%name' => $account
->getAccountName(),
]), 'User deleted.');
$this
->assertNull(User::load($account
->id()), 'User is not found in the database.');
}
public function testUserCancelUid1() {
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
\Drupal::service('module_installer')
->install([
'views',
]);
\Drupal::service('router.builder')
->rebuild();
$admin_user = $this
->drupalCreateUser([
'administer users',
]);
$this
->drupalLogin($admin_user);
$edit = [
'action' => 'user_cancel_user_action',
'user_bulk_form[0]' => TRUE,
];
$this
->drupalPostForm('admin/people', $edit, t('Apply to selected items'));
$user_storage
->resetCache([
1,
]);
$user1 = $user_storage
->load(1);
$this
->assertTrue($user1
->isActive(), 'User #1 still exists and is not blocked.');
}
public function testUserCancelInvalid() {
$node_storage = $this->container
->get('entity_type.manager')
->getStorage('node');
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$account = $this
->drupalCreateUser([
'cancel account',
]);
$this
->drupalLogin($account);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$this
->drupalPostForm('user/' . $account
->id() . '/edit', NULL, t('Cancel account'));
$timestamp = time();
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$bogus_timestamp = $timestamp + 60;
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$bogus_timestamp}/" . user_pass_rehash($account, $bogus_timestamp));
$this
->assertText(t('You have tried to use an account cancellation link that has expired. Please request a new one using the form below.'), 'Bogus cancelling request rejected.');
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$this
->assertTrue($account
->isActive(), 'User account was not canceled.');
$bogus_timestamp = $timestamp - 86400 - 60;
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$bogus_timestamp}/" . user_pass_rehash($account, $bogus_timestamp));
$this
->assertText(t('You have tried to use an account cancellation link that has expired. Please request a new one using the form below.'), 'Expired cancel account request rejected.');
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$this
->assertTrue($account
->isActive(), 'User account was not canceled.');
$node_storage
->resetCache([
$node
->id(),
]);
$test_node = $node_storage
->load($node
->id());
$this
->assertTrue($test_node
->getOwnerId() == $account
->id() && $test_node
->isPublished(), 'Node of the user has not been altered.');
}
public function testUserBlock() {
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_block')
->save();
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$web_user = $this
->drupalCreateUser([
'cancel account',
]);
$this
->drupalLogin($web_user);
$user_storage
->resetCache([
$web_user
->id(),
]);
$account = $user_storage
->load($web_user
->id());
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('Are you sure you want to cancel your account?'), 'Confirmation form to cancel account displayed.');
$this
->assertText(t('Your account will be blocked and you will no longer be able to log in. All of your content will remain attributed to your username.'), 'Informs that all content will be remain as is.');
$this
->assertNoText(t('Select the method to cancel the account above.'), 'Does not allow user to select account cancellation method.');
$timestamp = time();
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$timestamp}/" . user_pass_rehash($account, $timestamp));
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$this
->assertTrue($account
->isBlocked(), 'User has been blocked.');
$this
->assertRaw(t('%name has been disabled.', [
'%name' => $account
->getAccountName(),
]), "Confirmation message displayed to user.");
}
public function testUserBlockUnpublish() {
$node_storage = $this->container
->get('entity_type.manager')
->getStorage('node');
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_block_unpublish')
->save();
$this
->addDefaultCommentField('node', 'page');
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$account = $this
->drupalCreateUser([
'cancel account',
]);
$this
->drupalLogin($account);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$settings = get_object_vars($node);
$settings['revision'] = 1;
$node = $this
->drupalCreateNode($settings);
$comment_subject = $this
->randomMachineName(8);
$comment_body = $this
->randomMachineName(8);
$comment = Comment::create([
'subject' => $comment_subject,
'comment_body' => $comment_body,
'entity_id' => $node
->id(),
'entity_type' => 'node',
'field_name' => 'comment',
'status' => CommentInterface::PUBLISHED,
'uid' => $account
->id(),
]);
$comment
->save();
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('Are you sure you want to cancel your account?'), 'Confirmation form to cancel account displayed.');
$this
->assertText(t('Your account will be blocked and you will no longer be able to log in. All of your content will be hidden from everyone but administrators.'), 'Informs that all content will be unpublished.');
$timestamp = time();
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$timestamp}/" . user_pass_rehash($account, $timestamp));
$this
->assertSession()
->addressEquals('');
$this
->assertSession()
->statusCodeEquals(200);
$this
->assertRaw(t('%name has been disabled.', [
'%name' => $account
->getAccountName(),
]), "Confirmation message displayed to user.");
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$this
->assertTrue($account
->isBlocked(), 'User has been blocked.');
$node_storage
->resetCache([
$node
->id(),
]);
$test_node = $node_storage
->load($node
->id());
$this
->assertFalse($test_node
->isPublished(), 'Node of the user has been unpublished.');
$test_node = node_revision_load($node
->getRevisionId());
$this
->assertFalse($test_node
->isPublished(), 'Node revision of the user has been unpublished.');
$storage = \Drupal::entityTypeManager()
->getStorage('comment');
$storage
->resetCache([
$comment
->id(),
]);
$comment = $storage
->load($comment
->id());
$this
->assertFalse($comment
->isPublished(), 'Comment of the user has been unpublished.');
}
public function testUserAnonymize() {
$node_storage = $this->container
->get('entity_type.manager')
->getStorage('node');
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$this
->addDefaultCommentField('node', 'page');
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$account = $this
->drupalCreateUser([
'cancel account',
]);
$this
->drupalLogin($account);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$comment_subject = $this
->randomMachineName(8);
$comment_body = $this
->randomMachineName(8);
$comment = Comment::create([
'subject' => $comment_subject,
'comment_body' => $comment_body,
'entity_id' => $node
->id(),
'entity_type' => 'node',
'field_name' => 'comment',
'status' => CommentInterface::PUBLISHED,
'uid' => $account
->id(),
]);
$comment
->save();
$revision_node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$revision = $revision_node
->getRevisionId();
$settings = get_object_vars($revision_node);
$settings['revision'] = 1;
$settings['uid'] = 1;
$revision_node = $this
->drupalCreateNode($settings);
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('Are you sure you want to cancel your account?'), 'Confirmation form to cancel account displayed.');
$this
->assertRaw(t('Your account will be removed and all account information deleted. All of your content will be assigned to the %anonymous-name user.', [
'%anonymous-name' => $this
->config('user.settings')
->get('anonymous'),
]), 'Informs that all content will be attributed to anonymous account.');
$timestamp = time();
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$timestamp}/" . user_pass_rehash($account, $timestamp));
$user_storage
->resetCache([
$account
->id(),
]);
$this
->assertNull($user_storage
->load($account
->id()), 'User is not found in the database.');
$anonymous_user = User::getAnonymousUser();
$node_storage
->resetCache([
$node
->id(),
]);
$test_node = $node_storage
->load($node
->id());
$this
->assertTrue($test_node
->getOwnerId() == 0 && $test_node
->isPublished(), 'Node of the user has been attributed to anonymous user.');
$test_node = node_revision_load($revision, TRUE);
$this
->assertTrue($test_node
->getRevisionUser()
->id() == 0 && $test_node
->isPublished(), 'Node revision of the user has been attributed to anonymous user.');
$node_storage
->resetCache([
$revision_node
->id(),
]);
$test_node = $node_storage
->load($revision_node
->id());
$this
->assertTrue($test_node
->getOwnerId() != 0 && $test_node
->isPublished(), "Current revision of the user's node was not attributed to anonymous user.");
$storage = \Drupal::entityTypeManager()
->getStorage('comment');
$storage
->resetCache([
$comment
->id(),
]);
$test_comment = $storage
->load($comment
->id());
$this
->assertTrue($test_comment
->getOwnerId() == 0 && $test_comment
->isPublished(), 'Comment of the user has been attributed to anonymous user.');
$this
->assertEqual($test_comment
->getAuthorName(), $anonymous_user
->getDisplayName(), 'Comment of the user has been attributed to anonymous user name.');
$this
->assertRaw(t('%name has been deleted.', [
'%name' => $account
->getAccountName(),
]), "Confirmation message displayed to user.");
}
public function testUserAnonymizeBatch() {
$node_storage = $this->container
->get('entity_type.manager')
->getStorage('node');
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$account = $this
->drupalCreateUser([
'cancel account',
]);
$this
->drupalLogin($account);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$nodes = [];
for ($i = 0; $i < 11; $i++) {
$node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$nodes[$node
->id()] = $node;
}
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('Are you sure you want to cancel your account?'), 'Confirmation form to cancel account displayed.');
$this
->assertRaw(t('Your account will be removed and all account information deleted. All of your content will be assigned to the %anonymous-name user.', [
'%anonymous-name' => $this
->config('user.settings')
->get('anonymous'),
]), 'Informs that all content will be attributed to anonymous account.');
$timestamp = time();
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$timestamp}/" . user_pass_rehash($account, $timestamp));
$user_storage
->resetCache([
$account
->id(),
]);
$this
->assertNull($user_storage
->load($account
->id()), 'User is not found in the database.');
$node_storage
->resetCache(array_keys($nodes));
$test_nodes = $node_storage
->loadMultiple(array_keys($nodes));
foreach ($test_nodes as $test_node) {
$this
->assertTrue($test_node
->getOwnerId() == 0 && $test_node
->isPublished(), 'Node ' . $test_node
->id() . ' of the user has been attributed to anonymous user.');
}
}
public function testUserDelete() {
$node_storage = $this->container
->get('entity_type.manager')
->getStorage('node');
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_delete')
->save();
\Drupal::service('module_installer')
->install([
'comment',
]);
$this
->resetAll();
$this
->addDefaultCommentField('node', 'page');
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$account = $this
->drupalCreateUser([
'cancel account',
'post comments',
'skip comment approval',
]);
$this
->drupalLogin($account);
$user_storage
->resetCache([
$account
->id(),
]);
$account = $user_storage
->load($account
->id());
$node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$edit = [];
$edit['subject[0][value]'] = $this
->randomMachineName(8);
$edit['comment_body[0][value]'] = $this
->randomMachineName(16);
$this
->drupalPostForm('comment/reply/node/' . $node
->id() . '/comment', $edit, t('Preview'));
$this
->drupalPostForm(NULL, [], t('Save'));
$this
->assertText(t('Your comment has been posted.'));
$comments = \Drupal::entityTypeManager()
->getStorage('comment')
->loadByProperties([
'subject' => $edit['subject[0][value]'],
]);
$comment = reset($comments);
$this
->assertNotEmpty($comment
->id(), 'Comment found.');
$revision_node = $this
->drupalCreateNode([
'uid' => $account
->id(),
]);
$revision = $revision_node
->getRevisionId();
$settings = get_object_vars($revision_node);
$settings['revision'] = 1;
$settings['uid'] = 1;
$revision_node = $this
->drupalCreateNode($settings);
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('Are you sure you want to cancel your account?'), 'Confirmation form to cancel account displayed.');
$this
->assertText(t('Your account will be removed and all account information deleted. All of your content will also be deleted.'), 'Informs that all content will be deleted.');
$timestamp = time();
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$this
->drupalGet("user/" . $account
->id() . "/cancel/confirm/{$timestamp}/" . user_pass_rehash($account, $timestamp));
$user_storage
->resetCache([
$account
->id(),
]);
$this
->assertNull($user_storage
->load($account
->id()), 'User is not found in the database.');
$node_storage
->resetCache([
$node
->id(),
]);
$this
->assertNull($node_storage
->load($node
->id()), 'Node of the user has been deleted.');
$this
->assertNull(node_revision_load($revision), 'Node revision of the user has been deleted.');
$node_storage
->resetCache([
$revision_node
->id(),
]);
$this
->assertInstanceOf(Node::class, $node_storage
->load($revision_node
->id()));
\Drupal::entityTypeManager()
->getStorage('comment')
->resetCache([
$comment
->id(),
]);
$this
->assertNull(Comment::load($comment
->id()), 'Comment of the user has been deleted.');
$this
->assertRaw(t('%name has been deleted.', [
'%name' => $account
->getAccountName(),
]), "Confirmation message displayed to user.");
}
public function testUserCancelByAdmin() {
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$account = $this
->drupalCreateUser([]);
$admin_user = $this
->drupalCreateUser([
'administer users',
]);
$this
->drupalLogin($admin_user);
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertRaw(t('Are you sure you want to cancel the account %name?', [
'%name' => $account
->getAccountName(),
]), 'Confirmation form to cancel account displayed.');
$this
->assertText(t('Select the method to cancel the account above.'), 'Allows to select account cancellation method.');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertRaw(t('%name has been deleted.', [
'%name' => $account
->getAccountName(),
]), 'User deleted.');
$this
->assertNull(User::load($account
->id()), 'User is not found in the database.');
}
public function testUserWithoutEmailCancelByAdmin() {
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$account = $this
->drupalCreateUser([]);
$account->mail = '';
$account
->save();
$admin_user = $this
->drupalCreateUser([
'administer users',
]);
$this
->drupalLogin($admin_user);
$this
->drupalGet('user/' . $account
->id() . '/edit');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertRaw(t('Are you sure you want to cancel the account %name?', [
'%name' => $account
->getAccountName(),
]), 'Confirmation form to cancel account displayed.');
$this
->assertText(t('Select the method to cancel the account above.'), 'Allows to select account cancellation method.');
$this
->drupalPostForm(NULL, NULL, t('Cancel account'));
$this
->assertRaw(t('%name has been deleted.', [
'%name' => $account
->getAccountName(),
]), 'User deleted.');
$this
->assertNull(User::load($account
->id()), 'User is not found in the database.');
}
public function testMassUserCancelByAdmin() {
\Drupal::service('module_installer')
->install([
'views',
]);
\Drupal::service('router.builder')
->rebuild();
$this
->config('user.settings')
->set('cancel_method', 'user_cancel_reassign')
->save();
$user_storage = $this->container
->get('entity_type.manager')
->getStorage('user');
$this
->config('user.settings')
->set('notify.status_canceled', TRUE)
->save();
$admin_user = $this
->drupalCreateUser([
'administer users',
]);
$this
->drupalLogin($admin_user);
$users = [];
for ($i = 0; $i < 3; $i++) {
$account = $this
->drupalCreateUser([]);
$users[$account
->id()] = $account;
}
$edit = [];
$edit['action'] = 'user_cancel_user_action';
for ($i = 0; $i <= 4; $i++) {
$edit['user_bulk_form[' . $i . ']'] = TRUE;
}
$this
->drupalPostForm('admin/people', $edit, t('Apply to selected items'));
$this
->assertText(t('Are you sure you want to cancel these user accounts?'), 'Confirmation form to cancel accounts displayed.');
$this
->assertText(t('When cancelling these accounts'), 'Allows to select account cancellation method.');
$this
->assertText(t('Require email confirmation to cancel account'), 'Allows to send confirmation mail.');
$this
->assertText(t('Notify user when account is canceled'), 'Allows to send notification mail.');
$this
->drupalPostForm(NULL, NULL, t('Cancel accounts'));
$status = TRUE;
foreach ($users as $account) {
$status = $status && strpos($this
->getTextContent(), $account
->getAccountName() . ' has been deleted.') !== FALSE;
$user_storage
->resetCache([
$account
->id(),
]);
$status = $status && !$user_storage
->load($account
->id());
}
$this
->assertTrue($status, 'Users deleted and not found in the database.');
$this
->assertText(t('A confirmation request to cancel your account has been sent to your email address.'), 'Account cancellation request mailed message displayed.');
$admin_user = $user_storage
->load($admin_user
->id());
$this
->assertTrue($admin_user
->isActive(), 'Administrative user is found in the database and enabled.');
$user_storage
->resetCache([
1,
]);
$user1 = $user_storage
->load(1);
$this
->assertTrue($user1
->isActive(), 'User #1 still exists and is not blocked.');
}
public function testUserDeleteWithContentAndNodeAccess() {
\Drupal::service('module_installer')
->install([
'node_access_test',
]);
node_access_rebuild();
$account = $this
->drupalCreateUser([
'access content',
]);
$node = $this
->drupalCreateNode([
'type' => 'page',
'uid' => $account
->id(),
]);
$account
->delete();
$load2 = \Drupal::entityTypeManager()
->getStorage('node')
->load($node
->id());
$this
->assertTrue(empty($load2));
}
}