migmag-1.0.x-dev/tests/src/Traits/MigMagMigrationTestDatabaseTrait.php

tests/src/Traits/MigMagMigrationTestDatabaseTrait.php
<?php

namespace Drupal\Tests\migmag\Traits;

use Drupal\Core\Database\Database;

/**
 * Trait for importing custom data into the migrate source database.
 */
trait MigMagMigrationTestDatabaseTrait {

  /**
   * Changes the database connection to the prefixed one.
   *
   * @see \Drupal\Tests\migrate\Kernel\MigrateTestBase::createMigrationConnection()
   *
   * @todo Refactor when core don't use global.
   *   https://www.drupal.org/node/2552791
   */
  protected function createSourceMigrationConnection(string $source_db_key = 'migrate') {
    // If the backup already exists, something went terribly wrong.
    // This case is possible, because database connection info is a static
    // global state construct on the Database class, which at least persists
    // for all test methods executed in one PHP process.
    if (Database::getConnectionInfo("simpletest_original_$source_db_key")) {
      throw new \RuntimeException("Bad Database connection state: 'simpletest_original_$source_db_key' connection key already exists. Broken test?");
    }

    // Clone the current connection and replace the current prefix.
    $connection_info = Database::getConnectionInfo($source_db_key);
    if ($connection_info) {
      Database::renameConnection($source_db_key, "simpletest_original_$source_db_key");
    }
    $connection_info = Database::getConnectionInfo('default');
    foreach ($connection_info as $target => $value) {
      $prefix = is_array($value['prefix']) ? $value['prefix']['default'] : $value['prefix'];
      // Simpletest uses 7 character prefixes at most so this can't cause
      // collisions.
      if (is_string($connection_info[$target]['prefix'])) {
        $connection_info[$target]['prefix'] = $prefix . '0';
        continue;
      }

      $connection_info[$target]['prefix']['default'] = $prefix . '0';
      // Add the original simpletest prefix so SQLite can attach its database.
      // @see \Drupal\Core\Database\Driver\sqlite\Connection::init()
      $connection_info[$target]['prefix'][$value['prefix']['default']] = $prefix;
      break;
    }
    Database::addConnectionInfo($source_db_key, 'default', $connection_info['default']);

    // If we are in a functional test, we might use Drush for testing things.
    // So we write the connection info into settings.php.
    if (is_callable([$this, 'writeSettings'])) {
      $this->writeSettings([
        'databases' => [
          "{$source_db_key}']['default" => (object) [
            'value' => $connection_info['default'],
            'required' => TRUE,
          ],
        ],
      ]);
    }

    if ($source_db_key !== 'migrate') {
      \Drupal::state()->set('migmag.test_db', [
        'key' => $source_db_key,
        'target' => 'default',
      ]);
      \Drupal::state()->set('migrate.fallback_state_key', 'migmag.test_db');
    }
  }

  /**
   * Loads a database fixture into the source database connection.
   *
   * @param array $database
   *   The source data, keyed by table name. Each table is an array containing
   *   the rows in that table.
   *
   * @see \Drupal\Tests\migrate\Kernel\MigrateSqlSourceTestBase::getDatabase
   */
  protected function importSourceDatabase(array $database): void {
    // Create the tables and fill them with data.
    foreach ($database as $table => $rows) {
      // Use the biggest row to build the table schema.
      $counts = array_map('count', $rows);
      asort($counts);
      end($counts);
      $pilot = $rows[key($counts)];

      $schema = array_map(
        function ($value) {
          $type = [];

          // If the value is unserializable, use longblob.
          try {
            unserialize($value);
            $type = [
              'type' => 'blob',
              'size' => 'big',
            ];
          }
          catch (\Throwable $t) {
            // unserialize() throws a notice on error.
            $type['type'] = is_numeric($value) && !is_float($value + 0)
              ? 'int'
              : 'text';
          }
          $type['not null'] = FALSE;
          return $type;
        },
        $pilot
      );

      $this->sourceDatabase->schema()
        ->createTable($table, [
          'fields' => $schema,
        ]);

      $fields = array_keys($pilot);
      $default_nulls = array_combine(array_keys($schema), array_fill(0, count($schema), NULL));
      $insert = $this->sourceDatabase->insert($table)->fields($fields);
      foreach ($rows as $row) {
        $insert->values($row + $default_nulls);
      }
      $insert->execute();
    }
  }

  /**
   * Cleans up the test migrate connection.
   *
   * @see \Drupal\Tests\migrate\Kernel\MigrateTestBase::cleanupMigrateConnection()
   *
   * @todo Refactor when core don't use global.
   *   https://www.drupal.org/node/2552791
   */
  private function cleanupSourceMigrateConnection(string $source_db_key = 'migrate') {
    Database::removeConnection($source_db_key);
    $original_connection_info = Database::getConnectionInfo("simpletest_original_$source_db_key");
    if ($original_connection_info) {
      Database::renameConnection("simpletest_original_$source_db_key", $source_db_key);
    }
  }

}

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

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