scanner-8.x-1.0-rc3/src/Plugin/Scanner/Node.php

src/Plugin/Scanner/Node.php
<?php

namespace Drupal\scanner\Plugin\Scanner;

use Drupal\Component\Plugin\Exception\InvalidPluginDefinitionException;
use Drupal\Component\Plugin\Exception\PluginNotFoundException;
use Drupal\Core\Entity\EntityStorageException;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use Drupal\node\Entity\Node as CoreNode;
use Drupal\scanner\AdminHelper;

/**
 * A Scanner plugin for handling Node entities.
 *
 * @Scanner(
 *   id = "scanner_node",
 *   type = "node",
 * )
 */
class Node extends Entity {

  use StringTranslationTrait;

  /**
   * {@inheritdoc}
   */
  public function search(string $field, array $values): array {
    $title_collect = [];

    try {
      // $field will be string composed of entity type, bundle name, and field
      // name delimited by ':' characters.
      [$entityType, $bundle, $fieldname] = explode(':', $field);

      $query = $this->entityTypeManager->getStorage($entityType)->getQuery();
      $query->condition('type', $bundle, '=');
      if ($values['published']) {
        $query->condition('status', 1);
      }
      $conditionVals = parent::buildCondition($values['search'], $values['mode'], $values['wholeword'], $values['regex'], $values['preceded'], $values['followed']);
      $this->addQueryCondition($query, $conditionVals, $fieldname, $values['mode'], $values['language']);

      // Disable the normal access check.
      $query->accessCheck(FALSE);

      $entities = $query->execute();
      // Iterate over matched entities (nodes) to extract information that will
      // be rendered in the results.
      foreach ($entities as $id) {
        $node = CoreNode::load($id);
        $nodeField = $node->get($fieldname);
        $fieldType = $nodeField->getFieldDefinition()->getType();
        if (in_array($fieldType, ['text_with_summary', 'text', 'text_long'])) {
          $fieldValue = $nodeField->getValue()[0];
          $title_collect[$id]['title'] = $node->getTitle();
          // Find all instances of the term we're looking for.
          preg_match_all($conditionVals['phpRegex'], $fieldValue['value'], $matches, PREG_OFFSET_CAPTURE);
          $newValues = [];
          // Build an array of strings which are displayed in the results.
          foreach ($matches[0] as $v) {
            // The offset of the matched term(s) in the field's text.
            $start = $v[1];
            if ($values['preceded'] !== '') {
              // Bolding won't work if starting position is in the middle of a
              // word (non-word bounded searches), therefore move the start
              // position back as many character as there are in the 'preceded'
              // text.
              $start -= strlen($values['preceded']);
            }
            // Extract part of the text which include the search term plus six
            // "words" following it. After finding the string, bold the search
            // term.
            $replaced = preg_replace($conditionVals['phpRegex'], "<strong>$v[0]</strong>", preg_split("/\s+/", substr($fieldValue['value'], $start), 6));
            if (count($replaced) > 1) {
              // The final index contains the remainder of the text, which we
              // don't care about, so we discard it.
              array_pop($replaced);
            }
            $newValues[] = implode(' ', $replaced);
          }
          $title_collect[$id]['field'] = $newValues;
        }
        elseif (in_array($fieldType, ['string', 'link'])) {
          $title_collect[$id]['title'] = $node->getTitle();
          preg_match($conditionVals['phpRegex'], $nodeField->getString(), $matches, PREG_OFFSET_CAPTURE);
          $match = $matches[0][0];
          $replaced = preg_replace($conditionVals['phpRegex'], "<strong>$match</strong>", $nodeField->getString());
          $title_collect[$id]['field'] = [$replaced];
        }
      }
    }
    catch (InvalidPluginDefinitionException | PluginNotFoundException $e) {
      $this->getLogger('scanner')->error($e->getMessage());
    }

    return $title_collect;
  }

