Issue #2936995 by viappidu, mcaddz, acbramley, slydevil, yash.rode, sokru, quietone, Sandeep_k, smustgrave, amateescu, AaronMcHale, lauriii, longwave: Add taxonomy term revision UI
parent
bf4e65cf04
commit
4a0bdc34a4
|
@ -8,3 +8,4 @@ name: Forums
|
|||
vid: forums
|
||||
description: 'Forum navigation vocabulary'
|
||||
weight: -10
|
||||
new_revision: false
|
||||
|
|
|
@ -88,6 +88,7 @@ class VocabularyTest extends ConfigEntityResourceTestBase {
|
|||
'status' => TRUE,
|
||||
'dependencies' => [],
|
||||
'name' => 'Llama',
|
||||
'new_revision' => FALSE,
|
||||
'description' => NULL,
|
||||
'weight' => 0,
|
||||
'drupal_internal__vid' => 'llama',
|
||||
|
|
|
@ -5,3 +5,4 @@ name: Track changes import term
|
|||
vid: track_changes_import_term
|
||||
description: ''
|
||||
weight: 0
|
||||
new_revision: false
|
||||
|
|
|
@ -5,3 +5,4 @@ name: Tags
|
|||
vid: tags
|
||||
description: 'Use tags to group articles on similar topics into categories.'
|
||||
weight: 0
|
||||
new_revision: false
|
||||
|
|
|
@ -40,6 +40,9 @@ taxonomy.vocabulary.*:
|
|||
weight:
|
||||
type: integer
|
||||
label: 'Weight'
|
||||
new_revision:
|
||||
type: boolean
|
||||
label: 'Whether a new revision should be created by default'
|
||||
|
||||
field.formatter.settings.entity_reference_rss_category:
|
||||
type: mapping
|
||||
|
|
|
@ -32,7 +32,12 @@ use Drupal\user\StatusItem;
|
|||
* "views_data" = "Drupal\taxonomy\TermViewsData",
|
||||
* "form" = {
|
||||
* "default" = "Drupal\taxonomy\TermForm",
|
||||
* "delete" = "Drupal\taxonomy\Form\TermDeleteForm"
|
||||
* "delete" = "Drupal\taxonomy\Form\TermDeleteForm",
|
||||
* "revision-delete" = \Drupal\Core\Entity\Form\RevisionDeleteForm::class,
|
||||
* "revision-revert" = \Drupal\Core\Entity\Form\RevisionRevertForm::class,
|
||||
* },
|
||||
* "route_provider" = {
|
||||
* "revision" = \Drupal\Core\Entity\Routing\RevisionHtmlRouteProvider::class,
|
||||
* },
|
||||
* "translation" = "Drupal\taxonomy\TermTranslationHandler"
|
||||
* },
|
||||
|
@ -40,6 +45,7 @@ use Drupal\user\StatusItem;
|
|||
* data_table = "taxonomy_term_field_data",
|
||||
* revision_table = "taxonomy_term_revision",
|
||||
* revision_data_table = "taxonomy_term_field_revision",
|
||||
* show_revision_ui = TRUE,
|
||||
* translatable = TRUE,
|
||||
* entity_keys = {
|
||||
* "id" = "tid",
|
||||
|
@ -63,6 +69,10 @@ use Drupal\user\StatusItem;
|
|||
* "delete-form" = "/taxonomy/term/{taxonomy_term}/delete",
|
||||
* "edit-form" = "/taxonomy/term/{taxonomy_term}/edit",
|
||||
* "create" = "/taxonomy/term",
|
||||
* "revision" = "/taxonomy/term/{taxonomy_term}/revision/{taxonomy_term_revision}/view",
|
||||
* "revision-delete-form" = "/taxonomy/term/{taxonomy_term}/revision/{taxonomy_term_revision}/delete",
|
||||
* "revision-revert-form" = "/taxonomy/term/{taxonomy_term}/revision/{taxonomy_term_revision}/revert",
|
||||
* "version-history" = "/taxonomy/term/{taxonomy_term}/revisions",
|
||||
* },
|
||||
* permission_granularity = "bundle",
|
||||
* collection_permission = "access taxonomy overview",
|
||||
|
|
|
@ -57,6 +57,7 @@ use Drupal\taxonomy\VocabularyInterface;
|
|||
* "vid",
|
||||
* "description",
|
||||
* "weight",
|
||||
* "new_revision",
|
||||
* }
|
||||
* )
|
||||
*/
|
||||
|
@ -104,6 +105,13 @@ class Vocabulary extends ConfigEntityBundleBase implements VocabularyInterface {
|
|||
return $this->description;
|
||||
}
|
||||
|
||||
/**
|
||||
* The default revision setting for a vocabulary.
|
||||
*
|
||||
* @var bool
|
||||
*/
|
||||
protected $new_revision = FALSE;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
|
@ -161,4 +169,18 @@ class Vocabulary extends ConfigEntityBundleBase implements VocabularyInterface {
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function setNewRevision($new_revision) {
|
||||
$this->new_revision = $new_revision;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function shouldCreateNewRevision() {
|
||||
return $this->new_revision;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -69,6 +69,15 @@ class TaxonomyPermissions implements ContainerInjectionInterface {
|
|||
"create terms in $id" => ['title' => $this->t('%vocabulary: Create terms', $args)],
|
||||
"delete terms in $id" => ['title' => $this->t('%vocabulary: Delete terms', $args)],
|
||||
"edit terms in $id" => ['title' => $this->t('%vocabulary: Edit terms', $args)],
|
||||
"view term revisions in $id" => ['title' => $this->t('%vocabulary: View term revisions', $args)],
|
||||
"revert term revisions in $id" => [
|
||||
'title' => $this->t('%vocabulary: Revert term revisions', $args),
|
||||
'description' => $this->t('To revert a revision you also need permission to edit the taxonomy term.'),
|
||||
],
|
||||
"delete term revisions in $id" => [
|
||||
'title' => $this->t('%vocabulary: Delete term revisions', $args),
|
||||
'description' => $this->t('To delete a revision you also need permission to delete the taxonomy term.'),
|
||||
],
|
||||
];
|
||||
}
|
||||
|
||||
|
|
|
@ -46,6 +46,25 @@ class TermAccessControlHandler extends EntityAccessControlHandler {
|
|||
|
||||
return AccessResult::neutral()->setReason("The following permissions are required: 'delete terms in {$entity->bundle()}' OR 'administer taxonomy'.");
|
||||
|
||||
case 'view revision':
|
||||
case 'view all revisions':
|
||||
if ($account->hasPermission("view term revisions in {$entity->bundle()}") || $account->hasPermission("view all taxonomy revisions")) {
|
||||
return AccessResult::allowed()->cachePerPermissions();
|
||||
}
|
||||
return AccessResult::neutral()->setReason("The following permissions are required: 'view revisions in {$entity->bundle()}' OR 'view all taxonomy revisions'.");
|
||||
|
||||
case 'revert':
|
||||
if (($account->hasPermission("revert term revisions in {$entity->bundle()}") && $account->hasPermission("edit terms in {$entity->bundle()}")) || $account->hasPermission("revert all taxonomy revisions")) {
|
||||
return AccessResult::allowed()->cachePerPermissions();
|
||||
}
|
||||
return AccessResult::neutral()->setReason("The following permissions are required: 'revert term revisions in {$entity->bundle()}' OR 'revert all taxonomy revisions'.");
|
||||
|
||||
case 'delete revision':
|
||||
if (($account->hasPermission("delete term revisions in {$entity->bundle()}") && $account->hasPermission("delete terms in {$entity->bundle()}")) || $account->hasPermission("delete all taxonomy revisions")) {
|
||||
return AccessResult::allowed()->cachePerPermissions();
|
||||
}
|
||||
return AccessResult::neutral()->setReason("The following permissions are required: 'delete term revisions in {$entity->bundle()}' OR 'delete all taxonomy revisions'.");
|
||||
|
||||
default:
|
||||
// No opinion.
|
||||
return AccessResult::neutral()->cachePerPermissions();
|
||||
|
|
|
@ -76,6 +76,13 @@ class VocabularyForm extends BundleEntityFormBase {
|
|||
'#default_value' => $vocabulary->getDescription(),
|
||||
];
|
||||
|
||||
$form['revision'] = [
|
||||
'#type' => 'checkbox',
|
||||
'#title' => $this->t('Create new revision'),
|
||||
'#default_value' => $vocabulary->shouldCreateNewRevision(),
|
||||
'#description' => $this->t('Create a new revision by default for this vocabulary.'),
|
||||
];
|
||||
|
||||
// $form['langcode'] is not wrapped in an
|
||||
// if ($this->moduleHandler->moduleExists('language')) check because the
|
||||
// language_select form element works also without the language module being
|
||||
|
@ -117,6 +124,7 @@ class VocabularyForm extends BundleEntityFormBase {
|
|||
*/
|
||||
public function save(array $form, FormStateInterface $form_state) {
|
||||
$vocabulary = $this->entity;
|
||||
$vocabulary->setNewRevision($form_state->getValue(['revision']));
|
||||
|
||||
// Prevent leading and trailing spaces in vocabulary names.
|
||||
$vocabulary->set('name', trim($vocabulary->label()));
|
||||
|
|
|
@ -3,11 +3,12 @@
|
|||
namespace Drupal\taxonomy;
|
||||
|
||||
use Drupal\Core\Config\Entity\ConfigEntityInterface;
|
||||
use Drupal\Core\Entity\RevisionableEntityBundleInterface;
|
||||
|
||||
/**
|
||||
* Provides an interface defining a taxonomy vocabulary entity.
|
||||
*/
|
||||
interface VocabularyInterface extends ConfigEntityInterface {
|
||||
interface VocabularyInterface extends ConfigEntityInterface, RevisionableEntityBundleInterface {
|
||||
|
||||
/**
|
||||
* Denotes that no term in the vocabulary has a parent.
|
||||
|
@ -32,4 +33,12 @@ interface VocabularyInterface extends ConfigEntityInterface {
|
|||
*/
|
||||
public function getDescription();
|
||||
|
||||
/**
|
||||
* Sets whether a new revision should be created by default.
|
||||
*
|
||||
* @param bool $new_revision
|
||||
* TRUE if a new revision should be created by default.
|
||||
*/
|
||||
public function setNewRevision($new_revision);
|
||||
|
||||
}
|
||||
|
|
|
@ -5,9 +5,33 @@
|
|||
* Install, update and uninstall functions for the taxonomy module.
|
||||
*/
|
||||
|
||||
use Drupal\Core\Entity\Form\RevisionDeleteForm;
|
||||
use Drupal\Core\Entity\Form\RevisionRevertForm;
|
||||
use Drupal\Core\Entity\Routing\RevisionHtmlRouteProvider;
|
||||
use Drupal\Core\StringTranslation\TranslatableMarkup;
|
||||
|
||||
/**
|
||||
* Implements hook_update_last_removed().
|
||||
*/
|
||||
function taxonomy_update_last_removed() {
|
||||
return 8702;
|
||||
}
|
||||
|
||||
/**
|
||||
* Update entity definition to handle revision routes.
|
||||
*/
|
||||
function taxonomy_update_10100(&$sandbox = NULL): TranslatableMarkup {
|
||||
$entityDefinitionUpdateManager = \Drupal::entityDefinitionUpdateManager();
|
||||
$definition = $entityDefinitionUpdateManager->getEntityType('taxonomy_term');
|
||||
$routeProviders = $definition->get('route_provider');
|
||||
$routeProviders['revision'] = RevisionHtmlRouteProvider::class;
|
||||
$definition
|
||||
->setFormClass('revision-delete', RevisionDeleteForm::class)
|
||||
->setFormClass('revision-revert', RevisionRevertForm::class)
|
||||
->set('route_provider', $routeProviders)
|
||||
->setLinkTemplate('revision-delete-form', '/taxonomy/term/{taxonomy_term}/revision/{taxonomy_term}/delete')
|
||||
->setLinkTemplate('revision-revert-form', '/taxonomy/term/{taxonomy_term}/revision/{taxonomy_term}/revert')
|
||||
->setLinkTemplate('version-history', '/taxonomy/term/{taxonomy_term}/revisions');
|
||||
$entityDefinitionUpdateManager->updateEntityType($definition);
|
||||
return \t('Added revision routes to Taxonomy Term entity type.');
|
||||
}
|
||||
|
|
|
@ -5,5 +5,14 @@ access taxonomy overview:
|
|||
title: 'Access the taxonomy vocabulary overview page'
|
||||
description: 'Get an overview of all taxonomy vocabularies.'
|
||||
|
||||
revert all taxonomy revisions:
|
||||
title: 'Revert all term revisions'
|
||||
|
||||
delete all taxonomy revisions:
|
||||
title: 'Delete all term revisions'
|
||||
|
||||
view all taxonomy revisions:
|
||||
title: 'View all term revisions'
|
||||
|
||||
permission_callbacks:
|
||||
- Drupal\taxonomy\TaxonomyPermissions::permissions
|
||||
|
|
|
@ -5,6 +5,8 @@
|
|||
* Post update functions for Taxonomy.
|
||||
*/
|
||||
|
||||
use Drupal\Core\Config\Entity\ConfigEntityUpdater;
|
||||
|
||||
/**
|
||||
* Implements hook_removed_post_updates().
|
||||
*/
|
||||
|
@ -19,3 +21,13 @@ function taxonomy_removed_post_updates() {
|
|||
'taxonomy_post_update_clear_views_argument_validator_plugins_cache' => '10.0.0',
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* Re-save Taxonomy configurations with new_revision config.
|
||||
*/
|
||||
function taxonomy_post_update_set_new_revision(&$sandbox = NULL) {
|
||||
\Drupal::classResolver(ConfigEntityUpdater::class)
|
||||
->update($sandbox, 'taxonomy_vocabulary', function () {
|
||||
return TRUE;
|
||||
});
|
||||
}
|
||||
|
|
|
@ -55,6 +55,7 @@ abstract class VocabularyResourceTestBase extends ConfigEntityResourceTestBase {
|
|||
'name' => 'Llama',
|
||||
'description' => NULL,
|
||||
'weight' => 0,
|
||||
'new_revision' => FALSE,
|
||||
];
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,112 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Drupal\Tests\taxonomy\Functional;
|
||||
|
||||
use Drupal\Tests\BrowserTestBase;
|
||||
use Drupal\taxonomy\Entity\Term;
|
||||
use Drupal\Tests\taxonomy\Traits\TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* Taxonomy term revision delete form test.
|
||||
*
|
||||
* @group taxonomy
|
||||
* @coversDefaultClass \Drupal\Core\Entity\Form\RevisionDeleteForm
|
||||
*/
|
||||
class TaxonomyRevisionDeleteTest extends BrowserTestBase {
|
||||
|
||||
use TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected static $modules = [
|
||||
'system',
|
||||
'taxonomy',
|
||||
];
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $defaultTheme = 'stark';
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $permissions = [
|
||||
'view term revisions in test',
|
||||
'delete all taxonomy revisions',
|
||||
];
|
||||
|
||||
/**
|
||||
* Vocabulary for testing.
|
||||
*
|
||||
* @var \Drupal\taxonomy\VocabularyInterface
|
||||
*/
|
||||
private $vocabulary;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected function setUp(): void {
|
||||
parent::setUp();
|
||||
$this->vocabulary = $this->createVocabulary(['vid' => 'test', 'name' => 'Test']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests revision delete.
|
||||
*/
|
||||
public function testDeleteForm(): void {
|
||||
$termName = $this->randomMachineName();
|
||||
$entity = Term::create([
|
||||
'vid' => $this->vocabulary->id(),
|
||||
'name' => $termName,
|
||||
]);
|
||||
|
||||
$entity->setRevisionCreationTime((new \DateTimeImmutable('11 January 2009 4pm'))->getTimestamp())
|
||||
->setRevisionTranslationAffected(TRUE);
|
||||
$entity->setNewRevision();
|
||||
$entity->save();
|
||||
$revisionId = $entity->getRevisionId();
|
||||
|
||||
$this->drupalLogin($this->drupalCreateUser($this->permissions));
|
||||
|
||||
// Cannot delete latest revision.
|
||||
$this->drupalGet($entity->toUrl('revision-delete-form'));
|
||||
$this->assertSession()->statusCodeEquals(403);
|
||||
|
||||
// Create a new latest revision.
|
||||
$entity
|
||||
->setRevisionCreationTime((new \DateTimeImmutable('11 January 2009 5pm'))->getTimestamp())
|
||||
->setRevisionTranslationAffected(TRUE)
|
||||
->setNewRevision();
|
||||
$entity->save();
|
||||
|
||||
// Reload the entity.
|
||||
$revision = \Drupal::entityTypeManager()->getStorage('taxonomy_term')
|
||||
->loadRevision($revisionId);
|
||||
$this->drupalGet($revision->toUrl('revision-delete-form'));
|
||||
$this->assertSession()->pageTextContains('Are you sure you want to delete the revision from Sun, 01/11/2009 - 16:00?');
|
||||
$this->assertSession()->buttonExists('Delete');
|
||||
$this->assertSession()->linkExists('Cancel');
|
||||
|
||||
$countRevisions = static function (): int {
|
||||
return (int) \Drupal::entityTypeManager()->getStorage('taxonomy_term')
|
||||
->getQuery()
|
||||
->accessCheck(FALSE)
|
||||
->allRevisions()
|
||||
->count()
|
||||
->execute();
|
||||
};
|
||||
|
||||
$count = $countRevisions();
|
||||
$this->submitForm([], 'Delete');
|
||||
$this->assertEquals($count - 1, $countRevisions());
|
||||
$this->assertSession()->statusCodeEquals(200);
|
||||
$this->assertSession()->addressEquals(sprintf('taxonomy/term/%s/revisions', $entity->id()));
|
||||
$this->assertSession()->pageTextContains(sprintf('Revision from Sun, 01/11/2009 - 16:00 of Test %s has been deleted.', $termName));
|
||||
$this->assertSession()->elementsCount('css', 'table tbody tr', 1);
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,112 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Drupal\Tests\taxonomy\Functional;
|
||||
|
||||
use Drupal\Tests\BrowserTestBase;
|
||||
use Drupal\taxonomy\Entity\Term;
|
||||
use Drupal\Tests\taxonomy\Traits\TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* Taxonomy term revision form test.
|
||||
*
|
||||
* @group taxonomy
|
||||
* @coversDefaultClass \Drupal\Core\Entity\Form\RevisionRevertForm
|
||||
*/
|
||||
class TaxonomyRevisionRevertTest extends BrowserTestBase {
|
||||
|
||||
use TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected static $modules = [
|
||||
'system',
|
||||
'taxonomy',
|
||||
];
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $defaultTheme = 'stark';
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $permissions = [
|
||||
'view term revisions in test',
|
||||
'revert all taxonomy revisions',
|
||||
];
|
||||
|
||||
/**
|
||||
* Vocabulary for testing.
|
||||
*
|
||||
* @var \Drupal\taxonomy\VocabularyInterface
|
||||
*/
|
||||
private $vocabulary;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected function setUp(): void {
|
||||
parent::setUp();
|
||||
$this->vocabulary = $this->createVocabulary(['vid' => 'test', 'name' => 'Test']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests revision revert.
|
||||
*/
|
||||
public function testRevertForm(): void {
|
||||
$termName = $this->randomMachineName();
|
||||
$entity = Term::create([
|
||||
'vid' => $this->vocabulary->id(),
|
||||
'name' => $termName,
|
||||
]);
|
||||
|
||||
$entity->setRevisionCreationTime((new \DateTimeImmutable('11 January 2009 4pm'))->getTimestamp())
|
||||
->setRevisionTranslationAffected(TRUE);
|
||||
$entity->setNewRevision();
|
||||
$entity->save();
|
||||
$revisionId = $entity->getRevisionId();
|
||||
|
||||
$this->drupalLogin($this->drupalCreateUser($this->permissions));
|
||||
|
||||
// Cannot revert latest revision.
|
||||
$this->drupalGet($entity->toUrl('revision-revert-form'));
|
||||
$this->assertSession()->statusCodeEquals(403);
|
||||
|
||||
// Create a new latest revision.
|
||||
$entity
|
||||
->setRevisionCreationTime((new \DateTimeImmutable('11 January 2009 5pm'))->getTimestamp())
|
||||
->setRevisionTranslationAffected(TRUE)
|
||||
->setNewRevision();
|
||||
$entity->save();
|
||||
|
||||
// Reload the entity.
|
||||
$revision = \Drupal::entityTypeManager()->getStorage('taxonomy_term')
|
||||
->loadRevision($revisionId);
|
||||
$this->drupalGet($revision->toUrl('revision-revert-form'));
|
||||
$this->assertSession()->pageTextContains('Are you sure you want to revert to the revision from Sun, 01/11/2009 - 16:00?');
|
||||
$this->assertSession()->buttonExists('Revert');
|
||||
$this->assertSession()->linkExists('Cancel');
|
||||
|
||||
$countRevisions = static function (): int {
|
||||
return (int) \Drupal::entityTypeManager()->getStorage('taxonomy_term')
|
||||
->getQuery()
|
||||
->accessCheck(FALSE)
|
||||
->allRevisions()
|
||||
->count()
|
||||
->execute();
|
||||
};
|
||||
|
||||
$count = $countRevisions();
|
||||
$this->submitForm([], 'Revert');
|
||||
$this->assertEquals($count + 1, $countRevisions());
|
||||
$this->assertSession()->statusCodeEquals(200);
|
||||
$this->assertSession()->addressEquals(sprintf('taxonomy/term/%s/revisions', $entity->id()));
|
||||
$this->assertSession()->pageTextContains(sprintf('Test %s has been reverted to the revision from Sun, 01/11/2009 - 16:00.', $termName));
|
||||
$this->assertSession()->elementsCount('css', 'table tbody tr', 3);
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Drupal\Tests\taxonomy\Functional;
|
||||
|
||||
use Drupal\Tests\BrowserTestBase;
|
||||
use Drupal\Tests\taxonomy\Traits\TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* Tests the new_revision setting of taxonomy vocabularies.
|
||||
*
|
||||
* @group taxonomy
|
||||
*/
|
||||
class TaxonomyRevisionTest extends BrowserTestBase {
|
||||
|
||||
use TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected static $modules = [
|
||||
'system',
|
||||
'taxonomy',
|
||||
];
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $defaultTheme = 'stark';
|
||||
|
||||
/**
|
||||
* Tests default revision settings on vocabularies.
|
||||
*/
|
||||
public function testVocabularyTermRevision() {
|
||||
$assert = $this->assertSession();
|
||||
$vocabulary1 = $this->createVocabulary(['new_revision' => TRUE]);
|
||||
$vocabulary2 = $this->createVocabulary(['new_revision' => FALSE]);
|
||||
$user = $this->createUser([
|
||||
'administer taxonomy',
|
||||
]);
|
||||
$term1 = $this->createTerm($vocabulary1);
|
||||
$term2 = $this->createTerm($vocabulary2);
|
||||
|
||||
// Create some revisions so revision checkbox is visible.
|
||||
$term1 = $this->createTaxonomyTermRevision($term1);
|
||||
$term2 = $this->createTaxonomyTermRevision($term2);
|
||||
$this->drupalLogin($user);
|
||||
$this->drupalGet($term1->toUrl('edit-form'));
|
||||
$assert->statusCodeEquals(200);
|
||||
$assert->checkboxChecked('Create new revision');
|
||||
$this->drupalGet($term2->toUrl('edit-form'));
|
||||
$assert->statusCodeEquals(200);
|
||||
$assert->checkboxNotChecked('Create new revision');
|
||||
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,119 @@
|
|||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace Drupal\Tests\taxonomy\Functional;
|
||||
|
||||
use Drupal\Tests\BrowserTestBase;
|
||||
use Drupal\taxonomy\Entity\Term;
|
||||
use Drupal\Tests\taxonomy\Traits\TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* Taxonomy term version history test.
|
||||
*
|
||||
* @group taxonomy
|
||||
* @coversDefaultClass \Drupal\Core\Entity\Controller\VersionHistoryController
|
||||
*/
|
||||
class TaxonomyRevisionVersionHistoryTest extends BrowserTestBase {
|
||||
|
||||
use TaxonomyTestTrait;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected static $modules = [
|
||||
'system',
|
||||
'taxonomy',
|
||||
];
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $defaultTheme = 'stark';
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected $permissions = [
|
||||
'view term revisions in test',
|
||||
'revert all taxonomy revisions',
|
||||
'delete all taxonomy revisions',
|
||||
];
|
||||
|
||||
/**
|
||||
* Vocabulary for testing.
|
||||
*
|
||||
* @var \Drupal\taxonomy\VocabularyInterface
|
||||
*/
|
||||
private $vocabulary;
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
protected function setUp(): void {
|
||||
parent::setUp();
|
||||
$this->vocabulary = $this->createVocabulary(['vid' => 'test', 'name' => 'Test']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests version history page.
|
||||
*/
|
||||
public function testVersionHistory(): void {
|
||||
$entity = Term::create([
|
||||
'vid' => $this->vocabulary->id(),
|
||||
'name' => 'Test taxonomy term',
|
||||
]);
|
||||
|
||||
$entity
|
||||
->setDescription('Description 1')
|
||||
->setRevisionCreationTime((new \DateTimeImmutable('1st June 2020 7am'))->getTimestamp())
|
||||
->setRevisionLogMessage('first revision log')
|
||||
->setRevisionUser($this->drupalCreateUser(name: 'first author'))
|
||||
->setNewRevision();
|
||||
$entity->save();
|
||||
|
||||
$entity
|
||||
->setDescription('Description 2')
|
||||
->setRevisionCreationTime((new \DateTimeImmutable('2nd June 2020 8am'))->getTimestamp())
|
||||
->setRevisionLogMessage('second revision log')
|
||||
->setRevisionUser($this->drupalCreateUser(name: 'second author'))
|
||||
->setNewRevision();
|
||||
$entity->save();
|
||||
|
||||
$entity
|
||||
->setDescription('Description 3')
|
||||
->setRevisionCreationTime((new \DateTimeImmutable('3rd June 2020 9am'))->getTimestamp())
|
||||
->setRevisionLogMessage('third revision log')
|
||||
->setRevisionUser($this->drupalCreateUser(name: 'third author'))
|
||||
->setNewRevision();
|
||||
$entity->save();
|
||||
|
||||
$this->drupalLogin($this->drupalCreateUser($this->permissions));
|
||||
$this->drupalGet($entity->toUrl('version-history'));
|
||||
$this->assertSession()->elementsCount('css', 'table tbody tr', 3);
|
||||
|
||||
// Order is newest to oldest revision by creation order.
|
||||
$row1 = $this->assertSession()->elementExists('css', 'table tbody tr:nth-child(1)');
|
||||
// Latest revision does not have revert or delete revision operation.
|
||||
$this->assertSession()->elementNotExists('named', ['link', 'Revert'], $row1);
|
||||
$this->assertSession()->elementNotExists('named', ['link', 'Delete'], $row1);
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(1)', 'Current revision');
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(1)', 'third revision log');
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(1)', '06/03/2020 - 09:00 by third author');
|
||||
|
||||
$row2 = $this->assertSession()->elementExists('css', 'table tbody tr:nth-child(2)');
|
||||
$this->assertSession()->elementExists('named', ['link', 'Revert'], $row2);
|
||||
$this->assertSession()->elementExists('named', ['link', 'Delete'], $row2);
|
||||
$this->assertSession()->elementTextNotContains('css', 'table tbody tr:nth-child(2)', 'Current revision');
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(2)', 'second revision log');
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(2)', '06/02/2020 - 08:00 by second author');
|
||||
|
||||
$row3 = $this->assertSession()->elementExists('css', 'table tbody tr:nth-child(3)');
|
||||
$this->assertSession()->elementExists('named', ['link', 'Revert'], $row3);
|
||||
$this->assertSession()->elementExists('named', ['link', 'Delete'], $row3);
|
||||
$this->assertSession()->elementTextNotContains('css', 'table tbody tr:nth-child(2)', 'Current revision');
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(3)', 'first revision log');
|
||||
$this->assertSession()->elementTextContains('css', 'table tbody tr:nth-child(3)', '06/01/2020 - 07:00 by first author');
|
||||
}
|
||||
|
||||
}
|
|
@ -7,6 +7,7 @@ namespace Drupal\Tests\taxonomy\Traits;
|
|||
use Drupal\Core\Language\LanguageInterface;
|
||||
use Drupal\taxonomy\Entity\Vocabulary;
|
||||
use Drupal\taxonomy\Entity\Term;
|
||||
use Drupal\taxonomy\TermInterface;
|
||||
use Drupal\taxonomy\VocabularyInterface;
|
||||
|
||||
/**
|
||||
|
@ -63,4 +64,20 @@ trait TaxonomyTestTrait {
|
|||
return $term;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a new revision for a given taxonomy term.
|
||||
*
|
||||
* @param \Drupal\taxonomy\TermInterface $term
|
||||
* A taxonomy term object.
|
||||
*
|
||||
* @return \Drupal\taxonomy\TermInterface
|
||||
* The new taxonomy term object.
|
||||
*/
|
||||
protected function createTaxonomyTermRevision(TermInterface $term) {
|
||||
$term->set('name', $this->randomMachineName());
|
||||
$term->setNewRevision();
|
||||
$term->save();
|
||||
return $term;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -5,3 +5,4 @@ name: 'Recipe category'
|
|||
vid: recipe_category
|
||||
description: 'Use this taxonomy to group recipes of the same type together.'
|
||||
weight: 0
|
||||
new_revision: false
|
||||
|
|
|
@ -5,3 +5,4 @@ name: Tags
|
|||
vid: tags
|
||||
description: 'Use tags to group articles on similar topics into categories.'
|
||||
weight: 0
|
||||
new_revision: false
|
||||
|
|
|
@ -5,3 +5,4 @@ name: Tags
|
|||
vid: tags
|
||||
description: 'Use tags to group articles on similar topics into categories.'
|
||||
weight: 0
|
||||
new_revision: false
|
||||
|
|
|
@ -5,3 +5,4 @@ name: Tags
|
|||
vid: tags
|
||||
description: 'Use tags to group articles on similar topics into categories.'
|
||||
weight: 0
|
||||
new_revision: false
|
||||
|
|
Loading…
Reference in New Issue