From 97072d8670efd9841fa9725137c82d563570d9a6 Mon Sep 17 00:00:00 2001 From: webchick <webchick@24967.no-reply.drupal.org> Date: Fri, 24 Jan 2014 00:32:45 -0800 Subject: [PATCH] Issue #2150179 by swentel, larowlan: Delete confirm form for locked fields is hotlinkable. --- .../field/lib/Drupal/field/Entity/Field.php | 7 ++++ .../field/lib/Drupal/field/FieldInterface.php | 8 +++++ core/modules/field_ui/field_ui.services.yml | 4 +++ .../Access/FieldDeleteAccessCheck.php | 33 +++++++++++++++++++ .../field_ui/Routing/RouteSubscriber.php | 2 +- .../field_ui/Tests/ManageFieldsTest.php | 2 ++ 6 files changed, 55 insertions(+), 1 deletion(-) create mode 100644 core/modules/field_ui/lib/Drupal/field_ui/Access/FieldDeleteAccessCheck.php diff --git a/core/modules/field/lib/Drupal/field/Entity/Field.php b/core/modules/field/lib/Drupal/field/Entity/Field.php index b87ee9b0a7ff..3e5a63f30689 100644 --- a/core/modules/field/lib/Drupal/field/Entity/Field.php +++ b/core/modules/field/lib/Drupal/field/Entity/Field.php @@ -607,6 +607,13 @@ public function isMultiple() { return ($cardinality == static::CARDINALITY_UNLIMITED) || ($cardinality > 1); } + /** + * {@inheritdoc} + */ + public function isLocked() { + return $this->locked; + } + /** * {@inheritdoc} */ diff --git a/core/modules/field/lib/Drupal/field/FieldInterface.php b/core/modules/field/lib/Drupal/field/FieldInterface.php index ed2658c8e7e0..afa0ebae179e 100644 --- a/core/modules/field/lib/Drupal/field/FieldInterface.php +++ b/core/modules/field/lib/Drupal/field/FieldInterface.php @@ -23,4 +23,12 @@ interface FieldInterface extends ConfigEntityInterface, FieldDefinitionInterface */ public function getBundles(); + /** + * Returns whether the field is locked or not. + * + * @return bool + * TRUE if the field is locked. + */ + public function isLocked(); + } diff --git a/core/modules/field_ui/field_ui.services.yml b/core/modules/field_ui/field_ui.services.yml index 4f5ef7a2c7f1..e643e543ff94 100644 --- a/core/modules/field_ui/field_ui.services.yml +++ b/core/modules/field_ui/field_ui.services.yml @@ -4,6 +4,10 @@ services: arguments: ['@entity.manager'] tags: - { name: event_subscriber } + access_check.field_ui.field_delete: + class: Drupal\field_ui\Access\FieldDeleteAccessCheck + tags: + - { name: access_check, applies_to: _field_ui_field_delete_access } access_check.field_ui.view_mode: class: Drupal\field_ui\Access\ViewModeAccessCheck arguments: ['@entity.manager'] diff --git a/core/modules/field_ui/lib/Drupal/field_ui/Access/FieldDeleteAccessCheck.php b/core/modules/field_ui/lib/Drupal/field_ui/Access/FieldDeleteAccessCheck.php new file mode 100644 index 000000000000..c8f931b7eb4f --- /dev/null +++ b/core/modules/field_ui/lib/Drupal/field_ui/Access/FieldDeleteAccessCheck.php @@ -0,0 +1,33 @@ +<?php + +/** + * @file + * Contains \Drupal\field_ui\Access\FieldDeleteAccessCheck. + */ + +namespace Drupal\field_ui\Access; + +use Drupal\Core\Routing\Access\AccessInterface; +use Drupal\Core\Session\AccountInterface; +use Symfony\Component\Routing\Route; +use Symfony\Component\HttpFoundation\Request; + +/** + * Allows access to routes to be controlled by an '_access' boolean parameter. + */ +class FieldDeleteAccessCheck implements AccessInterface { + + /** + * {@inheritdoc} + */ + public function access(Route $route, Request $request, AccountInterface $account) { + $field_instance = $request->attributes->get('field_instance'); + if (!$field_instance->getField()->isLocked()) { + $permission = $route->getRequirement('_field_ui_field_delete_access'); + return $account->hasPermission($permission) ? static::ALLOW : static::DENY; + } + + return static::DENY; + } + +} diff --git a/core/modules/field_ui/lib/Drupal/field_ui/Routing/RouteSubscriber.php b/core/modules/field_ui/lib/Drupal/field_ui/Routing/RouteSubscriber.php index 3bebd66add71..2ec74381c295 100644 --- a/core/modules/field_ui/lib/Drupal/field_ui/Routing/RouteSubscriber.php +++ b/core/modules/field_ui/lib/Drupal/field_ui/Routing/RouteSubscriber.php @@ -68,7 +68,7 @@ protected function alterRoutes(RouteCollection $collection, $provider) { $route = new Route( "$path/fields/{field_instance}/delete", array('_entity_form' => 'field_instance.delete'), - array('_permission' => 'administer ' . $entity_type . ' fields') + array('_field_ui_field_delete_access' => 'administer ' . $entity_type . ' fields') ); $collection->add("field_ui.delete_$entity_type", $route); diff --git a/core/modules/field_ui/lib/Drupal/field_ui/Tests/ManageFieldsTest.php b/core/modules/field_ui/lib/Drupal/field_ui/Tests/ManageFieldsTest.php index 27197581a4c4..a8e6508ec743 100644 --- a/core/modules/field_ui/lib/Drupal/field_ui/Tests/ManageFieldsTest.php +++ b/core/modules/field_ui/lib/Drupal/field_ui/Tests/ManageFieldsTest.php @@ -415,6 +415,8 @@ function testLockedField() { $this->assertFalse(in_array('edit', $edit_link), 'Edit option for locked field is not present the UI'); $delete_link = $this->xpath('//tr[@id=:field_name]/td[4]', array(':field_name' => $field->name)); $this->assertFalse(in_array('delete', $delete_link), 'Delete option for locked field is not present the UI'); + $this->drupalGet('admin/structure/types/manage/' . $this->type . '/fields/node.' . $this->type . '.' . $field->name . '/delete'); + $this->assertResponse(403); } /** -- GitLab