<?php
/**
 * Created by PhpStorm.
 * User: Administrator
 * Date: 2019/5/16
 * Time: 18:39
 */
if (!function_exists('array_insert_replace')) {
    /**
     * 插入一个数组到到数组指定位置并对相同元素进行覆盖
     * @param $array  被插入的数组
     * @param $position 插入位置
     * @param $insert_array 插入并替换的数组
     */
    function array_insert_replace(array &$array, $position, array $insert_array)
    {
        $first_array = array_splice($array, 0, $position);
        #如果不需要替换把这一行注释掉
        $array = array_replace($array, $insert_array);
        $array = array_merge($first_array, $insert_array, $array);
        // var_dump($arrayMerge);die;

    }
}
/**
 *  统一支付（多合1统一支付插件化）- 非插件化的兼容函数
 * @param $wid @商户id
 * @param $openid @用户openid
 * @param $money @支付金额
 * @param $notifyFileName @回调文件名称
 * @param $OrderNo @订单号
 * @param $remark @备注
 * @param string $attach @回调 传回字符串
 * @param array $request
 * @return array
 */
function common_prepay($wid, $openid, $money, $notifyFileName, $OrderNo, $remark = '', $attach = '', $request = [])
{
    //通用支付逻辑
    //插件监听通用支付
    $pay_request = null;
    $remark = preg_replace("/[^a-zA-Z\p{Han}]/u","",$remark);
    $pay_type = get_pay_type($request['pay_type'], $wid);
    if ($pay_type == 'wechat') {
        $sykConfig = new Model('vshop_syk_pay');
        $sykConfig->find(array('wid' => $wid));
        if ($sykConfig && $sykConfig->status) $pay_type = 'syk';//开启商云客支付
    }
    $notify_url = stripos($notifyFileName,'addons')!==false ? Conf::$http_path_api . "{$notifyFileName}-{$pay_type}-{$wid}.html": Conf::$http_path_api . "Payment/CommonPay/{$notifyFileName}-{$pay_type}-{$wid}.html";//通知地址
    $extra = ['wid' => $wid, 'openid' => $openid, 'money' => $money,
        'notifyUrl' => $notify_url, 'OrderNo' => $OrderNo, 'remark' => $remark, 'attach' => $attach, 'pay_type' => $pay_type];
    \Lib\Hook::listen('pay_params', $pay_request, $extra);
    if (!$pay_request) {
        return error('暂不支持的支付方式:' . $pay_type);
    }
    if ($pay_request['status'] == 'error') {
        return error($pay_request['msg'], $pay_request['data']);
    }
    return success('获取成功', $pay_request['data']);
}

/**
 * 统一退款
 * @param $wid
 * @param $order_no
 * @param $out_trade_no
 * @param $money
 * @param int $pay_type_number
 * @param string $remark
 * @return array
 */
function common_refund($wid,$order_no,$out_trade_no,$money,$pay_type_number=0,$remark=''){
    $pay_request = null;
    $remark = preg_replace("/[^a-zA-Z\p{Han}]/u","",$remark);
    $pay_type = getPayTypeByNumber($pay_type_number);

    $extra = ['wid' => $wid, 'money' => $money, 'order_no' => $order_no, 'out_trade_no' => $out_trade_no, 'remark' => $remark, 'pay_type' => $pay_type];
    \Lib\Hook::listen('pay_refund', $pay_request, $extra);
    if (!$pay_request) {
        return error('暂不支持的退款方式:' . $pay_type);
    }
    if ($pay_request['status'] == 'error') {
        return error($pay_request['msg'], $pay_request['data']);
    }
    return success('退款成功', $pay_request['data']);
}
function get_pay_type($pay_type, $wid)
{
    $pay_type = empty($pay_type) ? get_applet_type() : $pay_type;
    if ($pay_type == 'wechat') {
        $sykConfig = new Model('vshop_syk_pay');
        $sykConfig->find(array('wid' => $wid));
        if ($sykConfig && $sykConfig->status) $pay_type = 'syk';//开启商云客支付
    }
    return $pay_type;
}

/**
 * 获取pub目录路径
 * @param string $son
 * @return string
 */
