<?php

/**
 * Lifestyle Webconsulting GmbH
 *
 * LICENSE: This Software is the property of Lifestyle Webconsulting GmbH (Aschaffenburg, Germany)
 * and is private by copyright law - it is NOT Freeware.
 *
 * Any unauthorized use of this software without a valid license
 * is a violation of the license agreement and will be prosecuted by
 * civil and criminal law.
 *
 * @copyright  2018 Lifestyle Webconsulting GmbH
 * @link       http://www.life-style.de
 */

namespace Sso\RestBundle\ModelRest\Common\Type;

use JMS\Serializer\Context;
use JMS\Serializer\GraphNavigator;
use JMS\Serializer\Handler\SubscribingHandlerInterface;
use JMS\Serializer\VisitorInterface;

/**
 * Class ArrayStringTypeHandler
 *
 * @copyright  2017 Lifestyle Webconsulting GmbH
 * @link       http://www.life-style.de
 * @package Sso\RestBundle\ModelRest\Common\Type
 */
class ArrayStringTypeHandler implements SubscribingHandlerInterface
{
    /**
     * @return array
     */
    public static function getSubscribingMethods()
    {
        $methods = array();
        $formats = array('json', 'xml');
        $type = 'Sso\RestBundle\ModelRest\Common\Type\ArrayStringType';
        foreach ($formats as $format) {
            $methods[] = array(
                'direction' => GraphNavigator::DIRECTION_SERIALIZATION,
                'type' => $type,
                'format' => $format,
                'method' => 'serialize' . ucfirst($format) . 'ArrayString',
            );

            $methods[] = array(
                'direction' => GraphNavigator::DIRECTION_DESERIALIZATION,
                'type' => $type,
                'format' => $format,
                'method' => 'deserialize' . ucfirst($format) . 'ArrayString',
            );
        }

        return $methods;
    }

    /**
     * @param VisitorInterface $visitor
     * @param ArrayStringType $arrayStringValue
     * @param array $type
     * @param Context $context
     * @return mixed
     */
    public function serializeJsonArrayString(
        VisitorInterface $visitor,
        ArrayStringType $arrayStringValue,
        array $type,
        Context $context
    ) {
        $value = $arrayStringValue->getValue();

        // We change the base type, and pass through possible parameters.
        if (is_array($value)) {
            $type['name'] = 'array';
            return $visitor->visitArray($value, $type, $context);
        }

        $type['name'] = 'string';
        return $visitor->visitString((string)$value, $type, $context);
    }

    /**
     * @param VisitorInterface $visitor
     * @param ArrayStringType $arrayStringValue
     * @param array $type
     * @param Context $context
     * @return mixed
     */
    public function serializeXmlArrayString(
        VisitorInterface $visitor,
        ArrayStringType $arrayStringValue,
        array $type,
        Context $context
    ) {
        $value = $arrayStringValue->getValue();

        // We change the base type, and pass through possible parameters.
        if (is_array($value)) {
            $type['name'] = 'array';
            return $visitor->visitArray($value, $type, $context);
        }

        $type['name'] = 'string';
        return $visitor->visitArray([(string)$value], $type, $context);
    }

    /**
     * @param VisitorInterface $visitor
     * @param array $data
     * @param array $type
     * @param Context $context
     * @return ArrayStringType
     */
    public function deserializeJsonArrayString(VisitorInterface $visitor, $data, array $type, Context $context)
    {
        // See above.
        if (is_array($data)) {
            $type['name'] = 'array';
            return new ArrayStringType($visitor->visitArray($data, $type, $context));
        }

        $type['name'] = 'string';
        return new ArrayStringType($visitor->visitString($data, $type, $context));
    }

    /**
     * @param VisitorInterface $visitor
     * @param array $data
     * @param array $type
     * @param Context $context
     * @return ArrayStringType
     */
    public function deserializeXmlArrayString(VisitorInterface $visitor, $data, array $type, Context $context)
    {
        // See above.
        $type['name'] = 'array';
        $type['params'] = [
            ['name' => 'string']
        ];
        return new ArrayStringType($visitor->visitArray($data, $type, $context));
    }
}
