<?php

namespace Internetgalerie\IgDatapoolFe\Property\TypeConverter;

use TYPO3\CMS\Extbase\Persistence\ObjectStorage;
use TYPO3\CMS\Extbase\Property\PropertyMappingConfigurationInterface;
use TYPO3\CMS\Extbase\Utility\TypeHandlingUtility;

class ObjectStorageConverter extends \TYPO3\CMS\Extbase\Property\TypeConverter\ObjectStorageConverter
{
    protected $debug = false;
    protected $debugLog = '/tmp/log2.txt';

    /**
     * @var array<string>
     */
    protected $sourceTypes = [ 'array' ];

    /**
     * @var string
     */
    protected $targetType = ObjectStorage::class;

    /**
     * Needs to take precedence over the available
     *
     * @var integer
     */
    protected $priority = 25;

    /*
    function castFileReference( \TYPO3\CMS\Extbase\Domain\Model\FileReference $fileRef) {
      return  $fileRef;
    }
    */
    public function log($text): void
    {
        $fp = fopen($this->debugLog, 'a');
        fputs($fp, $text ."\n");
        fclose($fp);
    }
    public function log_var_dump($var): void
    {
        $fp = fopen($this->debugLog, 'a');
        $text = var_export($var, true);
        fputs($fp, 'DUMP[ObjectStorageConverter]=' .  $text ."\n");
        fclose($fp);
    }

    /**
     * Actually convert from $source to $targetType, taking into account the fully
     * built $convertedChildProperties and $configuration.
     *
     * @param  mixed                                 $source
     * @param  string                                $targetType
     * @param  array                                 $convertedChildProperties
     * @param  PropertyMappingConfigurationInterface $configuration
     * @return ObjectStorage
     */

    public function convertFrom($source, string $targetType, array $convertedChildProperties = [], ?PropertyMappingConfigurationInterface $configuration = null): ObjectStorage
    {
        if ($this->debug) {
            $this->log("\n-----------------------------------------------------\nINIT ObjectStorageConverter.php");
            //          $this->log_var_dump($source);
        }
        $objectStorage = new ObjectStorage();
        foreach ($convertedChildProperties as $subProperty) {
            if ($this->debug) {
                $this->log('Foreach:');
            }
            if ($subProperty === null) {
                continue;
            }
            if ($this->debug) {
                $this->log('Object: '.$subProperty::class);
                /*
                  $this->log('Object: '.get_class($this->castFileReference($subProperty)));
                  $this->log('Object UID: '.$subProperty->getUid());
                  $this->log('Object Orig: '.get_class($subProperty->getOriginalResource()));
                  $this->log('Object Orig UID: '.$subProperty->getOriginalResource()->getUid());
                  //$this->log_var_dump($subProperty->getOriginalResource());
                  */
            }
            //$objectStorage->attach($this->castFileReference($subProperty));
            $objectStorage->attach($subProperty);
        }

        if ($this->debug) {
            $this->log('objectStorage-count:'. count($objectStorage));
        }

        return $objectStorage;
    }
    /**
     * Returns the source, if it is an array, otherwise an empty array.
     *
     * @param  mixed $source
     * @return array
     * @api
     */
    public function getSourceChildPropertiesToBeConverted($source): array
    {
        if ($this->debug) {
            $this->log('--> ObjectStorageConverter::getSourceChildPropertiesToBeConverted');
            //$this->log_var_dump($source);
        }
        if (is_array($source)) {
            if ($this->isDpFileReference($source)) {
                if ($this->debug) {
                    $this->log('isDpFileReference');
                }
                unset($source['__dpObject']);
            }
            if ($this->isDpObjectStorage($source)) {
                if ($this->debug) {
                    $this->log('isDpObjectStorage');
                }
                unset($source['__dpObject']);
                foreach ($source as $index=>$object) {
                    if ($this->debug) {
                        $this->log('object: '. $index);
                    }
                    //$this->log_var_dump($object);
                    if ($this->isDpFileReference($object)) {
                        if ($this->debug) {
                            $this->log('object: '. $index . ' IS isDpFileReference');
                        }
                        //$fileReference=$propertyMapper->convert( $object, FileReference::class);
                        //$this->log_var_dump($fileReference);
                        //unset($source[$index]);
                    }
                }
            }
            return $source;
        }
        return [];
    }
    /**
     * Return the type of a given sub-property inside the $targetType
     *
     * @param string $targetType
     */
    public function getTypeOfChildProperty($targetType, string $propertyName, PropertyMappingConfigurationInterface $configuration): string
    {
        $parsedTargetType = TypeHandlingUtility::parseType($targetType);
        if ($this->debug) {
            $this->log('--> ObjectStorageConverter.::getTypeOfChildProperty: elementType='.$parsedTargetType['elementType']);
        }
        return $parsedTargetType['elementType'];
    }
    public function isDpFileReference($source)
    {
        return is_array($source) && isset($source['__dpObject']) && $source['__dpObject']=='FileReference';
    }
    public function isDpObjectStorage($source)
    {
        return is_array($source) && isset($source['__dpObject']) && $source['__dpObject']=='ObjectStorage';
    }
}
