<?php
defined('BASEPATH') OR exit('No direct script access allowed');

class Loyalty extends CI_Controller
{
    function __construct()
    {
        parent::__construct();
        $this->load->model('common');
        $this->load->helper(array('form', 'url'));
        $this->load->library('session');
    }

    /**
     * Main loyalty settings page
     */
    public function index()
    {
        // Get or create loyalty settings
        $settings = $this->getLoyaltySettings();
        $data['settings'] = $settings;
        
        // Get all rewards
        $rewards = $this->getRewards();
        $data['rewards'] = $rewards;
        
        // Get tier configuration
        $tiers = $this->getTiers();
        $data['tiers'] = $tiers;
        
        // Get double points days
        $doublePointsDays = $this->getDoublePointsDays();
        $data['doublePointsDays'] = $doublePointsDays;
        
        // Get VIP promotions
        $vipPromotions = $this->getVIPPromotions();
        $data['vipPromotions'] = $vipPromotions;
        
        $this->template->template_render('loyalty_settings', $data);
    }

    /**
     * Customer loyalty history page
     */
    public function history()
    {
        $data = array();
        
        // Get filter parameters
        $customerId = $this->input->get('customerId');
        $fromDate = $this->input->get('fromDate') ? strtotime($this->input->get('fromDate')) * 1000 : strtotime('-30 days') * 1000;
        $toDate = $this->input->get('toDate') ? strtotime($this->input->get('toDate')) * 1000 : time() * 1000;
        
        // Get all customers for dropdown
        $allCustomers = $this->common->readdatafromcollectionwhereclause('Users');
        // Filter to only customers
        $customers = array();
        foreach ($allCustomers as $id => $user) {
            if (isset($user['userRole']) && $user['userRole'] == 'user') {
                $customers[$id] = $user;
            }
        }
        $data['customers'] = $customers;
        
        // Get loyalty transactions
        $transactions = $this->getLoyaltyTransactions($customerId, $fromDate, $toDate);
        $data['transactions'] = $transactions;
        $data['selectedCustomerId'] = $customerId;
        $data['fromDate'] = date('Y-m-d', $fromDate / 1000);
        $data['toDate'] = date('Y-m-d', $toDate / 1000);
        
        // Calculate statistics
        $stats = array(
            'totalTransactions' => count($transactions),
            'totalPointsEarned' => 0,
            'totalPointsRedeemed' => 0,
            'totalPointsExpired' => 0
        );
        
        foreach ($transactions as $transaction) {
            if (isset($transaction['type'])) {
                if ($transaction['type'] == 'earned') {
                    $stats['totalPointsEarned'] += isset($transaction['points']) ? intval($transaction['points']) : 0;
                } elseif ($transaction['type'] == 'redeemed') {
                    $stats['totalPointsRedeemed'] += isset($transaction['points']) ? intval($transaction['points']) : 0;
                } elseif ($transaction['type'] == 'expired') {
                    $stats['totalPointsExpired'] += isset($transaction['points']) ? intval($transaction['points']) : 0;
                }
            }
        }
        
        $data['stats'] = $stats;
        
        $this->template->template_render('loyalty_history', $data);
    }