function pub_path($son=''){
    return DOXCX_FRAME_PATH.'pub/'.ltrim($son,'/\\');
}

/**
 * 获取应用所在路径
 * @param string $son
 * @return string
 */
function app_path($son=''){
    return DOXCX_FRAME_PATH.ltrim($son,'/\\');
}

/**
 * 框架所在目录
 * @param string $son
 * @return string
 */
function lib_path($son=''){
    return DOXCX_LIB.ltrim($son,'/\\');

}

/**
 * 静态文件路径
 * @param string $son
 * @return string
 */
function static_path($son=''){
    return DOXCX_STATIC.ltrim($son,'/\\');
}
function addons_path($son=''){
    $dispatcher_info_list = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 4);
    $dispatcher_info=[];
    foreach ($dispatcher_info_list as $dispatcher){
        if(!empty($dispatcher['file'])&&strpos($dispatcher['file'],DS."Addons".DS)){
            $dispatcher_info=$dispatcher;
            break;
        }
    }
    $addons_path=str_replace('\\','/',DOXCX_FRAME_PATH.'Addons/');
    $addons_module_name=strstr(str_replace(['\\',$addons_path],['/',''],$dispatcher_info['file']),'/',true);
    return DOXCX_FRAME_PATH.'Addons/'.ltrim($addons_module_name,'/\\')."/".ltrim($son,'/\\');

}

/**
 * 插件前端路径
 * @param string $son
 * @return string
 */
function plugin_static($son=''){
    $dispatcher_info_list = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 4);
    $dispatcher_info=[];
    foreach ($dispatcher_info_list as $dispatcher){
        if(!empty($dispatcher['file'])&&strpos($dispatcher['file'],DS."Addons".DS)){
            $dispatcher_info=$dispatcher;
            break;
        }
    }
    $addons_path=str_replace('\\','/',DOXCX_FRAME_PATH.'Addons/');
    $addons_module_name=strstr(str_replace(['\\',$addons_path],['/',''],$dispatcher_info['file']),'/',true);
    return  pub_path('Addons/'.ltrim($addons_module_name,'/\\')."/".ltrim($son,'/\\'));
}

/**
 * 移除路径中网站目录
 * @param string $path
 * @return mixed|string
 */
function remove_path($path=''){
    $file_path=str_replace('\\','/',$path);
    $file_path=trim(str_replace($_SERVER['DOCUMENT_ROOT'],'',$file_path));
    return $file_path;
}

/**
 * 获取带域名url
 * @param string $son
 * @return string
 */
function get_host($son=''){
        $pageURL = 'http';

        if ($_SERVER["HTTPS"] == "on")
        {
            $pageURL .= "s";
        }
        $pageURL .= "://";
        $pageURL.=$_SERVER["HTTP_HOST"];
//        if ($_SERVER["SERVER_PORT"] != "80")
//        {
//            $pageURL .= $_SERVER["SERVER_NAME"] . ":" . $_SERVER["SERVER_PORT"] ;
//        }
//        else
//        {
//            $pageURL .= $_SERVER["HTTP_HOST"] ;
//        }
        $pageURL=rtrim($pageURL,'/');
        if(strlen($son) > 0){
            $pageURL=$pageURL.'/'.trim($son,'/');
        }
        return $pageURL;
    }


/**
 * 获取小程序类型
 */
function get_applet_type()
{
    $refererUrl = parse_url($_SERVER['HTTP_REFERER']);
    $host = empty($refererUrl['host']) ? '' : $refererUrl['host'];
    $type = '';
    switch ($host) {
        case 'appservice.qq.com':
            $type = 'qq';
            break;
        case 'servicewechat.com':
            $type = 'wechat';
            break;
        case 'tmaservice.developer.toutiao.com':
            $type = 'toutiao';
            break;
        case 'smartapp.baidu.com':
            $type = 'baidu';
            break;
        case strpos($host,'hybrid.alipay-eco.com' ) || strpos($_SERVER['HTTP_USER_AGENT'],'AlipayID'):
            $type = 'alipay';
            break;
        default:
            break;
    }
    return $type;

}

//1：支付宝2：财付通3：线下支付4：微信支付5：余额支付6：百度聚合支付7：头条抖音支付8：第三方支付）
function get_payment_number($pay_type = '')
{
    $number = 0;
    switch ($pay_type) {
        case 'alipay':
            $number = 1;
            break;
        case 'qq':
            $number = 2;
            break;
        case 'offline':
            $number = 3;
            break;
        case 'wechat':
            $number = 4;
            break;
        case 'vipcard':
            $number = 5;
            break;
        case 'baidu':
            $number = 6;
            break;
        case 'toutiao':
            $number = 7;
            break;
        case 'syk':
            $number = 8;
            break;
        case 'tt_pay':
            $number = 9 ;
            break;
        case 'wechhat_h5':
            $number = 10;
            break;
        default:
            $number = 0;
            break;

    }
    return $number;
}

/**
 * 根据支付类型数字获取支付类型
 * @param $number
 * @return mixed|string
 */
function getPayTypeByNumber($number){
    $type_arr=[
        1=>'alipay',
        2=>'qq',
        3=>'offline',
        4=>'wechat',
        5=>'vipcard',
        6=>'baidu',
        7=>'toutiao',
        8=>'syk',
        9=>'tt_pay', //头条新收银台
        10=>'wechat_h5',
        0=>''
    ];
    $number=intval($number);
    if(isset($type_arr[$number])){
        return $type_arr[$number];
    }else{
        return '';
    }
}

/**
 * 获取插件url
 * @param $url
 * @param $params
 * @return string
 */
function addonsUrl($url, $params=[])
{
    global $_PAGE;
    $host = '';
    $url = trim($url, '/');
    if (strpos($url, '://') === false) {

        $host = 'http';

        if ($_SERVER["HTTPS"] == "on") {
            $host .= "s";
        }
        $host .= "://";

        if ($_SERVER["SERVER_PORT"] != "80" && $_SERVER["SERVER_PORT"] != "443") {
            $host .= $_SERVER['HTTP_HOST'] . ":" . $_SERVER["SERVER_PORT"];
        } else {
            $host .= $_SERVER['HTTP_HOST'];
        }
        $host = rtrim($host, '/');

    }
    $ext = '';
    if (strstr($url, Conf::$suffix) !== Conf::$suffix) {
        $ext = Conf::$suffix;
    }
    $url_arr = explode('/', trim($url, '/'));
    if(strpos($url, '://') === false&&stripos($url_arr[0],'addons')===false){

        $dispatcher_info = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 4);
        $dispatcher_cur = [];
        foreach ($dispatcher_info as $key => $dispatcher_row) {
            if (!empty($dispatcher_row['class']) && $dispatcher_row['class'] === 'BaseController') {
                $dispatcher_cur = $dispatcher_info[$key + 1];
                break;
            }
        }
        if ($dispatcher_cur) { #优先根据控制器寻找路径 找不到再按照访问路径
            $controller_path = ltrim(str_replace(['\\', '/Controller/'], ['/', '/'], $dispatcher_cur['class']), '/');
            $url_base = $controller_path . '/' . $dispatcher_cur['function'];
        } else {
            $controller_path = ltrim(str_replace(['\\', '/Controller/'], ['/', '/'], $_PAGE->controller), '/');
            $url_base = $controller_path . '/' . $_PAGE->method;
        }
        $url_base_arr = explode('/', $url_base);
//        $url_base_arr=array_map(function ($item){
//            return uncamelize(lcfirst($item)); #转换风格成下划线形式
//        },$url_base_arr);
        $url_arr = array_reverse(array_replace(array_reverse($url_base_arr), array_reverse($url_arr)));
    }

    $base_url =implode('/', $url_arr);
    $query_str = !is_array($params) ? $params : http_build_query($params);
    if (!empty($query_str)) $query_str = '?' . $query_str;
    return $host . '/' . rtrim($base_url,'/') . $ext . $query_str;
}

/**
 * 钩子模版使用
 * @param $tag
 * @param $params
 * @param array $extra
 * @param bool $once
 * @return mixed
 */
function hook($tag,&$params,$extra=[], $once = true){
    return  \Lib\Hook::listen($tag,$params,$extra,$once);
}

