<?php
/**
 * Item value handler for JSON serialized values.
 *
 * @package Ealab\Deployer
 */

namespace Ealab\Deployer\Tracking\ItemValueHandler;

use Ealab\Deployer\Exception\WpDeployException;

/**
 * Item value handler for JSON serialized values.
 *
 * This is a convenience item value handler that will make the value more readable in the exported file.
 * For performance reasons, it's still better to use the scalar item value handler.
 */
class JsonItemValueHandler extends ItemValueHandlerBase {
	/**
	 * {@inheritDoc}
	 */
	public static function getHandlerBaseId(): string {
		return 'json';
	}

	/**
	 * {@inheritDoc}
	 */
	public static function getLabel(): string {
		return _dpgettext( 'deployer-core', 'item value handler', 'JSON serialized value' );
	}

	/**
	 * {@inheritDoc}
	 */
	protected function getUnprocessedValue( int $operation, ?callable $progress_callback = null ) {
		if ( static::OPERATION__EXPORT === $operation ) {
			if ( static::ORIGIN__DATABASE !== $this->origin ) {
				// Return the value as is; it is already deserialized.
				return $this->value;
			}

			try {
				$deserialized_value = json_decode( $this->value );
			} catch ( \Throwable $e ) {
				throw new WpDeployException( 'Cannot deserialize JSON value.', 0, $e );
			}

			if ( JSON_ERROR_NONE !== json_last_error() ) {
				throw new WpDeployException( 'Cannot deserialize JSON value.' );
			}

			return $deserialized_value;
		}

		if ( static::ORIGIN__DATABASE === $this->origin ) {
			// Return the value as is; it is already serialized.
			return $this->value;
		}

		try {
			// Serialize the value for import.
			$serialized_value = json_encode( $this->value );
		} catch ( \Throwable $e ) {
			throw new WpDeployException( 'Cannot serialize to JSON value.', 0, $e );
		}

		if ( JSON_ERROR_NONE !== json_last_error() ) {
			throw new WpDeployException( 'Cannot serialize to JSON value.' );
		}

		return $serialized_value;
	}
}
