<?php

namespace MintyPHP\Service\Import;

use MintyPHP\Repository\Audit\ImportAuditRunRepository;
use MintyPHP\Service\Access\AccessServicesFactory;
use MintyPHP\Service\Access\PermissionGateway;
use MintyPHP\Service\Audit\ImportAuditService;
use MintyPHP\Service\Import\Profile\DepartmentImportGateway;
use MintyPHP\Service\Import\Profile\DepartmentImportProfile;
use MintyPHP\Service\Import\Profile\UserImportGateway;
use MintyPHP\Service\Import\Profile\UserImportProfile;
use MintyPHP\Service\Settings\SettingGateway;
use MintyPHP\Service\Settings\SettingServicesFactory;
use MintyPHP\Service\User\UserServicesFactory;

class ImportServicesFactory
{
    private ?AccessServicesFactory $accessServicesFactory = null;
    private ?CsvReaderService $csvReaderService = null;
    private ?ImportTempFileService $importTempFileService = null;
    private ?ImportStateStoreService $importStateStoreService = null;
    private ?ImportAuditRunRepository $importAuditRunRepository = null;
    private ?ImportAuditService $importAuditService = null;
    private ?PermissionGateway $permissionGateway = null;
    private ?SettingServicesFactory $settingServicesFactory = null;
    private ?SettingGateway $settingGateway = null;
    private ?ImportService $importService = null;
    private ?UserServicesFactory $userServicesFactory = null;

    public function createImportService(): ImportService
    {
        if ($this->importService !== null) {
            return $this->importService;
        }

        $profiles = [
            'users' => new UserImportProfile(new UserImportGateway(
                $this->getUserServicesFactory()->createUserReadRepository(),
                $this->getUserServicesFactory()->createUserAccountService()
            )),
            'departments' => new DepartmentImportProfile(new DepartmentImportGateway()),
        ];

        return $this->importService = new ImportService(
            $this->getCsvReaderService(),
            $this->getImportTempFileService(),
            $this->createImportAuditService(),
            $this->createImportStateStoreService(),
            $profiles,
            $this->createPermissionGateway(),
            $this->createSettingGateway(),
            $this->getUserServicesFactory()->createUserScopeGateway()
        );
    }

    public function createImportAuditService(): ImportAuditService
    {
        return $this->importAuditService ??= new ImportAuditService($this->getImportAuditRunRepository());
    }

    public function createImportStateStoreService(): ImportStateStoreService
    {
        return $this->importStateStoreService ??= new ImportStateStoreService($this->getImportTempFileService());
    }

    private function getCsvReaderService(): CsvReaderService
    {
        return $this->csvReaderService ??= new CsvReaderService();
    }

    private function getImportTempFileService(): ImportTempFileService
    {
        return $this->importTempFileService ??= new ImportTempFileService();
    }

    private function getImportAuditRunRepository(): ImportAuditRunRepository
    {
        return $this->importAuditRunRepository ??= new ImportAuditRunRepository();
    }

    private function getUserServicesFactory(): UserServicesFactory
    {
        return $this->userServicesFactory ??= new UserServicesFactory();
    }

    private function createPermissionGateway(): PermissionGateway
    {
        return $this->permissionGateway ??= $this->accessServicesFactory()->createPermissionGateway();
    }

    private function accessServicesFactory(): AccessServicesFactory
    {
        return $this->accessServicesFactory ??= new AccessServicesFactory();
    }

    private function createSettingGateway(): SettingGateway
    {
        return $this->settingGateway ??= $this->settingServicesFactory()->createSettingGateway();
    }

    private function settingServicesFactory(): SettingServicesFactory
    {
        return $this->settingServicesFactory ??= new SettingServicesFactory();
    }
}
