<?php

namespace App\Http\Controllers\Web\Admin;

use App\Http\Controllers\Controller;
use App\Models\Deposit\FiatDeposit;
use App\Models\Market\Market;
use App\Models\Withdrawal\FiatWithdrawal;
use App\Models\Withdrawal\Withdrawal;
use App\Repositories\Currency\CurrencyRepository;
use App\Repositories\Deposit\DepositRepository;
use App\Repositories\Deposit\FiatDepositRepository;
use App\Repositories\Transaction\ReferralTransactionRepository;
use App\Repositories\Transaction\TransactionRepository;
use App\Repositories\Wallet\WalletRepository;
use App\Repositories\Withdrawal\FiatWithdrawalRepository;
use App\Repositories\Withdrawal\WithdrawalRepository;
use App\Services\Market\MarketService;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Http;
use Illuminate\Support\Facades\Redirect;
use Illuminate\Support\Str;
use Inertia\Inertia;
use Setting;

class LiquidityController extends Controller
{
    public $home_path = 'HOME=/var/www';

    public function index() {

        $prefix = 'LIQ-';
        $marketService = new MarketService();
        $enabled_markets = [];
        $markets = collect($marketService->getMarkets(true, true))->toArray();

        $marketWatcherEnabled = false;
        $queueWatcherEnabled = false;
        $ordersWatcherEnabled = false;
        $futuresWatcherEnabled = false;
        $optionsWatcherEnabled = false;
        $peerOrdersWatcherEnabled = false;

        $daemons = supervisor($this->home_path)->list();

        $debug = true;

        foreach ($daemons as $item) {

            if(Str::startsWith($item->name, $prefix) && $item->pm2Env->status == "online") {
                list($prefixStr, $marketName) = explode($prefix, $item->name);
                $enabled_markets[$marketName] = true;
            }

            if(Str::startsWith($item->name, 'market-watcher') && $item->pm2Env->status == "online") {
                $marketWatcherEnabled = true;
            }

            if(Str::startsWith($item->name, 'horizon') && $item->pm2Env->status == "online") {
                $queueWatcherEnabled = true;
            }

            if(Str::startsWith($item->name, 'order-processor') && $item->pm2Env->status == "online") {
                $ordersWatcherEnabled = true;
            }

            if(Str::startsWith($item->name, 'futures-processor') && $item->pm2Env->status == "online") {
                $futuresWatcherEnabled = true;
            }

            if(Str::startsWith($item->name, 'options-processor') && $item->pm2Env->status == "online") {
                $optionsWatcherEnabled = true;
            }

            if(Str::startsWith($item->name, 'peer-order-processor') && $item->pm2Env->status == "online") {
                $peerOrdersWatcherEnabled = true;
            }


        }

        foreach ($markets['data'] as $key=>$market) {
            $markets['data'][$key]['liq_enabled'] = isset($enabled_markets[market_sanitize($market['name'])]);
        }

        $services = [
            [
                'title' => 'Market Price Tracker Process',
                'name' => 'market-watcher',
                'command' => 'market-watcher:stats',
                'status' => $marketWatcherEnabled,
            ],
            [
                'title' => 'Queue System',
                'name' => 'horizon',
                'command' => 'horizon',
                'status' => $queueWatcherEnabled,
            ],
            [
                'title' => 'Spot Order Processor',
                'name' => 'order-processor',
                'command' => 'market:order-process',
                'status' => $ordersWatcherEnabled,
            ],
            [
                'title' => 'P2P Order Processor',
                'name' => 'peer-order-processor',
                'command' => 'peer-order:watcher',
                'status' => $peerOrdersWatcherEnabled,
            ]
        ];

        if(config('app.plan') == 5) {
            $services[] = [
                'title' => 'Futures Liquidation Tracker Process',
                'name' => 'futures-processor',
                'command' => 'market-watcher:liquidation',
                'status' => $futuresWatcherEnabled,
            ];

            $services[] = [
                'title' => 'Binary Option Trade Tracker Process',
                'name' => 'options-processor',
                'command' => 'options-watcher:process',
                'status' => $optionsWatcherEnabled,
            ];
        }

        if(config('app.readonly')) {
            $debug = false;
            $daemons = [];
        }

        return Inertia::render('Admin/Liquidity/Index', [
            'markets' => $markets,
            'services' => $services,
            'daemons' => $daemons,
            'debug' => $debug
        ]);
    }

    public function run(Request $request) {

        $service = $request->get('service');
        $command = $request->get('command');

        if($service) {

            if(supervisor($this->home_path)->findBy('name', $service)) {
                supervisor($this->home_path)->delete($service);
            }

            supervisor($this->home_path)->start(base_path('artisan'), [
                'name' => $service,
                'interpreter' => '/usr/bin/php',
                'cron-restart' => '0 */2 * * *',
                ' '.$command
            ]);

            return response()->json([
                'status' => "The process has been started",
            ]);
        }

        $market = $request->get('market');
        $marketModel = Market::whereName($market)->first();

        if(supervisor($this->home_path)->findBy('name', 'LIQ-' . market_sanitize($market))) {
            supervisor($this->home_path)->delete('LIQ-' . market_sanitize($market));
        }

        $rand = rand(1,6);

        $liq = false;

        if(!$marketModel->custom_liquidity) {

            supervisor($this->home_path)->start(base_path('artisan'), [
                'name' => 'LIQ-'.market_sanitize($market),
                'interpreter' => '/usr/bin/php',
                'cron-restart' => '0 */'.$rand.' * * *',
                ' market:run-liquidity '.$market
            ]);

            $response = Http::get('https://api.binance.com/api/v3/ticker/24hr', [
                'symbol' => market_sanitize($market)
            ]);

            if ($response->successful()) {

                $liq = true;

                $ticker = $response->json();

                if ($marketModel) {
                    $ratio = 0;
                    $marketModel->last = $ticker['prevClosePrice'] + ($ticker['prevClosePrice'] * $ratio);
                    $marketModel->liq = $liq;
                    $marketModel->update();
                }
            }

        } else {

            supervisor($this->home_path)->start(base_path('artisan'), [
                'name' => 'LIQ-'.market_sanitize($market),
                'interpreter' => '/usr/bin/php',
                'cron-restart' => '0 */'.$rand.' * * *',
                ' market:custom-token-liquidity '.$market
            ]);

            $liq = true;
        }

        (new MarketService())->updateMarketsInfoCache();

        return response()->json([
            'liq' => $liq,
            'status' => "Market Liquidity will be started soon if the market exists and active on Liquidity Provider's market",
            'markets' => [],
        ]);
    }

    public function stop(Request $request) {

        $service = $request->get('service');

        if($service) {

            supervisor($this->home_path)->delete($service);

            return response()->json([
                'status' => 'The process has been stopped'
            ]);
        }


        $market = $request->get('market');

        $marketModel = Market::whereName($market)->first();

        supervisor($this->home_path)->delete('LIQ-'. market_sanitize($market));

        $marketModel->liq = false;
        $marketModel->update();

        Cache::forget("markets_liquidity.$market.bids");
        Cache::forget("markets_liquidity.$market.bids_total");

        Cache::forget("markets_liquidity.$market.asks");
        Cache::forget("markets_liquidity.$market.asks_total");

        return response()->json([
            'status' => 'Market Liquidity was stopped',
            'liq' => false,
        ]);
    }
}
