<?php
if ( ! defined( 'ABSPATH' ) ) { exit; }

/**
 * KNSDD_Tier_Service
 *
 * Ürün sayfasında gösterilecek miktar kademelerini (min/max, indirim türü/değeri) hesaplar.
 * - Sadece standard (miktar indirimi) kurallar dahil edilir. Özel kampanyalar hariçtir.
 * - Kullanıcıya uygunluk (login, allowed_customers, kullanım limitleri, ilk sipariş vb.) kontrol edilir.
 * - Çıktı eşik (max) etiketli sade formata uygundur: 2, 3, 4+; gerekirse aralık etiketi: 2–4.
 * - Performans için transient cache kullanılır ve knsdd_cache_version ile invalidation yapılır.
 */
class KNSDD_Tier_Service {

    /**
     * Ürün için kademe listesini döndürür.
     * @param int $product_id
     * @return array [ [ 'min'=>int, 'max'=>int, 'type'=>'percent|fixed', 'value'=>float ] , ... ]
     */
    public static function get_quantity_tiers_for_product( $product_id ) {
        if ( ! KNSDD_Data::is_globally_enabled() ) {
            return [];
        }
        $product_id = absint( $product_id );
        if ( $product_id <= 0 ) { return []; }

        // Kullanıcı kimliği (optimize edilmiş yol varsa kullan)
        $identity = class_exists('KNSDD_Performance_Optimizer')
            ? KNSDD_Performance_Optimizer::get_user_identity()
            : [ 'user_id' => get_current_user_id(), 'email' => '' ];
        $uid = (int) $identity['user_id'];
        $email = (string) $identity['email'];

        $cache_version = get_option( 'knsdd_cache_version', 1 );
        $email_hash = $email ? md5( strtolower( $email ) ) : 'noeml';
        $ckey = 'knsdd_tt_' . $product_id . '_' . $uid . '_' . $email_hash . '_' . $cache_version;
        $cached = get_transient( $ckey );
        if ( false !== $cached ) { return is_array($cached) ? $cached : []; }

        $product = wc_get_product( $product_id );
        if ( ! $product ) {
            set_transient( $ckey, [], HOUR_IN_SECONDS );
            return [];
        }

        $product_cats = wc_get_product_term_ids( $product_id, 'product_cat' );
        if ( empty( $product_cats ) ) {
            // Varyasyon ürünlerde kategoriler ebeveyn üründe olabilir
            $parent_id = (int) wp_get_post_parent_id( $product_id );
            if ( $parent_id > 0 ) {
                $parent_cats = wc_get_product_term_ids( $parent_id, 'product_cat' );
                if ( is_array( $parent_cats ) ) {
                    $product_cats = $parent_cats;
                }
            }
        }

        // Gruplar ve tarihler (optimize edilmiş yol varsa)
        $groups_data = class_exists('KNSDD_Performance_Optimizer')
            ? KNSDD_Performance_Optimizer::get_groups_and_dates()
            : [ 'groups' => KNSDD_Data::get_groups(), 'dates' => KNSDD_Data::get_all_group_dates() ];
        $all_groups = (array) $groups_data['groups'];
        $all_group_dates = (array) $groups_data['dates'];

        // 1) Aday kurallar: sadece standard (miktar) kurallar
        $candidates = [];
        foreach ( $all_groups as $group ) {
            if ( KNSDD_Data::is_group_paused( $group ) ) { continue; }
            $dates = $all_group_dates[ $group ] ?? null;
            $status_info = $dates ? KNSDD_Utils::get_group_status_info( $dates ) : [ 'status' => 'closed' ];
            if ( $status_info['status'] !== 'open' ) { continue; }

            $rules = KNSDD_Data::get_rules_for_group( $group );
            foreach ( (array) $rules as $rule ) {
                if ( empty( $rule['rule_id'] ) ) { continue; }
                // Özel kampanyaları atla
                if ( isset($rule['rule_type']) && $rule['rule_type'] === 'special_campaign' ) { continue; }

                // Ürün veya kategori kapsamı (hiyerarşik destek)
                $applies = false;
                $rule_cats = isset($rule['category']) ? (array) $rule['category'] : [];
                if ( ! empty( $rule['product'] ) && is_array( $rule['product'] ) ) {
                    if ( in_array( $product_id, $rule['product'], true ) ) { $applies = true; }
                } elseif ( ! empty( $rule_cats ) && ! empty( $product_cats ) ) {
                    // Ürün kategorilerini genişlet (alt → üst)
                    $expanded_product_cats = array_map( 'intval', $product_cats );
                    foreach ( $product_cats as $cat_id ) {
                        $ancestors = get_ancestors( (int) $cat_id, 'product_cat', 'taxonomy' );
                        if ( ! empty( $ancestors ) ) {
                            $expanded_product_cats = array_merge( $expanded_product_cats, array_map( 'intval', $ancestors ) );
                        }
                    }
                    $expanded_product_cats = array_unique( $expanded_product_cats );
                    if ( array_intersect( $expanded_product_cats, $rule_cats ) ) { $applies = true; }
                }
                if ( ! $applies ) { continue; }

                // min/max normalize
                $mn = isset($rule['min']) ? max(0, (int)$rule['min']) : 0;
                $mx = isset($rule['max']) ? max(0, (int)$rule['max']) : 0; // 0 => sonsuz

                // İndirim türü/değeri
                $dtype = (isset($rule['discount_type']) && $rule['discount_type'] === 'fixed') ? 'fixed' : 'percentage';
                $dval  = isset($rule['discount_value']) ? (float) $rule['discount_value'] : 0.0;
                if ( $dval <= 0 ) { continue; }

                $rule['__group'] = (string) $group;
                $rule['__mn'] = $mn; $rule['__mx'] = $mx; $rule['__dtype'] = $dtype; $rule['__dval'] = $dval;
                $candidates[] = $rule;
            }
        }

        if ( empty( $candidates ) ) {
            set_transient( $ckey, [], HOUR_IN_SECONDS );
            return [];
        }

        // 2) Kullanım verilerini toplu çek + koşullar (login, allowed_customers, limitler, ilk sipariş)
        $candidate_ids = wp_list_pluck( $candidates, 'rule_id' );
        $usage_rule_ids = [];
        foreach ( $candidate_ids as $rid ) {
            $group_ids = class_exists('KNSDD_Data') && method_exists( 'KNSDD_Data', 'get_tier_group_rule_ids' )
                ? KNSDD_Data::get_tier_group_rule_ids( $rid )
                : array( $rid );
            foreach ( (array) $group_ids as $gid ) {
                $usage_rule_ids[ (string) $gid ] = true;
            }
        }
        $usage_rule_ids = array_keys( $usage_rule_ids );

        $all_usage = KNSDD_Data::get_usage_for_multiple_rules( $usage_rule_ids );
        $email_usage = [];
        if ( ! empty( $email ) ) {
            $email_usage = KNSDD_Data::get_usage_for_multiple_rules_by_email( $usage_rule_ids, $email );
        }

        $applicable = [];
        foreach ( $candidates as $r ) {
            if ( KNSDD_Discount_Engine::is_rule_conditions_met( $r, $uid, $all_usage, $email, $email_usage ) ) {
                $applicable[] = $r;
            }
        }
        if ( empty( $applicable ) ) {
            set_transient( $ckey, [], HOUR_IN_SECONDS );
            return [];
        }

        // 3) Kapsam önceliği: Aynı aralıkta ürün kuralı kategori kuralına tercih edilir.
        // Ayrıca tamamen aynı min/max için daha yüksek indirim değerini tercih et.
        // Not: Çoğu çakışma zaten validator'larca engellenir.
        $by_key = [];
        foreach ( $applicable as $r ) {
            $key = $r['__mn'] . '|' . $r['__mx'];
            if ( ! isset( $by_key[$key] ) ) {
                $by_key[$key] = $r;
                continue;
            }
            $cur = $by_key[$key];
            $cur_is_product = ! empty($cur['product']);
            $new_is_product = ! empty($r['product']);
            if ( $new_is_product && ! $cur_is_product ) { $by_key[$key] = $r; continue; }
            if ( $new_is_product === $cur_is_product ) {
                // Aynı kapsam düzeyi: Yüksek indirim değerini tercih (yüzde vs tutar kıyaslaması ürün fiyatına bağlı olduğundan yapılmaz)
                if ( $r['__dtype'] === $cur['__dtype'] && $r['__dval'] > $cur['__dval'] ) {
                    $by_key[$key] = $r;
                }
            }
        }

        $tiers = [];
        foreach ( $by_key as $key => $r ) {
            $tiers[] = [
                'min'   => $r['__mn'],
                'max'   => $r['__mx'],
                'type'  => ($r['__dtype'] === 'percentage') ? 'percent' : 'fixed',
                'value' => (float) $r['__dval'],
            ];
        }

        // 4) Sıralama: 'max' artan (0 sonsuz -> INF)
        usort( $tiers, function( $a, $b ) {
            $ax = ($a['max'] === 0) ? PHP_INT_MAX : (int) $a['max'];
            $bx = ($b['max'] === 0) ? PHP_INT_MAX : (int) $b['max'];
            if ( $ax === $bx ) {
                return ((int)$a['min'] < (int)$b['min']) ? -1 : 1;
            }
            return ($ax < $bx) ? -1 : 1;
        });

        // 5) Tek tier varsa ve sınırsız ise (min<=1, max=0) bu bir kademe indirimi DEĞİL,
        // basit bir % veya sabit indirim. Tablo gösterilmemeli.
        if ( count( $tiers ) === 1 ) {
            $single = $tiers[0];
            // min=0 veya min=1 ve max=0 (sınırsız) ise kademe tablosu gösterme
            if ( (int) $single['min'] <= 1 && (int) $single['max'] === 0 ) {
                set_transient( $ckey, [], HOUR_IN_SECONDS );
                return [];
            }
        }

        set_transient( $ckey, $tiers, HOUR_IN_SECONDS );
        return $tiers;
    }
}