    /**
     * Update loyalty settings
     */
    public function updateSettings()
    {
        $post = $this->input->post();
        
        $settings = array(
            'pointEarningRate' => isset($post['pointEarningRate']) ? floatval($post['pointEarningRate']) : 1.0, // Points per dollar
            'pointsPerDollar' => isset($post['pointsPerDollar']) ? floatval($post['pointsPerDollar']) : 1.0,
            'birthdayBonusEnabled' => isset($post['birthdayBonusEnabled']) ? true : false,
            'birthdayBonusPoints' => isset($post['birthdayBonusPoints']) ? intval($post['birthdayBonusPoints']) : 100,
            'pointsExpiryEnabled' => isset($post['pointsExpiryEnabled']) ? true : false,
            'pointsExpiryDays' => isset($post['pointsExpiryDays']) ? intval($post['pointsExpiryDays']) : 365,
            'updatedAt' => time() * 1000,
            'updatedBy' => $this->session->userdata['session_data']['userId']
        );
        
        $response = $this->common->updatedatamodel('LoyaltySettings', 'main', $settings);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'Loyalty settings updated successfully' : 'Failed to update settings'
            ));
        } else {
            if ($response) {
                $this->session->set_flashdata('successmessage', 'Loyalty settings updated successfully');
            } else {
                $this->session->set_flashdata('warningmessage', 'Failed to update settings');
            }
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Update tier thresholds
     */
    public function updateTiers()
    {
        $post = $this->input->post();
        
        $tiers = array();
        
        // Process tier data
        if (isset($post['tiers']) && is_array($post['tiers'])) {
            foreach ($post['tiers'] as $tierKey => $tierData) {
                $tiers[$tierKey] = array(
                    'name' => isset($tierData['name']) ? $tierData['name'] : '',
                    'threshold' => isset($tierData['threshold']) ? intval($tierData['threshold']) : 0,
                    'benefits' => isset($tierData['benefits']) ? $tierData['benefits'] : '',
                    'enabled' => isset($tierData['enabled']) ? true : false
                );
            }
        }
        
        $settings = array(
            'tiers' => $tiers,
            'updatedAt' => time() * 1000,
            'updatedBy' => $this->session->userdata['session_data']['userId']
        );
        
        $response = $this->common->updatedatamodel('LoyaltySettings', 'main', $settings);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'Tier thresholds updated successfully' : 'Failed to update tiers'
            ));
        } else {
            if ($response) {
                $this->session->set_flashdata('successmessage', 'Tier thresholds updated successfully');
            } else {
                $this->session->set_flashdata('warningmessage', 'Failed to update tiers');
            }
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Add or update reward
     */
    public function saveReward()
    {
        $post = $this->input->post();
        
        $rewardId = isset($post['rewardId']) ? $post['rewardId'] : time();
        
        $reward = array(
            'name' => isset($post['name']) ? $post['name'] : '',
            'description' => isset($post['description']) ? $post['description'] : '',
            'pointsRequired' => isset($post['pointsRequired']) ? intval($post['pointsRequired']) : 0,
            'discountType' => isset($post['discountType']) ? $post['discountType'] : 'percentage', // percentage or fixed
            'discountValue' => isset($post['discountValue']) ? floatval($post['discountValue']) : 0,
            'enabled' => isset($post['enabled']) ? true : false,
            'updatedAt' => time() * 1000
        );
        
        $response = $this->common->updatedatamodel('Rewards', $rewardId, $reward);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'Reward saved successfully' : 'Failed to save reward',
                'rewardId' => $rewardId
            ));
        } else {
            if ($response) {
                $this->session->set_flashdata('successmessage', 'Reward saved successfully');
            } else {
                $this->session->set_flashdata('warningmessage', 'Failed to save reward');
            }
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Delete reward
     */
    public function deleteReward($rewardId)
    {
        $response = $this->common->deletedatamodel('Rewards', $rewardId);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'Reward deleted successfully' : 'Failed to delete reward'
            ));
        } else {
            if ($response) {
                $this->session->set_flashdata('successmessage', 'Reward deleted successfully');
            } else {
                $this->session->set_flashdata('warningmessage', 'Failed to delete reward');
            }
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Add double points day
     */
    public function addDoublePointsDay()
    {
        $post = $this->input->post();
        
        $dayId = isset($post['dayId']) ? $post['dayId'] : time();
        
        $day = array(
            'date' => isset($post['date']) ? strtotime($post['date']) * 1000 : time() * 1000,
            'multiplier' => isset($post['multiplier']) ? floatval($post['multiplier']) : 2.0,
            'description' => isset($post['description']) ? $post['description'] : '',
            'enabled' => isset($post['enabled']) ? true : false,
            'createdAt' => time() * 1000
        );
        
        $response = $this->common->updatedatamodel('DoublePointsDays', $dayId, $day);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'Double points day added successfully' : 'Failed to add double points day',
                'dayId' => $dayId
            ));
        } else {
            if ($response) {
                $this->session->set_flashdata('successmessage', 'Double points day added successfully');
            } else {
                $this->session->set_flashdata('warningmessage', 'Failed to add double points day');
            }
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Delete double points day
     */
    public function deleteDoublePointsDay($dayId)
    {
        $response = $this->common->deletedatamodel('DoublePointsDays', $dayId);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'Double points day deleted successfully' : 'Failed to delete'
            ));
        } else {
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Add VIP promotion
     */
    public function addVIPPromotion()
    {
        $post = $this->input->post();
        
        $promoId = isset($post['promoId']) ? $post['promoId'] : time();
        
        $promotion = array(
            'title' => isset($post['title']) ? $post['title'] : '',
            'description' => isset($post['description']) ? $post['description'] : '',
            'tierRequired' => isset($post['tierRequired']) ? $post['tierRequired'] : 'gold',
            'pointsMultiplier' => isset($post['pointsMultiplier']) ? floatval($post['pointsMultiplier']) : 1.5,
            'startDate' => isset($post['startDate']) ? strtotime($post['startDate']) * 1000 : time() * 1000,
            'endDate' => isset($post['endDate']) ? strtotime($post['endDate']) * 1000 : time() * 1000,
            'enabled' => isset($post['enabled']) ? true : false,
            'createdAt' => time() * 1000
        );
        
        $response = $this->common->updatedatamodel('VIPPromotions', $promoId, $promotion);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'VIP promotion added successfully' : 'Failed to add promotion',
                'promoId' => $promoId
            ));
        } else {
            if ($response) {
                $this->session->set_flashdata('successmessage', 'VIP promotion added successfully');
            } else {
                $this->session->set_flashdata('warningmessage', 'Failed to add promotion');
            }
            redirect(base_url('loyalty'));
        }
    }

    /**
     * Delete VIP promotion
     */
    public function deleteVIPPromotion($promoId)
    {
        $response = $this->common->deletedatamodel('VIPPromotions', $promoId);
        
        if ($this->input->is_ajax_request()) {
            echo json_encode(array(
                'success' => $response,
                'message' => $response ? 'VIP promotion deleted successfully' : 'Failed to delete'
            ));
        } else {
            redirect(base_url('loyalty'));
        }
    }

    // Helper methods
    
    private function getLoyaltySettings()
    {
        $settings = $this->common->readdatadocument('LoyaltySettings', 'main');
        
        if (empty($settings)) {
            // Default settings
            $defaultSettings = array(
                'pointEarningRate' => 1.0,
                'pointsPerDollar' => 1.0,
                'birthdayBonusEnabled' => true,
                'birthdayBonusPoints' => 100,
                'pointsExpiryEnabled' => false,
                'pointsExpiryDays' => 365,
                'tiers' => array(
                    'bronze' => array('name' => 'Bronze', 'threshold' => 0, 'benefits' => 'Standard rewards', 'enabled' => true),
                    'silver' => array('name' => 'Silver', 'threshold' => 500, 'benefits' => '5% bonus points', 'enabled' => true),
                    'gold' => array('name' => 'Gold', 'threshold' => 1000, 'benefits' => '10% bonus points', 'enabled' => true),
                    'platinum' => array('name' => 'Platinum', 'threshold' => 2500, 'benefits' => '15% bonus points', 'enabled' => true)
                ),
                'createdAt' => time() * 1000
            );
            
            $this->common->adddatamodel('LoyaltySettings', 'main', $defaultSettings);
            return $defaultSettings;
        }
        
        return $settings;
    }
    
    private function getRewards()
    {
        $rewards = $this->common->readdatafromcollectionwhereclause('Rewards');
        return $rewards ? $rewards : array();
    }
    
    private function getTiers()
    {
        $settings = $this->getLoyaltySettings();
        return isset($settings['tiers']) ? $settings['tiers'] : array();
    }
    
    private function getDoublePointsDays()
    {
        $days = $this->common->readdatafromcollectionwhereclause('DoublePointsDays');
        return $days ? $days : array();
    }
    
    private function getVIPPromotions()
    {
        $promos = $this->common->readdatafromcollectionwhereclause('VIPPromotions');
        return $promos ? $promos : array();
    }
    
    private function getLoyaltyTransactions($customerId = null, $fromDate = null, $toDate = null)
    {
        $transactions = $this->common->readdatafromcollectionwhereclause('LoyaltyTransactions');
        if (!$transactions) {
            $transactions = array();
        }
        
        $filtered = array();
        foreach ($transactions as $id => $transaction) {
            $transactionDate = isset($transaction['timestamp']) ? $transaction['timestamp'] : 0;
            
            // Filter by customer
            if ($customerId && (!isset($transaction['customerId']) || $transaction['customerId'] != $customerId)) {
                continue;
            }
            
            // Filter by date
            if ($fromDate && $transactionDate < $fromDate) {
                continue;
            }
            if ($toDate && $transactionDate > $toDate) {
                continue;
            }
            
            $filtered[$id] = $transaction;
        }
        
        // Sort by timestamp descending
        uasort($filtered, function($a, $b) {
            $timeA = isset($a['timestamp']) ? $a['timestamp'] : 0;
            $timeB = isset($b['timestamp']) ? $b['timestamp'] : 0;
            return $timeB - $timeA;
        });
        
        return $filtered;
    }
}