  /**
   * {@inheritdoc}
   */
  public function replace(string $field, array $values, array $undo_data): array {
    $data = $undo_data;
    [$entityType, $bundle, $fieldname] = explode(':', $field);

    try {
      $query = $this->entityTypeManager->getStorage($entityType)->getQuery();
      $query->condition('type', $bundle);
      if ($values['published']) {
        $query->condition('status', 1);
      }
      $conditionVals = parent::buildCondition($values['search'], $values['mode'], $values['wholeword'], $values['regex'], $values['preceded'], $values['followed']);
      $this->addQueryCondition($query, $conditionVals, $fieldname, $values['mode'], $values['language']);

      // Disable the normal access check.
      $query->accessCheck(FALSE);

      $entities = $query->execute();

      foreach ($entities as $id) {
        $node = CoreNode::load($id);
        $nodeField = $node->get($fieldname);
        $fieldType = $nodeField->getFieldDefinition()->getType();
        if (in_array($fieldType, ['text_with_summary', 'text', 'text_long'])) {
          if ($values['language'] === 'all') {
            $other_languages = AdminHelper::getAllEnabledLanguages();
            foreach ($other_languages as $langcode => $languageName) {
              if ($node->hasTranslation($langcode)) {
                $node = $node->getTranslation($langcode);
                $nodeField = $node->get($fieldname);
              }
              $fieldValue = $nodeField->getValue()[0];
              // Replace the search term with the replacement term.
              $fieldValue['value'] = preg_replace($conditionVals['phpRegex'], $values['replace'], $fieldValue['value']);
              $node->$fieldname = $fieldValue;
            }
          }
          else {
            $requested_lang = $values['language'];
            if ($node->hasTranslation($requested_lang)) {
              $node = $node->getTranslation($requested_lang);
              $nodeField = $node->get($fieldname);
            }
            $fieldValue = $nodeField->getValue()[0];
            // Replace the search term with the replacement term.
            $fieldValue['value'] = preg_replace($conditionVals['phpRegex'], $values['replace'], $fieldValue['value']);
            $node->$fieldname = $fieldValue;
          }
          if (!isset($data["node:$id"]['new_vid'])) {
            $data["node:$id"]['old_vid'] = $node->vid->getString();
            // Crete a new revision so that we can have the option of undoing it
            // later on.
            $node->setNewRevision();
            $node->revision_log = $this->t('Replaced %search with %replace via Scanner Search and Replace module.', [
              '%search' => $values['search'],
              '%replace' => $values['replace'],
            ]);
            $node->setRevisionUserId($this->currentUser->id());
          }
          // Save the updated node.
          $node->save();
          // Fetch the new revision id.
          $data["node:$id"]['new_vid'] = $node->vid->getString();
        }
        elseif ($fieldType == 'string') {
          if (!isset($data["node:$id"]['new_vid'])) {
            if ($values['language'] === 'all') {
              $all_languages = AdminHelper::getAllEnabledLanguages();
              foreach ($all_languages as $langcode => $languageName) {
                if ($node->hasTranslation($langcode)) {
                  $node = $node->getTranslation($langcode);
                  $nodeField = $node->get($fieldname);
                }
                $fieldValue = preg_replace($conditionVals['phpRegex'], $values['replace'], $nodeField->getString());
                $node->$fieldname = $fieldValue;
              }
            }
            else {
              $requested_lang = $values['language'];
              if ($node->hasTranslation($requested_lang)) {
                // $nodeField = $nodeField->getTranslation($requested_lang);
                $node = $node->getTranslation($requested_lang);
                $nodeField = $node->get($fieldname);
              }
              $fieldValue = preg_replace($conditionVals['phpRegex'], $values['replace'], $nodeField->getString());
              $node->$fieldname = $fieldValue;
            }
            $data["node:$id"]['old_vid'] = $node->vid->getString();
            $node->setNewRevision();
            $node->revision_log = $this->t('Replaced %search with %replace via Scanner Search and Replace module.', [
              '%search' => $values['search'],
              '%replace' => $values['replace'],
            ]);
            $node->setRevisionUserId($this->currentUser->id());
          }
          $node->save();
          $data["node:$id"]['new_vid'] = $node->vid->getString();
        }
        elseif ($fieldType == 'link') {
          if (!isset($data["node:$id"]['new_vid'])) {
            if ($values['language'] === 'all') {
              $all_languages = AdminHelper::getAllEnabledLanguages();
              foreach ($all_languages as $langcode => $languageName) {
                if ($node->hasTranslation($langcode)) {
                  $node = $node->getTranslation($langcode);
                  $nodeField = $node->get($fieldname);
                }
                $new_value = [];
                foreach ($nodeField->getValue() as $delta => $field_value) {
                  foreach ($field_value as $field_element => $field_element_value) {
                    if (is_string($field_element_value)) {
                      $fieldValue = preg_replace($conditionVals['phpRegex'], $values['replace'], $field_element_value);
                    }
                    else {
                      $fieldValue = $field_element_value;
                    }
                    $new_value[$delta][$field_element] = $fieldValue;
                  }
                }
                $node->$fieldname = $new_value;
              }
              $data["node:$id"]['old_vid'] = $node->vid->getString();
              $node->setNewRevision();
              $node->revision_log = $this->t('Replaced %search with %replace via Scanner Search and Replace module.', [
                '%search' => $values['search'],
                '%replace' => $values['replace'],
              ]);
            }
            else {
              $requested_lang = $values['language'];
              if ($node->hasTranslation($requested_lang)) {
                // $nodeField = $nodeField->getTranslation($requested_lang);
                $node = $node->getTranslation($requested_lang);
                $nodeField = $node->get($fieldname);
              }
              $new_value = [];
              foreach ($nodeField->getValue() as $delta => $field_value) {
                foreach ($field_value as $field_element => $field_element_value) {
                  if (is_string($field_element_value)) {
                    $fieldValue = preg_replace($conditionVals['phpRegex'], $values['replace'], $field_element_value);
                  }
                  else {
                    $fieldValue = $field_element_value;
                  }
                  $new_value[$delta][$field_element] = $fieldValue;
                }
              }
              $node->$fieldname = $new_value;
              $data["node:$id"]['old_vid'] = $node->vid->getString();
              $node->setNewRevision();
              $node->revision_log = $this->t('Replaced %search with %replace via Scanner Search and Replace module.', [
                '%search' => $values['search'],
                '%replace' => $values['replace'],
              ]);
            }
          }
          $node->setRevisionUserId($this->currentUser->id());
          $node->save();
          $data["node:$id"]['new_vid'] = $node->vid->getString();
        }
      }
    }
    catch (InvalidPluginDefinitionException | PluginNotFoundException | EntityStorageException $e) {
      $this->getLogger('scanner')->error($e->getMessage());
    }

    return $data;
  }

  /**
   * {@inheritdoc}
   */
  public function undo(array $data): void {
    try {
      $revision = $this->entityTypeManager->getStorage('node')
        ->loadRevision($data['old_vid']);
      $revision->setNewRevision(TRUE);
      $revision->revision_log = $this->t('Copy of the revision from %date via Search and Replace Undo', [
        '%date' => $this->dateFormatter->format($revision->getRevisionCreationTime()),
      ]);
      $revision->isDefaultRevision(TRUE);
      $revision->setRevisionUserId($this->currentUser->id());
      $revision->save();
    }
    catch (InvalidPluginDefinitionException | PluginNotFoundException | EntityStorageException $e) {
      $this->getLogger('scanner')->error($e->getMessage());
    }
  }

}

Главная | Обратная связь

drupal hosting | друпал хостинг | it patrol .inc