<?php

namespace Drupal\languagewire_translation_provider\Test\Database;

use Drupal\languagewire_translation_provider\Adapter\Database\LanguageWireConfigurationItemRepositoryInterface;
use Drupal\languagewire_translation_provider\Adapter\TMGMT\TmgmtTranslatorInterface;
use Drupal\languagewire_translation_provider\Client\TranslationMemory;
use Drupal\languagewire_translation_provider\Database\TypedTranslationMemoryRepository;
use PHPUnit\Framework\TestCase;
use stdClass;

/**
 * Typed Translation Memory Repository Test.
 */
class TypedTranslationMemoryRepositoryTest extends TestCase {
  use \Prophecy\PhpUnit\ProphecyTrait;

  /**
   * Config Item Repository .
   *
   * @var \Prophecy\Prophecy\ObjectProphecy
   */
  private $configItemRepository;

  /**
   * Translator .
   *
   * @var \Prophecy\Prophecy\ObjectProphecy
   */
  private $translator;

  /**
   * Set Up .
   */
  protected function setUp(): void {
    $this->configItemRepository = $this->prophesize(LanguageWireConfigurationItemRepositoryInterface::class);
    $this->translator = $this->prophesize(TmgmtTranslatorInterface::class);
  }

  /**
   * Removes All Configuration Items Stored For Translator .
   *
   * @test
   */
  public function removesAllConfigurationItemsStoredForTranslator(): void {
    $translator = $this->translator->reveal();
    $repository = $this->repository();

    $repository->removeAll($translator);

    $this->configItemRepository->removeAll($translator, 'translation_memory')
      ->shouldHaveBeenCalled();
  }

  /**
   * Saves All Configuration Items For Translator .
   *
   * @test
   */
  public function savesAllConfigurationItemsForTranslator(): void {
    $translator = $this->translator->reveal();
    $items = [];
    $repository = $this->repository();

    $repository->saveAll($items, $translator);

    $this->configItemRepository->saveAll($items, $translator, 'translation_memory')
      ->shouldHaveBeenCalled();
  }

  /**
   * Fetches All Configuration Items For Translator .
   *
   * @test
   */
  public function fetchesAllConfigurationItemsForTranslator(): void {
    $translator = $this->translator->reveal();
    $databaseItem = $this->databaseItem();
    $this->configItemRepository->getAll($translator, 'translation_memory')
      ->willReturn([$databaseItem]);
    $repository = $this->repository();

    $result = $repository->getAll($translator);

    $this->assertCount(1, $result);
    $translationMemory = $result[0];
    $this->assertInstanceOf(TranslationMemory::class, $translationMemory);
    $this->assertSame($databaseItem->item_id, $translationMemory->id());
    $this->assertSame($databaseItem->name, $translationMemory->name());
  }

  /**
   * Fetches Translation Memory By Id .
   *
   * @test
   */
  public function fetchesTranslationMemoryById(): void {
    $translationMemoryId = 1;
    $translator = $this->translator->reveal();
    $databaseItem = $this->databaseItem();
    $this->configItemRepository->getByIdAndType($translator, $translationMemoryId, 'translation_memory')
      ->willReturn($databaseItem);
    $repository = $this->repository();

    $translationMemory = $repository->getById($translationMemoryId, $translator);

    $this->assertInstanceOf(TranslationMemory::class, $translationMemory);
    $this->assertSame($databaseItem->item_id, $translationMemory->id());
    $this->assertSame($databaseItem->name, $translationMemory->name());
  }

  /**
   * Repository .
   */
  private function repository(): TypedTranslationMemoryRepository {
    return new TypedTranslationMemoryRepository($this->configItemRepository->reveal());
  }

  /**
   * Database Item .
   */
  private function databaseItem(): stdClass {
    $item = new stdClass();
    $item->item_id = 1;
    $item->name = 'Foo';

    return $item;
  }

}
