<?php

/**
* @author Tassos Marinos <info@tassos.gr>
* @link http://www.tassos.gr
* @copyright Copyright © 2021 Tassos Marinos All Rights Reserved
* @license GNU GPLv3 <http://www.gnu.org/licenses/gpl.html> or later
*/

namespace ACF\Helpers\Fields;

defined('_JEXEC') or die;

use YOOtheme\Builder\Joomla\Fields\Type\FieldsType;
use YOOtheme\Str;
use Joomla\CMS\Factory;

class Upload
{
	
    public static function deleteFilesFromItem($item_id = '')
    {
		if (!$item_id)
		{
			return;
		}

		self::deleteFileUploadFiles($item_id);
		
		if (version_compare(JVERSION, '4', '>='))
		{
			self::deleteFileUploadFilesInSubform($item_id);
		}
    }

	protected static function deleteFileUploadFiles($item_id = '')
	{
		if (!$item_id)
		{
			return;
		}
		
		$db = Factory::getDbo();
		$query = $db->getQuery(true)
			->select('fv.value')
			->from('#__fields_values AS fv')
			->join('LEFT', '#__fields AS f ON fv.field_id = f.id')
			->where('fv.item_id = ' . $db->quote($item_id))
			->where('f.type = ' . $db->quote('acfupload'));

		$db->setQuery($query);

		$fieldsValues = $db->loadAssocList();

		if (!$fieldsValues)
		{
			return;
		}

		foreach ($fieldsValues as $value)
		{
			$files = json_decode($value['value'], true);
	
			if (!$files)
			{
				return;
			}
	
			foreach ($files as $file)
			{
				$filePath = implode(DIRECTORY_SEPARATOR, [JPATH_ROOT, $file['value']]);
	
				if (!file_exists($filePath))
				{
					continue;
				}
				
				unlink($filePath);
			}
		}
	}

	protected static function deleteFileUploadFilesInSubform($item_id = '')
	{
		if (!$item_id)
		{
			return;
		}

		$db = Factory::getDbo();

		// Get all ACF File Upload custom field IDs
		$query = $db->getQuery(true)
			->select('distinct f.id')
			->from('#__fields as f')
			->join('LEFT', '#__fields_values AS fv ON fv.field_id = f.id')
			->where('fv.item_id = ' . (int) $item_id)
			->where('f.type = ' . $db->quote('acfupload'));
			$db->setQuery($query);
		$fileupload_ids = array_keys($db->loadAssocList('id'));

		if (!$fileupload_ids)
		{
			return;
		}

		// Get all Subform custom fields
        $query->clear()
            ->select('f.id as field_id, fv.item_id as item_id, fv.value as value')
            ->from('#__fields as f')
            ->join('LEFT', '#__fields_values AS fv ON fv.field_id = f.id')
			->where('fv.item_id = ' . (int) $item_id)
            ->where('f.type = ' . $db->quote('subform'));
        $db->setQuery($query);
        $subform_fields = $db->loadAssocList();

		foreach ($subform_fields as $subform_field)
		{
			if (!$subform_field_items = json_decode($subform_field['value'], true))
			{
				continue;
			}

			foreach ($subform_field_items as $row => &$row_items)
			{
				if (!is_array($row_items))
				{
					continue;
				}

				foreach ($row_items as $field_name => &$field_value)
				{
					// Get the field id
					$field_id = str_replace('field', '', $field_name);
					
					// Check if its a gallery field
					if (!in_array($field_id, $fileupload_ids))
					{
						continue;
					}

					if (!is_array($field_value))
					{
						continue;
					}

					foreach ($field_value as $file)
					{
						$filePath = implode(DIRECTORY_SEPARATOR, [JPATH_ROOT, $file['value']]);

						if (!file_exists($filePath))
						{
							continue;
						}
						
						unlink($filePath);
					}
				}
			}
		}
	}
	
	
	/**
	* Returns the YooTheme type.
	*
	* If this accepts one image:
	* - Tells YooTheme to use the default type for the dropdown mapping option.
	*
	* If this accepts multiple images:
	* - Tells YooTheme to only return the value of this field in the dropdown mapping option.
	*
	* @param object $field
	* @param object $source
	*
	* @return array
	*/
	public static function getYooType($field = [], $source = [])
	{
		$limit_files = (int) $field->fieldparams->get('limit_files', 0);

		$fields = [
			[
				'type' => 'String',
				'name' => 'value',
				'metadata' => [
					'label' => 'File URL'
				],
			],
			[
				'type' => 'String',
				'name' => 'title',
				'metadata' => [
					'label' => 'Title'
				],
			],
			[
				'type' => 'String',
				'name' => 'description',
				'metadata' => [
					'label' => 'Description'
				],
			],
			[
				'type' => 'String',
				'name' => 'filesize',
				'metadata' => [
					'label' => 'File size'
				],
			],
		];
		$name = Str::camelCase(['Field', $field->name], true);
		$source->objectType($name, compact('fields'));

		if ($limit_files === 1)
		{
			return $name;
		}

		return ['listOf' => $name];
	}

	/**
	* Transforms the field value to an appropriate value that YooTheme can understand.
	*
	* @return array
	*/
	public static function yooResolve($item, $args, $ctx, $info)
	{
		$name = str_replace('String', '', strtr($info->fieldName, '_', '-'));

		// Check if it's a subform field
		$subfield = clone \ACF\Helpers\Yoo::getSubfield($args['field_id'], $args['context']);

		// When we have a subform field, the $item is an array of values
		if (!$subfield || !is_array($item))
		{
			if (!isset($item->id) || !($field = FieldsType::getField($name, $item, $args['context'])))
			{
				return;
			}
		}
		else
		{
			// Set rawvalue
			$subfield->rawvalue = isset($item["field{$args['field_id']}"]) ? json_encode($item["field{$args['field_id']}"]) : '';

			// Use the subform field
			$field = $subfield;
		}

		$value = $field->rawvalue;

		$value = is_string($value) ? json_decode($value, true) ?? $value : $value;

		if (!is_array($value))
		{
			return;
		}
		
		$value = array_values($value);

		if (is_array($value))
		{
			// Fix new lines in description
			foreach ($value as $key => &$val)
			{
				if (isset($val['description']))
				{
					$val['description'] = nl2br($val['description']);
				}
			}
		}

		foreach ($value as $key => &$val)
		{
			$val['filesize'] = '';
			
			$path = implode(DIRECTORY_SEPARATOR, [JPATH_ROOT, $val['value']]);
			if (file_exists($path))
			{
				$val['filesize'] = filesize($path);
				$val['filesize'] = sprintf("%4.2f MB", $val['filesize'] / 1024 / 1024);
			}

			if (isset($val['value']))
			{
				$val['value'] = $val['value'];
			}

			// If title is empty, use the filename
			if (empty($val['title']))
			{
				$val['title'] = basename($val['value']);
			}
		}

		$limit_files = (int) $field->fieldparams->get('limit_files', 0);
		if ($limit_files === 1 && is_array($value) && count($value) === 1)
		{
			return $value[0];
		}

		return $value;
	}
}