HEX
Server: LiteSpeed
System: Linux cpir1.prohostdns.com 4.18.0-553.123.2.lve.el8.x86_64 #1 SMP Thu May 7 23:17:13 UTC 2026 x86_64
User: pelakir (2976)
PHP: 8.2.31
Disabled: exec, shell_exec, system, passthru, proc_open, proc_close, proc_terminate, proc_get_status, popen, pclose, pcntl_exec
Upload Files
File: //home/pelakir/public_html/wp-content/plugins/wc-digipay-plugin/DPGateway.php
<?php

class DPGateway
{
    private $username;
    private $password;
    private $client_id;
    private $client_secret;
    private $access_token;
    private $refresh_token;
    private $type;
    private $request_retries   = true;
    private $verify_retries    = 0;
    private $liveApi           = true;
    private $tokenUpdaterHook  = null;

    public function __construct($settings, $tokenUpdaterHook = null)
    {
        $this->username             = htmlspecialchars_decode($settings['username']);
        $this->password             = htmlspecialchars_decode($settings['password']);
        $this->client_id            = htmlspecialchars_decode($settings['client_id']);
        $this->client_secret        = htmlspecialchars_decode($settings['client_secret']);
        $this->access_token         = $settings['access_token'];
        $this->refresh_token        = $settings['refresh_token'];
        $this->type                 = "11";
        $this->tokenUpdaterHook     = $tokenUpdaterHook;

        if(empty($this->access_token)){
            $this->authenticate();
        }
    }

    private function request($endPoint, $data, $headers = [],$isJSON = false)
    {
        $_headers = [];

        foreach (array_merge([
            'Content-Type'      => $isJSON ? 'application/json' : 'application/x-www-form-urlencoded; charset=utf-8',
            'Agent'             => 'WEB',
            'Digipay-Version'   => '2022-02-02',
            'Plugin-Version'   => WC_DP_VERSION
        ],$headers) as $key => $val) {
            $_headers[] = $key.': '.$val;
        }


        $ch = curl_init(($this->liveApi ? 'https://api.mydigipay.com' : 'https://uat.mydigipay.info') . '/digipay/api/' . $endPoint );

        $requestBody = $isJSON ? json_encode($data) : http_build_query($data);
        curl_setopt($ch, CURLOPT_POST,              true);
        curl_setopt($ch, CURLOPT_POSTFIELDS,        $requestBody);
        curl_setopt($ch, CURLOPT_SSL_VERIFYHOST,    0);
        curl_setopt($ch, CURLOPT_SSL_VERIFYPEER,    0);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER,    true);
        curl_setopt($ch, CURLINFO_HEADER_OUT, true); // enable tracking
        curl_setopt($ch, CURLOPT_HTTPHEADER,        $_headers);


        $result = curl_exec($ch);

        wc_get_logger()->debug(
            "End Point: $endPoint",
            ['source' => 'digipay']
        );

        wc_get_logger()->debug(
            "Body: $requestBody",
            ['source' => 'digipay']
        );

        wc_get_logger()->debug(
            "Headers: ". curl_getinfo($ch, CURLINFO_HEADER_OUT),
            ['source' => 'digipay']
        );

        if(curl_errno($ch) === false){
            throw new Exception("[CURL_ERR] " . curl_error($ch));
        }

        wc_get_logger()->debug(
            "Result: ". $result,
            ['source' => 'digipay']
        );

        $responseCode = curl_getinfo($ch)['http_code'];
        if($responseCode != 200){
            if ('oauth/token' === $endPoint) {
                $authResponse = json_decode($result,true);
                if (isset($authResponse['result']['message'])) {
                    throw new Exception($authResponse['result']['message']);
                } else {
                    throw new Exception($authResponse['error']);
                }
            }elseif($responseCode == 401 && $isJSON && $this->request_retries){
                $this->access_token = $this->refresh_token = null;
                $this->authenticate();
                $this->request_retries = false;
                return $this->request($endPoint, $data, array_merge($headers, [
                    'Authorization' => 'Bearer ' . $this->access_token
                ]), $isJSON);

            }

            if($responseCode == 401){
                $result = 'خطا در احراز هویت درگاه دیجی‌پی';
            }


            if(WP_DEBUG){
                throw new Exception("[REQUEST_ERR][CODE:". $responseCode ."]" . $result. ((!empty($data['providerId'])) ? "[providerId:". $data['providerId'] ."]" : ''));
            }else{
                $resultData = @json_decode($result, true);


                if($resultData && !empty($resultData['result'])){
                    $result = $resultData['result']['message'];
                }
                throw new Exception($result);
            }

        }

