<?php
require_once LPC_PUBLIC . 'pickup' . DS . 'lpc_pickup_selection.php';

class LpcAdminOrderAffect extends LpcComponent {

	protected $lpcShippingMethods;

	protected $lpcCapabilitiesByCountry;

	protected $lpcAdminPickupWebService;

	protected $lpcAdminPickupWidget;


	public function __construct(
		LpcShippingMethods $shippingMethods = null,
		LpcCapabilitiesPerCountry $capabilitiesPerCountry = null,
		LpcAdminPickupWebService $lpcAdminPickupWebService = null,
		LpcAdminPickupWidget $lpcAdminPickupWidget = null
	) {
		$this->lpcShippingMethods       = LpcRegister::get('shippingMethods', $shippingMethods);
		$this->lpcCapabilitiesByCountry = LpcRegister::get('capabilitiesPerCountry', $capabilitiesPerCountry);
		$this->lpcAdminPickupWebService = LpcRegister::get('adminPickupWebService', $lpcAdminPickupWebService);
		$this->lpcAdminPickupWidget     = LpcRegister::get('adminPickupWidget', $lpcAdminPickupWidget);
	}

	public function init() {
		add_action('woocommerce_after_order_itemmeta', array($this, 'addAffectLink'), 10, 2);
		add_action('save_post', array($this, 'updateShippingMethod'), 10, 3);

		LpcHelper::enqueueScript('lpc_order_affect',
			plugins_url('/js/orders/lpc_order_affect.js', LPC_ADMIN . 'init.php'), null, ['jquery-core']);

		LpcHelper::enqueueStyle('lpc_order_affect_methods',
			plugins_url('/css/orders/lpc_order_affect_methods.css', LPC_ADMIN . 'init.php'), null);
	}

	public function addAffectLink($itemId, $item) {
		if (empty($item) || $item->get_type() !== 'shipping') {
			return;
		}

		$order = $item->get_order();

		if (!empty($this->lpcShippingMethods->getColissimoShippingMethodOfOrder($order)) || !$order->is_editable()) {
			return;
		}

		$methods = $this->getColissimoShippingMethodsAvailable($order);

		$methods = array_map(function ($value) {
			return $value->get_method_title();
		}, $methods);

		$args['lpc_shipping_methods'] = $methods;

		$args['link_choose_relay'] = 'yes' === LpcHelper::get_option('lpc_prUseWebService', 'no')
			? $this->lpcAdminPickupWebService->addGoogleMaps($order)
			: $this->lpcAdminPickupWidget->addWidget($order);

		echo LpcHelper::renderPartial('orders' . DS . 'lpc_order_affect_methods.php', $args);
	}

	public function updateShippingMethod($post_id, $post, $update) {
		$slug = 'shop_order';

		if (
			!is_admin()
			|| $slug != $post->post_type
			|| !isset($_REQUEST['lpc_order_affect_update_method'])
			|| (
				isset($_REQUEST['lpc_order_affect_update_method'])
				&& empty(sanitize_text_field(wp_unslash($_REQUEST['lpc_order_affect_update_method'])))
			)
		) {
			return;
		}

		$lpcNewShippingMethodId = isset($_REQUEST['lpc_new_shipping_method']) ? sanitize_text_field(wp_unslash($_REQUEST['lpc_new_shipping_method'])) : '';
		$orderShippingItemId    = isset($_REQUEST['lpc_order_affect_shipping_item_id']) ? sanitize_text_field(wp_unslash($_REQUEST['lpc_order_affect_shipping_item_id'])) : '';
		$relayInformation       = isset($_REQUEST['lpc_order_affect_relay_informations']) ? sanitize_text_field(wp_unslash($_REQUEST['lpc_order_affect_relay_informations'])) : '';
		$order                  = wc_get_order($post_id);

		if (empty($orderShippingItemId) || empty($order) || empty($lpcNewShippingMethodId)) {
			return;
		}

		$shippingItem         = $order->get_item($orderShippingItemId);
		$lpcMethods           = $this->getColissimoShippingMethodsAvailable($order);
		$lpcNewShippingMethod = $lpcMethods[$lpcNewShippingMethodId];

		if (empty($lpcNewShippingMethod) || (LpcRelay::ID === $lpcNewShippingMethod->id && empty($relayInformation))) {
			return;
		}

		if (LpcRelay::ID === $lpcNewShippingMethod->id) {
			$relayInformationData = json_decode(stripslashes($relayInformation));

			update_post_meta($post_id, LpcPickupSelection::PICKUP_LOCATION_ID_META_KEY,
				$relayInformationData->identifiant);
			update_post_meta($post_id, LpcPickupSelection::PICKUP_LOCATION_LABEL_META_KEY,
				$relayInformationData->nom);
			update_post_meta($post_id, LpcPickupSelection::PICKUP_PRODUCT_CODE_META_KEY,
				$relayInformationData->typeDePoint);

			$order->set_shipping_address_1($relayInformationData->adresse1);
			$order->set_shipping_postcode($relayInformationData->codePostal);
			$order->set_shipping_city($relayInformationData->localite);
			$order->set_shipping_country($relayInformationData->codePays);
			$order->set_shipping_company($relayInformationData->nom);

			$order->save();
		}

		$shippingItem->set_props(
			array(
				'method_id'    => $lpcNewShippingMethod->id,
				'method_title' => $lpcNewShippingMethod->get_method_title(),
			)
		);

		$shippingItem->save();
	}

	/**
	 * Retrieve Colissimo shipping methods avalaible for an order by country
	 *
	 * @param WC_Order $order
	 * @return array
	 */
	protected function getColissimoShippingMethodsAvailable(WC_Order $order) {
		$allShippingMethods                  = WC()->shipping() ? WC()->shipping()->load_shipping_methods() : array();
		$colissimoShipppingMethodsPerCountry = $this->lpcCapabilitiesByCountry->getCapabilitiesForCountry($order->get_shipping_country());
		$methods                             = array();

		foreach ($allShippingMethods as $oneMethod) {
			if (!empty($colissimoShipppingMethodsPerCountry[$oneMethod->id])) {
				$methods[$oneMethod->id] = $oneMethod;
			}
		}

		return $methods;
	}
}
