From 629095a2b47b339103275fc1f1587ae352d1fc85 Mon Sep 17 00:00:00 2001 From: qadan Date: Thu, 9 Jul 2020 13:42:51 -0300 Subject: [PATCH 01/12] first pass at coding standards overhaul --- .../embargoes_embargo_entity.schema.yml | 8 +- .../embargoes_ip_range_entity.schema.yml | 11 +- embargoes.install | 14 +- embargoes.libraries.yml | 7 - embargoes.module | 173 +++----------- embargoes.services.yml | 29 ++- js/embargoes-file-embargoes.js | 8 - src/Access/EmbargoedAccessInterface.php | 48 ++++ src/Access/EmbargoedAccessResult.php | 219 ++++++++++++++++++ src/Access/EmbargoedFileAccess.php | 51 ++++ src/Access/EmbargoedMediaAccess.php | 51 ++++ src/Access/EmbargoedNodeAccess.php | 49 ++++ .../EmbargoesIpAccessDeniedController.php | 60 ++++- src/Controller/EmbargoesLogController.php | 48 +++- .../EmbargoesNodeEmbargoesController.php | 64 ++++- src/EmbargoesEmbargoEntityListBuilder.php | 8 +- src/EmbargoesEmbargoesService.php | 201 ++++++++++++---- src/EmbargoesEmbargoesServiceInterface.php | 144 +++++++++++- src/EmbargoesIpRangeEntityListBuilder.php | 2 +- src/EmbargoesIpRangesService.php | 45 +++- src/EmbargoesIpRangesServiceInterface.php | 40 +++- src/EmbargoesLogService.php | 22 +- src/EmbargoesLogServiceInterface.php | 8 +- src/Entity/EmbargoesEmbargoEntity.php | 131 ++++++++++- .../EmbargoesEmbargoEntityInterface.php | 151 +++++++++++- src/Entity/EmbargoesIpRangeEntity.php | 34 ++- .../EmbargoesIpRangeEntityInterface.php | 52 ++++- src/Form/EmbargoesEmbargoEntityForm.php | 103 +++++--- src/Form/EmbargoesIpRangeEntityForm.php | 31 ++- src/Form/EmbargoesNodeEmbargoesForm.php | 140 +++++++---- src/Form/EmbargoesNotificationsForm.php | 147 ++++++------ src/Form/EmbargoesSettingsForm.php | 7 +- .../Block/EmbargoesEmbargoPoliciesBlock.php | 84 ++++++- .../Condition/EmbargoesEmbargoedCondition.php | 24 +- 34 files changed, 1742 insertions(+), 472 deletions(-) delete mode 100644 embargoes.libraries.yml delete mode 100644 js/embargoes-file-embargoes.js create mode 100644 src/Access/EmbargoedAccessInterface.php create mode 100644 src/Access/EmbargoedAccessResult.php create mode 100644 src/Access/EmbargoedFileAccess.php create mode 100644 src/Access/EmbargoedMediaAccess.php create mode 100644 src/Access/EmbargoedNodeAccess.php diff --git a/config/schema/embargoes_embargo_entity.schema.yml b/config/schema/embargoes_embargo_entity.schema.yml index bca5cbd..6d2659c 100644 --- a/config/schema/embargoes_embargo_entity.schema.yml +++ b/config/schema/embargoes_embargo_entity.schema.yml @@ -17,6 +17,7 @@ embargoes.embargoes_embargo_entity.*: exempt_ips: type: string label: 'Exempt IP Ranges' + nullable: true exempt_users: type: sequence label: 'Exempt Users' @@ -26,8 +27,13 @@ embargoes.embargoes_embargo_entity.*: target_id: type: integer additional_emails: - type: string + type: sequence label: 'Additional Emails' + sequence: + type: mapping + mapping: + additional_email: + type: string embargoed_node: type: integer label: 'Embargoed Node' diff --git a/config/schema/embargoes_ip_range_entity.schema.yml b/config/schema/embargoes_ip_range_entity.schema.yml index ce296c8..0d9894c 100644 --- a/config/schema/embargoes_ip_range_entity.schema.yml +++ b/config/schema/embargoes_ip_range_entity.schema.yml @@ -8,9 +8,14 @@ embargoes.embargoes_ip_range_entity.*: label: type: label label: 'Label' - range: - type: string - label: 'Range' + ranges: + type: sequence + label: 'Ranges' + sequence: + type: mapping + mapping: + range: + type: string proxy_url: type: string label: 'Proxy URL' diff --git a/embargoes.install b/embargoes.install index fc77727..38c2651 100644 --- a/embargoes.install +++ b/embargoes.install @@ -1,15 +1,15 @@ 'Embargo log table.', diff --git a/embargoes.libraries.yml b/embargoes.libraries.yml deleted file mode 100644 index 2316543..0000000 --- a/embargoes.libraries.yml +++ /dev/null @@ -1,7 +0,0 @@ -embargoes-file-embargoes: - version: 1.x - js: - js/embargoes-file-embargoes.js: {} - dependencies: - - core/jquery - - core/jquery.once diff --git a/embargoes.module b/embargoes.module index 2ba2e54..cfc0be4 100644 --- a/embargoes.module +++ b/embargoes.module @@ -1,167 +1,64 @@ id()); - $ip = \Drupal::request()->getClientIp(); - $embargoes = \Drupal::service('embargoes.embargoes')->getActiveNodeEmbargoesByNids($nids, $ip, $account); - $ip_allowed_embargoes = \Drupal::service('embargoes.embargoes')->getIpAllowedEmbargoes($embargoes); - if (!empty($embargoes) && empty($ip_allowed_embargoes)) { - $access = \Drupal\Core\Access\AccessResult::forbidden(); - } - else { - $access = \Drupal\Core\Access\AccessResult::neutral(); - } - return $access; +function embargoes_node_access(NodeInterface $node, $operation, AccountInterface $account) { + return \Drupal::service('embargoes.node_access')->isActivelyEmbargoed($node, $account); } /** * Implements hook_ENTITY_TYPE_access(). */ -function embargoes_media_access(\Drupal\Core\Entity\EntityInterface $entity, $operation, \Drupal\Core\Session\AccountInterface $account){ - $nids = \Drupal::service('embargoes.embargoes')->getMediaParentNids($entity->id()); - $ip = \Drupal::request()->getClientIp(); - $active_embargoes = \Drupal::service('embargoes.embargoes')->getActiveEmbargoesByNids($nids, $ip, $account); - $ip_allowed_embargoes = \Drupal::service('embargoes.embargoes')->getIpAllowedEmbargoes($active_embargoes); - if (!empty($active_embargoes) && empty($ip_allowed_embargoes)) { - $access = \Drupal\Core\Access\AccessResult::forbidden(); - } - else { - $access = \Drupal\Core\Access\AccessResult::neutral(); - } - return $access; +function embargoes_media_access(EntityInterface $media, $operation, AccountInterface $account) { + return \Drupal::service('embargoes.media_access')->isActivelyEmbargoed($media, $account); } /** * Implements hook_ENTITY_TYPE_access(). */ -function embargoes_file_access(\Drupal\Core\Entity\EntityInterface $entity, $operation, \Drupal\Core\Session\AccountInterface $account){ - $nids = \Drupal::service('embargoes.embargoes')->getParentNidsOfFileEntity($entity); - $ip = \Drupal::request()->getClientIp(); - $active_embargoes = \Drupal::service('embargoes.embargoes')->getActiveEmbargoesByNids($nids, $ip, $account); - $ip_allowed_embargoes = \Drupal::service('embargoes.embargoes')->getIpAllowedEmbargoes($active_embargoes); - if (!empty($active_embargoes) && empty($ip_allowed_embargoes)) { - $access = \Drupal\Core\Access\AccessResult::forbidden(); - } - else { - $access = \Drupal\Core\Access\AccessResult::neutral(); - } - return $access; +function embargoes_file_access(EntityInterface $file, $operation, AccountInterface $account) { + return \Drupal::service('embargoes.file_access')->isActivelyEmbargoed($file, $account); } /** * Implements hook_node_view(). */ -function embargoes_node_view(array &$build, \Drupal\Core\Entity\EntityInterface $entity, \Drupal\Core\Entity\Display\EntityViewDisplayInterface $display, $view_mode) { - $ip = \Drupal::request()->getClientIp(); - $user = \Drupal::currentUser(); - $path = \Drupal::request()->getRequestUri(); - $active_embargoes = \Drupal::service('embargoes.embargoes')->getActiveEmbargoesByNids(array($entity->id()), $ip, $user); - $active_node_embargoes = \Drupal::service('embargoes.embargoes')->getActiveNodeEmbargoesByNids(array($entity->id()), $ip, $user); - $ip_allowed_embargoes = \Drupal::service('embargoes.embargoes')->getIpAllowedEmbargoes($active_node_embargoes); - if (!empty($active_node_embargoes)) { - $build['#attached']['library'][] = 'embargoes/embargoes-file-embargoes'; - } - if (!empty($active_node_embargoes) && !empty($ip_allowed_embargoes)) { - $imploded_ranges = implode('.', array_unique($ip_allowed_embargoes)); - $response = new RedirectResponse("/embargoes/ip-access-denied?path={$path}&ranges={$imploded_ranges}"); +function embargoes_node_view(array &$build, EntityInterface $entity, EntityViewDisplayInterface $display, $view_mode) { + $node_embargo = \Drupal::service('embargoes.node_access'); + $ip_url = $node_embargo->getIpEmbargoedRedirectUrl($entity); + if ($ip_url) { + $response = new RedirectResponse($ip_url); $response->send(); } - else if ((\Drupal::config('embargoes.settings')->get('show_embargo_message') == FALSE || is_null(\Drupal::config('embargoes.settings')->get('show_embargo_message'))) && $view_mode != 'teaser') {; - $embargoes = \Drupal::service('embargoes.embargoes')->getCurrentEmbargoesByNids(array($entity->id())); - if (!empty($embargoes)) { - $build['#cache']['max-age'] = 0; - $embargo_count = count($embargoes); - $embargo_word = ($embargo_count > 1 ? "embargoes" : "embargo" ); - drupal_set_message("This resource is under {$embargo_count} {$embargo_word}:", 'warning'); - foreach ($embargoes as $embargo_id) { - $embargo = \Drupal::entityTypeManager()->getStorage('embargoes_embargo_entity')->load($embargo_id); - $embargo_message = "- Access to "; - if ($embargo->getEmbargoTypeAsInt() == 0) { - $embargo_message .= " all associated files of this resource"; - } - else { - $embargo_message .= " this resource and all associated files"; - } - $embargo_message .= " is restricted"; - if ($embargo->getExemptIps() != 'none') { - $ip_range = \Drupal::entityTypeManager()->getStorage('embargoes_ip_range_entity')->load($embargo->getExemptIps()); - $embargo_message .= " to the {$ip_range->label()} network"; - } - else { - } - if ($embargo->getExpirationTypeAsInt() == 0) { - $embargo_message .= " indefinitely."; - } - else { - $embargo_message .= " until {$embargo->getExpirationDate()}."; - } - drupal_set_message($embargo_message, 'warning'); - } - } + else { + $node_embargo->setEmbargoMessage($entity); } } /** * Implements hook_ENTITY_TYPE_view(). */ -function embargoes_media_view(array &$build, \Drupal\Core\Entity\EntityInterface $entity, \Drupal\Core\Entity\Display\EntityViewDisplayInterface $display, $view_mode) { - $ip = \Drupal::request()->getClientIp(); - $user = \Drupal::currentUser(); - $path = \Drupal::request()->getRequestUri(); - $nids = \Drupal::service('embargoes.embargoes')->getMediaParentNids($entity->id()); - $active_embargoes = \Drupal::service('embargoes.embargoes')->getActiveEmbargoesByNids($nids, $ip, $user); - $active_node_embargoes = \Drupal::service('embargoes.embargoes')->getActiveNodeEmbargoesByNids(array($entity->id()), $ip, $user); - $ip_allowed_embargoes = \Drupal::service('embargoes.embargoes')->getIpAllowedEmbargoes($active_embargoes); - if (!empty($active_embargoes)) { - $build['#attached']['library'][] = 'embargoes/embargoes-file-embargoes'; - } - if (!empty($active_node_embargoes) && !empty($ip_allowed_embargoes)) { - $imploded_ranges = implode('.', array_unique($ip_allowed_embargoes)); - $response = new RedirectResponse("/embargoes/ip-access-denied?path={$path}&ranges={$imploded_ranges}"); +function embargoes_media_view(array &$build, EntityInterface $entity, EntityViewDisplayInterface $display, $view_mode) { + $media_embargo = \Drupal::service('embargoes.media_access'); + $ip_url = $media_embargo->getIpEmbargoedRedirectUrl($entity); + if ($ip_url) { + $response = new RedirectResponse($ip_url); $response->send(); } - else if ((\Drupal::config('embargoes.settings')->get('show_embargo_message') == FALSE) || is_null(\Drupal::config('embargoes.settings')->get('show_embargo_message')) && $view_mode != 'teaser') {; - $embargoes = \Drupal::service('embargoes.embargoes')->getCurrentEmbargoesByNids(array($entity->id())); - if (!empty($embargoes)) { - $build['#cache']['max-age'] = 0; - $embargo_count = count($embargoes); - $embargo_word = ($embargo_count > 1 ? "embargoes" : "embargo" ); - drupal_set_message("This resource is under {$embargo_count} {$embargo_word}:", 'warning'); - foreach ($embargoes as $embargo_id) { - $embargo = \Drupal::entityTypeManager()->getStorage('embargoes_embargo_entity')->load($embargo_id); - $embargo_message = "- Access to "; - if ($embargo->getEmbargoTypeAsInt() == 0) { - $embargo_message .= " all associated files of this resource"; - } - else { - $embargo_message .= " this resource and all associated files"; - } - $embargo_message .= " is restricted"; - if ($embargo->getExemptIps() != 'none') { - $ip_range = \Drupal::entityTypeManager()->getStorage('embargoes_ip_range_entity')->load($embargo->getExemptIps()); - $embargo_message .= " to the {$ip_range->label()} network"; - } - else { - } - if ($embargo->getExpirationTypeAsInt() == 0) { - $embargo_message .= " indefinitely."; - } - else { - $embargo_message .= " until {$embargo->getExpirationDate()}."; - } - drupal_set_message($embargo_message, 'warning'); - } - } + else { + $media_embargo->setEmbargoMessage($entity); } } @@ -172,17 +69,11 @@ function embargoes_file_download($uri) { $files = \Drupal::entityTypeManager() ->getStorage('file') ->loadByProperties(['uri' => $uri]); - $file = array_values($files)[0]; - $nids = \Drupal::service('embargoes.embargoes')->getParentNidsOfFileEntity($file); - $ip = \Drupal::request()->getClientIp(); - $user = \Drupal::currentUser(); - $path = \Drupal::request()->getRequestUri(); - $embargoes = \Drupal::service('embargoes.embargoes')->getActiveEmbargoesByNids($nids, $ip, $user); - $ip_allowed_embargoes = \Drupal::service('embargoes.embargoes')->getIpAllowedEmbargoes($embargoes); - if (!empty($embargoes) && !empty($ip_allowed_embargoes)) { - $imploded_ranges = implode('.', array_unique($ip_allowed_embargoes)); - $response = new RedirectResponse("/embargoes/ip-access-denied?path={$path}&ranges={$imploded_ranges}"); + $file = reset($files); + $file_embargo = \Drupal::service('embargoes.file_access'); + $ip_url = $file_embargo->getIpEmbargoedRedirectUrl($file); + if ($ip_url) { + $response = new RedirectResponse($ip_url); $response->send(); } - return NULL; } diff --git a/embargoes.services.yml b/embargoes.services.yml index 486675f..28a9b31 100644 --- a/embargoes.services.yml +++ b/embargoes.services.yml @@ -7,7 +7,32 @@ services: arguments: ['@database'] embargoes.embargoes: class: Drupal\embargoes\EmbargoesEmbargoesService - arguments: [] + arguments: ['@entity_type.manager', '@entity_field.manager', '@embargoes.ips'] embargoes.ips: class: Drupal\embargoes\EmbargoesIpRangesService - arguments: [] + arguments: ['@entity_type.manager'] + embargoes.node_access: + class: Drupal\embargoes\Access\EmbargoedNodeAccess + arguments: ['@embargoes.embargoes', '@request_stack', '@entity_type.manager', '@config.factory', '@messenger', '@string_translation', '@url_generator', '@current_user'] + embargoes.media_access: + class: Drupal\embargoes\Access\EmbargoedMediaAccess + arguments: + - '@embargoes.embargoes' + - '@request_stack' + - '@entity_type.manager' + - '@config.factory' + - '@messenger' + - '@string_translation' + - '@url_generator' + - '@current_user' + embargoes.file_access: + class: Drupal\embargoes\Access\EmbargoedFileAccess + arguments: + - '@embargoes.embargoes' + - '@request_stack' + - '@entity_type.manager' + - '@config.factory' + - '@messenger' + - '@string_translation' + - '@url_generator' + - '@current_user' diff --git a/js/embargoes-file-embargoes.js b/js/embargoes-file-embargoes.js deleted file mode 100644 index c506dbb..0000000 --- a/js/embargoes-file-embargoes.js +++ /dev/null @@ -1,8 +0,0 @@ -(function ($, Drupal) { - Drupal.behaviors.embargoes = { - attach: function (context, settings) { - $('div.field--type-file a').css('color', 'lightgray'); - $('div.field--type-file a').attr('title', 'Access to this file is restricted.'); - } - }; -})(jQuery, Drupal); diff --git a/src/Access/EmbargoedAccessInterface.php b/src/Access/EmbargoedAccessInterface.php new file mode 100644 index 0000000..17a3e9c --- /dev/null +++ b/src/Access/EmbargoedAccessInterface.php @@ -0,0 +1,48 @@ +embargoes = $embargoes; + $this->request = $request_stack->getCurrentRequest(); + $this->entityTypeManager = $entity_type_manager; + $this->config = $config; + $this->messenger = $messenger; + $this->translator = $translator; + $this->urlGenerator = $url_generator; + $this->currentUser = $current_user; + } + + /** + * Return the type of entity this should apply to. + * + * @return string + * The entity type this access control should apply to. + */ + public static function entityType() { + return ''; + } + + /** + * {@inheritdoc} + */ + public function isActivelyEmbargoed(EntityInterface $entity) { + $group_type = $entity->getEntityType()->getGroupType(); + $expected = static::entityType(); + if ($group_type !== $expected) { + throw new InvalidArgumentException($this->translator->translate('Attempting to check embargoed access status for an entity of type %type (expected: %expected)', [ + '%type' => $group_type, + '%expected' => $expected, + ])); + } + return AccessResult::neutral(); + } + + /** + * {@inheritdoc} + */ + public function setEmbargoMessage(EntityInterface $entity) { + $embargoes = $this->embargoes->getCurrentEmbargoesByNids([$entity->id()]); + if ($this->shouldSetEmbargoMessage() && !empty($embargoes)) { + // Warnings to pop. + $messages = [ + $this->translator->formatPlural(count($embargoes), 'This resource is under 1 embargo', 'This resource is under @count embargoes'), + ]; + // Pop additional warnings per embargo. + foreach ($embargoes as $embargo_id) { + $embargo = $this->entityTypeManager + ->getStorage('embargoes_embargo_entity') + ->load($embargo_id); + if ($embargo) { + // Custom built message from three conditions: are nodes or files + // embargoed, are networks exempt, and does it expire? + $type = $embargo->getEmbargoType(); + $ip_range = $embargo->getExemptIps() ? + $this->entityTypeManager->getStorage('embargoes_ip_range_entity')->load($embargo->getExemptIps()) : + NULL; + $expiration = $embargo->getExpirationType(); + $expiration_date = $expiration ? $embargo->getExpirationDate() : ''; + $args = [ + '%date' => $expiration_date, + '%ip_range' => $ip_range, + ]; + // Determine a message to set. + if (!$type && is_null($ip_range) && !$expiration) { + $messages[] = $this->translator->translate('- Access to all associated files of this resource is restricted indefinitely.'); + } + elseif (!$type && is_null($ip_range) && $expiration) { + $messages[] = $this->translator->translate('- Access to all associated files of this resource is restricted until %date.', $args); + } + elseif (!$type && !is_null($ip_range) && !$expiration) { + $messages[] = $this->translator->translate('- Access to all associated files of this resource is restricted to the %ip_range network indefinitely.', $args); + } + elseif (!$type && !is_null($ip_range) && $expiration) { + $messages[] = $this->translator->translate('- Access to all associated files of this resource is restricted to the %ip_range network until %date.', $args); + } + elseif ($type && is_null($ip_range) && !$expiration) { + $messages[] = $this->translator->translate('- Access to this resource and all associated resources is restricted indefinitely.'); + } + elseif ($type && is_null($ip_range) && $expiration) { + $messages[] = $this->translator->translate('- Access to this resource and all associated resources is restricted until %date.', $args); + } + elseif ($type && !is_null($ip_range) && !$expiration) { + $messages[] = $this->translator->translate('- Access to this resource and all associated resources is restricted to the %ip_range network indefinitely.', $args); + } + else { + $messages[] = $this->translator->translate('- Access to this resource and all associated resources is restricted to the %ip_range network until %date.', $args); + } + } + } + foreach ($messages as $message) { + $this->messenger->addWarning($message); + } + } + } + + /** + * Helper to determine if the embargo message should be set. + * + * @return bool + * TRUE or FALSE depending on whether an embargo message should be set. + */ + protected function shouldSetEmbargoMessage() { + $show_embargo_message = $this->config + ->get('embargoes.settings') + ->get('show_embargo_message'); + return (bool) $show_embargo_message; + } + + /** + * {@inheritdoc} + */ + public function getIpEmbargoRedirectUrl(EntityInterface $entity) { + return $this->urlGenerator->generateFromRoute('embargoes.ip_access_denied', [ + 'query' => [ + 'path' => $this->request->getRequestUri(), + 'ranges' => [], + ], + ]); + } + +} diff --git a/src/Access/EmbargoedFileAccess.php b/src/Access/EmbargoedFileAccess.php new file mode 100644 index 0000000..8fba2d9 --- /dev/null +++ b/src/Access/EmbargoedFileAccess.php @@ -0,0 +1,51 @@ +currentUser); + $parent_nodes = $this->embargoes->getParentNidsOfFileEntity($file); + $embargoes = $this->embargoes->getActiveNodeEmbargoesByNids($parent_nodes, $this->request->getClientIp(), $this->currentUser); + if (!empty($embargoes) && empty($this->embargoes->getIpAllowedEmbargoes($embargoes))) { + $state = AccessResult::forbidden(); + } + return $state; + } + + /** + * {@inheritdoc} + */ + public function getIpEmbargoedRedirectUrl(EntityInterface $file) { + $parent_nodes = $this->embargoes->getParentNidsOfFileEntity($file); + $embargoes = $this->embargoes->getActiveNodeEmbargoesByNids($parent_nodes, $this->request->getClientIp(), $this->currentUser); + $ip_allowed_embargoes = $this->embargoes->getIpAllowedEmbargoes($embargoes); + if (!empty($embargoes) && !empty($ip_allowed_embargoes)) { + return $this->urlGenerator->generateFromRoute('embargoes.ip_access_denied', [ + 'query' => [ + 'path' => $this->request->getRequestUri(), + 'ranges' => $ip_allowed_embargoes, + ], + ]); + } + return NULL; + } + +} diff --git a/src/Access/EmbargoedMediaAccess.php b/src/Access/EmbargoedMediaAccess.php new file mode 100644 index 0000000..ac95c29 --- /dev/null +++ b/src/Access/EmbargoedMediaAccess.php @@ -0,0 +1,51 @@ +currentUser); + $parent_nodes = $this->embargoes->getMediaParentNids($media->id()); + $embargoes = $this->embargoes->getActiveNodeEmbargoesByNids($parent_nodes, $this->request->getClientIp(), $this->currentUser); + if (!empty($embargoes) && empty($this->embargoes->getIpAllowedEmbargoes($embargoes))) { + $state = AccessResult::forbidden(); + } + return $state; + } + + /** + * {@inheritdoc} + */ + public function getIpEmbargoedRedirectUrl(EntityInterface $media) { + $parent_nodes = $this->embargoes->getMediaParentNids($media->id()); + $embargoes = $this->embargoes->getActiveNodeEmbargoesByNids($parent_nodes, $this->request->getClientIp(), $this->currentUser); + $ip_allowed_embargoes = $this->embargoes->getIpAllowedEmbargoes($embargoes); + if (!empty($embargoes) && !empty($ip_allowed_embargoes)) { + return $this->urlGenerator->generateFromRoute('embargoes.ip_access_denied', [ + 'query' => [ + 'path' => $this->request->getRequestUri(), + 'ranges' => $ip_allowed_embargoes, + ], + ]); + } + return NULL; + } + +} diff --git a/src/Access/EmbargoedNodeAccess.php b/src/Access/EmbargoedNodeAccess.php new file mode 100644 index 0000000..db12788 --- /dev/null +++ b/src/Access/EmbargoedNodeAccess.php @@ -0,0 +1,49 @@ +currentUser); + $embargoes = $this->embargoes->getActiveNodeEmbargoesByNids([$node->id()], $this->request->getClientIp(), $this->currentUser); + if (!empty($embargoes) && empty($this->embargoes->getIpAllowedEmbargoes($embargoes))) { + $state = AccessResult::forbidden(); + } + return $state; + } + + /** + * {@inheritdoc} + */ + public function getIpEmbargoedRedirectUrl(EntityInterface $node) { + $embargoes = $this->embargoes->getActiveNodeEmbargoesByNids([$node->id()], $this->request->getClientIp(), $this->currentUser); + $ip_allowed_embargoes = $this->embargoes->getIpAllowedEmbargoes($embargoes); + if (!empty($embargoes) && !empty($ip_allowed_embargoes)) { + return $this->urlGenerator->generateFromRoute('embargoes.ip_access_denied', [ + 'query' => [ + 'path' => $this->request->getRequestUri(), + 'ranges' => $ip_allowed_embargoes, + ], + ]); + } + return NULL; + } + +} diff --git a/src/Controller/EmbargoesIpAccessDeniedController.php b/src/Controller/EmbargoesIpAccessDeniedController.php index ed411bb..8b2af19 100644 --- a/src/Controller/EmbargoesIpAccessDeniedController.php +++ b/src/Controller/EmbargoesIpAccessDeniedController.php @@ -3,25 +3,69 @@ namespace Drupal\embargoes\Controller; use Drupal\Core\Controller\ControllerBase; -use Drupal\Core\Render\Markup; +use Symfony\Component\DependencyInjection\ContainerInterface; +use Symfony\Component\HttpFoundation\Request; /** * Class EmbargoesLogController. */ class EmbargoesIpAccessDeniedController extends ControllerBase { + /** + * The HTTP request. + * + * @var Symfony\Component\HttpFoundation\Request + */ + protected $request; + + /** + * Constructs an IP access denied controller. + * + * @param Symfony\Component\HttpFoundation\Request $request + * The current request. + */ + public function __construct(Request $request = NULL) { + $this->request = $request; + } + + /** + * {@inheritdoc} + */ + public static function create(ContainerInterface $container) { + return new static( + $container->get('request_stack')->getCurrentRequest()); + } + + /** + * Helper function to attempt to get the current request. + * + * @return string|null + * The requested resource, or NULL if there is no current request. + */ + protected function getRequestedResource() { + if (!is_null($this->request)) { + $path = $this->request->query->get('path'); + $host = $this->request->getSchemeAndHttpHost(); + return "{$host}{$path}"; + } + } + + /** + * Formats a response for an IP access denied page. + * + * @return array + * Renderable array of markup for IP access denied. + */ public function response() { - $allowed_ranges = explode('.', $_GET['ranges']); - $host = \Drupal::request()->getSchemeAndHttpHost(); - $path = $_GET['path']; - $requested_resource = $host . $path; - $contact_email = \Drupal::config('embargoes.settings')->get('embargo_contact_email'); + $allowed_ranges = explode('.', $this->request->query->get('ranges')); + $requested_resource = $this->getRequestedResource(); + $contact_email = $this->config('embargoes.settings')->get('embargo_contact_email'); $message = "

Your request for the following resource could not be resolved:
{$requested_resource}


"; $message .= "

Access to this resource is restricted to the following networks: