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

class cron extends MX_Controller
{

    public function __construct()
    {
        parent::__construct();
        $this->load->model(get_class($this) . '_model', 'main_model');
        $this->cron_token();
        $this->provider = new Smm_api();
    }

    public function index()
    {
        redirect(cn());
    }

    public function status()
    {
        $lock = fopen('_lock_file_status.lock', 'w');
        if (!($lock && flock($lock, LOCK_EX | LOCK_NB)))
            die('Order already running');
        $params = [
            'limit' => 15,
            'start' => 0,
        ];
        $items = $this->main_model->list_items($params, ['task' => 'list-items-status']);
        if (!$items) {
            echo "There is no order at the present.<br>";
            exit();
        }
        foreach ($items as $key => $item) {
            $api = $this->main_model->get_item(['id' => $item['api_provider_id']], ['task' => 'get-item-provider']);
            if (!$api) {
                $response = ['error' => "API Provider does not exists"];
                $this->main_model->save_item(['item' => $item, 'response' => $response], ['task' => 'item-status']);
                continue;
            }
            $response = $this->provider->status($api, $item['api_order_id']);
            $this->main_model->save_item(['item' => $item, 'response' => $response], ['task' => 'item-status']);
        }
        echo "Successfully";
    }

    public function dripfeed()
    {
        $lock = fopen('_lock_file_dripfeed.lock', 'w');
        if (!($lock && flock($lock, LOCK_EX | LOCK_NB)))
            die('Dripfeed already running');
        $params = [
            'limit' => 15,
            'start' => 0,
        ];
        $items = $this->main_model->list_items($params, ['task' => 'list-items-dripfeed-new-order']);
        if (!$items) {
            echo "There is no order at the present.<br>";
            exit();
        }
        foreach ($items as $key => $item) {
            $this->main_model->save_item_by_dripfeed(['item' => $item]);
        }
        echo "Successfully";
    }

    public function dripfeed_old()
    {
        $lock = fopen('_lock_file_dripfeed.lock', 'w');
        if (!($lock && flock($lock, LOCK_EX | LOCK_NB)))
            die('Dripfeed already running');
        $params = [
            'limit' => 15,
            'start' => 0,
        ];
        $items = $this->main_model->list_items($params, ['task' => 'list-items-dripfeed-status']);
        if (!$items) {
            echo "There is no order at the present.<br>";
            exit();
        }
        foreach ($items as $key => $item) {
            $api = $this->main_model->get_item(['id' => $item['api_provider_id']], ['task' => 'get-item-provider']);
            if (!$api) {
                $response = ['error' => "API Provider does not exists"];
                $this->main_model->save_item(['order_id' => $item['id'], 'response' => $response], ['task' => 'item-dripfeed-status']);
                continue;
            }
            $response = $this->provider->status($api, $item['api_order_id']);
            $this->main_model->save_item(['item' => $item, 'item_api' => $api, 'response' => $response], ['task' => 'item-dripfeed-status']);
        }
        echo "Successfully";
    }

    public function subscriptions()
    {
        $lock = fopen('_lock_file_subscriptions.lock', 'w');
        if (!($lock && flock($lock, LOCK_EX | LOCK_NB)))
            die('Subscriptions already running');
        $params = [
            'limit' => 15,
            'start' => 0,
        ];
        $items = $this->main_model->list_items($params, ['task' => 'list-items-subscriptions-status']);
        if (!$items) {
            echo "There is no order at the present.<br>";
            exit();
        }
        foreach ($items as $key => $item) {
            $api = $this->main_model->get_item(['id' => $item['api_provider_id']], ['task' => 'get-item-provider']);
            if (!$api) {
                $response = ['error' => "API Provider does not exists"];
                $this->main_model->save_item(['order_id' => $item['id'], 'response' => $response], ['task' => 'item-subscriptions-status']);
                continue;
            }
            $response = $this->provider->status($api, $item['api_order_id']);
            $this->main_model->save_item(['item' => $item, 'item_api' => $api, 'response' => $response], ['task' => 'item-subscriptions-status']);
        }
        echo "Successfully";
    }

    public function multiple_status()
    {
        $lock = fopen('_lock_file_multiple_status.lock', 'w');
        if (!($lock && flock($lock, LOCK_EX | LOCK_NB)))
            die('Orders already running');
        $params = [
            'limit' => 100,
            'start' => 0,
        ];
        $items = $this->main_model->list_items($params, ['task' => 'list-items-multiple-status']);
        if (!$items) {
            echo "There is no order at the present.<br>";
            exit();
        }

        $items_group_by_api = group_by_criteria($items, 'api_provider_id');
        foreach ($items_group_by_api as $api_id => $items_group) {
            $api = $this->main_model->get_item(['id' => $api_id], ['task' => 'get-item-provider']);
            if (!$api) {
                $response = ['error' => "API Provider does not exists"];
                $params = [
                    'order_ids' => array_column($items_group, 'id'),
                    'response' => $response,
                ];
                $this->main_model->save_item($params, ['task' => 'item-multiple_status']);
                continue;
            } else {

                $response = $this->provider->multiStatus($api, array_column($items_group, 'api_order_id'));
                if ($response) {
                    $exist_items = [];
                    foreach ($items_group as $key => $item) {
                        if (isset($response[$item['api_order_id']]) && !in_array($item['api_order_id'], $exist_items)) {
                            $this->main_model->save_item(['item' => $item, 'response' => $response[$item['api_order_id']]], ['task' => 'item-status']);
                            $exist_items[] = $item['api_order_id'];
                        }
                    }
                } else {
                    $response = [
                        'connect' => false,
                        'message' => "API Request Error: Unable to connect to the external service!"
                    ];
                    $params = [
                        'order_ids' => array_column($items_group, 'id'),
                        'response' => $response,
                    ];
                    $this->main_model->save_item($params, ['task' => 'item-multiple_status']);
                    continue;
                }
            }
        }
        echo "Successfully";
    }

    //Send
    public function order()
    {
        $lock = fopen('_lock_file_multiple_order.lock', 'w');
        if (!($lock && flock($lock, LOCK_EX | LOCK_NB)))
            die('Order already running');
        $items = $this->main_model->list_items('', ['task' => 'list-items-new-order']);
        if (!$items) {
            echo "There is no order at the present.<br>";
            exit();
        }
        foreach ($items as $key => $row) {

            $this->db->trans_start();

            $api = $this->main_model->get_item(['id' => $row->api_provider_id], ['task' => 'get-item-provider']);
            if (!$api) {
                $response = ['error' => "API Provider does not exists"];
                $this->main_model->save_item(['order_id' => $row->id, 'response' => $response], ['task' => 'item-new-update']);
                continue;
            }
            $data_post = [
                'action' => 'add',
                'service' => $row->api_service_id,
            ];
            switch ($row->service_type) {
                case 'subscriptions':
                    $data_post["username"] = $row->username;
                    $data_post["min"] = $row->sub_min;
                    $data_post["max"] = $row->sub_max;
                    $data_post["posts"] = ($row->sub_posts == -1) ? 0 : $row->sub_posts;
                    $data_post["delay"] = $row->sub_delay;
                    $data_post["expiry"] = (!empty($row->sub_expiry)) ? date("d/m/Y", strtotime($row->sub_expiry)) : ""; //change date format dd/mm/YYYY
                    break;

                case 'custom_comments':
                    $data_post["link"] = $row->link;
                    $data_post["comments"] = json_decode($row->comments);
                    break;

                case 'mentions_with_hashtags':
                    $data_post["link"] = $row->link;
                    $data_post["quantity"] = $row->quantity;
                    $data_post["usernames"] = $row->usernames;
                    $data_post["hashtags"] = $row->hashtags;
                    break;

                case 'mentions_custom_list':
                    $data_post["link"] = $row->link;
                    $data_post["usernames"] = json_decode($row->usernames);
                    break;

                case 'mentions_hashtag':
                    $data_post["link"] = $row->link;
                    $data_post["quantity"] = $row->quantity;
                    $data_post["hashtag"] = $row->hashtag;
                    break;

                case 'mentions_user_followers':
                    $data_post["link"] = $row->link;
                    $data_post["quantity"] = $row->quantity;
                    $data_post["username"] = $row->username;
                    break;

                case 'mentions_media_likers':
                    $data_post["link"] = $row->link;
                    $data_post["quantity"] = $row->quantity;
                    $data_post["media"] = $row->media;
                    break;

                case 'package':
                    $data_post["link"] = $row->link;
                    break;

                case 'custom_comments_package':
                    $data_post["link"] = $row->link;
                    $data_post["comments"] = json_decode($row->comments);
                    break;

                case 'comment_likes':
                    $data_post["link"] = $row->link;
                    $data_post["quantity"] = $row->quantity;
                    $data_post["username"] = $row->username;
                    break;

                default:
                    $data_post["link"] = $row->link;
                    if (isset($row->is_drip_feed) && $row->is_drip_feed == 1) {
                        $data_post["runs"] = $row->runs;
                        $data_post["interval"] = $row->interval;
                        $data_post["quantity"] = $row->dripfeed_quantity;
                    } else {
                        if (isset($row->service_overflow) && $row->service_overflow > 0) {
                            $data_post["quantity"] = $row->quantity * (1 + $row->service_overflow / 100);
                        } else {
                            $data_post["quantity"] = $row->quantity;
                        }
                    }
                    break;
            }
            $response = $this->provider->order($api, $data_post);
            $this->main_model->save_item(['order_id' => $row->id, 'response' => $response], ['task' => 'item-new-update']);

            $this->db->trans_complete();
        }
        echo "Successfully";
    }

    protected function cron_token() 
    {
        $cron_key =  get_cron_key();
        if ($cron_key != get('key')) {
            exit('Invalid token');
        }
        return true;
    }

}
