Commit 2069bf0c authored by webchick's avatar webchick

Issue #2109433 by herom, dawehner, damiankloip: Replace user_access() through...

Issue #2109433 by herom, dawehner, damiankloip: Replace user_access() through injected user accounts in views.
parent 7a001160
......@@ -8,6 +8,7 @@
namespace Drupal\comment\Plugin\views\field;
use Drupal\comment\CommentInterface;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\ResultRow;
/**
......@@ -19,9 +20,12 @@
*/
class LinkApprove extends Link {
public function access() {
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
//needs permission to administer comments in general
return user_access('administer comments');
return $account->hasPermission('administer comments');
}
/**
......
......@@ -7,6 +7,7 @@
namespace Drupal\comment\Plugin\views\field;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\ResultRow;
/**
......@@ -18,9 +19,12 @@
*/
class LinkDelete extends Link {
public function access() {
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
//needs permission to administer comments in general
return user_access('administer comments');
return $account->hasPermission('administer comments');
}
/**
......
......@@ -7,6 +7,7 @@
namespace Drupal\comment\Plugin\views\field;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\ResultRow;
/**
......@@ -18,9 +19,12 @@
*/
class LinkReply extends Link {
public function access() {
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
//check for permission to reply to comments
return user_access('post comments');
return $account->hasPermission('post comments');
}
/**
......
......@@ -9,6 +9,7 @@
use Drupal\Core\Access\AccessManager;
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Session\AccountInterface;
use Drupal\user\Plugin\views\field\Link;
use Drupal\views\ResultRow;
use Symfony\Component\DependencyInjection\ContainerInterface;
......@@ -93,7 +94,7 @@ public function buildOptionsForm(&$form, &$form_state) {
/**
* {@inheritdoc}
*/
public function access() {
public function access(AccountInterface $account) {
// The access logic is implemented per row.
return TRUE;
}
......
......@@ -17,6 +17,7 @@
use Drupal\Core\Field\FormatterPluginManager;
use Drupal\Core\Language\Language;
use Drupal\Core\Language\LanguageManager;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\Views;
use Drupal\views\ViewExecutable;
use Drupal\views\Plugin\views\display\DisplayPluginBase;
......@@ -167,15 +168,12 @@ public function init(ViewExecutable $view, DisplayPluginBase $display, array &$o
}
/**
* Check whether current user has access to this handler.
*
* @return bool
* Return TRUE if the user has access to view this field.
* {@inheritdoc}
*/
public function access() {
public function access(AccountInterface $account) {
$base_table = $this->get_base_table();
$access_controller = $this->entityManager->getAccessController($this->definition['entity_tables'][$base_table]);
return $access_controller->fieldAccess('view', $this->field_info);
return $access_controller->fieldAccess('view', $this->field_info, $account);
}
/**
......
......@@ -7,6 +7,7 @@
namespace Drupal\node\Plugin\views\field;
use Drupal\Core\Session\AccountInterface;
use Drupal\node\Plugin\views\field\Link;
use Drupal\views\Plugin\views\display\DisplayPluginBase;
use Drupal\views\ResultRow;
......@@ -30,8 +31,11 @@ public function init(ViewExecutable $view, DisplayPluginBase $display, array &$o
$this->additional_fields['node_vid'] = array('table' => 'node_revision', 'field' => 'vid');
}
public function access() {
return user_access('view revisions') || user_access('administer nodes');
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
return $account->hasPermission('view revisions') || $account->hasPermission('administer nodes');
}
/**
......
......@@ -7,6 +7,7 @@
namespace Drupal\node\Plugin\views\field;
use Drupal\Core\Session\AccountInterface;
use Drupal\node\Plugin\views\field\RevisionLink;
use Drupal\views\ResultRow;
......@@ -19,8 +20,11 @@
*/
class RevisionLinkDelete extends RevisionLink {
public function access() {
return user_access('delete revisions') || user_access('administer nodes');
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
return $account->hasPermission('delete revisions') || $account->hasPermission('administer nodes');
}
/**
......
......@@ -7,6 +7,7 @@
namespace Drupal\node\Plugin\views\field;
use Drupal\Core\Session\AccountInterface;
use Drupal\node\Plugin\views\field\RevisionLink;
use Drupal\views\ResultRow;
......@@ -19,8 +20,11 @@
*/
class RevisionLinkRevert extends RevisionLink {
public function access() {
return user_access('revert revisions') || user_access('administer nodes');
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
return $account->hasPermission('revert revisions') || $account->hasPermission('administer nodes');
}
/**
......
......@@ -28,7 +28,7 @@ public function canExpose() {
* See _node_access_where_sql() for a non-views query based implementation.
*/
public function query() {
if (!user_access('administer nodes')) {
if (!$this->view->getUser()->hasPermission('administer nodes')) {
$table = $this->ensureMyTable();
$grants = db_or();
foreach (node_access_grants('view') as $realm => $gids) {
......
......@@ -33,7 +33,7 @@ class Permission extends AccessPluginBase {
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
return user_access($this->options['perm'], $account) || user_access('access all views', $account);
return $account->hasPermission($this->options['perm']) || $account->hasPermission('access all views');
}
/**
......
......@@ -33,7 +33,7 @@ class Role extends AccessPluginBase {
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
return user_access('access all views', $account) || array_intersect(array_filter($this->options['role']), $account->getRoles());
return $account->hasPermission('access all views') || array_intersect(array_filter($this->options['role']), $account->getRoles());
}
/**
......
......@@ -24,7 +24,7 @@ class Language extends User {
protected function renderLink($data, ResultRow $values) {
if (!empty($this->options['link_to_user'])) {
$uid = $this->getValue($values, 'uid');
if (user_access('access user profiles') && $uid) {
if ($this->view->getUser()->hasPermission('access user profiles') && $uid) {
$this->options['alter']['make_link'] = TRUE;
$this->options['alter']['path'] = 'user/' . $uid;
}
......
......@@ -7,6 +7,7 @@
namespace Drupal\user\Plugin\views\field;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\Plugin\views\field\FieldPluginBase;
use Drupal\views\Plugin\views\display\DisplayPluginBase;
use Drupal\views\ResultRow;
......@@ -53,9 +54,11 @@ public function buildOptionsForm(&$form, &$form_state) {
parent::buildOptionsForm($form, $form_state);
}
// An example of field level access control.
public function access() {
return user_access('administer users') || user_access('access user profiles');
/**
* {@inheritdoc}
*/
public function access(AccountInterface $account) {
return $account->hasPermission('administer users') || $account->hasPermission('access user profiles');
}
public function query() {
......
......@@ -63,7 +63,7 @@ public function buildOptionsForm(&$form, &$form_state) {
* Returns a string for the link text.
*/
protected function renderLink($data, ResultRow $values) {
if (!empty($this->options['link_to_user']) && user_access('access user profiles') && ($entity = $this->getEntity($values)) && $data !== NULL && $data !== '') {
if (!empty($this->options['link_to_user']) && $this->view->getUser()->hasPermission('access user profiles') && ($entity = $this->getEntity($values)) && $data !== NULL && $data !== '') {
$this->options['alter']['make_link'] = TRUE;
$uri = $entity->uri();
$this->options['alter']['path'] = $uri['path'];
......
......@@ -11,6 +11,7 @@
use Drupal\Component\Utility\Unicode;
use Drupal\Component\Utility\Url;
use Drupal\Component\Utility\Xss;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\Plugin\views\display\DisplayPluginBase;
use Drupal\views\Plugin\views\PluginBase;
use Drupal\views\ViewExecutable;
......@@ -461,14 +462,15 @@ public function showExposeForm(&$form, &$form_state) {
/**
* Check whether current user has access to this handler.
*
* @param AccountInterface $account
* @return boolean
*/
public function access() {
public function access(AccountInterface $account) {
if (isset($this->definition['access callback']) && function_exists($this->definition['access callback'])) {
if (isset($this->definition['access arguments']) && is_array($this->definition['access arguments'])) {
return call_user_func_array($this->definition['access callback'], $this->definition['access arguments']);
return call_user_func_array($this->definition['access callback'], array($account) + $this->definition['access arguments']);
}
return $this->definition['access callback']();
return $this->definition['access callback']($account);
}
return TRUE;
......
......@@ -9,6 +9,7 @@
use Drupal\Component\Utility\String;
use Drupal\Core\Language\Language;
use Drupal\Core\Session\AccountInterface;
use Drupal\Core\Theme\Registry;
use Drupal\views\Plugin\views\area\AreaPluginBase;
use Drupal\views\ViewExecutable;
......@@ -874,6 +875,8 @@ public function &getHandler($type, $id) {
/**
* Get a full array of handlers for $type. This caches them.
*
* @return \Drupal\views\Plugin\views\HandlerBase[]
*/
public function getHandlers($type) {
if (!isset($this->handlers[$type])) {
......@@ -2406,17 +2409,18 @@ public function renderArea($area, $empty = FALSE) {
/**
* Determine if the user has access to this display of the view.
*/
public function access($account = NULL) {
public function access(AccountInterface $account = NULL) {
if (!isset($account)) {
$account = \Drupal::currentUser();
}
// Full override.
if (user_access('access all views', $account)) {
if ($account->hasPermission('access all views')) {
return TRUE;
}
$plugin = $this->getPlugin('access');
/** @var \Drupal\views\Plugin\views\access\AccessPluginBase $plugin */
if ($plugin) {
return $plugin->access($account);
}
......
......@@ -361,8 +361,9 @@ public function testDestroy() {
protected function assertViewDestroy($view) {
$reflection = new \ReflectionClass($view);
$defaults = $reflection->getDefaultProperties();
// The storage should remain.
// The storage and user should remain.
unset($defaults['storage']);
unset($defaults['user']);
foreach ($defaults as $property => $default) {
$this->assertIdentical($this->getProtectedProperty($view, $property), $default);
......
......@@ -7,6 +7,7 @@
namespace Drupal\views;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\Plugin\views\query\QueryPluginBase;
use Drupal\views\ViewStorageInterface;
use Drupal\Component\Utility\Tags;
......@@ -406,6 +407,13 @@ class ViewExecutable {
),
);
/**
* The current user.
*
* @var \Drupal\Core\Session\AccountInterface
*/
protected $user;
/**
* Should the admin links be shown on the rendered view.
*
......@@ -418,11 +426,14 @@ class ViewExecutable {
*
* @param \Drupal\views\ViewStorageInterface $storage
* The view config entity the actual information is stored on.
* @param \Drupal\Core\Session\AccountInterface $user
* The current user.
*/
public function __construct(ViewStorageInterface $storage) {
public function __construct(ViewStorageInterface $storage, AccountInterface $user) {
// Reference the storage and the executable to each other.
$this->storage = $storage;
$this->storage->set('executable', $this);
$this->user = $user;
// Add the default css for a view.
$this->element['#attached']['library'][] = array('views', 'views.module');
......@@ -627,7 +638,7 @@ public function chooseDisplay($displays) {
$this->initDisplay();
foreach ($displays as $display_id) {
if ($this->displayHandlers->get($display_id)->access()) {
if ($this->displayHandlers->get($display_id)->access($this->user)) {
return $display_id;
}
}
......@@ -883,7 +894,7 @@ protected function _initHandler($key, $info) {
// Run through and test for accessibility.
foreach ($handlers as $id => $handler) {
if (!$handler->access()) {
if (!$handler->access($this->user)) {
unset($handlers[$id]);
}
}
......@@ -1485,7 +1496,7 @@ public function attachDisplays() {
// Find out which other displays attach to the current one.
foreach ($this->display_handler->getAttachedDisplays() as $id) {
// Create a clone for the attachments to manipulate. 'static' refers to the current class name.
$cloned_view = new static($this->storage);
$cloned_view = new static($this->storage, $this->user);
$this->displayHandlers->get($id)->attachTo($cloned_view, $this->current_display);
}
$this->is_attachment = FALSE;
......@@ -1528,7 +1539,7 @@ public function access($displays = NULL, $account = NULL) {
}
if (!$account) {
$account = \Drupal::currentUser();
$account = $this->user;
}
// We can't use choose_display() here because that function
......@@ -1701,6 +1712,18 @@ public function getPath() {
return $this->display_handler->getPath();
}
/**
* Gets the current user.
*
* Views plugins can recieve the current user in order to not need dependency
* injection.
*
* @return \Drupal\Core\Session\AccountInterface
*/
public function getUser() {
return $this->user;
}
/**
* Creates a duplicate ViewExecutable object.
*
......@@ -1730,9 +1753,10 @@ public function destroy() {
$reflection = new \ReflectionClass($this);
$defaults = $reflection->getDefaultProperties();
// The storage should not be reset. This is not generated by the execution
// of a view.
// The external dependencies should not be reset. This is not generated by
// the execution of a view.
unset($defaults['storage']);
unset($defaults['user']);
foreach ($defaults as $property => $default) {
$this->{$property} = $default;
}
......
......@@ -7,6 +7,7 @@
namespace Drupal\views;
use Drupal\Core\Session\AccountInterface;
use Drupal\views\ViewStorageInterface;
/**
......@@ -14,6 +15,23 @@
*/
class ViewExecutableFactory {
/**
* Stores the current user.
*
* @var \Drupal\Core\Session\AccountInterface
*/
protected $user;
/**
* Constructs a new ViewExecutableFactory
*
* @param \Drupal\Core\Session\AccountInterface $user
* The current user.
*/
public function __construct(AccountInterface $user) {
$this->user = $user;
}
/**
* Instantiates a ViewExecutable class.
*
......@@ -23,8 +41,8 @@ class ViewExecutableFactory {
* @return \Drupal\views\ViewExecutable
* A ViewExecutable instance.
*/
public static function get(ViewStorageInterface $view) {
return new ViewExecutable($view);
public function get(ViewStorageInterface $view) {
return new ViewExecutable($view, $this->user);
}
}
......@@ -115,7 +115,7 @@ public function testAccessDeniedView() {
->method('access')
->will($this->returnValue(FALSE));
$this->executableFactory->staticExpects($this->once())
$this->executableFactory->expects($this->once())
->method('get')
->with($view)
->will($this->returnValue($executable));
......@@ -162,7 +162,7 @@ protected function setupValidMocks() {
->method('preview')
->will($this->returnValue(array('#markup' => 'View result')));
$this->executableFactory->staticExpects($this->once())
$this->executableFactory->expects($this->once())
->method('get')
->with($view)
->will($this->returnValue($executable));
......
......@@ -94,8 +94,9 @@ protected function setUp() {
->getMock();
$this->executableFactory = $this->getMockBuilder('Drupal\views\ViewExecutableFactory')
->disableOriginalConstructor()
->getMock();
$this->executableFactory->staticExpects($this->any())
$this->executableFactory->expects($this->any())
->method('get')
->with($this->view)
->will($this->returnValue($this->executable));
......
......@@ -51,7 +51,8 @@ public function setUp() {
->method('label')
->will($this->returnValue('ResultTest'));
$this->view = new ViewExecutable($storage);
$user = $this->getMock('Drupal\Core\Session\AccountInterface');
$this->view = new ViewExecutable($storage, $user);
$this->resultHandler = new Result(array(), 'result', array());
$this->resultHandler->view = $this->view;
......
......@@ -80,7 +80,8 @@ protected function setUp() {
);
$storage = new View($config, 'view');
$this->view = $this->getMock('Drupal\views\ViewExecutable', NULL, array($storage));
$user = $this->getMock('Drupal\Core\Session\AccountInterface');
$this->view = $this->getMock('Drupal\views\ViewExecutable', NULL, array($storage, $user));
$this->display = $this->getMockBuilder('Drupal\views\Plugin\views\display\DisplayPluginBase')
->disableOriginalConstructor()
......
......@@ -87,7 +87,7 @@ public function testPageController() {
->with('default', array())
->will($this->returnValue(array('#markup' => 'example output')));
$this->executableFactory->staticExpects($this->any())
$this->executableFactory->expects($this->any())
->method('get')
->with($view)
->will($this->returnValue($executable));
......@@ -131,7 +131,7 @@ public function testHandleWithArgumentsWithoutOverridden() {
->method('executeDisplay')
->with('page_1', array('test-argument'));
$this->executableFactory->staticExpects($this->any())
$this->executableFactory->expects($this->any())
->method('get')
->with($view)
->will($this->returnValue($executable));
......@@ -177,7 +177,7 @@ public function testHandleWithArgumentsOnOveriddenRoute() {
->method('executeDisplay')
->with('page_1', array('test-argument'));
$this->executableFactory->staticExpects($this->any())
$this->executableFactory->expects($this->any())
->method('get')
->with($view)
->will($this->returnValue($executable));
......@@ -227,7 +227,7 @@ public function testHandleWithArgumentsOnOveriddenRouteWithUpcasting() {
->method('executeDisplay')
->with('page_1', array('example_id'));
$this->executableFactory->staticExpects($this->any())
$this->executableFactory->expects($this->any())
->method('get')
->with($view)
->will($this->returnValue($executable));
......
......@@ -43,7 +43,8 @@ public function testBuildThemeFunctions() {
);
$storage = new View($config, 'view');
$view = new ViewExecutable($storage);
$user = $this->getMock('Drupal\Core\Session\AccountInterface');
$view = new ViewExecutable($storage, $user);
$expected = array(
'test_hook__test_view',
......
......@@ -30,7 +30,8 @@ protected function setUp() {
parent::setUp();
$container = new ContainerBuilder();
$container->set('views.executable', new ViewExecutableFactory());
$user = $this->getMock('Drupal\Core\Session\AccountInterface');
$container->set('views.executable', new ViewExecutableFactory($user));
$this->view = new View(array('id' => 'test_view'), 'view');
......
......@@ -64,6 +64,7 @@ services:
arguments: ['@views.views_data']
views.executable:
class: Drupal\views\ViewExecutableFactory
arguments: ['@current_user']
views.analyzer:
class: Drupal\views\Analyzer
arguments: ['@module_handler']
......
......@@ -114,7 +114,8 @@ public function testBuildRowEntityList() {
)));
$container = new ContainerBuilder();
$executable_factory = new ViewExecutableFactory();
$user = $this->getMock('Drupal\Core\Session\AccountInterface');
$executable_factory = new ViewExecutableFactory($user);
$container->set('views.executable', $executable_factory);
$container->set('plugin.manager.views.display', $display_manager);
$container->set('string_translation', $this->getStringTranslationStub());
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment