<?php
/**
 * Class ShipmentTemplateMetabox
 *
 * @package DhlPolska\ShipmentTemplates
 */

namespace DhlPolska\ShipmentTemplates;

use DhlPolska\Shipment\ShipmentData;
use DhlPolska\Shipment\ShipmentTypes;
use DhlPolska\WooCommerceSettings\Templates\TemplatesRepository;
use DhlPolskaVendor\WPDesk\PluginBuilder\Plugin\Hookable;

/**
 * Render and save shipment template metabox.
 */
class ShipmentTemplateMetabox implements Hookable {
	public const NONCE_ACTION = 'dhl_polska_template_meta';
	public const NONCE_FIELD  = 'dhl_polska_template_meta_nonce';

	public const FIELD_WEIGHT              = 'dhl_polska_template_weight';
	public const FIELD_TYPE                = 'dhl_polska_template_type';
	public const FIELD_LENGTH              = 'dhl_polska_template_length';
	public const FIELD_WIDTH               = 'dhl_polska_template_width';
	public const FIELD_HEIGHT              = 'dhl_polska_template_height';
	public const FIELD_COD                 = 'dhl_polska_template_cod';
	public const FIELD_INSURANCE           = 'dhl_polska_template_insurance';
	public const FIELD_SERVICE_1722        = 'dhl_polska_template_service_1722';
	public const FIELD_SERVICE_SOBOTA      = 'dhl_polska_template_service_sobota';
	public const FIELD_SERVICE_NAD_SOBOTA  = 'dhl_polska_template_service_nad_sobota';
	public const FIELD_SERVICE_PDI         = 'dhl_polska_template_service_pdi';
	public const FIELD_SERVICE_ROD         = 'dhl_polska_template_service_rod';
	public const FIELD_SERVICE_POD         = 'dhl_polska_template_service_pod';
	public const FIELD_SERVICE_AGEVER      = 'dhl_polska_template_service_agever';
	public const FIELD_SERVICE_NST         = 'dhl_polska_template_service_nst';
	public const FIELD_SERVICE_EURO_RETURN = 'dhl_polska_template_service_euro_return';

	private TemplatesRepository $templates_repository;

	private ShipmentTypes $shipment_types;

	public function __construct( TemplatesRepository $templates_repository, ShipmentTypes $shipment_types ) {
		$this->templates_repository = $templates_repository;
		$this->shipment_types       = $shipment_types;
	}

	/**
	 * Hooks.
	 */
	public function hooks() {
		add_action( 'add_meta_boxes', [ $this, 'register_metabox' ] );
		add_action( 'save_post_' . ShipmentTemplatePostType::POST_TYPE, [ $this, 'save_template_meta' ] );
	}

	/**
	 * @return void
	 */
	public function register_metabox(): void {
		add_meta_box(
			'dhl-polska-template-meta',
			__( 'Parametry szablonu', 'dhl-polska' ),
			[ $this, 'render_metabox' ],
			ShipmentTemplatePostType::POST_TYPE,
			'normal',
			'high'
		);
	}

	/**
	 * @param \WP_Post $post .
	 *
	 * @return void
	 */
	public function render_metabox( $post ): void {
		/** @phpstan-ignore-next-line */
		$post_id        = is_object( $post ) && isset( $post->ID ) ? (int) $post->ID : 0;
		$template       = $this->templates_repository->get_template_meta( $post_id );
		$weight_unit    = get_option( 'woocommerce_weight_unit', 'kg' );
		$dimension_unit = get_option( 'woocommerce_dimension_unit', 'cm' );
		$type_options   = $this->get_type_options();
		$service_fields = $this->get_service_fields();

		include __DIR__ . '/views/html-shipment-template-metabox.php';
	}

	/**
	 * @param int $post_id .
	 *
	 * @return void
	 */
	public function save_template_meta( int $post_id ): void {
		if ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) {
			return;
		}

		if ( ! isset( $_POST[ self::NONCE_FIELD ] ) ) {
			return;
		}

