content_deploy-1.0.1/src/Form/SingleImportWithDependenciesForm.php

src/Form/SingleImportWithDependenciesForm.php
<?php

namespace Drupal\content_deploy\Form;

use Drupal\Core\Archiver\ArchiveTar;
use Drupal\Core\Form\FormBase;
use Drupal\Core\Form\FormStateInterface;
use Drupal\content_deploy\Importer\ContentImporterInterface;
use Drupal\Core\Entity\EntityTypeManagerInterface;
use Drupal\Component\Serialization\Yaml;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Drupal\Core\File\FileSystemInterface;

/**
 * Defines the content import form.
 */
class SingleImportWithDependenciesForm extends FormBase {


  /**
   * @var \Drupal\Core\Entity\EntityTypeManagerInterface
   */
  protected $entityTypeManager;

  /**
   * @var \Drupal\content_deploy\Importer\ContentImporterInterface
   */
  protected $contentImporter;

  /**
   * @var
   */
  protected $importedFiles;

  /**
   * @var
   */
  protected $processedEntities;

  /**
   * ContentImportForm constructor.
   */
  public function __construct(EntityTypeManagerInterface $entity_type_manager = NULL, ContentImporterInterface $content_importer = NULL, $importedFiles = [], $processedEntities = []) {
    $this->entityTypeManager = $entity_type_manager;
    $this->contentImporter = $content_importer;
    $this->importedFiles = $importedFiles;
    $this->processedEntities = $processedEntities;
  }

  /**
   *
   */
  public static function create(ContainerInterface $container) {
    return new static(
      $container->get('entity_type.manager'),
      $container->get('content_deploy.importer')
    );
  }

  /**
   * {@inheritdoc}
   */
  public function getFormId() {
    return 'import_with_dependencies_form';
  }

  /**
   * {@inheritdoc}
   */
  public function buildForm(array $form, FormStateInterface $form_state) {
    $directory = \Drupal::service('file_system')->getTempDirectory();
    $directory_is_writable = is_writable($directory);
    if (!$directory_is_writable) {
      $this->logger('content_deploy')->error('The directory %directory is not writable.', ['%directory' => $directory, 'link' => 'Import Archive']);
      \Drupal::messenger()->addError(t('The directory %directory is not writable.', ['%directory' => $directory]));
    }

    $form['import_tarball'] = [
      '#type' => 'file',
      '#title' => $this->t('Configuration archive'),
      '#description' => $this->t('Allowed types: @extensions.', ['@extensions' => 'tar.gz']),
    ];

    $form['submit'] = [
      '#type' => 'submit',
      '#value' => $this->t('Upload'),
      '#disabled' => !$directory_is_writable,
    ];
    return $form;
  }

  /**
   * {@inheritdoc}
   */
  public function validateForm(array &$form, FormStateInterface $form_state) {
    $all_files = $this->getRequest()->files->get('files', []);
    if (!empty($all_files['import_tarball'])) {
      $file_upload = $all_files['import_tarball'];
      if ($file_upload->isValid()) {
        $form_state->setValue('import_tarball', $file_upload->getRealPath());
        return;
      }
    }
    $form_state->setErrorByName('import_tarball', $this->t('The file could not be uploaded.'));
  }

