<?php
/**
 * Service Util
 */

namespace WkwcAdyen\Helper\Common;

// prevent direct access data leaks
defined( 'ABSPATH' ) || exit;

class Wkwc_Adyen_Service_Util {

	/**
	 * Adyen_Service_Util constructor.
	 */
	public function __construct() {
	}

	/**
	 * Gets the page where the customer will be redirected.
	 *
	 * @since 1.2.0
	 * @param \WC_Order $order
	 * @param string    $result_code
	 * @return string
	 */
	public static function get_return_page_url( \WC_Order $order, $result_code ) {

		$url = in_array( strtolower( $result_code ), array( 'pending', 'error', 'cancelled', 'refused' ) ) ? add_query_arg( array( 'payment_result' => 'failed' ), $order->get_checkout_payment_url() ) : $order->get_checkout_order_received_url();

		return $url;
	}



	/**
	 * Retrieves the checkout URL.
	 *
	 * @param \WC_Order $order
	 * @return string
	 */
	public static function get_checkout_url( $order ) {
		return self::has_subscription() ? wc_get_checkout_url() : $order->get_checkout_payment_url();
	}


	/**
	 * Gets the number of installments based on the country.
	 *
	 * @since 1.2.0 - return the installments based on $max_installments value
	 * @since 1.0.3
	 * @param string $country - ISO CODE
	 * @param string $max_installments - the max number of allowed installments
	 * @return array|void
	 */
	public static function get_installments_by_country( $country, $max_installments ) {

		$max_installments = empty( $max_installments ) ? 20 : $max_installments;
		$br               = array();

		for ( $i = 2; $i <= $max_installments; $i++ ) {
			$br[] = $i;
		}

		$mx         = array();
		$mx_allowed = array( 3, 6, 9, 12, 18 );
		$tr         = array();
		$tr_allowed = array( 2, 3, 6, 9 );

		foreach ( $mx_allowed as $mx_val ) {
			if ( $mx_val <= $max_installments ) {
				$mx[] = $mx_val;
			}
		}

		foreach ( $tr_allowed as $tr_val ) {
			if ( $tr_val <= $max_installments ) {
				$tr[] = $tr_val;
			}
		}

		$list = array(
			'BR' => $br,
			'MX' => $mx,
			'TR' => $tr,
		);

		if ( isset( $list[ $country ] ) ) {
			return $list[ $country ];
		}

		return '';
	}



	/**
	 * List of payment methods which are immediately captured.
	 *
	 * @since 1.1.0
	 * @return array
	 */
	public static function immediate_payment_methods() {

		return array(
			'bcmc',
		);
	}



	/**
	 * List of payment methods which are manually captured.
	 *
	 * @since 1.2.0 - include Klarna only if the option is disabled
	 * @since 1.1.0
	 * @return array
	 */
	public static function manual_payment_methods() {

		$list = array();

		if ( 'yes' !== get_option( WKWC_ADN_PREFIX . '_auto_klarna_payments' ) ) {

			$list = array_merge(
				$list,
				array(
					'klarna',
					'klarna_paynow',
				)
			);

		}

		/**
		 * Let 3rd-parties to filter the manual payment methods.
		 *
		 * @param array $list
		 * @since 1.8.0
		 * @return array
		 */
		return apply_filters( WKWC_ADN_PREFIX . 'manual_payment_methods_lists', $list );
	}



	/**
	 * Checks whether the given payment method is manually captured.
	 *
	 * @since 1.1.0
	 * @param string $method
	 * @return boolean
	 */
	public static function is_manual_payment( $method ) {

		if ( in_array( $method, self::manual_payment_methods() ) ) {
			return true;
		}

		return false;
	}



	/**
	 * Checks whether the given payment method is immediately captured.
	 *
	 * @since 1.1.0
	 * @param string $method
	 * @return boolean
	 */
	public static function is_immediate_payment( $method ) {

		if ( in_array( $method, self::immediate_payment_methods() ) ) {
			return true;
		}

		return false;
	}



	/**
	 * Checks whether or not a given country code is valid (exists in the WC countries list).
	 *
	 * @since 1.0.0
	 * @param string $code
	 * @return boolean
	 */
	public static function is_valid_country_code( $code ) {

		$countries = ( new \WC_Countries() )->get_countries();

		if ( array_key_exists( strtoupper( $code ), $countries ) ) {
			return true;
		}

		return false;
	}



	/**
	 * Checks whether or not the given payment method is activated
	 *
	 * @since 1.0.4 - add caching for 1 hour
	 * @since 1.0.0
	 * @param string $method
	 * @return boolean
	 */
	public static function is_payment_method_active( $method ) {
		$is_active = get_transient( WKWC_ADN_PREFIX . '_is_active_' . $method );
		if ( empty( $is_active ) ) {
			foreach ( ( new Wkwc_Adyen_Checkout_Action() )->wkwc_adyen_get_payment_methods() as $item ) {
				if ( $item['type'] === $method ) {
					set_transient( WKWC_ADN_PREFIX . '_is_active_' . $method, true, HOUR_IN_SECONDS );
					return true;
				}
			}
		}

		return $is_active;
	}



	/**
	 * Checks whether or not the installment value is valid.
	 *
	 * @since 1.2.0 - set default $max_installments to 20
	 * @since 1.0.3
	 * @param string|int $number
	 * @param string     $country
	 * @param string|int $max_installments
	 * @param string     $are_installments_allowed
	 * @return boolean
	 */
	public static function is_valid_installment( $number, $country, $max_installments, $are_installments_allowed = 'yes' ) {

		if ( 'yes' !== $are_installments_allowed ) {
			return false;
		}

		$is_valid         = true;
		$max_installments = empty( $max_installments ) ? 20 : $max_installments;
		$value            = self::get_installments_by_country( $country, $max_installments );

		if ( is_array( $value ) ) {

			if ( ! in_array( $number, $value ) ) {
				$is_valid = false;
			}
		} elseif ( (int) $value > 0 && $number > $max_installments ) {
				$is_valid = false;
		}

		return $is_valid;

	}

	/**
	 * Checks if checkout contains at least one subscription.
	 *
	 * @since 1.0.9 - added support for variable subscription
	 *              - change name to `has_subscription`
	 * @since 1.0.3
	 * @return bool
	 */
	public static function has_subscription() {

		if ( WC()->cart ) {

			foreach ( WC()->cart->get_cart() as $item ) {
				if ( $item['data']->is_type( array( 'subscription_variation', 'subscription' ) ) ) {
					return true;
				}
			}
		}

		return false;
	}

}