/**
 * 获取请求类实例
 * @return \Lib\Request
 */
function request(){
    return \Lib\Request::instance();
}

/**
 * 根据文件后缀获取网络常见文件格式mime类型
 * @param $ext
 * @return string
 */
function getMimeTypeByExt($ext){
    $mimeType = [
        'xml'   => 'application/xml,text/xml,application/x-xml',
        'json'  => 'application/json,text/x-json,application/jsonrequest,text/json',
        'js'    => 'text/javascript,application/javascript,application/x-javascript',
        'css'   => 'text/css',
        'rss'   => 'application/rss+xml',
        'yaml'  => 'application/x-yaml,text/yaml',
        'atom'  => 'application/atom+xml',
        'pdf'   => 'application/pdf',
        'text'  => 'text/plain',
        'txt'   =>'text/plain,application/octet-stream',
        'image' => 'image/png,image/jpg,image/jpeg,image/pjpeg,image/gif,image/webp,image/*',
        'csv'   => 'text/csv',
        'html'  => 'text/html,application/xhtml+xml,application/marc,*/*',
    ];
    $ext_arr=is_string($ext) ? explode(',',$ext) :$ext;

    $type='';
        foreach ($ext_arr as $key => $val) {
            if(isset($mimeType[$val])){
                $type.=",{$mimeType[$val]}";
            }

        }
        return ltrim($type,',');
}


function up_make_sign($params, $key)
{
    ksort($params);
    $string = array_to_string($params);  //参数进行拼接key=value&k=v

    //签名步骤二：在string后加入KEY
    $string = $string . "&key=" . $key;
    //签名步骤三：MD5加密
    $string = md5($string);
    //签名步骤四：所有字符转为大写
    $result = strtoupper($string);
    return $result;
}

/**
 * 简单对称解密
 * @param string $string [加密后的值]
 * @param string $skey [加密的key]
 * @return [type]         [加密前的字符串]
 */
function decode($string = '', $skey = 'cxphp')
{
    $strArr = str_split(str_replace(array('O0O0O', 'o000o', 'oo00o'), array('=', '+', '/'), $string), 2);
    $strCount = count($strArr);
    foreach (str_split($skey) as $key => $value)
        $key <= $strCount && isset($strArr[$key]) && $strArr[$key][1] === $value && $strArr[$key] = $strArr[$key][0];
    return base64_decode(join('', $strArr));
}

//清空文件夹函数和清空文件夹后删除空文件夹函数的处理
function deldir($path)
{
    //如果是目录则继续
    if (is_dir($path)) {
        //扫描一个文件夹内的所有文件夹和文件并返回数组
        $p = scandir($path);
        foreach ($p as $val) {
            //排除目录中的.和..
            if ($val != "." && $val != "..") {
                //如果是目录则递归子目录，继续操作
                if (is_dir($path . $val)) {
                    //子目录中操作删除文件夹和文件
                    deldir($path . $val . '/');
                    //目录清空后删除空文件夹
                    @rmdir($path . $val . '/');
                } else {
                    //如果是文件直接删除
                    unlink($path . $val);
                }
            }
        }
    }
}


/**
 * 自动找到内容bom头并去除
 * @param $content
 * @return bool|string
 */
function removeBom($content){
    $contents=$content;
    $charset[1]=substr($contents,0,1);
    $charset[2]=substr($contents,1,1);
    $charset[3]=substr($contents,2,1);
    if(ord($charset[1])==239 && ord($charset[2])==187 && ord($charset[3])==191){

        $content=substr($content,3);
    }
    return $content;
}
/**
 * 返回正确信息
 * @param string $msg
 * @param null $data
 * @param array $exts
 * @return mixed
 */
function send_success($msg = 'OK', $data = null, $exts = []){
    return  \Lib\Response::create(success($msg ,$data ,$exts ),'json')->send();
}

/**
 * 返回错误信息
 * @param string $msg
 * @param null $data
 * @param array $exts
 * @return mixed
 */
function send_error($msg = 'ERR', $data = null, $exts = []){
    return  \Lib\Response::create(error($msg ,$data ,$exts ),'json')->send();
}
