'app_data_log', '2'=>'app_card_data', '3'=>'app_user_data', '4'=>'pc_vitalcapacity_standard', '5'=>'admin_estimate', '6'=>'app_account_number' ]; protected $ceshiyong_token = ['57bd45e3a963b372ea2d873e4bd8d1f8','e0966788d02cc93290d9d674921d9715']; protected $base_call_method = ['内部']; protected $token_time = 30;//30天的秒数 protected $return_data_all = [ // '0' => ['success',[]], '10001'=>'关键参数缺失', '10002'=>'操作失败', '10003'=>'信息核实错误', '10004'=>'未找到有效数据', '10005'=>'参数格式错误', '10006'=>'参数不能为空', '10007'=>'参数错误', '10008'=>'', '10009'=>'', '10010'=>'自定义信息', '20001'=>'登录失效', '99999'=>'网络异常,请稍后重试', ]; // 加 bcadd(,,20) // 减 bcsub(,,20) // 乘 bcmul(,,20) // 除 bcdiv(,,20) ################################################################接口################################################################ ################################################################接口################################################################ ################################################################接口################################################################ // 接口记录 public function record_api_log($params, $error = null, $response = null){ $logContent = "接口请求参数:" . json_encode($params, JSON_UNESCAPED_UNICODE) . PHP_EOL; if ($error) { $logContent .= "错误信息:" . $error['all_content'] . PHP_EOL; if(!cache($error['flie']."_".$error['line'])){ cache($error['flie']."_".$error['line'],"API错误",3600); $this->send_email_api_error(["tsf3920322@126.com"],['title'=>'接口报错','from_user_name'=>'青测API','content'=>$logContent]); } } if ($response) { $logContent .= "返回信息:" . json_encode($response, JSON_UNESCAPED_UNICODE) . PHP_EOL; } // 使用ThinkPHP的日志记录方法 Log::record($logContent, 'api_log'); } // 检查变量是否是一个只有数字的一维数组 public function is_num_array($array = [1,2,3]) { if (!is_array($array)) { return false; // 变量不是数组 } foreach ($array as $value) { if (!is_numeric($value)) { return false; // 数组中包含非数字元素 } } $result = Db::table($this->base_use_db_name['2'])->where(['is_del'=>0])->cache(true,600)->select();//查询结果缓存3600秒 if(empty(array_diff($array, array_column($result, 'id')))){ return true;// 数组是一维的且只包含数字,且已经跟数据库比对过,每个数值都是有效 }else{ return false;//跟数据库比对过,存在无效数值 } } public function validate_user_identity($data) { $validate_user = Db::table($this->base_use_db_name['3'])->where(['id'=>$data])->count(); if($validate_user<=0){ return false; }else{ return true; } } // 判断字符串是手机还是邮箱 public function is_tel_email($str) { // 手机号码的正则表达式(中国大陆格式)(下面正则实际判断的是是否为11位数字) $mobilePattern = '/^\d{11}$/'; // 电子邮件地址的正则表达式 $emailPattern = '/^[a-zA-Z0-9._%-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/'; // 判断是否为手机号码 if (preg_match($mobilePattern, $str)) { return 'tel'; } // 判断是否为电子邮件地址 if (preg_match($emailPattern, $str)) { return 'email'; } // 如果都不是,返回其他 return false; } // 计算年龄 public function calculate_age($data = '1991-04-20'){ $today = time(); // 获取当前时间的 Unix 时间戳 $birthDate = strtotime($data); // 将出生日期字符串转换为 Unix 时间戳 if ($birthDate !== false) { $age = date('Y', $today) - date('Y', $birthDate); // 如果当前年份的月份和日期小于出生年份的月份和日期,那么年龄减一 if (date('m-d', $today) < date('m-d', $birthDate)) { $age--; } return $age; } else { return false; } } // 秒转化格式,00:00:00 public function handle_hour_branch_second($data = '2000'){ $data = abs($data); $hours = intval($data / 3600); $minutes = intval(($data % 3600) / 60); $remainingSeconds = $data % 60; return [ 'h' => str_pad($hours, 2, '0', STR_PAD_LEFT), 'm' => str_pad($minutes, 2, '0', STR_PAD_LEFT), 's' => str_pad($remainingSeconds, 2, '0', STR_PAD_LEFT) ]; } // 判断token是否过期 public function token_time_validate($token){ // 591b70e0d80b5fa6d77e6e1384453ab9 if(is_string($token)){ $length = strlen($token); if ($length < 10 ) { Log::record('用户尝试更新token时间,token:' . $token.',但是更新token失败,字符串长度小于10', 'token_log'); return ['state'=>false,'language'=>null]; } }else{ Log::record('用户尝试更新token时间,token:' . $token.',但是更新token失败,不是字符串', 'token_log'); return ['state'=>false,'language'=>null]; } $user_login = Db::table($this->base_use_db_name['6'])->where(['token'=>$token,'is_del'=>0])->field('id,login_time,language')->find(); if(!$user_login){ Log::record('用户尝试更新token时间,token:' . $token.',但是更新token失败,未找到用户token', 'token_log'); return ['state'=>false,'language'=>null]; } // 创建 DateTime 对象来表示指定的日期和时间 $specifiedDateTime = new \DateTime($user_login['login_time']); // 获取当前时间的 DateTime 对象 $currentDateTime = new \DateTime(); // 计算两个日期之间的差异(以秒为单位) $interval = $currentDateTime->diff($specifiedDateTime); // 将差异转换为天数(注意:这里的天数可能不是整数,因为差异可能包括小时、分钟等) $daysDifference = $interval->days; // 如果需要更精确的计算(包括小时、分钟等转换成的天数),可以使用以下方式: // $totalSecondsDifference = $interval->format('%a') * 86400 + $interval->format('%h') * 3600 + $interval->format('%i') * 60 + $interval->format('%s'); // $daysDifference = floor($totalSecondsDifference / 86400); // 将总秒数转换为天数并取整 // 判断差异是否超过指定的天数 if ($daysDifference > $this->token_time) { // echo "超过 {$specifiedDays} 天"; Log::record('用户尝试更新token时间,token:' . $token.',但是更新token失败,原因没有找到该token,或该token已经超过30天', 'token_log'); return ['state'=>false,'language'=>$user_login['language']]; } else { // echo "未超过 {$specifiedDays} 天"; $result = Db::table($this->base_use_db_name['6'])->where(['token'=>$token])->update(['login_time'=>date('Y-m-d H:i:s')]); if($result){ Log::record('用户尝试更新token时间,token:' . $token.',记录成功,最新的时间为'.date('Y-m-d H:i:s'), 'token_log'); return ['state'=>true,'language'=>$user_login['language']]; }else{ Log::record('用户尝试更新token时间,token:' . $token.',但是更新token失败,数据库更新时间未成功', 'token_log'); return ['state'=>true,'language'=>$user_login['language']]; } } } // 计算天数 public function daysSince($pastDate,$now = false) { // 创建一个表示过去日期的 DateTime 对象 $past = new \DateTime($pastDate); if($now === false){ // 创建一个表示当前日期的 DateTime 对象 $now = new \DateTime(); }else{ $now = new \DateTime($now); } // 使用 DateTime::diff() 方法计算两个日期之间的差值 $interval = $past->diff($now); // 返回相差的天数 return $interval->format('%a'); } // 计算月龄 public function calculateAgeInMonthsWithPrecision($birthDateStr) { // 获取当前日期 $now = new \DateTime(); // 将出生日期字符串转换为 DateTime 对象 $birthDate = \DateTime::createFromFormat('Y-m-d', $birthDateStr); // 计算两者之间的差距(以月为单位,包含部分月份的小数) $interval = $now->diff($birthDate); $ageInMonths = $interval->y * 12 + $interval->m; // 年份乘以12加上月份 $remainingDays = $interval->d; // 当前月内的剩余天数 // 将剩余天数转换为小数月份(假设一个月为30天,进行近似计算) $partialMonth = $remainingDays / 30; // 结果精确到小数点后两位 // $ageInMonthsPrecise = round($ageInMonths + $partialMonth, 2); // 整月+剩余月取整 $ageInMonthsPrecise = intval($ageInMonths + $partialMonth); return $ageInMonthsPrecise; } // 曲线页面-底部统计动作 public function base_target_initial_cumulative_weight($data = []){ // 第一种:用户详情(所有数据都有) // 第二种:手动记录(只有最新体重) // 第三种:修改原始体重(只有原始体重) // $result_data['target_weight'] 目标体重 // $result_data['initial_weight'] 最初体重 // $result_data['weight'] 最近一次测量重量 // $result_data['initial_date'] 初始体重日期 if(count($data) > 0){ $result_data['target_weight'] = $data['target_weight']; $result_data['initial_weight'] = $data['initial_weight']; $result_data['cumulative_weight'] = bcsub($data['weight'],$data['initial_weight'],2); $result_data['cumulative_day'] = $data['initial_date'] == 0?0:$this->daysSince($data['initial_date']); }else{ $result_data['target_weight'] = 0; $result_data['initial_weight'] = 0; $result_data['cumulative_weight'] = 0; $result_data['cumulative_day'] = 0; } return $result_data; } // 判断一个参数是否为数字且大于等于0 public function isPositiveNumber($value) { return is_numeric($value) && $value >= 0; } // 判断是否为整型,或者字符串类型的整型数字 public function isValidInteger($var) { // 直接检查是否为整型 if (is_int($var)) { return true; } // 检查是否为字符串且是有效的整数表示 if (is_string($var) && filter_var($var, FILTER_VALIDATE_INT) !== false) { return true; } // 其他情况 return false; } // 判断一个字符串是否为两位以内小数 public function isTwoDecimalOrLess($str) { return preg_match('/^\d*(\.\d{1,2})?$/', $str) === 1; } // 获取用户肺活量的标准值 public function get_vitalcapacity_data($id){ $standard_data = [ ['min_val'=>'90','max_val'=>'100','text'=>'优秀','color'=>'#6492F6'], ['min_val'=>'80','max_val'=>'89','text'=>'良好','color'=>'#5AD06D'], ['min_val'=>'60','max_val'=>'79','text'=>'及格','color'=>'#FFAB00'], ['min_val'=>'10','max_val'=>'59','text'=>'不及格','color'=>'#FF5656'], ['min_val'=>'0','max_val'=>'9','text'=>'无效','color'=>'#FF5656'], ]; $grade = Db::table($this->base_use_db_name['3'])->where(['id'=>$id])->field('id,grade,gender,birthday')->find(); if(!$grade){ return []; } if($grade['grade'] == 'nothing'){ // 计算年龄判断是属于哪个年级 $user_age = $this->calculate_age($grade['birthday']); if($user_age <= 7){ $grade['grade'] = 'grade_s_1'; }else if($user_age == 8){ $grade['grade'] = 'grade_s_2'; }else if($user_age == 9){ $grade['grade'] = 'grade_s_3'; }else if($user_age == 10){ $grade['grade'] = 'grade_s_4'; }else if($user_age == 11){ $grade['grade'] = 'grade_s_5'; }else if($user_age == 12){ $grade['grade'] = 'grade_s_6'; }else if($user_age == 13){ $grade['grade'] = 'grade_m_1'; }else if($user_age == 14){ $grade['grade'] = 'grade_m_2'; }else if($user_age == 15){ $grade['grade'] = 'grade_m_3'; }else if($user_age == 16){ $grade['grade'] = 'grade_h_1'; }else if($user_age == 17){ $grade['grade'] = 'grade_h_2'; }else if($user_age == 18){ $grade['grade'] = 'grade_h_3'; }else if($user_age == 19 || $user_age == 20){ $grade['grade'] = 'grade_u_12'; }else if($user_age >= 21){ $grade['grade'] = 'grade_u_34'; } } $sql_min = "WITH RankedGrades AS ( SELECT id, level, ".$grade['grade'].", ROW_NUMBER() OVER(PARTITION BY level ORDER BY ".$grade['grade']." ASC, id ASC) AS rn FROM ".$this->base_use_db_name['4']." WHERE sex = ".$grade['gender']." ) SELECT id, level, ".$grade['grade']." FROM RankedGrades WHERE rn = 1"; $result_min = Db::query($sql_min); foreach ($result_min as $key => $value) { foreach ($standard_data as $sdk => $sdv) { if($value['level'] == $sdv['text']){ $standard_data[$sdk]['min_val'] = $value[$grade['grade']]; } } } for ($i=count($standard_data)-1; $i >= 1; $i--) { $standard_data[$i]['max_val'] = $standard_data[$i-1]['min_val']; } $standard_data[0]['max_val'] = '5140'; return $standard_data; } // 时间日期转换 public function addCurrentTimeToDateString($dateStr) { // 将日期字符串转换为DateTime对象 $dateTime = new \DateTime($dateStr); // 获取当前的时分秒 $currentTime = new \DateTime('now'); $hours = $currentTime->format('H'); $minutes = $currentTime->format('i'); $seconds = $currentTime->format('s'); // 设置DateTime对象的时间部分为当前时间 $dateTime->setTime($hours, $minutes, $seconds); // 返回格式化为"Y-m-d H:i:s"的字符串 return $dateTime->format('Y-m-d H:i:s'); } // 处理分秒变秒 public function convertMinutesSecondsToStringSeconds($timeString) { // 分割字符串获取分钟和秒 list($minutes, $seconds) = explode(':', $timeString); // 将分钟和秒转换为秒 $totalSeconds = ($minutes * 60) + intval($seconds); // 确保秒是整数 return $totalSeconds; } // 转换数字"90.00", "88.11", "66.50", ".00"为正常数字 public function convertStringToNumber($str) { // 去除字符串两端的空格(如果有的话) $str = trim($str); // 检查字符串是否为空或只包含小数点 if ($str === '' || $str === '.') { return 0; } // 尝试将字符串转换为浮点数 $number = (float)$str; // 格式化浮点数,去掉末尾多余的零 $formattedNumber = rtrim(rtrim(sprintf('%.2f', $number), '0'), '.'); // 如果结果为空字符串(比如,原字符串是“.00”),则返回0 if ($formattedNumber === '') { return '0'; } // 返回结果,转换为整数如果小数点后没有数字 if (strpos($formattedNumber, '.') === false) { $formattedNumber = (int)$formattedNumber; return "$formattedNumber"; } return $formattedNumber; } // 时间加一或者减一 public function adjustDateTime($datetimeStr, $type) { // 将时间字符串转换为时间戳 $timestamp = strtotime($datetimeStr); // 检查时间戳是否有效 if ($timestamp === false) { return "无效的日期时间格式"; } // 根据$type参数调整时间戳 switch ($type) { case 'add': $newTimestamp = strtotime('+1 day', $timestamp); break; case 'subtract': $newTimestamp = strtotime('-1 day', $timestamp); break; default: return false; } // 将新的时间戳转换回日期时间字符串 $newDateTimeStr = date('Y-m-d', $newTimestamp); return $newDateTimeStr; } // 对于任意浮点字符串的指定位四舍五入 public function roundToString($numberStr, $numDecimals) { // 将字符串转换为浮点数 $number = floatval($numberStr); // 四舍五入到指定的小数位数 $roundedNumber = round($number, $numDecimals); // 将结果转换回字符串 return strval($roundedNumber); } // 发送一个PSOT请求 public function postRequest($url, $data = [], $headers = []) { $ch = curl_init(); // 初始化cURL会话 if (!$ch) { return [ 'error' => true, 'message' => 'cURL init failed' ]; } // 设置cURL选项 curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); // 禁用证书验证 curl_setopt($ch, CURLOPT_URL, $url); // 要请求的URL curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); // 将curl_exec()获取的信息以文件流的形式返回,而不是直接输出 curl_setopt($ch, CURLOPT_POST, true); // 发送一个常规的POST请求 curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($data)); // POST数据 // 设置请求头 if (!empty($headers)) { curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data)); curl_setopt($ch, CURLOPT_HTTPHEADER, $headers); }else{ // 如果需要发送JSON数据,可以使用以下设置: curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data)); curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type:application/json')); } // 执行cURL会话 $response = curl_exec($ch); if ($response === false) { $error = curl_error($ch); curl_close($ch); return [ 'error' => true, 'message' => "cURL Error: $error" ]; } $decodedResponse = json_decode($response, true); $jsonError = json_last_error(); curl_close($ch); if ($jsonError !== JSON_ERROR_NONE) { return [ 'error' => true, 'message' => 'Invalid JSON Response', 'raw_response' => $response ]; } return $decodedResponse; } public function msg($data,$str='',$result = []){ if(is_array($data)){ if($str != ''){ return json(['code'=>0,'msg'=>$str,'data'=>$data]); }else{ return json(['code'=>0,'msg'=>'操作成功','data'=>$data]); } }else{ if($str != ''){ return json(['code'=>$data,'msg'=>$str,'data'=>$result]); } return json(['code'=>$data,'msg'=>$this->return_data_all[$data],'data'=>$result]); } } /* 接口说明(发邮件) * $address(收件人的邮箱地址) 数组 格式: ['460834639@qq.com','460834639@qq.com'.......] * $content(邮件的主题数据信息) 数组 格式:['title'=>'123','from_user_name'=>'123','content'=>'123'] * $annex(附件路径信息) 字符串 */ public function send_email_api_error($address,$content,$annex=''){ // $ad = '460834639@qq.com'; $ad1 = '295155911@qq.com'; $mail = new PHPMailer(); //实例化 $mail->IsSMTP(); // 启用SMTP $mail->Host = "smtp.126.com"; //SMTP服务器 163邮箱例子 $mail->Port = 465; //邮件发送端口 $mail->SMTPAuth = true; //启用SMTP认证 $mail->SMTPSecure = 'ssl'; $mail->CharSet = "UTF-8"; //字符集 $mail->Encoding = "base64"; //编码方式 $mail->Username = "tsf3920322@126.com"; //你的邮箱 $mail->Password = "HLWXNRPUCTHJFIIX"; //你的密码(邮箱后台的授权密码) $mail->From = "tsf3920322@126.com"; //发件人地址(也就是你的邮箱) // $mail->Subject = "微盟测试邮件"; //邮件标题 $mail->Subject = $content['title']; //邮件标题 // $mail->FromName = "微盟体测中心"; //发件人姓名 $mail->FromName = $content['from_user_name']; //发件人姓名 for ($i=0; $i < count($address); $i++) { $mail->AddAddress($address[$i], ""); //添加收件人(地址,昵称) } if($annex != ''){ // $url = ROOT_PATH. 'public' . DS . 'tsf' . DS .'demoooo.jpg'; $mail->AddAttachment($annex,''); // 添加附件,并指定名称 } $mail->IsHTML(true); //支持html格式内容 $neirong = $content['content']; $mail->Body = $neirong; //邮件主体内容 //发送 if (!$mail->Send()) { return ['code' => 10003,'msg'=>$mail->ErrorInfo]; // return $mail->ErrorInfo; } else { return ['code' => 0]; // return 'success'; } } // 验证是否字符串 public function verify_data_is_ok($data = 2,$type){ if($type == 'str'){ if (is_string($data)) { return true; } else { // $this->record_api_log($data, null, ['code'=>10005,'msg'=>'校验参数不为字符串',[]]); return false; } }else if($type == 'num'){ if (is_numeric($data)) { return true; } else { // $this->record_api_log($data, null, ['code'=>10005,'msg'=>'校验参数不为数字',[]]); return false; } }else if($type == 'intnum'){ $pattern = '/^\d+$/'; if (preg_match($pattern, $data)) { return true; // 匹配成功,返回 true } else { // $this->record_api_log($data, null, ['code'=>10005,'msg'=>'校验参数不为整数数字',[]]); return false; // 匹配失败,返回 false } }else if($type == 'datetime'){ $formats = ['Y-m-d','Y-m-d H:i:s']; foreach ($formats as $format) { $dateTime = \DateTime::createFromFormat($format, $data); // 检查时间字符串是否成功解析,并且解析后的日期时间与原始字符串表示的时间一致 if ($dateTime && $dateTime->format($format) === $data) { return true; } } // 如果所有格式都解析失败,则返回 false // $this->record_api_log($data, null, ['code'=>10005,'msg'=>'校验参数不为日期格式',[]]); return false; }else if($type == 'other'){ } } // 处理身高体重的单位,转换它们为cm和kg。 public function convertHeightAndWeight($height, $weight) { // 加 bcadd(,,20) // 减 bcsub(,,20) // 乘 bcmul(,,20) // 除 bcdiv(,,20) // 定义单位转换比例 $heightConversion = [ 'cm' => 1, 'inch' => 2.54, 'ft-in' => function($value) { list($ft, $in) = explode('-', $value); return $ft * 30.48 + $in * 2.54; // 1 foot = 30.48 cm, 1 inch = 2.54 cm } ]; $weightConversion = [ 'kg' => 1, '斤' => 0.5, // 1斤 = 0.5kg 'st:lb' => function($value) { list($st, $lb) = explode(':', $value); return $st * 6.35029318 + $lb * 0.45359237; // 1 stone = 6.35029318 kg, 1 lb = 0.45359237 kg }, 'lb' => 0.45359237 // 1 lb = 0.45359237 kg ]; // 处理 height if (preg_match('/([\d.]+)(cm|inch|ft-in)/', $height, $matches)) { // $heightValue = floatval($matches[1]); $heightValue = $matches[1]; $heightUnit = $matches[2]; if($heightUnit == 'ft-in'){ // 如果单位为st:lb但是数据格式不对 $heightValue = str_replace($heightUnit, "", $height); if(count(explode('-', $heightValue)) < 2){ $heightValue = str_replace("-", "", $heightValue); $heightValue = $heightValue."-0"; } } if (isset($heightConversion[$heightUnit])) { if (is_callable($heightConversion[$heightUnit])) { $heightInCm = $heightConversion[$heightUnit]($heightValue); } else { $heightInCm = $heightValue * $heightConversion[$heightUnit]; } } else { // 未知单位,返回错误 $heightInCm = false; } } else { // 未找到指定单位判断是否是数字 if (preg_match('/^-?\d+(\.\d+)?$/', $height)) { $heightInCm = $height; } else { $heightInCm = false; } } // 处理 weight if (preg_match('/([\d.:]+)(kg|斤|st:lb|lb)/', $weight, $matches)) { $weightValue = $matches[1]; $weightUnit = $matches[2]; if($weightUnit == 'st:lb'){ // 如果单位为st:lb但是数据格式不对 $weightValue = str_replace($weightUnit, "", $weight); if(count(explode(':', $weightValue)) < 2){ $weightValue = str_replace(":", "", $weightValue); $weightValue = $weightValue.":0"; } } if (isset($weightConversion[$weightUnit])) { if (is_callable($weightConversion[$weightUnit])) { $weightInKg = $weightConversion[$weightUnit]($weightValue); } else { $weightInKg = $weightValue * $weightConversion[$weightUnit]; } } else { // 未知单位,返回错误 $weightInKg = false; } } else { // 未找到指定单位判断是否是数字 if (preg_match('/^-?\d+(\.\d+)?$/', $weight)) { $weightInKg = $weight; } else { $weightInKg = false; } } return [ 'height_in_cm' => bcmul($heightInCm,1,2), 'weight_in_kg' => bcmul($weightInKg,1,2) ]; } public function ceshiyong($aa = 4,$gd = 0.2){ phpinfo(); die; $token = 'cd3f27cf4c4002170ea7bceeb723ac91'; $data = Db::table('pc_bmistand2')->select(); for ($i=0; $i < count($data); $i++) { foreach ($data[$i] as $key => $value) { $data[$i][$key] = str_replace(' ', '',$data[$i][$key]); } Db::table('pc_bmistand2')->where(['id'=>$data[$i]['id']])->update([ 'month'=>$data[$i]['month'], 'sex'=>$data[$i]['sex'], // 'f3sd'=>$data[$i]['f3sd'], // 'f2sd'=>$data[$i]['f2sd'], 'f1sd'=>$data[$i]['f1sd'], 'median'=>$data[$i]['median'], 'z1sd'=>$data[$i]['z1sd'], 'z2sd'=>$data[$i]['z2sd'], // 'z3sd'=>$data[$i]['z3sd'], ]); } die; // $this->send_email_api_error(["tsf3920322@126.com"],['title'=>'接口报错','from_user_name'=>'青测API','content'=>'123']); } }