<?php
/**
 * Created by PhpStorm.
 * User: z-yang
 * Date: 2019/7/27
 * Time: 18:01
 */

namespace App\Modules\User\Services;

use App\Modules\User\Models\UserMonthOrder;
use App\Modules\User\Models\UserMonthOrderCallbackv2;
use App\Modules\User\Models\UserMonthOrderRecord;
use App\Modules\User\Models\UserMonthSign;
use App\Modules\User\Models\UserMonthSignOrigin;
use GuzzleHttp\Client;
use EasyWeChat\Support\XML;

class UserMonthService
{
    const MONTH_PAY_KEY = 'Manyuedu869815753951852456456852';
    const MONTH_PAY_APPID = 'wx34804c803efab065';
    const MONTH_PAY_MCH_ID = '1278120701';

    public static function createSign(int $uid, int $plan_id, string $change_type,string $openid,string $type)
    {
        $model = new UserMonthSign();
        $info = $model->where('uid', $uid)->where('plan_id', $plan_id)->first();
        if ($info) {
            $info->change_type = $change_type;
            $info->save();
        } else {
            $model->uid = $uid;
            $model->plan_id = $plan_id;
            $model->change_type = $change_type;
            $model->openid = $openid;
            $model->type = $type;
            $model->save();
        }
        return;
    }

    public static function isSignMonth($openid){
        $model = new UserMonthSign();
        return $model->where('openid',$openid)->where('change_type','ADD')->select('id')->first();
    }

    public static function getLastOrder(int $uid){
        $model = new UserMonthOrder();
        return $model->where('uid',$uid)->orderBy('id','desc')->first();
    }

    public static function createLOrder(int $uid, int $plan_id, int $total_fee, string $trade_no,string $out_trade_no,string $type)
    {
        $model = new UserMonthOrder();
        $model->uid = $uid;
        $model->plan_id = $plan_id;
        $model->total_fee = $total_fee;
        $model->trade_no = $trade_no;
        $model->out_trade_no = $out_trade_no;
        $model->type = $type;
        $model->save();
        return;
    }

    public static function getOrderByOrder($trade_no,$out_trade_no){
        $model = new UserMonthOrder();
        $info = $model->where('trade_no',$trade_no)->first();
        return $info;
    }

    public static function getOrderAndSignStatusByUid($uid){
        $result = UserMonthOrder::join('user_month_sign','user_month_sign.uid','=','user_month_order.uid')
            ->select('user_month_order.type','user_month_sign.change_type')
            ->where('user_month_order.uid',$uid)
            ->where('user_month_sign.change_type','DELETE')
            ->get();
        if($result->isEmpty()) return [];
        $return_result = [];
        foreach ($result as $item){
            $return_result[] = $item->type;
        }
        return $return_result;
    }



    public static function checkOrderStatus(int $user_id,int $plan_id,string $app_id,string $key,string $app_secret){
        $pay_year = date('Y');
        $pay_month = date('m');
        $sign = strtoupper(_sign(compact('app_id','app_secret','user_id','plan_id','pay_year','pay_month'),$key.$key));
        $client = new Client();
        $url = 'http://pap.manyuedu.org/checkpay.php?';
        $url .= http_build_query(compact('user_id','app_secret','app_id','plan_id','pay_year','pay_month','sign'));
        $result = $client->request('post',$url)->getBody()->getContents();
        return json_decode($result,true);
    }


    public static function isMonthOrderUser($uid){
        $info = UserMonthOrder::where('uid',$uid)
            ->where('type','MONTH')
            ->orderBy('id','desc')
            ->select('created_at')
            ->first();
        if($info && strtotime($info->created_at)+365*86400 >time() ){
            return true;
        }
        return false;
    }


    public static function monthOrderLink($uid,$plan_id){
        $key = self::MONTH_PAY_KEY;
        $appid = self::MONTH_PAY_APPID;
        $mch_id = self::MONTH_PAY_MCH_ID;
        $contract_code = $uid;
        $request_serial = getMillisecond();
        $contract_display_account = $uid;
        $notify_url = env('MONTH_PAY_SIGN_NOTIFY_URLV2');
        $version = '1.0';
        $timestamp = time();
        $return_web = 1;
        $request_param = compact('appid','mch_id','plan_id','contract_code','request_serial','contract_display_account','notify_url','version','timestamp','return_web');
        $sign = _sign($request_param,$key);
        $request_param['sign'] = $sign;
        $url = 'https://api.mch.weixin.qq.com/papay/entrustweb/?'.http_build_query($request_param);
        return $url;
    }

    public static function monthPayApplypap($uid,$contract_id,$total_fee,$body,$ip,$order_way,$attach=''){
        $url = 'https://api.mch.weixin.qq.com/pay/pappayapply';
        $data = [
            'appid'=>self::MONTH_PAY_APPID,
            'mch_id'=>self::MONTH_PAY_MCH_ID,
            'nonce_str'=>str_random(32),
            'body'=>$body,
            'attach'=>$attach,
            'out_trade_no'=>date("YmdHis") . str_shuffle(hexdec(uniqid())),
            'total_fee'=>$total_fee,
            'spbill_create_ip'=>$ip,
            'notify_url'=>env('MONTH_PAY_CALLBACK_URLV2'),
            'trade_type'=>'PAP',
            'contract_id'=>$contract_id
        ];
        $sign = _sign($data,self::MONTH_PAY_KEY);
        $data['sign'] = $sign;
        $client = new Client();
        $result = $client->request('post',$url,[
            'body'=>XML::build($data)
        ])->getBody()->getContents();

        $result = XML::parse($result);
        UserMonthOrderRecord::create([
            'uid'=>$uid,
            'nonce_str'=>$data['nonce_str'],
            'body'=>$data['body'],
            'attach'=>$data['attach'],
            'out_trade_no'=>$data['out_trade_no'],
            'total_fee'=>$data['total_fee'],
            'spbill_create_ip'=>$data['spbill_create_ip'],
            'contract_id'=>$data['contract_id'],
            'order_way'=>$order_way,
            'result_code'=>isset($result['result_code'])?$result['result_code']:'',
            'result_text'=>\GuzzleHttp\json_encode($result)
        ]);
        return ;
    }

    public static function monthCallBackRecordV2(array $data)
    {
        try{
            UserMonthOrderCallbackv2::create($data);
        }catch (\Exception $e){
            \Log::error($e);
        }
    }

    public static function monthOrderSignRecord(array $data){
        try{
            UserMonthSignOrigin::create($data);
        }catch (\Exception $e){
            \Log::error($e);
        }
    }

    public static function getLastMonthOrderInfo($uid,$type){
        return UserMonthOrder::where('uid',$uid)
            ->where('type',$type)
            ->orderBy('id','desc')
            ->select('id','plan_id','created_at')
            ->first();
    }
}