		$nonce = sanitize_text_field( wp_unslash( $_POST[ self::NONCE_FIELD ] ) );
		if ( ! wp_verify_nonce( $nonce, self::NONCE_ACTION ) ) {
			return;
		}

		if ( ! current_user_can( 'edit_post', $post_id ) ) {
			return;
		}

		$services = [];
		// phpcs:disable WordPress.Security.NonceVerification.Missing
		foreach ( $this->get_service_field_map() as $service_key => $field_name ) {
			$services[ $service_key ] = isset( $_POST[ $field_name ] );
		}

		$payload = [
			'weight'     => isset( $_POST[ self::FIELD_WEIGHT ] ) ? sanitize_text_field( wp_unslash( $_POST[ self::FIELD_WEIGHT ] ) ) : '',
			'type'       => isset( $_POST[ self::FIELD_TYPE ] ) ? sanitize_text_field( wp_unslash( $_POST[ self::FIELD_TYPE ] ) ) : '',
			'dimensions' => [
				'length' => isset( $_POST[ self::FIELD_LENGTH ] ) ? sanitize_text_field( wp_unslash( $_POST[ self::FIELD_LENGTH ] ) ) : '',
				'width'  => isset( $_POST[ self::FIELD_WIDTH ] ) ? sanitize_text_field( wp_unslash( $_POST[ self::FIELD_WIDTH ] ) ) : '',
				'height' => isset( $_POST[ self::FIELD_HEIGHT ] ) ? sanitize_text_field( wp_unslash( $_POST[ self::FIELD_HEIGHT ] ) ) : '',
			],
			'services'   => $services,
		];
		// phpcs:enable WordPress.Security.NonceVerification.Missing

		$this->templates_repository->save_template_meta( $post_id, $payload );
	}

	/**
	 * @return array<string, string>
	 */
	private function get_type_options(): array {
		return $this->shipment_types->get_type_labels();
	}

	/**
	 * @return array<string, string>
	 */
	private function get_service_field_map(): array {
		$map = [];

		foreach ( $this->get_service_fields() as $service_key => $service ) {
			$map[ (string) $service_key ] = $service['field'];
		}

		return $map;
	}

	/**
	 * @return array<string, array{field: string, label: string}>
	 */
	private function get_service_fields(): array {
		return [
			ShipmentData::TEMPLATE_SERVICE_1722 => [
				'field' => self::FIELD_SERVICE_1722,
				'label' => __( '1722 - Doręczenie w godzinach 18-22', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_SOBOTA => [
				'field' => self::FIELD_SERVICE_SOBOTA,
				'label' => __( 'SOBOTA - Doręczenie w sobotę', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_NAD_SOBOTA => [
				'field' => self::FIELD_SERVICE_NAD_SOBOTA,
				'label' => __( 'NAD_SOBOTA - Nadanie w sobotę', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_INSURANCE => [
				'field' => self::FIELD_INSURANCE,
				'label' => __( 'UBEZP - Ubezpieczenie przesyłki', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_COD => [
				'field' => self::FIELD_COD,
				'label' => __( 'COD - Zwrot pobrania', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_PDI => [
				'field' => self::FIELD_SERVICE_PDI,
				'label' => __( 'PDI - Informacje przed doręczeniem', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_ROD => [
				'field' => self::FIELD_SERVICE_ROD,
				'label' => __( 'ROD - Zwrot potwierdzonych dokumentów', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_POD => [
				'field' => self::FIELD_SERVICE_POD,
				'label' => __( 'POD - Potwierdzenie doręczenia / Dla produktu PI - Usługi utylizacji', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_AGEVER => [
				'field' => self::FIELD_SERVICE_AGEVER,
				'label' => __( 'AGEVER - Odbiór przez osobę dorosłą', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_NST => [
				'field' => self::FIELD_SERVICE_NST,
				'label' => __( 'NST - Przesyłka niestandardowa', 'dhl-polska' ),
			],
			ShipmentData::TEMPLATE_SERVICE_EURO_RETURN => [
				'field' => self::FIELD_SERVICE_EURO_RETURN,
				'label' => __( 'EURO RETURN - Zwrot palet', 'dhl-polska' ),
			],
		];
	}
}