  /**
   * {@inheritdoc}
   */
  public function submitForm(array &$form, FormStateInterface $form_state) {
    if ($path = $form_state->getValue('import_tarball')) {
      $directory = \Drupal::service('file_system')->getTempDirectory();
      try {
        $archiver = new ArchiveTar($path, 'gz');

        $files = [];
        $parentEntity = '';
        $attachedFiles = [];
        foreach ($archiver->listContent() as $file) {
          if (strpos($file['filename'], '/parent/') !== FALSE) {
            $parentEntity = $file['filename'];
          }
          elseif (strpos($file['filename'], '/attached_files/') !== FALSE) {
            $attachedFiles[] = $file['filename'];
          }
          else {
            $files[] = $file['filename'];
          }
        }
        $files[] = $parentEntity;

        $archiver->extractList($attachedFiles, $directory);
        if (!empty($attachedFiles)) {
          foreach ($attachedFiles as $singleAttachedFile) {
            $fileDestinationArr = explode('attached_files', $singleAttachedFile);
            if (isset($fileDestinationArr[1]) && !empty($fileDestinationArr[1])) {
              $fileDestinationArr = trim($fileDestinationArr[1], '/');
              $fileDestinationArr = explode('/', $fileDestinationArr);
              $scheme = $fileDestinationArr[0];
              array_shift($fileDestinationArr);
              $fileDestination = $scheme . '://' . implode('/', $fileDestinationArr);
              $prepareDirPath = str_replace(basename($fileDestination), '', $fileDestination);
              $prepareDir = \Drupal::service('file_system')->prepareDirectory($prepareDirPath, FileSystemInterface::CREATE_DIRECTORY);
              if ($prepareDir) {
                copy($directory . '/' . $singleAttachedFile, $fileDestination);
              }
            }
          }
        }

        $archiver->extractList($files, $directory);
        if (!empty($files)) {
          foreach ($files as $file) {
            if (!file_exists($directory . '/' . $file) || in_array(basename($file), $this->importedFiles)) {
              continue;
            }
            $data = file_get_contents($directory . '/' . $file);
            $ymlData = Yaml::decode($data);
            if (!in_array(basename($file), $this->processedEntities)) {
              $this->processedEntities[] = basename($file);
              if (isset($ymlData['_content_deploy']['entity_dependencies']) && !empty($ymlData['_content_deploy']['entity_dependencies'])) {
                $entityDependencies = $ymlData['_content_deploy']['entity_dependencies'];
                $this->_import_entity_dependencies($entityDependencies, $files, $directory);
              }
            }
            $entity = $this->contentImporter->importEntity($ymlData);
            if ($entity) {
              $this->importedFiles[] = basename($file);
              \Drupal::messenger()->addStatus($this->t('Entity @label (@entity_type: @id) imported successfully.', [
                '@label' => $entity->label(),
                '@entity_type' => $entity->getEntityTypeId(),
                '@id' => $entity->id(),
              ]));
            }
          }
        }
        \Drupal::messenger()->addStatus($this->t('Your content files are successfully imported.'));
        $this->logger('content_deploy')->notice('Your content files are successfully imported.', ['link' => 'Import Archive']);
        $form_state->setRedirect('content.import_single_with_dependencies');

      }
      catch (\Exception $e) {
        \Drupal::messenger()->addStatus($this->t('Could not extract the contents of the tar file. The error message is <em>@message</em>', ['@message' => $e->getMessage()]));
        $this->logger('content_deploy')->error('Could not extract the contents of the tar file. The error message is <em>@message</em>', ['@message' => $e->getMessage(), 'link' => 'Import Archive']);
      }
    }
  }

  /**
   * Provides help to import child dependencies.
   */
  private function _import_entity_dependencies($entityDependencies, $files, $directory) {

    if (empty($entityDependencies) || empty($files) || empty($directory)) {
      $this->logger('content_deploy')->error('Entity dependencies or content files or directory name is empty');
      return;
    }

    foreach ($entityDependencies as $entityType => $singleTypeEntityDependency) {
      foreach ($singleTypeEntityDependency as $singleEntityDependency) {
        $singleEntityDependencyFile = $singleEntityDependency . '.yml';
        $matches = array_filter($files, function ($var) use ($singleEntityDependencyFile) {
          return preg_match("/\b$singleEntityDependencyFile\b/i", $var);
        });

        if (!empty($matches)) {
          $file = reset($matches);
          if (!file_exists($directory . '/' . $file) || in_array(basename($file), $this->importedFiles)) {
            continue;
          }
          $data = file_get_contents($directory . '/' . $file);
          $ymlData = Yaml::decode($data);
          if (!in_array(basename($file), $this->processedEntities)) {
            $this->processedEntities[] = basename($file);
            if (isset($ymlData['_content_deploy']['entity_dependencies']) && !empty($ymlData['_content_deploy']['entity_dependencies'])) {
              $entityDependencies = $ymlData['_content_deploy']['entity_dependencies'];
              $this->_import_entity_dependencies($entityDependencies, $files, $directory);
            }
          }
          $entity = $this->contentImporter->importEntity($ymlData);
          if ($entity) {
            $this->importedFiles[] = basename($file);
            \Drupal::messenger()->addStatus($this->t('Entity @label (@entity_type: @id) imported successfully.', [
              '@label' => $entity->label(),
              '@entity_type' => $entity->getEntityTypeId(),
              '@id' => $entity->id(),
            ]));
          }
        }
      }
    }
  }

}

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

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