<?php

namespace Ignite\Core\Files\Processors;

use Ignite\Core\Contracts\Files\FileProcessor;
use Ignite\Core\Files\File;
use Ignite\Core\Files\TemporaryFile;
use Ignite\Core\Models\Import\File as ImportFile;

class ToImportFile implements FileProcessor
{
    /**
     * The type of import we're creating this file for.
     *
     * @var string
     */
    protected $type;

    /**
     * Keep the original file after processing?
     *
     * @var bool
     */
    protected $keepOriginal = false;

    public function __construct(string $type)
    {
        $this->type = $type;
    }

    /**
     * Instantiate this class for the given type.
     *
     * @param string $type
     * @return static
     */
    public static function forType(string $type): self
    {
        return app(static::class, compact('type'));
    }

    /**
     * Keep the original file after processing?
     *
     * @param bool $value
     * @return static
     */
    public function keepOriginal(bool $value = true): self
    {
        $this->keepOriginal = $value;
        return $this;
    }

    /**
     * {@inheritdoc}
     * @throws \Illuminate\Contracts\Filesystem\FileExistsException
     * @throws \Illuminate\Contracts\Filesystem\FileNotFoundException
     */
    public function run(File $file): File
    {
        $importFile = ImportFile::fromFile($file, $this->type);

        $this->handleKeepOriginal($file, $importFile);

        return new File($importFile->getFile(), $importFile->getDisk());
    }

    /**
     * Either delete the original file or make sure we keep it.
     *
     * @param File $file
     * @param ImportFile $importFile
     * @return void
     */
    protected function handleKeepOriginal(File $file, ImportFile $importFile): void
    {
        if ($this->keepOriginal) {
            if ($file instanceof TemporaryFile) {
                $file->keep();
            }
        } else if (! $importFile->toFile()->is($file)) {
            // Delete only if the original file is not the import file.
            $file->delete();
        }
    }
}
