<?php

namespace DetailTask;

use EmisKemenagClient;
use Jenjang;
use LogHelper;
use MadrasahProvince;

/**
 * @property EmisKemenagClient $client
 */
class EmisKemenagTask extends AbstractTask {
    #region Attributes
    /**
     * @var MadrasahProvince[]
     */
    private $provinces;

    /**
     * @var integer
     */
    private $totalPage;

    /**
     * @var integer
     */
    private $totalMadrasah;

    /**
     * @var array of string jenjang name
     */
    private $arrayOfJenjang;
    #endregion

    #region Main
    public function init()
    {
        $this->client = new EmisKemenagClient($this->config['emis_kemenag_prop']);
        $this->client->setLogger($this->logger);
        $this->arrayOfJenjang = [];
        $this->totalMadrasah = 0;
    }

    /**
     * @return void
     * Logging disimpan ke file log. Tracker last update per halaman disimpan di madrasah_province
     */
    public function processMadrasah() {
        $startTime = microtime(true);
        $this->init();
        try {
            $this->setProvinces();
            //Login to EMIS
            $this->client->partnerLogin();
            foreach ($this->provinces as $province) {
                $this->totalPage = 1;
                $page = $province->last_update_page ? (int) $province->last_update_page : 1;
                //refresh token each time the province code changed
                try {
                    $this->client->refreshToken();
                    $response = $this->client->institutionInfoByProvinceCode($province->province_code, $page);
                    $this->setTotalPage($response);
                    $this->setArrayOfJenjangAndSaveMadrasah($response);
                    $page++;
                }
                catch (\Exception $e) {
                    print_r($e->getMessage());
                    //NOTE: Skip, tidak perlu update madrasah_province, karena gagal update dari awal
                }

                while ($page <= $this->totalPage) {
                    try {
                        //refresh token each 50 pages
                        if ($page % 50 == 0)
                            $this->client->refreshToken();

                        $response = $this->client->institutionInfoByProvinceCode($province->province_code, $page);
                        $this->setArrayOfJenjangAndSaveMadrasah($response);
                        $page++;
                    }
                    catch (\Exception $e) {
                        print_r($e->getMessage());
                        //NOTE: keluar loop while, lalu simpan last page & update ke madrasah_province
                        break;
                    }
                }

                $province->last_update_page = ($page >= $this->totalPage ? 'LAST' : $page);
                $province->last_update_at = date('Y-m-d H:i:s');
                $province->save();
            }

            $this->updateJenjangMadrasah();
            LogHelper::logInfo("Process Emis Kemenag ended", $startTime, microtime(true), [$this->totalMadrasah . " madrasah successfully updated"], self::LOG_TYPE, $this->logger);
        }
        catch (\Exception $exception) {
            LogHelper::logInfo("Process Emis Kemenag ended with exception", $startTime, microtime(true), [$exception->getMessage(), $this->totalMadrasah . " madrasah successfully updated"], self::LOG_TYPE, $this->logger);
            print_r($exception->getMessage());
        }
    }
    #endregion

    #region Helper
    private function setProvinces() {
        $this->provinces = MadrasahProvince::find([
            'conditions' => 'last_update_at IS NULL OR last_update_at <= ?0 OR last_update_page <> ?1 OR last_update_page IS NULL',
            'bind' => [
                date('Y-m-d', strtotime('-30 day')),
                'LAST'
            ]
        ]);
    }

    private function setTotalPage($response) {
        if (array_key_exists('success', $response)) {
            if ($response['success'] || $response['success'] == "true") {
                if (array_key_exists('metadata', $response)) {
                    if (array_key_exists('pagination', $response['metadata'])) {
                        if (array_key_exists('last_page', $response['metadata']['pagination'])) {
                            $this->totalPage = $response['metadata']['pagination']['last_page'];
                        }
                    }
                }
            }
        }
    }

    private function setArrayOfJenjangAndSaveMadrasah($response) {
        if (array_key_exists('success', $response)) {
            if ($response['success'] || $response['success'] == "true") {
                if (array_key_exists('results', $response)) {
                    $data = $response['results'];
                    foreach ($data as $item) {
                        $this->arrayOfJenjang = $this->client->saveDataMadrasah($item, $this->arrayOfJenjang);
                        $this->totalMadrasah++;
                    }
                }
            }
        }
    }

    private function updateJenjangMadrasah() {
        foreach ($this->arrayOfJenjang as $jenjang) {
            $jenjangData = Jenjang::findFirst([
                'conditions' => 'nama_jenjang ILIKE ?0',
                'bind' => [
                    $jenjang
                ]
            ]);
            if(!$jenjangData)
                $jenjangData = new Jenjang();
            $jenjangData->nama_jenjang = $jenjang;
            $jenjangData->src = 'madrasah';
            $jenjangData->is_shown = 0;
            $jenjangData->save();
        }

        $qUpdateJenjangId = "UPDATE jaga.madrasah SET jenjang_id=subquery.id FROM (SELECT id, nama_jenjang FROM jaga.jenjang WHERE src ILIKE :src) subquery WHERE subquery.nama_jenjang = jaga.madrasah.category";
        $this->rawQuery($qUpdateJenjangId, [
            'src' => 'madrasah'
        ]);
    }
    #endregion
}
