<?php
/**
 * Created by PhpStorm.
 * User: leo
 * Date: 2018/5/17
 * Time: 下午2:44
 */

namespace common\helpers\http;

use common\models\Uploads;
use yii\base\BaseObject;
use yii\base\StaticInstanceTrait;
use yii\httpclient\Client;

class RemoteUploadApi extends BaseObject
{
    use StaticInstanceTrait;

    /**
     * 通讯密钥
     */
    public $authKey;

    /**
     * 上传地址
     * @var
     */
    public $uploadUrl;

    /**
     * action地址
     * @var
     */
    public $actionUrl;

    public $filePath;

    /**
     * 上传的用户ID
     * @var
     */
    public $id;

    const CATEGORY_EXPORT = 'export';
    const FORBIDDEN_NOTIFY_URL = 'forbidden';

    /**
     * 初始化
     * @throws \yii\base\Exception
     */
    public function init()
    {
        parent::init();
        $this->authKey = \Yii::$app->params['http']['remoteUploadApi']['authKey'];
        $this->uploadUrl = \Yii::$app->params['http']['remoteUploadApi']['host'].'/upload';
        $this->actionUrl = \Yii::$app->params['http']['remoteUploadApi']['host'].'/action';
        $this->filePath = \Yii::$app->params['http']['remoteUploadApi']['host'].'/files/';
        $this->id = \Yii::$app->security->generateRandomString(32);
    }

    /**
     * @param $uid
     * @param array $params
     * @return array
     */
    public function generateToken($uid, $params = []){
        if(!isset($params['date']) || !$params['date']){
            $params['date'] = date('YmdH');
        }
        if(!isset($params['authKey']) || !$params['authKey']){
            $params['authKey'] = \Yii::$app->params['http']['remoteUploadApi']['authKey'];
        }
        $hash = 'uid:'.$uid.'&secretkey:'.(string)$params['authKey'].'&datetime:'.(string)$params['date'];
        if(!isset($params['notifyUrl']) || !$params['notifyUrl']){
            $params['notifyUrl'] = \Yii::$app->params['http']['remoteUploadApi']['remoteUploadNotifyUrl'];
        }elseif($params['notifyUrl'] == self::FORBIDDEN_NOTIFY_URL){
            $params['notifyUrl'] = '';
        }
        $hash .= '&notifyurl:' . (string)$params['notifyUrl'];
        $md5 = md5($hash);
        return [
            'date' => $params['date'],
            'token' => $md5,
            'notifyUrl' => $params['notifyUrl'],
        ];
    }

    /**
     * 上传
     * @param $filePath
     * @return bool|mixed
     * @throws \yii\base\InvalidConfigException
     * @throws \yii\httpclient\Exception
     */
    public function upload($filePath){
        $token = $this->generateToken($this->id);
        // 上传
        $client = new Client();
        $response = $client->createRequest()
            ->setMethod('POST')
            ->addHeaders([
                'UPLOAD-SERVER-TOKEN' => $token['token'],
                'UPLOAD-SERVER-USER' => $this->id,
                'UPLOAD-SERVER-NOTIFY-URL'=>$token['notifyUrl'],
                'UPLOAD-SERVER-DATE'=>$token['date'],
            ])
            ->setUrl($this->uploadUrl)
            ->addFile('ATTACHMENT', $filePath)
            ->send();
        if($response->isOk && isset($response->data['url'])){
            return $response->data;
        } else {
            return false;
        }
    }

    /**
     * 删除
     * @param $filePath
     * @return bool
     * @throws \yii\base\InvalidConfigException
     */
    public function delete($filePath){
        // 处理$filePath
        if(strpos($filePath, $this->filePath) !== false){
            $filePath = str_replace($this->filePath, '', $filePath);
        }
        $token = $this->generateToken($this->id);
        $client = new Client();
        $response = $client->createRequest()
            ->setMethod('POST')
            ->addHeaders([
                'UPLOAD-SERVER-TOKEN' => $token['token'],
                'UPLOAD-SERVER-USER' => $this->id,
                'UPLOAD-SERVER-NOTIFY-URL'=>$token['notifyUrl'],
                'UPLOAD-SERVER-DATE'=>$token['date'],
            ])
            ->setUrl($this->actionUrl)
            ->setData([
                'action' => 'delete',
                'post_data' => $filePath,
            ])
            ->send();
        if($response->isOk && isset($response->data['success']) && $response->data['success'] == 1){
            return $response->data;
        } else {
            return false;
        }
    }

}