You are here

ExportPluginManager.php in Search API Synonym 8

File

src/Export/ExportPluginManager.php
View source
<?php

namespace Drupal\search_api_synonym\Export;

use Drupal\Core\Cache\CacheBackendInterface;
use Drupal\Core\Extension\ModuleHandlerInterface;
use Drupal\Core\File\FileSystemInterface;
use Drupal\Core\Plugin\DefaultPluginManager;

/**
 * Base class for search api synonym export plugin managers.
 *
 * @ingroup plugin_api
 */
class ExportPluginManager extends DefaultPluginManager {

  /**
   * Active plugin id
   *
   * @var string
   */
  protected $pluginId;

  /**
   * Export options.
   *
   * @var array
   */
  protected $exportOptions;

  /**
   * The file system service.
   *
   * @var \Drupal\Core\File\FileSystemInterface
   */
  protected $fileSystem;

  /**
   * {@inheritdoc}
   */
  public function __construct(\Traversable $namespaces, CacheBackendInterface $cache_backend, ModuleHandlerInterface $module_handler, FileSystemInterface $file_system = NULL) {
    parent::__construct('Plugin/search_api_synonym/export', $namespaces, $module_handler, 'Drupal\\search_api_synonym\\Export\\ExportPluginInterface', 'Drupal\\search_api_synonym\\Annotation\\SearchApiSynonymExport');
    $this
      ->alterInfo('search_api_synonym_export_info');
    $this
      ->setCacheBackend($cache_backend, 'search_api_synonym_export_info_plugins');
    $this->fileSystem = $file_system;
  }

  /**
   * Set active plugin.
   *
   * @param string $plugin_id
   *   The active plugin.
   */
  public function setPluginId($plugin_id) {
    $this->pluginId = $plugin_id;
  }

  /**
   * Get active plugin.
   *
   * @return string
   *   The active plugin.
   */
  public function getPluginId() {
    return $this->pluginId;
  }

  /**
   * Set export options.
   *
   * @param array $export_options
   *   Array with export options
   */
  public function setExportOptions(array $export_options) {
    $this->exportOptions = $export_options;
  }

  /**
   * Get export options.
   *
   * @return array
   *   Array with export options
   */
  public function getExportOptions() {
    return $this->exportOptions;
  }

  /**
   * Get single export option.
   *
   * @param string $key
   *   Option key
   *
   * @return string
   *   Option value
   */
  public function getExportOption($key) {
    return isset($this->exportOptions[$key]) ? $this->exportOptions[$key] : '';
  }

  /**
   * Gets a list of available export plugins.
   *
   * @return array
   *   An array with the plugin names as keys and the descriptions as values.
   */
  public function getAvailableExportPlugins() {

    // Use plugin system to get list of available export plugins.
    $plugins = $this
      ->getDefinitions();
    $output = [];
    foreach ($plugins as $id => $definition) {
      $output[$id] = $definition;
    }
    return $output;
  }

  /**
   * Validate that a specific export plugin exists.
   *
   * @param string $plugin
   *   The plugin machine name.
   *
   * @return boolean
   *   TRUE if the plugin exists.
   */
  public function validatePlugin($plugin) {
    if ($this
      ->getDefinition($plugin, FALSE)) {
      return TRUE;
    }
    else {
      return FALSE;
    }
  }

  /**
   * Execute the synonym export.
   *
   * @return mixed
   *   Export result
   */
  public function executeExport() {

    // Export plugin instance
    $instance = $this
      ->createInstance($this
      ->getPluginId(), []);

    // Get synonyms data matching the options.
    $synonyms = $this
      ->getSynonymsData();

    // We only export if full export or if their is new synonyms.
    if (!($this
      ->getExportOption('incremental') && empty($synonyms))) {

      // Get data in the plugin instance format
      $data = $instance
        ->getFormattedSynonyms($synonyms);
      return $this
        ->saveSynonymsFile($data);
    }
    else {
      return FALSE;
    }
  }

  /**
   * Get synonyms  matching the export options.
   *
   * @return array
   *   Array with synonyms
   */
  private function getSynonymsData() {

    // Create the db query.
    $query = \Drupal::database()
      ->select('search_api_synonym', 's');
    $query
      ->fields('s', [
      'sid',
      'type',
      'word',
      'synonyms',
    ]);
    $query
      ->condition('s.status', 1);
    $query
      ->condition('s.langcode', $this
      ->getExportOption('langcode'));
    $query
      ->orderBy('s.word');

    // Add type condition if it is set and different from all.
    $type = $this
      ->getExportOption('type');
    if ($type && $type != 'all') {
      $query
        ->condition('s.type', $type);
    }

    // Add filter condition if it is set and different from all.
    $filter = $this
      ->getExportOption('filter');
    if ($filter && $filter != 'all') {
      switch ($filter) {
        case 'nospace':
          $query
            ->condition('s.word', '% %', 'NOT LIKE');
          $query
            ->condition('s.synonyms', '% %', 'NOT LIKE');
          break;
        case 'onlyspace':
          $group = $query
            ->orConditionGroup()
            ->condition('s.word', '% %', 'LIKE')
            ->condition('s.synonyms', '% %', 'LIKE');
          $query = $query
            ->condition($group);
          break;
      }
    }

    // Add changed condition if incremental option is set.
    if ($incremental = $this
      ->getExportOption('incremental')) {
      $query
        ->condition('s.changed', $incremental, '>=');
    }

    // Fetch the result.
    return $query
      ->execute()
      ->fetchAllAssoc('sid');
  }

  /**
   * Save synonyms data to a file.
   *
   * @param string $data
   *   String with the synonyms data being written to a file.
   *
   * @return string
   *   Return path to the saved synonyms file.
   */
  private function saveSynonymsFile($data) {
    if ($file = $this
      ->getExportOption('file')) {
      $filename = $file;
    }
    else {
      $filename = $this
        ->generateFileName();
    }

    // Create folder if it does not exist.
    $folder = 'public://synonyms';
    $this->fileSystem
      ->prepareDirectory($folder, FileSystemInterface::CREATE_DIRECTORY | FileSystemInterface::MODIFY_PERMISSIONS);

    // Save file and return result.
    $path = $folder . '/' . $filename;
    return $this->fileSystem
      ->saveData($data, $path, FileSystemInterface::EXISTS_REPLACE);
  }

  /**
   * Generate an export file name based on export options.
   *
   * @return string
   *   The generated file name.
   */
  private function generateFileName() {
    $options = $this
      ->getExportOptions();

    // Add benning of file name
    $name[] = 'synonyms';

    // Add language code as the first part of the file name.
    $name[] = "lang_{$options['langcode']}";

    // Add type option to file name
    if (!empty($options['type'])) {
      $name[] = "type_{$options['type']}";
    }

    // Add filter option to file name
    if (!empty($options['filter'])) {
      $name[] = "filter_{$options['filter']}";
    }

    // Implode the name parts.
    return implode('__', $name) . '.txt';
  }

}

Classes

Namesort descending Description
ExportPluginManager Base class for search api synonym export plugin managers.