Update to Drupal 8.0.0 beta 14. For more information, see https://drupal.org/node/2544542

This commit is contained in:
Pantheon Automation 2015-08-27 12:03:05 -07:00 committed by Greg Anderson
parent 3b2511d96d
commit 81ccda77eb
2155 changed files with 54307 additions and 46870 deletions

View file

@ -257,6 +257,9 @@ function comment_node_view_alter(array &$build, EntityInterface $node, EntityVie
*
* @return array
* An array as expected by drupal_render().
*
* @deprecated in Drupal 8.x and will be removed before Drupal 9.0.
* Use \Drupal::entityManager()->getViewBuilder('comment')->view().
*/
function comment_view(CommentInterface $comment, $view_mode = 'full', $langcode = NULL) {
return entity_view($comment, $view_mode, $langcode);
@ -277,6 +280,9 @@ function comment_view(CommentInterface $comment, $view_mode = 'full', $langcode
* @return array
* An array in the format expected by drupal_render().
*
* @deprecated in Drupal 8.x and will be removed before Drupal 9.0.
* Use \Drupal::entityManager()->getViewBuilder('comment')->viewMultiple().
*
* @see drupal_render()
*/
function comment_view_multiple($comments, $view_mode = 'full', $langcode = NULL) {
@ -339,7 +345,8 @@ function comment_entity_storage_load($entities, $entity_type) {
if (!\Drupal::entityManager()->getDefinition($entity_type)->isSubclassOf('Drupal\Core\Entity\FieldableEntityInterface')) {
return;
}
if (!\Drupal::service('comment.manager')->getFields($entity_type)) {
// @todo Investigate in https://www.drupal.org/node/2527866 why we need that.
if (!\Drupal::hasService('comment.manager') || !\Drupal::service('comment.manager')->getFields($entity_type)) {
// Do not query database when entity has no comment fields.
return;
}

View file

@ -7,6 +7,8 @@
use Drupal\Component\Utility\SafeMarkup;
use Drupal\Component\Utility\Xss;
use Drupal\Core\Datetime\Entity\DateFormat;
use Drupal\Core\Render\BubbleableMetadata;
/**
* Implements hook_token_info().
@ -105,7 +107,7 @@ function comment_token_info() {
/**
* Implements hook_tokens().
*/
function comment_tokens($type, $tokens, array $data = array(), array $options = array()) {
function comment_tokens($type, $tokens, array $data, array $options, BubbleableMetadata $bubbleable_metadata) {
$token_service = \Drupal::token();
$url_options = array('absolute' => TRUE);
@ -138,6 +140,11 @@ function comment_tokens($type, $tokens, array $data = array(), array $options =
case 'mail':
$mail = $comment->getAuthorEmail();
// Add the user cacheability metadata in case the author of the comment
// is not the anonymous user.
if ($comment->getOwnerId()) {
$bubbleable_metadata->addCacheableDependency($comment->getOwner());
}
$replacements[$original] = $sanitize ? SafeMarkup::checkPlain($mail) : $mail;
break;
@ -170,26 +177,37 @@ function comment_tokens($type, $tokens, array $data = array(), array $options =
case 'author':
$name = $comment->getAuthorName();
// Add the user cacheability metadata in case the author of the comment
// is not the anonymous user.
if ($comment->getOwnerId()) {
$bubbleable_metadata->addCacheableDependency($comment->getOwner());
}
$replacements[$original] = $sanitize ? Xss::filter($name) : $name;
break;
case 'parent':
if ($comment->hasParentComment()) {
$parent = $comment->getParentComment();
$bubbleable_metadata->addCacheableDependency($parent);
$replacements[$original] = $sanitize ? Xss::filter($parent->getSubject()) : $parent->getSubject();
}
break;
case 'created':
$date_format = DateFormat::load('medium');
$bubbleable_metadata->addCacheableDependency($date_format);
$replacements[$original] = format_date($comment->getCreatedTime(), 'medium', '', NULL, $langcode);
break;
case 'changed':
$date_format = DateFormat::load('medium');
$bubbleable_metadata->addCacheableDependency($date_format);
$replacements[$original] = format_date($comment->getChangedTime(), 'medium', '', NULL, $langcode);
break;
case 'entity':
$entity = $comment->getCommentedEntity();
$bubbleable_metadata->addCacheableDependency($entity);
$title = $entity->label();
$replacements[$original] = $sanitize ? Xss::filter($title) : $title;
break;
@ -199,23 +217,23 @@ function comment_tokens($type, $tokens, array $data = array(), array $options =
// Chained token relationships.
if ($entity_tokens = $token_service->findwithPrefix($tokens, 'entity')) {
$entity = $comment->getCommentedEntity();
$replacements += $token_service->generate($comment->getCommentedEntityTypeId(), $entity_tokens, array($comment->getCommentedEntityTypeId() => $entity), $options);
$replacements += $token_service->generate($comment->getCommentedEntityTypeId(), $entity_tokens, array($comment->getCommentedEntityTypeId() => $entity), $options, $bubbleable_metadata);
}
if ($date_tokens = $token_service->findwithPrefix($tokens, 'created')) {
$replacements += $token_service->generate('date', $date_tokens, array('date' => $comment->getCreatedTime()), $options);
$replacements += $token_service->generate('date', $date_tokens, array('date' => $comment->getCreatedTime()), $options, $bubbleable_metadata);
}
if ($date_tokens = $token_service->findwithPrefix($tokens, 'changed')) {
$replacements += $token_service->generate('date', $date_tokens, array('date' => $comment->getChangedTime()), $options);
$replacements += $token_service->generate('date', $date_tokens, array('date' => $comment->getChangedTime()), $options, $bubbleable_metadata);
}
if (($parent_tokens = $token_service->findwithPrefix($tokens, 'parent')) && $parent = $comment->getParentComment()) {
$replacements += $token_service->generate('comment', $parent_tokens, array('comment' => $parent), $options);
$replacements += $token_service->generate('comment', $parent_tokens, array('comment' => $parent), $options, $bubbleable_metadata);
}
if (($author_tokens = $token_service->findwithPrefix($tokens, 'author')) && $account = $comment->getOwner()) {
$replacements += $token_service->generate('user', $author_tokens, array('user' => $account), $options);
$replacements += $token_service->generate('user', $author_tokens, array('user' => $account), $options, $bubbleable_metadata);
}
}
elseif ($type == 'entity' & !empty($data['entity'])) {

View file

@ -65,7 +65,7 @@
var $comment = $(placeholder)
.removeClass('hidden')
.text(newCommentString)
.closest('.comment')
.closest('.js-comment')
// Add 'new' class to the comment, so it can be styled.
.addClass('new');

View file

@ -67,22 +67,6 @@ class CommentForm extends ContentEntityForm {
$this->renderer = $renderer;
}
/**
* {@inheritdoc}
*/
protected function init(FormStateInterface $form_state) {
$comment = $this->entity;
// Make the comment inherit the current content language unless specifically
// set.
if ($comment->isNew()) {
$language_content = \Drupal::languageManager()->getCurrentLanguage(LanguageInterface::TYPE_CONTENT);
$comment->langcode->value = $language_content->getId();
}
parent::init($form_state);
}
/**
* Overrides Drupal\Core\Entity\EntityForm::form().
*/
@ -258,7 +242,6 @@ class CommentForm extends ContentEntityForm {
'#type' => 'submit',
'#value' => $this->t('Preview'),
'#access' => $preview_mode != DRUPAL_DISABLED,
'#validate' => array('::validate'),
'#submit' => array('::submitForm', '::preview'),
);

View file

@ -12,9 +12,9 @@ use Drupal\Core\Entity\EntityFormBuilderInterface;
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Entity\EntityManagerInterface;
use Drupal\Core\Extension\ModuleHandlerInterface;
use Drupal\Core\Render\RendererInterface;
use Drupal\Core\Session\AccountInterface;
use Drupal\Core\Url;
use Drupal\Core\Render\Renderer;
/**
* Defines a service for comment #lazy_builder callbacks.
@ -59,7 +59,7 @@ class CommentLazyBuilders {
/**
* The renderer service.
*
* @var \Drupal\Core\Render\Renderer
* @var \Drupal\Core\Render\RendererInterface
*/
protected $renderer;
@ -76,10 +76,10 @@ class CommentLazyBuilders {
* The comment manager service.
* @param \Drupal\Core\Extension\ModuleHandlerInterface $module_handler
* The module handler service.
* @param \Drupal\Core\Render\Renderer $renderer
* @param \Drupal\Core\Render\RendererInterface $renderer
* The renderer service.
*/
public function __construct(EntityManagerInterface $entity_manager, EntityFormBuilderInterface $entity_form_builder, AccountInterface $current_user, CommentManagerInterface $comment_manager, ModuleHandlerInterface $module_handler, Renderer $renderer) {
public function __construct(EntityManagerInterface $entity_manager, EntityFormBuilderInterface $entity_form_builder, AccountInterface $current_user, CommentManagerInterface $comment_manager, ModuleHandlerInterface $module_handler, RendererInterface $renderer) {
$this->entityManager = $entity_manager;
$this->entityFormBuilder = $entity_form_builder;
$this->currentUser = $current_user;

View file

@ -46,7 +46,7 @@ class CommentTypeListBuilder extends ConfigEntityListBuilder {
*/
public function buildRow(EntityInterface $entity) {
$row['type'] = SafeMarkup::checkPlain($entity->label());
$row['description'] = Xss::filterAdmin($entity->getDescription());
$row['description']['data'] = ['#markup' => $entity->getDescription()];
return $row + parent::buildRow($entity);
}

View file

@ -71,11 +71,9 @@ class CommentViewBuilder extends EntityViewBuilder {
->getFieldDefinition($entity->getFieldName())
->getSetting('default_mode') === CommentManagerInterface::COMMENT_MODE_THREADED;
// If threading is enabled, don't render cache individual comments, but do
// keep the cache tags, so they can bubble up.
// keep the cacheability metadata, so it can bubble up.
if ($build['#comment_threaded']) {
$cache_tags = $build['#cache']['tags'];
$build['#cache'] = [];
$build['#cache']['tags'] = $cache_tags;
unset($build['#cache']['keys']);
}
return $build;

View file

@ -11,6 +11,7 @@ use Drupal\comment\CommentInterface;
use Drupal\comment\CommentManagerInterface;
use Drupal\comment\Plugin\Field\FieldType\CommentItemInterface;
use Drupal\Core\Access\AccessResult;
use Drupal\Core\Cache\CacheableResponseInterface;
use Drupal\Core\Controller\ControllerBase;
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Entity\EntityManagerInterface;
@ -129,7 +130,8 @@ class CommentController extends ControllerBase {
// Find the current display page for this comment.
$page = $this->entityManager()->getStorage('comment')->getDisplayOrdinal($comment, $field_definition->getSetting('default_mode'), $field_definition->getSetting('per_page'));
// @todo: Cleaner sub request handling.
$redirect_request = Request::create($entity->url(), 'GET', $request->query->all(), $request->cookies->all(), array(), $request->server->all());
$subrequest_url = $entity->urlInfo()->toString(TRUE);
$redirect_request = Request::create($subrequest_url->getGeneratedUrl(), 'GET', $request->query->all(), $request->cookies->all(), array(), $request->server->all());
$redirect_request->query->set('page', $page);
// Carry over the session to the subrequest.
if ($session = $request->getSession()) {
@ -137,7 +139,16 @@ class CommentController extends ControllerBase {
}
// @todo: Convert the pager to use the request object.
$request->query->set('page', $page);
return $this->httpKernel->handle($redirect_request, HttpKernelInterface::SUB_REQUEST);
$response = $this->httpKernel->handle($redirect_request, HttpKernelInterface::SUB_REQUEST);
if ($response instanceof CacheableResponseInterface) {
// @todo Once path aliases have cache tags (see
// https://www.drupal.org/node/2480077), add test coverage that
// the cache tag for a commented entity's path alias is added to the
// comment's permalink response, because there can be blocks or
// other content whose renderings depend on the subrequest's URL.
$response->addCacheableDependency($subrequest_url);
}
return $response;
}
throw new NotFoundHttpException();
}

View file

@ -81,7 +81,7 @@ class Comment extends ContentEntityBase implements CommentInterface {
}
if ($this->isNew()) {
// Add the comment to database. This next section builds the thread field.
// Also see the documentation for comment_view().
// @see \Drupal\comment\CommentViewBuilder::buildComponents()
$thread = $this->getThread();
if (empty($thread)) {
if ($this->threadLock) {

View file

@ -9,8 +9,12 @@ namespace Drupal\comment\Plugin\Action;
use Drupal\Component\Utility\Tags;
use Drupal\Core\Action\ConfigurableActionBase;
use Drupal\Core\Entity\EntityViewBuilderInterface;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Plugin\ContainerFactoryPluginInterface;
use Drupal\Core\Render\RendererInterface;
use Drupal\Core\Session\AccountInterface;
use Symfony\Component\DependencyInjection\ContainerInterface;
/**
* Unpublishes a comment containing certain keywords.
@ -21,14 +25,62 @@ use Drupal\Core\Session\AccountInterface;
* type = "comment"
* )
*/
class UnpublishByKeywordComment extends ConfigurableActionBase {
class UnpublishByKeywordComment extends ConfigurableActionBase implements ContainerFactoryPluginInterface {
/**
* The comment entity builder handler.
*
* @var \Drupal\Core\Entity\EntityViewBuilderInterface
*/
protected $viewBuilder;
/**
* The renderer.
*
* @var \Drupal\Core\Render\RendererInterface
*/
protected $renderer;
/**
* Constructs a UnpublishByKeywordComment object.
*
* @param array $configuration
* A configuration array containing information about the plugin instance.
* @param string $plugin_id
* The plugin ID for the plugin instance.
* @param mixed $plugin_definition
* The plugin implementation definition.
* @param \Drupal\Core\Entity\EntityViewBuilderInterface $comment_view_builder
* The comment entity builder handler.
* @param \Drupal\Core\Render\RendererInterface $renderer
* The renderer.
*/
public function __construct(array $configuration, $plugin_id, $plugin_definition, EntityViewBuilderInterface $comment_view_builder, RendererInterface $renderer) {
parent::__construct($configuration, $plugin_id, $plugin_definition);
$this->viewBuilder = $comment_view_builder;
$this->renderer = $renderer;
}
/**
* {@inheritdoc}
*/
public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) {
return new static(
$configuration,
$plugin_id,
$plugin_definition,
$container->get('entity.manager')->getViewBuilder('comment'),
$container->get('renderer')
);
}
/**
* {@inheritdoc}
*/
public function execute($comment = NULL) {
$build = comment_view($comment);
$text = \Drupal::service('renderer')->renderPlain($build);
$build = $this->viewBuilder->view($comment);
$text = $this->renderer->renderPlain($build);
foreach ($this->configuration['keywords'] as $keyword) {
if (strpos($text, $keyword) !== FALSE) {
$comment->setPublished(FALSE);
@ -52,9 +104,9 @@ class UnpublishByKeywordComment extends ConfigurableActionBase {
*/
public function buildConfigurationForm(array $form, FormStateInterface $form_state) {
$form['keywords'] = array(
'#title' => t('Keywords'),
'#title' => $this->t('Keywords'),
'#type' => 'textarea',
'#description' => t('The comment will be unpublished if it contains any of the phrases above. Use a case-sensitive, comma-separated list of phrases. Example: funny, bungee jumping, "Company, Inc."'),
'#description' => $this->t('The comment will be unpublished if it contains any of the phrases above. Use a case-sensitive, comma-separated list of phrases. Example: funny, bungee jumping, "Company, Inc."'),
'#default_value' => Tags::implode($this->configuration['keywords']),
);
return $form;

View file

@ -10,12 +10,14 @@ namespace Drupal\comment\Plugin\Menu\LocalTask;
use Drupal\comment\CommentStorageInterface;
use Drupal\Core\Menu\LocalTaskDefault;
use Drupal\Core\Plugin\ContainerFactoryPluginInterface;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use Symfony\Component\DependencyInjection\ContainerInterface;
/**
* Provides a local task that shows the amount of unapproved comments.
*/
class UnapprovedComments extends LocalTaskDefault implements ContainerFactoryPluginInterface {
use StringTranslationTrait;
/**
* The comment storage service.
@ -57,7 +59,7 @@ class UnapprovedComments extends LocalTaskDefault implements ContainerFactoryPlu
* {@inheritdoc}
*/
public function getTitle() {
return t('Unapproved comments (@count)', array('@count' => $this->commentStorage->getUnapprovedCount()));
return $this->t('Unapproved comments (@count)', array('@count' => $this->commentStorage->getUnapprovedCount()));
}
}

View file

@ -86,11 +86,7 @@ class CommentCacheTagsTest extends EntityWithUriCacheTagsTestBase {
* {@inheritdoc}
*/
protected function getAdditionalCacheContextsForEntity(EntityInterface $entity) {
return [
// Field access for the user picture rendered as part of the node that
// this comment is created on.
'user.permissions',
];
return [];
}
/**

View file

@ -7,6 +7,7 @@
namespace Drupal\comment\Tests;
use Drupal\Core\Cache\Cache;
use Drupal\Core\Session\UserSession;
use Drupal\comment\CommentInterface;
use Drupal\system\Tests\Entity\EntityUnitTestBase;
@ -69,7 +70,8 @@ class CommentDefaultFormatterCacheTagsTest extends EntityUnitTestBase {
->getViewBuilder('entity_test')
->view($commented_entity);
$renderer->renderRoot($build);
$expected_cache_tags = array(
$cache_context_tags = \Drupal::service('cache_contexts_manager')->convertTokensToKeys($build['#cache']['contexts'])->getCacheTags();
$expected_cache_tags = Cache::mergeTags($cache_context_tags, [
'entity_test_view',
'entity_test:' . $commented_entity->id(),
'comment_list',
@ -78,9 +80,9 @@ class CommentDefaultFormatterCacheTagsTest extends EntityUnitTestBase {
'config:field.field.entity_test.entity_test.comment',
'config:field.storage.comment.comment_body',
'config:user.settings',
);
]);
sort($expected_cache_tags);
$this->assertEqual($build['#cache']['tags'], $expected_cache_tags, 'The test entity has the expected cache tags before it has comments.');
$this->assertEqual($build['#cache']['tags'], $expected_cache_tags);
// Create a comment on that entity. Comment loading requires that the uid
// also exists in the {users} table.
@ -111,7 +113,8 @@ class CommentDefaultFormatterCacheTagsTest extends EntityUnitTestBase {
->getViewBuilder('entity_test')
->view($commented_entity);
$renderer->renderRoot($build);
$expected_cache_tags = array(
$cache_context_tags = \Drupal::service('cache_contexts_manager')->convertTokensToKeys($build['#cache']['contexts'])->getCacheTags();
$expected_cache_tags = Cache::mergeTags($cache_context_tags, [
'entity_test_view',
'entity_test:' . $commented_entity->id(),
'comment_list',
@ -125,9 +128,9 @@ class CommentDefaultFormatterCacheTagsTest extends EntityUnitTestBase {
'config:field.field.entity_test.entity_test.comment',
'config:field.storage.comment.comment_body',
'config:user.settings',
);
]);
sort($expected_cache_tags);
$this->assertEqual($build['#cache']['tags'], $expected_cache_tags, 'The test entity has the expected cache tags when it has comments.');
$this->assertEqual($build['#cache']['tags'], $expected_cache_tags);
}
}

View file

@ -165,12 +165,12 @@ class CommentFieldsTest extends CommentTestBase {
// Install core content type module (book).
$edit = array();
$edit['modules[Core][book][enable]'] = 'book';
$this->drupalPostForm('admin/modules', $edit, t('Save configuration'));
$this->drupalPostForm('admin/modules', $edit, t('Install'));
// Now install the comment module.
$edit = array();
$edit['modules[Core][comment][enable]'] = 'comment';
$this->drupalPostForm('admin/modules', $edit, t('Save configuration'));
$this->drupalPostForm('admin/modules', $edit, t('Install'));
$this->rebuildContainer();
$this->assertTrue($this->container->get('module_handler')->moduleExists('comment'), 'Comment module enabled.');

View file

@ -180,7 +180,7 @@ class CommentNonNodeTest extends WebTestBase {
* @param bool $reply
* Boolean indicating whether the comment is a reply to another comment.
*
* @return boolean
* @return bool
* Boolean indicating whether the comment was found.
*/
function commentExists(CommentInterface $comment = NULL, $reply = FALSE) {
@ -201,7 +201,7 @@ class CommentNonNodeTest extends WebTestBase {
/**
* Checks whether the commenter's contact information is displayed.
*
* @return boolean
* @return bool
* Contact info is available.
*/
function commentContactInfoAvailable() {

View file

@ -8,6 +8,7 @@
namespace Drupal\comment\Tests;
use Drupal\comment\Plugin\Field\FieldType\CommentItemInterface;
use Drupal\Core\Cache\Cache;
use Drupal\Core\Entity\Entity\EntityViewDisplay;
use Drupal\system\Tests\Cache\AssertPageCacheContextsAndTagsTrait;
@ -52,16 +53,23 @@ class CommentRssTest extends CommentTestBase {
$this->postComment($this->node, $this->randomMachineName(), $this->randomMachineName());
$this->drupalGet('rss.xml');
$this->assertCacheTags([
'config:views.view.frontpage', 'node:1', 'node_list', 'node_view', 'user:3',
]);
$this->assertCacheContexts([
$cache_contexts = [
'languages:language_interface',
'theme',
'url.site',
'user.node_grants:view',
'user.permissions',
'timezone',
]);
];
$this->assertCacheContexts($cache_contexts);
$cache_context_tags = \Drupal::service('cache_contexts_manager')->convertTokensToKeys($cache_contexts)->getCacheTags();
$this->assertCacheTags(Cache::mergeTags($cache_context_tags, [
'config:views.view.frontpage',
'node:1', 'node_list',
'node_view',
'user:3',
]));
$raw = '<comments>' . $this->node->url('canonical', array('fragment' => 'comments', 'absolute' => TRUE)) . '</comments>';
$this->assertRaw($raw, 'Comments as part of RSS feed.');

View file

@ -182,7 +182,7 @@ abstract class CommentTestBase extends WebTestBase {
* @param bool $reply
* Boolean indicating whether the comment is a reply to another comment.
*
* @return boolean
* @return bool
* Boolean indicating whether the comment was found.
*/
function commentExists(CommentInterface $comment = NULL, $reply = FALSE) {
@ -323,7 +323,7 @@ abstract class CommentTestBase extends WebTestBase {
/**
* Checks whether the commenter's contact information is displayed.
*
* @return boolean
* @return bool
* Contact info is available.
*/
function commentContactInfoAvailable() {

View file

@ -7,7 +7,6 @@
namespace Drupal\comment\Tests;
use Drupal\Component\Utility\SafeMarkup;
use Drupal\Component\Utility\Unicode;
use Drupal\comment\Plugin\Field\FieldType\CommentItemInterface;
@ -42,10 +41,7 @@ trait CommentTestTrait {
$comment_type_storage = $entity_manager->getStorage('comment_type');
if ($comment_type = $comment_type_storage->load($comment_type_id)) {
if ($comment_type->getTargetEntityTypeId() !== $entity_type) {
throw new \InvalidArgumentException(SafeMarkup::format('The given comment type id %id can only be used with the %entity_type entity type', array(
'%id' => $comment_type_id,
'%entity_type' => $entity_type,
)));
throw new \InvalidArgumentException("The given comment type id $comment_type_id can only be used with the $entity_type entity type");
}
}
else {

View file

@ -10,6 +10,7 @@ namespace Drupal\comment\Tests;
use Drupal\Component\Utility\SafeMarkup;
use Drupal\Component\Utility\Xss;
use Drupal\comment\Entity\Comment;
use Drupal\Core\Render\BubbleableMetadata;
use Drupal\node\Entity\Node;
/**
@ -60,6 +61,7 @@ class CommentTokenReplaceTest extends CommentTestBase {
$tests['[comment:langcode]'] = SafeMarkup::checkPlain($comment->language()->getId());
$tests['[comment:url]'] = $comment->url('canonical', $url_options + array('fragment' => 'comment-' . $comment->id()));
$tests['[comment:edit-url]'] = $comment->url('edit-form', $url_options);
$tests['[comment:created]'] = \Drupal::service('date.formatter')->format($comment->getCreatedTime(), 'medium', array('langcode' => $language_interface->getId()));
$tests['[comment:created:since]'] = \Drupal::service('date.formatter')->formatTimeDiffSince($comment->getCreatedTime(), array('langcode' => $language_interface->getId()));
$tests['[comment:changed:since]'] = \Drupal::service('date.formatter')->formatTimeDiffSince($comment->getChangedTimeAcrossTranslations(), array('langcode' => $language_interface->getId()));
$tests['[comment:parent:cid]'] = $comment->hasParentComment() ? $comment->getParentComment()->id() : NULL;
@ -71,12 +73,48 @@ class CommentTokenReplaceTest extends CommentTestBase {
$tests['[comment:author:uid]'] = $comment->getOwnerId();
$tests['[comment:author:name]'] = SafeMarkup::checkPlain($this->adminUser->getUsername());
$base_bubbleable_metadata = BubbleableMetadata::createFromObject($comment);
$metadata_tests = [];
$metadata_tests['[comment:cid]'] = $base_bubbleable_metadata;
$metadata_tests['[comment:hostname]'] = $base_bubbleable_metadata;
$bubbleable_metadata = clone $base_bubbleable_metadata;
$bubbleable_metadata->addCacheableDependency($this->adminUser);
$metadata_tests['[comment:author]'] = $bubbleable_metadata;
$bubbleable_metadata = clone $base_bubbleable_metadata;
$bubbleable_metadata->addCacheableDependency($this->adminUser);
$metadata_tests['[comment:mail]'] = $bubbleable_metadata;
$metadata_tests['[comment:homepage]'] = $base_bubbleable_metadata;
$metadata_tests['[comment:title]'] = $base_bubbleable_metadata;
$metadata_tests['[comment:body]'] = $base_bubbleable_metadata;
$metadata_tests['[comment:langcode]'] = $base_bubbleable_metadata;
$metadata_tests['[comment:url]'] = $base_bubbleable_metadata;
$metadata_tests['[comment:edit-url]'] = $base_bubbleable_metadata;
$bubbleable_metadata = clone $base_bubbleable_metadata;
$metadata_tests['[comment:created]'] = $bubbleable_metadata->addCacheTags(['rendered']);
$bubbleable_metadata = clone $base_bubbleable_metadata;
$metadata_tests['[comment:created:since]'] = $bubbleable_metadata->setCacheMaxAge(0);
$bubbleable_metadata = clone $base_bubbleable_metadata;
$metadata_tests['[comment:changed:since]'] = $bubbleable_metadata->setCacheMaxAge(0);
$bubbleable_metadata = clone $base_bubbleable_metadata;
$metadata_tests['[comment:parent:cid]'] = $bubbleable_metadata->addCacheTags(['comment:1']);
$metadata_tests['[comment:parent:title]'] = $bubbleable_metadata;
$bubbleable_metadata = clone $base_bubbleable_metadata;
$metadata_tests['[comment:entity]'] = $bubbleable_metadata->addCacheTags(['node:2']);
// Test node specific tokens.
$metadata_tests['[comment:entity:nid]'] = $bubbleable_metadata;
$metadata_tests['[comment:entity:title]'] = $bubbleable_metadata;
$bubbleable_metadata = clone $base_bubbleable_metadata;
$metadata_tests['[comment:author:uid]'] = $bubbleable_metadata->addCacheTags(['user:2']);
$metadata_tests['[comment:author:name]'] = $bubbleable_metadata;
// Test to make sure that we generated something for each token.
$this->assertFalse(in_array(0, array_map('strlen', $tests)), 'No empty tokens generated.');
foreach ($tests as $input => $expected) {
$output = $token_service->replace($input, array('comment' => $comment), array('langcode' => $language_interface->getId()));
$bubbleable_metadata = new BubbleableMetadata();
$output = $token_service->replace($input, array('comment' => $comment), array('langcode' => $language_interface->getId()), $bubbleable_metadata);
$this->assertEqual($output, $expected, format_string('Sanitized comment token %token replaced.', array('%token' => $input)));
$this->assertEqual($bubbleable_metadata, $metadata_tests[$input]);
}
// Generate and test unsanitized tokens.

View file

@ -32,6 +32,18 @@ class CommentTranslationUITest extends ContentTranslationUITestBase {
*/
protected $adminUser;
/**
* {inheritdoc}
*/
protected $defaultCacheContexts = [
'languages:language_interface',
'theme',
'user.permissions',
'timezone',
'url.query_args.pagers:0',
'user.roles'
];
/**
* Modules to install.
*

View file

@ -8,6 +8,7 @@
namespace Drupal\comment\Tests\Views;
use Drupal\comment\Entity\Comment;
use Drupal\Core\Render\RenderContext;
use Drupal\Core\Session\AnonymousUserSession;
use Drupal\user\RoleInterface;
use Drupal\views\Views;
@ -58,6 +59,8 @@ class CommentFieldNameTest extends CommentTestBase {
* Test comment field name.
*/
public function testCommentFieldName() {
/** @var \Drupal\Core\Render\RendererInterface $renderer */
$renderer = \Drupal::service('renderer');
$view = Views::getView('test_comment_field_name');
$this->executeView($view);
@ -85,8 +88,14 @@ class CommentFieldNameTest extends CommentTestBase {
$view = Views::getView('test_comment_field_name');
$this->executeView($view);
// Test that data rendered.
$this->assertIdentical($this->comment->getFieldName(), $view->field['field_name']->advancedRender($view->result[0]));
$this->assertIdentical($this->customComment->getFieldName(), $view->field['field_name']->advancedRender($view->result[1]));
$output = $renderer->executeInRenderContext(new RenderContext(), function () use ($view) {
return $view->field['field_name']->advancedRender($view->result[0]);
});
$this->assertIdentical($this->comment->getFieldName(), $output);
$output = $renderer->executeInRenderContext(new RenderContext(), function () use ($view) {
return $view->field['field_name']->advancedRender($view->result[1]);
});
$this->assertIdentical($this->customComment->getFieldName(), $output);
}
}

View file

@ -67,32 +67,22 @@
*/
#}
<article{{ attributes }}>
{% if title %}
{{ title_prefix }}
{% endif %}
<article{{ attributes.addClass('js-comment') }}>
{#
Hide the "new" indicator by default, let a piece of JavaScript ask
the server which comments are new for the user. Rendering the final
"new" indicator here would break the render cache.
Hide the "new" indicator by default, let a piece of JavaScript ask the
server which comments are new for the user. Rendering the final "new"
indicator here would break the render cache.
#}
<mark class="hidden" data-comment-timestamp="{{ new_indicator_timestamp }}"></mark>
{% if title %}
<h3{{ title_attributes }}>{{ title }}</h3>
{{ title_suffix }}
{% endif %}
<footer>
{{ user_picture }}
<p>{{ submitted }}</p>
{#
Indicate the semantic relationship between parent and child comments
for accessibility. The list is difficult to navigate in a screen
reader without this information.
Indicate the semantic relationship between parent and child comments for
accessibility. The list is difficult to navigate in a screen reader
without this information.
#}
{% if parent %}
<p class="visually-hidden">{{ parent }}</p>
@ -102,9 +92,11 @@
</footer>
<div{{ content_attributes }}>
{{ content|without('links') }}
{% if title %}
{{ title_prefix }}
<h3{{ title_attributes }}>{{ title }}</h3>
{{ title_suffix }}
{% endif %}
{{ content }}
</div>
{% if content.links %}
{{ content.links }}
{% endif %}
</article>