        $this->request_retries = 0;

        return json_decode($result, true);

    }

    public function authenticate($refreshToken = true)
    {
        $data = ($refreshToken && !empty($this->refresh_token)) ?
            [
                'refresh_token' => $this->refresh_token,
                'grant_type'    => 'refresh_token'
            ]
            :
            [
                'username'      => $this->username,
                'password'      => $this->password,
                'grant_type'    => 'password'
            ];

        try {

            $data = $this->request('oauth/token', $data, [
                'Authorization' => 'Basic ' . base64_encode($this->client_id . ':' . $this->client_secret)
            ]);

            $this->access_token     = $data['access_token'];
            $this->refresh_token    = $data['refresh_token'];

        }catch (Exception $e){
            $this->access_token = $this->refresh_token  = null;
            wc_add_notice($e->getMessage(), 'error');
            return false;
        }

        if(!empty($this->tokenUpdaterHook)){

            $hook = $this->tokenUpdaterHook;
            $hook($this->access_token, $this->refresh_token);
        }

        return true;
    }

    public function createTicket($amount, $providerId, $redirectUrl, $items, $cellNumber = null, $returnURL = true)
    {
        $data = $this->request('tickets/business?type=' . $this->type, [
            'amount'        => $amount,
            'cellNumber'    => $cellNumber,
            'providerId'    => $providerId,
            'callbackUrl'   => $redirectUrl,
            'basketDetailsDto' => [
                'basketId' => $providerId,
                'items' => $items
            ]
        ], [
            'Authorization' => 'Bearer ' . $this->access_token
        ], true);

        if(!empty($data['result']) && $data['result']['status'] == 0){
            //successful payment
            return $returnURL ? $data['redirectUrl'] : [
                'url'       => $data['redirectUrl'],
                'ticket'    => $data['ticket']
            ];

        }else{

            $message = !empty($data['result']['message']) ? $data['result']['message'] : 'unknown error';
            throw new Exception($message);
        }
    }

    public function verifyTicket($trackingCode, $providerId, $type = 0)
    {
        if ($this->verify_retries > 3) {
            throw new Exception("DP_ERR : MAX_RETRIES_EXCEEDED");
        }

        $data = $this->request('purchases/verify?type=' . $type, [
            'trackingCode' => $trackingCode,
            'providerId'   => $providerId
        ], [
            'Authorization' => 'Bearer ' . $this->access_token
        ], true); // send JSON body

        $status = $data['result']['status'] ?? -1;

        if ($status == 0) {
            return true;
        }

        // Pending status → retry
        if ($status == 9011) {
            sleep(5);
            $this->verify_retries++;
            return $this->verifyTicket($trackingCode, $providerId, $type);
        }

        $message = !empty($data['result']['message']) ? $data['result']['message'] : 'unknown error';
        throw new Exception("DP_ERR : " . $message);
    }

    public function refund($amount, $providerId, $trackingCode, $type = 0, $reason = null)
    {
        $data = $this->request('refunds?type=' . $type, [
            'amount'                => $amount,
            'providerId'            => $providerId,
            'saleTrackingCode'      => $trackingCode,
            'description'           => $reason
        ], [
            'Authorization' => 'Bearer ' . $this->access_token
        ], true);
        if(!empty($data['result']) && $data['result']['status'] == 0){
            return $data['trackingCode'];
        }else{
            $message = !empty($data['result']['message']) ? $data['result']['message'] : 'unknown error';
            throw new Exception($message);
        }
    }


}