<?php

namespace Application\Service\Extension\Helper\components;

use Application\Service\Extension\Helper\base\BaseHelper;
use Application\Service\Extension\Helper\DocumentHelper;
use Application\Service\Extension\Laminas;

class AnalysisHelper extends BaseHelper
{
    private float $startTime = 0;

    private int $maxResponseTime = 0;

    /** @var string 请求次数 */
    public const REQUEST_TIMES = 'REQUEST_TIMES';

    /** @var string 响应速度 */
    public const RESPONSE_TIME = 'RESPONSE_TIME';

    protected function setCache($value, string $helperKey = self::HELPER_KEY_BASE)
    {
        // TODO: Implement setCache() method.
    }

    protected function getCacheKey()
    {
        // TODO: Implement getCacheKey() method.
    }

    public function init($params = [])
    {
        if (key_exists(self::RESPONSE_TIME, $params)) {
            $this->startTime = microtime(true);
            if (isset($params[self::RESPONSE_TIME]['max']) && $params[self::RESPONSE_TIME]['max']) {
                $this->maxResponseTime = intval($params[self::RESPONSE_TIME]['max']);
            }
        }

        if (key_exists(self::REQUEST_TIMES, $params)) {
            $key = self::getRequestTimesKey();
            if (Laminas::$serviceManager->redisExtend->getRedisInstance()->hSetNx($key, DocumentHelper::getTag('actionUrl'), 0)) {
                // 存一个星期
                Laminas::$serviceManager->redisExtend->getRedisInstance()->expire($key, 60 * 60 * 24 * 7);
            }

            Laminas::$serviceManager->redisExtend->getRedisInstance()->hIncrBy($key, DocumentHelper::getTag('actionUrl'), 1);
        }
    }

    public static function getRequestTimesKey($hour = null, $date = null): string
    {
        $date = $date !== null ? $date : date('m-d');
        $hour = intval($hour !== null ? $hour : date('H'));
        return "$date:ANALYSIS:" . self::REQUEST_TIMES . ":$hour";
    }

    public static function getResponseTimeKey($date = null): string
    {
        $date = $date !== null ? $date : date('m-d');
        return "$date:ANALYSIS:" . self::RESPONSE_TIME;
    }

    public function __destruct()
    {
        if ($this->startTime) {
            $responseTime = round(microtime(true) - $this->startTime, 2) * 1000;
            if ($responseTime > $this->maxResponseTime) {
                $key = self::getResponseTimeKey() . ':' . DocumentHelper::getTag('actionUrl');
                $index = Laminas::$serviceManager->redisExtend->getRedisInstance()->lPush($key, json_encode([
                    'time' => $responseTime . 'ms',
                    'post' => $_POST,
                    'identity' => Laminas::$serviceManager->identity->getIdentityData() ?? [],
                ]));

                if ($index == 1) {
                    Laminas::$serviceManager->redisExtend->getRedisInstance()->expire($key, 60 * 60 * 24 * 7);
                }
            }
        }
    }
}