_periodNum = $periodNum; } /** * 获取期数 * @return int */ public function getPeriodNum() { return $this->_periodNum; } /** * 加入错误错误 * @param string $attr * @param string $error */ public function addError(string $attr, string $error) { $this->_errors[$attr][] = $error; } /** * 获取错误信息 * @return array */ public function getErrors() { return $this->_errors; } /** * 生成流水号 * @return string */ private function _generateSn() { return Date::today('Ymd') . $this->_random(10, 1); } /** * 生成随机数 * @param $length * @param int $numeric * @return string */ private function _random($length, $numeric = 0) { $seed = base_convert(md5(microtime() . $_SERVER['DOCUMENT_ROOT']), 16, $numeric ? 10 : 35); $seed = $numeric ? (str_replace('0', '', $seed) . '012340567890') : ($seed . 'zZ' . strtoupper($seed)); $hash = ''; $max = strlen($seed) - 1; for ($i = 0; $i < $length; $i++) { $hash .= $seed[mt_rand(0, $max)]; } return $hash; } /** * 处理order表中有remain_pv的订单 * 将结果写入到remainPv相关表中 * */ private function _calcRemainPv(){ $orders = Order::find()->where('PERIOD_NUM=:PERIOD_NUM AND REMAIN_PV>0',[':PERIOD_NUM'=>$this->_periodNum])->asArray()->all(); foreach($orders as $order){ $oRemainPv = RemainPv::find()->where(['USER_ID' => $order['USER_ID']])->one(); $transactionRemain = \Yii::$app->db->beginTransaction(); try{ $flowRemainPvModel = new FlowRemainPv(); $flowRemainPvModel->ID = $this->_generateSn(); $flowRemainPvModel->USER_ID = $order['USER_ID']; $flowRemainPvModel->REMAIN_PV_FLOW = $order['REMAIN_PV']; $flowRemainPvModel->REMAIN_PV_TOTAL = $oRemainPv['REMAIN_PV'] + $order['REMAIN_PV']; $flowRemainPvModel->PERIOD_NUM = $this->_periodNum; $flowRemainPvModel->UPDATED_AT = Date::nowTime(); $flowRemainPvModel->ORDER_SN = $order['SN']; if(!$flowRemainPvModel->save()){ $this->addErrors($flowRemainPvModel->getErrors()); return false; } $oRemainPv = RemainPv::find()->where(['USER_ID' => $order['USER_ID']])->one(); if($oRemainPv){ $oRemainPv->updateCounters(['REMAIN_PV'=>$order['REMAIN_PV']]); }else{ $remainPvModel = new RemainPv(); $remainPvModel->ID = $this->_generateSn(); $remainPvModel->USER_ID = $order['USER_ID']; $remainPvModel->UPDATED_AT = Date::nowTime(); $remainPvModel->REMAIN_PV = $order['REMAIN_PV']; $remainPvModel->STATUS = 1; if(!$remainPvModel->save()){ $this->addErrors($remainPvModel->getErrors()); return false; } } $transactionRemain->commit(); } catch (Exception $e) { $transactionRemain->rollBack(); $this->addError('add', $e->getMessage()); return null; } } return null; } /** * 生成假订单 * */ public static function _createFakeOrder($periodNum){ echo('假假假'.$periodNum. PHP_EOL); $sysConfig = Cache::getSystemConfig(); $mesureUpCondition = $sysConfig['monthPcsPvFxCondition']['VALUE']; // 月达标条件 NG默认30 $userHaveRemain = RemainPv::findAllAsArray('REMAIN_PV >=:MESURE_UP',[':MESURE_UP'=>$mesureUpCondition]); $currentPeriod = Period::getInfoByPeriodNum($periodNum); $sysConfig = Cache::getSystemConfig(); $mesureUpCondition = $sysConfig['monthPcsPvFxCondition']['VALUE']; // 月达标条件 NG默认30 if($currentPeriod['IS_MONTH']){ print_r('是月结点'.PHP_EOL); $periods = Period::getCurrentMonthPeriodByPeriodNum($periodNum); //先清除本期的假订单 echo('首先,清除上次尝试生成业绩单时所创建的虚假订单'. date('Y-m-d H:i:s', time()) . PHP_EOL); $delFOrder = Order::deleteAll(['IS_AUTO'=>'1','PERIOD_NUM'=>$periodNum]); echo('检查有结余PV的用户,如果他当月PV不足'.$mesureUpCondition.',则为其创建假订单'. PHP_EOL); foreach($userHaveRemain as $uR){ $myPv = Order::find()->where(['PERIOD_NUM'=>$periods, 'USER_ID'=>$uR['USER_ID']])->SUM('PV'); if($myPv < $mesureUpCondition){ //制造虚拟订单 echo('不足'.$mesureUpCondition.'了,生成假订单' . PHP_EOL); $newOrderForm = new OrderForm(); $newOrderForm->addFakeOrder($uR['USER_ID'],$periodNum); } } } } /** * 计算步骤 * @param $periodNum * @param null $handleUserId * @return bool */ public function calcStep($periodNum, $handleUserId = null) { try { $this->_errors = []; $this->setPeriodNum($periodNum); $this->_handleUserId = $handleUserId; $t1 = microtime(true); // 初始化结算任务 $this->initCalcTask(); // 设置结算状态 $this->setCalcStatus('start'); // 清空所有本期结算用到的缓存 CalcCache::clearAll($this->_periodNum); // 清空会员推荐和接点关系缓存 CalcCache::clearNetCache(); // 清空相关表数据 $this->clearTableData(); $t2 = microtime(true); echo(PHP_EOL . $periodNum. '期,生成业绩单,开始' . PHP_EOL); echo('初始化、清空缓存及相关数据表完成,耗时:' . round($t2 - $t1, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(10); // 计算月奖,才需要向缓存中加入按推荐深度的所有用户 echo('向缓存中加入用户开始 ' . date('Y-m-d H:i:s', time()) . PHP_EOL); // // 先把有remainPv的订单处理一下,将remainPv加入到remain_pv及流水表 // echo('处理当期REMAIN PV ' . date('Y-m-d H:i:s', time()) . PHP_EOL); // $this->_calcRemainPv(); echo('若需要,生成假订单' . date('Y-m-d H:i:s', time()) . PHP_EOL); $this->_createFakeOrder($periodNum); echo('生成假订单完成,开始缓存用户'. date('Y-m-d H:i:s', time()) . PHP_EOL); //修改每一期都缓存所有用户 CalcCache::addUsers($this->_periodNum); $t3 = microtime(true); echo('向缓存中加入用户完成,耗时:' . round($t3 - $t2, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(20); // 周结,循环向上级计入业绩并加入业绩单 $this->loopCalcPeriodPerfByDecOrder(); $this->loopCalcPeriodPerfByOrderDec(); $t4 = microtime(true); echo('计算周业绩表中的数据完成,耗时:' . round($t4 - $t1, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(40); // 从会员的复销订单会员计算复销业绩并加入业绩单 $this->loopCalcPerfByFXOrder(); $this->loopCalcPerfByShopFXOrder(); $t5 = microtime(true); echo('计算复销业绩并写入业绩单完成,耗时:' . round($t5 - $t4, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(60); //本期业绩入库 $this->loopWriteNowPerf(); $t6 = microtime(true); echo('本期业绩入库完成,耗时:' . round($t6 - $t5, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(70); //计算月业绩表中的数据 $this->loopCalcMonthPerfTableData(); $t7 = microtime(true); echo('计算月业绩表中的数据完成,耗时:' . round($t7 - $t6, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(80); //每月计算聘级 // modify 聘级字段改成蓝星奖的 奖衔级别(蓝星奖的等级).不在使用荣衔奖金.聘级的等级切换成蓝星奖等级, // 此等级会影响团队将的封顶. // $this->loopCalcEmpLevel(); $t8 = microtime(true); // echo('计算聘级完成,耗时:' . round($t8 - $t7, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); //$this->_updatePercent(90); //本月业绩入库 $this->loopWriteMonthPerf(); $t7 = microtime(true); echo('本月业绩入库完成,耗时:' . round($t7 - $t6, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(90); // //达标业绩 $this->loopCalcPerfByStandardFXOrder(); // //达标业绩入库 $this->loopWriteStandardPerf(); $t9 = microtime(true); echo('本月业绩入库完成,耗时:' . round($t9 - $t7, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL); $this->_updatePercent(95); // 通过插入到perforder中的业绩订单数据,生成此业绩期活跃用户数据 // $this->loopWriteActiveUser(); $this->_updatePercent(100); $t10 = microtime(true); echo('业绩结算全部完成,共耗时:' . round($t10 - $t9, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL . PHP_EOL); } catch (\Exception $e) { $this->errorCalcTask(); $this->addError('calc', sprintf('File【%s】, Line【%s】, Msg【%s】', $e->getFile(), $e->getLine(), $e->getMessage())); return false; } return true; } /** * 结算完成 * @return bool */ public function endCalcTask() { // 更新结算状态 $this->setCalcStatus('end'); //如果自动结算 if(boolval($this->_sysConfig['autoCalcPeriod']['VALUE'])){ $period = Period::instance(); if($period->isLastSent($this->_periodNum)) { $bonusCalc = BonusCalc::instance(); $asyncResult = $bonusCalc->calcStep($this->_periodNum); if ($asyncResult) { $bonusCalc->endCalcTask(); } else { $bonusCalc->errorCalcTask(); } return $asyncResult; } } } /** * 结算错误 */ public function errorCalcTask() { // 清空所有本期结算用到的缓存 CalcCache::clearAll($this->_periodNum); // 更新结算状态 $this->setCalcStatus('fail'); } /** * 设置生成业绩单状态 * @param $type * start|end|fail */ public function setCalcStatus($type) { if ($type == 'start') { Period::updateAll(['IS_PERFING' => 1, 'IS_PERFED' => Period::PERF_NONE, 'PERF_STARTED_AT' => Date::nowTime()], 'PERIOD_NUM=:PERIOD_NUM', [':PERIOD_NUM' => $this->_periodNum]); } elseif ($type == 'end') { Period::updateAll(['IS_PERFING' => 0, 'IS_PERFED' => Period::PERF_FINISH, 'PERFED_AT' => Date::nowTime()], 'PERIOD_NUM=:PERIOD_NUM', [':PERIOD_NUM' => $this->_periodNum]); } elseif ($type == 'fail') { Period::updateAll(['IS_PERFING' => 0, 'IS_PERFED' => Period::PERF_FAIL, 'PERFED_AT' => 0], 'PERIOD_NUM=:PERIOD_NUM', [':PERIOD_NUM' => $this->_periodNum]); } } /** * 初始化结算任务 * @throws \yii\db\Exception */ public function initCalcTask() { $this->_sysConfig = Cache::getSystemConfig(); $this->_decLevelConfig = Cache::getDecLevelConfig(); $this->_empLevelConfig = Cache::getEmpLevelConfig(); $this->_decRoleConfig = CalcCache::getDecRoleConfig($this->_periodNum); $periodNum = $this->_periodNum; // 获取本年月和上年月 $periodObj = Period::instance(); $periodDataArr = $periodObj->setPeriodNum($periodNum); $this->_periodId = $periodDataArr['ID']; $this->_isCalcMonth = $periodObj->isCalcMonth($periodNum); $this->_calcYear = $periodObj->getYear($periodNum); $this->_calcMonth = $periodObj->getMonth($periodNum); $this->_calcYearMonth = $periodObj->getYearMonth($periodNum); $lastYearMonthArr = $periodObj->getLastMonth($periodNum); $this->_lastCalcYear = $lastYearMonthArr['year']; $this->_lastCalcMonth = $lastYearMonthArr['month']; $this->_lastCalcYearMonth = $lastYearMonthArr['yearMonth']; $this->_lastPeriodNum = $periodNum - 1; if (Period::isExistsPeriodNum($this->_lastPeriodNum)) { $this->_lastPeriodYear = $periodObj->getYear($this->_lastPeriodNum); $this->_lastPeriodMonth = $periodObj->getMonth($this->_lastPeriodNum); $this->_lastPeriodYearMonth = $periodObj->getYearMonth($this->_lastPeriodNum); } else { $this->_lastPeriodYear = 0; $this->_lastPeriodMonth = 0; $this->_lastPeriodYearMonth = 0; } $this->_pvRatio = $this->_sysConfig['pvRatio']['VALUE']; } /** * 清空相关表数据 */ public function clearTableData() { // 周业绩 PerfPeriod::pageDeleteAll('PERIOD_NUM='.$this->_periodNum); // 业绩单 PerfOrder::pageDeleteAll('PERIOD_NUM='.$this->_periodNum); // 删除活跃用户 // PerfActiveUser::pageDeleteAll('PERIOD_NUM='.$this->_periodNum.' AND IS_SENT=0 '); // 月结时要清空的数据 if ($this->_isCalcMonth) { // 月业绩表 PerfMonth::pageDeleteAll("CALC_MONTH='{$this->_calcYearMonth}'"); //达标业绩表 PerfStandard::pageDeleteAll("CALC_MONTH='{$this->_calcYearMonth}'"); } } /** * 循环判断活跃会员,并入库 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopWriteActiveUser($offset = 0) { echo sprintf("时间:[%s]本期活跃用户PerfOrder表中,当前offset为:【%s】" . PHP_EOL, date('Y-m-d H:i:s', time()) , $offset); // 从PerfOrder表中获取此周期的用户数据 $data = PerfPeriod::findUseDbCalc() ->select('USER_ID') ->where('PERIOD_NUM=:PERIOD_NUM',[ ':PERIOD_NUM' => $this->_periodNum ])->offset($offset)->limit($this->_limit)->asArray()->all(); if ($data) { foreach ($data as $upv) { $userId = $upv['USER_ID']; // 判断用户每周是否是活跃用户 $allData = PerfOrder::findUseDbCalc() ->select('USER_ID,PV,DEC_AMOUNT,PERIOD_NUM,CALC_MONTH,P_CALC_MONTH, DEC_SN,ORDER_CREATED_AT') ->where('PERIOD_NUM=:PERIOD_NUM AND USER_ID=:USER_ID',[ ':PERIOD_NUM' => $this->_periodNum, ':USER_ID' => $userId ]) ->orderBy('ORDER_CREATED_AT DESC') ->asArray() ->all(); if($allData) { $this->weekMonthOrder($allData); unset($insertDataPeriodPerf, $allData); } unset($allData); } unset($data); return $this->loopWriteActiveUser($offset + $this->_limit); } return true; } // 活跃判断 public function weekMonthOrder($data) { // 获取每个订单是周几,把他们分别放到各自的周里面. // 因为是自然月,所以需要知道是此月的几号,是此月的第几周.然后往前和往后推出时间戳范围内pv的累计之和是多少 $one = 24*60*60; // 一天的时间戳 $time_arr = []; foreach ($data as $orders) { $day = intval(date('d', $orders['ORDER_CREATED_AT'])); // 当月第多少号 $weekDay = (date('w', $orders['ORDER_CREATED_AT']) == 0) ? 7 : date('w', $orders['ORDER_CREATED_AT']);// 周几 1-7 $format = date('Y-m-d', $orders['ORDER_CREATED_AT']); $orderDayStart = strtotime($format.' 0:0:0'); $orderDayEnd = strtotime($format.' 23:59:59'); $startCaluc = $weekDay-1; $endCaluc = 7-$weekDay; $calucWeekStart = $orderDayStart - $startCaluc*$one; $calucWeekEnd = $orderDayEnd + $endCaluc*$one; if (!isset($time_arr[$calucWeekStart])) { $time_arr[$calucWeekStart] = array_merge($orders, [ 'temp_start' => $calucWeekStart, 'temp_end' => $calucWeekEnd, 'calculate_total_pv' => $orders['PV'] ]); } else { $time_arr[$calucWeekStart]['calculate_total_pv'] = $time_arr[$calucWeekStart]['calculate_total_pv'] + $orders['PV']; } } unset($data); $insert = []; // 循环判断,当周pv累计是否达到400 foreach ($time_arr as $k => $v) { if ($v['calculate_total_pv'] >= $this->_sysConfig['activeUserPvCondition']['VALUE']) { // 如果个人业累计绩达400PV,取得连续四周活跃 // 取出周末再增加三周的时间戳 $insert[] = [ 'ID' => SnowFake::instance()->generateId(), 'USER_ID' => $v['USER_ID'], 'PERIOD_NUM' => $v['PERIOD_NUM'], 'CALC_MONTH' => $v['CALC_MONTH'], 'P_CALC_MONTH' => $v['P_CALC_MONTH'], 'SRATR_AT' => $v['temp_start'], 'END_AT' => $v['temp_end']+(3*7*24*60*60), 'CREATED_AT' => time(), 'PV' => $v['calculate_total_pv'], ]; } } PerfActiveUser::batchInsert($insert); unset($insert); return true; } /** * 周结,向上级算业绩,并计入业绩单 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopCalcPeriodPerfByDecOrder($offset = 0) { // 循环获取全部报单 $allData = DecOrder::findUseDbCalc()->select('ID,DEC_SN,ORDER_SN,USER_ID,TYPE,TO_USER_ID,IS_ADMIN,DEC_AMOUNT,DEC_PV,PERIOD_NUM,CALC_MONTH,IS_DEL,P_CALC_MONTH,CREATED_AT,DEC_ID')->where("PERIOD_NUM=:PERIOD_NUM AND IS_DEL=0 AND TYPE='ZC'", [':PERIOD_NUM' => $this->_periodNum])->orderBy('CREATED_AT DESC,ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); if ($allData) { $insertPerfOrderData = []; foreach ($allData as $data) { // 是否关停等状态不能拿业绩 if (!$this->isHasPerf($data['TO_USER_ID'])) { continue; } //零售单不累计业绩,仅存业绩单 // if($data['TYPE']!='LS') { // 给自己增加PCS(个人消费) CalcCache::nowPeriodPerf($data['TO_USER_ID'], $this->_periodNum, [ 'PV_PCS' => $data['DEC_PV'], 'PV_PCS_ZC' => $data['DEC_PV'], ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($data['TO_USER_ID'], $this->_periodNum); //加入到报单会员中 $toInfo = CalcCache::getUserInfo($data['TO_USER_ID'], $this->_periodNum); CalcCache::addHasBDUsers($data['TO_USER_ID'], $this->_periodNum, [ 'TO_USER_ID' => $data['TO_USER_ID'], 'USER_ID' => $data['USER_ID'], 'DEC_ID' => $data['DEC_ID'], //考虑可能会移网的情况 'REC_USER_ID' => $toInfo['REC_UID'] ?? '', 'CON_USER_ID' => $toInfo['CON_UID'] ?? '', 'DEC_AMOUNT' => $data['DEC_AMOUNT'], 'DEC_PV' => $data['DEC_PV'], ]); // 给上追加业绩 $this->loopNetworkParentDo($data['TO_USER_ID'], function ($parent) use (&$data) { // 给上级会员追加业绩到缓存中 // CalcCache::addUserPerf($parent['PARENT_UID'], $this->_periodNum, [ // 'PV_'.$parent['LOCATION'].'L' => $data['DEC_PV'], // ]); // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_' . $parent['LOCATION'] . 'L' => $data['DEC_PV'], 'PV_' . $parent['LOCATION'] . 'L_TOUCH' => $data['DEC_PV'], 'PV_' . $parent['LOCATION'] . 'L_' . $data['TYPE'] => $data['DEC_PV'], ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); unset($parent); }); //给推荐关系累计增加业绩 $this->loopRelationParentDo($data['TO_USER_ID'], function ($parent) use (&$data) { // 给上级会员追加业绩到缓存中 // CalcCache::addUserPerf($parent['PARENT_UID'], $this->_periodNum, [ // 'PV_'.$parent['LOCATION'].'L' => $data['DEC_PV'], // ]); // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_PSS' => $data['DEC_PV'], ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); unset($parent); }); // } // 写入业绩单表 $decInfo = CalcCache::getUserInfo($data['USER_ID'], $this->_periodNum); $sn = PerfOrder::generateSN(); $insertPerfOrderData[] = [ 'FROM_TABLES' => 'dec_order', 'ID' => SnowFake::instance()->generateId(), 'SN' => $data['ORDER_SN'], 'DEC_SN' => $data['DEC_SN'], 'DEC_TYPE' => strtoupper($data['TYPE']), 'DEC_STATUS' => PerfOrder::STATUS_NORMAL, 'USER_ID' => $data['TO_USER_ID'], 'LAST_REC_USER_NAME' => $toInfo['REC_USER_NAME'], 'LAST_REC_REAL_NAME' => $toInfo['REC_REAL_NAME'], 'LAST_DEC_LV' => $toInfo['DEC_LV'], 'LAST_EMP_LV' => $toInfo['EMP_LV'], 'LAST_STATUS' => $toInfo['STATUS'], 'PV' => $data['DEC_PV'], 'DEC_AMOUNT' => $data['DEC_AMOUNT'], 'LAST_SUB_COM_ID' => $toInfo['SUB_COM_ID'], 'LAST_PROVINCE' => $toInfo['PROVINCE'], 'LAST_CITY' => $toInfo['CITY'], 'LAST_COUNTY' => $toInfo['COUNTY'], 'DEC_USER_ID' => $data['USER_ID'], 'LAST_DEC_DEC_LV' => $decInfo['DEC_LV'], 'LAST_DEC_SUB_COM_ID' => $decInfo['SUB_COM_ID'], 'LAST_DEC_PROVINCE' => $decInfo['DEC_PROVINCE'], 'LAST_DEC_CITY' => $decInfo['DEC_CITY'], 'LAST_DEC_COUNTY' => $decInfo['DEC_COUNTY'], 'PERIOD_NUM' => $this->_periodNum, 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), 'CLOSED_AT' => 0, 'ORDER_CREATED_AT' => $data['CREATED_AT'], ]; unset($data, $decInfo, $sn, $toInfo); } PerfOrder::batchInsert($insertPerfOrderData); unset($insertPerfOrderData, $allData, $snArr); return $this->loopCalcPeriodPerfByDecOrder($offset + $this->_limit); } unset($allData); return true; } /** * 周结,向上级算业绩,并计入业绩单 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopCalcPeriodPerfByOrderDec($offset = 0) { // 循环获取全部报单 $allData = OrderDec::findUseDbCalc()->select('CREATED_AT,ID,SN,USER_ID,ORDER_TYPE,ORDER_AMOUNT,PV,PAY_AMOUNT,PAY_PV,PERIOD_NUM,PAY_TYPE')->where("PERIOD_NUM=:PERIOD_NUM AND IS_DELETE=0 AND ORDER_TYPE=:ORDER_TYPE", [':PERIOD_NUM' => $this->_periodNum, ':ORDER_TYPE'=>'ZC'])->orderBy('ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); if ($allData) { $insertPerfOrderData = []; foreach ($allData as $data) { // 是否关停等状态不能拿业绩 if (!$this->isHasPerf($data['USER_ID'])) { continue; } // 给自己增加PCS(个人消费) CalcCache::nowPeriodPerf($data['USER_ID'], $this->_periodNum, [ 'PV_PCS' => $data['PAY_PV'], 'PV_PCS_ZC' => $data['PAY_PV'], ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($data['USER_ID'], $this->_periodNum); //加入到报单会员中 $toInfo = CalcCache::getUserInfo($data['USER_ID'], $this->_periodNum); CalcCache::addHasBDUsers($data['USER_ID'], $this->_periodNum, [ 'TO_USER_ID' => $data['USER_ID'], 'USER_ID' => $toInfo['DEC_ID'], 'DEC_ID' => $toInfo['DEC_ID'], //考虑可能会移网的情况 'REC_USER_ID' => $toInfo['REC_UID'] ?? '', 'CON_USER_ID' => $toInfo['CON_UID'] ?? '', 'DEC_AMOUNT' => $data['ORDER_AMOUNT'], 'DEC_PV' => $data['PAY_PV'], ]); // 给上追加业绩 $this->loopNetworkParentDo($data['USER_ID'], function ($parent) use (&$data) { // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_' . $parent['LOCATION'] . 'L' => $data['PAY_PV'], 'PV_' . $parent['LOCATION'] . 'L_TOUCH' => $data['PAY_PV'], 'PV_' . $parent['LOCATION'] . 'L_' . $data['ORDER_TYPE'] => $data['PAY_PV'], ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); unset($parent); }); //给推荐关系累计增加业绩 $this->loopRelationParentDo($data['USER_ID'], function ($parent) use (&$data) { // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_PSS' => $data['PAY_PV'], ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); unset($parent); }); // 写入业绩单表 $decInfo = CalcCache::getUserInfo($toInfo['DEC_ID'], $this->_periodNum); $sn = PerfOrder::generateSN(); $insertPerfOrderData[] = [ 'FROM_TABLES' => 'order_dec', 'ID' => SnowFake::instance()->generateId(), 'SN' => $data['SN'], 'DEC_SN' => $data['SN'], 'DEC_TYPE' => strtoupper($data['ORDER_TYPE']), 'DEC_STATUS' => PerfOrder::STATUS_NORMAL, 'USER_ID' => $data['USER_ID'], 'LAST_REC_USER_NAME' => $toInfo['REC_USER_NAME'], 'LAST_REC_REAL_NAME' => $toInfo['REC_REAL_NAME'], 'LAST_DEC_LV' => $toInfo['DEC_LV'], 'LAST_EMP_LV' => $toInfo['EMP_LV'], 'LAST_STATUS' => $toInfo['STATUS'], 'PV' => $data['PAY_PV'], 'DEC_AMOUNT' => $data['ORDER_AMOUNT'], 'LAST_SUB_COM_ID' => $toInfo['SUB_COM_ID'], 'LAST_PROVINCE' => $toInfo['PROVINCE'], 'LAST_CITY' => $toInfo['CITY'], 'LAST_COUNTY' => $toInfo['COUNTY'], 'DEC_USER_ID' => $toInfo['DEC_ID'], 'LAST_DEC_DEC_LV' => $decInfo['DEC_LV'], 'LAST_DEC_SUB_COM_ID' => $decInfo['SUB_COM_ID'], 'LAST_DEC_PROVINCE' => $decInfo['DEC_PROVINCE'], 'LAST_DEC_CITY' => $decInfo['DEC_CITY'], 'LAST_DEC_COUNTY' => $decInfo['DEC_COUNTY'], 'PERIOD_NUM' => $this->_periodNum, 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), 'CLOSED_AT' => 0, 'ORDER_CREATED_AT' => $data['CREATED_AT'] ]; unset($data, $decInfo, $sn, $toInfo); } PerfOrder::batchInsert($insertPerfOrderData); unset($insertPerfOrderData, $allData, $snArr); return $this->loopCalcPeriodPerfByOrderDec($offset + $this->_limit); } unset($allData); return true; } /** * 从会员的复销订单会员计算复销业绩并加入业绩单 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopCalcPerfByFXOrder(int $offset = 0) { // 循环获取全部报单 $allData = Order::findUseDbCalc()->select('ID,SN,DEC_SN,USER_ID,ORDER_TYPE,ORDER_AMOUNT,PAY_AMOUNT,PAY_PV,PAY_TYPE,PERIOD_NUM,STATUS,IS_DELETE,P_CALC_MONTH,CREATED_AT')->where("PERIOD_NUM=:PERIOD_NUM AND IS_DELETE=0 AND ORDER_TYPE=:ORDER_TYPE", [':PERIOD_NUM' => $this->_periodNum, ':ORDER_TYPE'=>DeclarationForm::TYPE_FX])->orderBy('CREATED_AT DESC,ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); if ($allData) { $insertPerfOrderData = []; foreach ($allData as $data) { // 是否关停等状态不能拿业绩 if (!$this->isHasPerf($data['USER_ID'])) { continue; } //如果支付方式是现金,那么实际业绩是支付PV的50% if( $data['PAY_TYPE'] === self::ORDER_PAY_TYPE_CASH || $data['PAY_TYPE'] === self::ORDER_PAY_TYPE_STACK) { $orderCashAmount = $data['ORDER_AMOUNT']; //111期开始由50%改为60%-by 2020-04-30修改 $payPv = $data['PAY_PV'] * $this->_sysConfig['cashReconsumeBonusPercent']['VALUE'] / 100; $cacheDataKey = 'PV_PCS_FX_CASH'; }else { $orderCashAmount = 0; $payPv = $data['PAY_PV']; $cacheDataKey = 'PV_PCS_FX_POINT'; } if( $payPv <= 0 ) continue; // 给自己增加PCS(个人消费) CalcCache::nowPeriodPerf($data['USER_ID'], $this->_periodNum, [ 'FX_AMOUNT_CASH' => $orderCashAmount, 'PV_PCS' => $payPv, 'PV_PCS_FX' => $payPv, $cacheDataKey => $payPv, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($data['USER_ID'], $this->_periodNum); // 给上追加业绩 try { $this->loopNetworkParentDo($data['USER_ID'], function ($parent) use (&$data, $payPv) { // 给上级会员追加业绩到缓存中 // CalcCache::addUserPerf($parent['PARENT_UID'], $this->_periodNum, [ // 'PV_'.$parent['LOCATION'].'L' => $data['DEC_PV'], // ]); // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_' . $parent['LOCATION'] . 'L' => $payPv, 'PV_' . $parent['LOCATION'] . 'L_TOUCH' => $payPv, 'PV_' . $parent['LOCATION'] . 'L_FX' => $payPv, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); }); } catch(\Exception $e) { file_put_contents('loopNetworkParentDo_error.txt', var_export([ 'USER_ID' => $data['USER_ID'], '_periodNum' => $this->_periodNum, 'error' => $e->getMessage() ],true)); } //给推荐关系累计增加业绩 $this->loopRelationParentDo($data['USER_ID'], function ($parent) use ($data, $payPv) { // 给上级会员追加业绩到缓存中 // CalcCache::addUserPerf($parent['PARENT_UID'], $this->_periodNum, [ // 'PV_'.$parent['LOCATION'].'L' => $data['DEC_PV'], // ]); // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_PSS' => $payPv, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); }); // } // 写入业绩单表 $baseInfo = CalcCache::getUserInfo($data['USER_ID'], $this->_periodNum); $sn = PerfOrder::generateSN(); $insertPerfOrderData[] = [ 'FROM_TABLES' => 'order', 'ID' => SnowFake::instance()->generateId(), 'SN' => $data['SN'], 'DEC_SN' => null, 'DEC_TYPE' => 'FX', 'DEC_STATUS' => PerfOrder::STATUS_NORMAL, 'USER_ID' => $data['USER_ID'], 'LAST_REC_USER_NAME' => $baseInfo['REC_USER_NAME'], 'LAST_REC_REAL_NAME' => $baseInfo['REC_REAL_NAME'], 'LAST_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_EMP_LV' => $baseInfo['EMP_LV'], 'LAST_STATUS' => $baseInfo['STATUS'], 'PV' => $payPv, 'DEC_AMOUNT' => $data['PAY_AMOUNT'], 'LAST_SUB_COM_ID' => $baseInfo['SUB_COM_ID'], 'LAST_PROVINCE' => $baseInfo['PROVINCE'], 'LAST_CITY' => $baseInfo['CITY'], 'LAST_COUNTY' => $baseInfo['COUNTY'], 'DEC_USER_ID' => $data['USER_ID'], 'LAST_DEC_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_DEC_SUB_COM_ID' => $baseInfo['SUB_COM_ID'], 'LAST_DEC_PROVINCE' => $baseInfo['PROVINCE'], 'LAST_DEC_CITY' => $baseInfo['CITY'], 'LAST_DEC_COUNTY' => $baseInfo['COUNTY'], 'PERIOD_NUM' => $this->_periodNum, 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), 'CLOSED_AT' => 0, 'ORDER_CREATED_AT' => $data['CREATED_AT'] ]; unset($data, $baseInfo, $sn, $orderCashAmount, $payPv, $cacheDataKey); } PerfOrder::batchInsert($insertPerfOrderData); unset($insertPerfOrderData, $allData, $snArr); return $this->loopCalcPerfByFXOrder($offset + $this->_limit); } unset($allData); return true; } /** * 从会员的商城复销订单会员计算复销业绩并加入业绩单 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopCalcPerfByShopFXOrder(int $offset = 0) { // 循环获取全部报单 $allData = OrderShop::findUseDbCalc()->select('ID,SN,DEC_SN,USER_ID,ORDER_TYPE,ORDER_AMOUNT,PAY_AMOUNT,PAY_PV,PAY_TYPE,PERIOD_NUM,STATUS,IS_DELETE,P_CALC_MONTH,CREATED_AT')->where("PERIOD_NUM=:PERIOD_NUM AND IS_DELETE=0 AND ORDER_TYPE=:ORDER_TYPE", [':PERIOD_NUM' => $this->_periodNum, ':ORDER_TYPE'=>DeclarationForm::TYPE_FX])->orderBy('CREATED_AT DESC,ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); if ($allData) { $insertPerfOrderData = []; foreach ($allData as $data) { // 是否关停等状态不能拿业绩 if (!$this->isHasPerf($data['USER_ID'])) { continue; } //如果支付方式是现金,那么实际业绩是支付PV的50% if( $data['PAY_TYPE'] === self::ORDER_PAY_TYPE_CASH || $data['PAY_TYPE'] === self::ORDER_PAY_TYPE_STACK) { $orderCashAmount = $data['ORDER_AMOUNT']; //111期开始由50%改为60%-by 2020-04-30修改 $payPv = $data['PAY_PV'] * $this->_sysConfig['cashReconsumeBonusPercent']['VALUE'] / 100; $cacheDataKey = 'PV_PCS_FX_CASH'; }else { $orderCashAmount = 0; $payPv = $data['PAY_PV']; $cacheDataKey = 'PV_PCS_FX_POINT'; } if( $payPv <= 0 ) continue; // 给自己增加PCS(个人消费) CalcCache::nowPeriodPerf($data['USER_ID'], $this->_periodNum, [ 'FX_AMOUNT_CASH' => $orderCashAmount, 'PV_PCS' => $payPv, 'PV_PCS_FX' => $payPv, $cacheDataKey => $payPv, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($data['USER_ID'], $this->_periodNum); // 给上追加业绩 $this->loopNetworkParentDo($data['USER_ID'], function ($parent) use (&$data, $payPv) { // 给上级会员追加业绩到缓存中 // CalcCache::addUserPerf($parent['PARENT_UID'], $this->_periodNum, [ // 'PV_'.$parent['LOCATION'].'L' => $data['DEC_PV'], // ]); // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_' . $parent['LOCATION'] . 'L' => $payPv, 'PV_' . $parent['LOCATION'] . 'L_TOUCH' => $payPv, 'PV_' . $parent['LOCATION'] . 'L_FX' => $payPv, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); }); //给推荐关系累计增加业绩 $this->loopRelationParentDo($data['USER_ID'], function ($parent) use ($data, $payPv) { // 给上级会员追加业绩到缓存中 // CalcCache::addUserPerf($parent['PARENT_UID'], $this->_periodNum, [ // 'PV_'.$parent['LOCATION'].'L' => $data['DEC_PV'], // ]); // 给上级会员追加本期业绩到缓存中 CalcCache::nowPeriodPerf($parent['PARENT_UID'], $this->_periodNum, [ 'PV_PSS' => $payPv, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasPerfUsers($parent['PARENT_UID'], $this->_periodNum); }); // } // 写入业绩单表 $baseInfo = CalcCache::getUserInfo($data['USER_ID'], $this->_periodNum); $sn = PerfOrder::generateSN(); $insertPerfOrderData[] = [ 'FROM_TABLES' => 'order_shop', 'ID' => SnowFake::instance()->generateId(), 'SN' => $data['SN'], 'DEC_SN' => null, 'DEC_TYPE' => 'FX', 'DEC_STATUS' => PerfOrder::STATUS_NORMAL, 'USER_ID' => $data['USER_ID'], 'LAST_REC_USER_NAME' => $baseInfo['REC_USER_NAME'], 'LAST_REC_REAL_NAME' => $baseInfo['REC_REAL_NAME'], 'LAST_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_EMP_LV' => $baseInfo['EMP_LV'], 'LAST_STATUS' => $baseInfo['STATUS'], 'PV' => $payPv, 'DEC_AMOUNT' => $data['PAY_AMOUNT'], 'LAST_SUB_COM_ID' => $baseInfo['SUB_COM_ID'], 'LAST_PROVINCE' => $baseInfo['PROVINCE'], 'LAST_CITY' => $baseInfo['CITY'], 'LAST_COUNTY' => $baseInfo['COUNTY'], 'DEC_USER_ID' => $data['USER_ID'], 'LAST_DEC_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_DEC_SUB_COM_ID' => $baseInfo['SUB_COM_ID'], 'LAST_DEC_PROVINCE' => $baseInfo['PROVINCE'], 'LAST_DEC_CITY' => $baseInfo['CITY'], 'LAST_DEC_COUNTY' => $baseInfo['COUNTY'], 'PERIOD_NUM' => $this->_periodNum, 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), 'CLOSED_AT' => 0, 'ORDER_CREATED_AT' => $data['CREATED_AT'] ]; unset($data, $baseInfo, $sn, $orderCashAmount, $payPv, $cacheDataKey); } PerfOrder::batchInsert($insertPerfOrderData); unset($insertPerfOrderData, $allData, $snArr); return $this->loopCalcPerfByShopFXOrder($offset + $this->_limit); } unset($allData); return true; } /** * 达标复销订单 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopCalcPerfByStandardFXOrder(int $offset = 0) { if (!$this->_isCalcMonth) { return true; } $allData = OrderStandard::findUseDbCalc()->select('ID,SN,DEC_SN,USER_ID,ORDER_TYPE,ORDER_AMOUNT,PAY_AMOUNT,PAY_PV,PAY_TYPE,PERIOD_NUM,STATUS,IS_DELETE,CREATED_AT')->where("CALC_MONTH=:CALC_MONTH", [':CALC_MONTH' => $this->_calcYearMonth])->orderBy('ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); if ($allData) { $insertPerfOrderData = []; foreach ($allData as $data) { // 是否关停等状态不能拿业绩 if (!$this->isHasPerf($data['USER_ID'])) { continue; } //如果支付方式是现金,那么实际业绩是支付PV的50% if( $data['PAY_TYPE'] === self::ORDER_PAY_TYPE_CASH ) { $orderCashAmount = $data['ORDER_AMOUNT']; // $payPv = $data['PAY_PV'] * $this->_sysConfig['cashReconsumeBonusPercent']['VALUE'] / 100; }else { $orderCashAmount = 0; // $payPv = $data['PAY_PV']; } if( $orderCashAmount <= 0 ) continue; // 给自己增加个人业绩 CalcCache::nowStandardMonthPerf($data['USER_ID'], $this->_periodNum, [ 'AMOUNT_PCS' => $orderCashAmount, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasStandardMonthPerfUsers($data['USER_ID'], $this->_periodNum); //只有无聘级业绩才向上累加 $baseInfo = CalcCache::getUserInfo($data['USER_ID'], $this->_periodNum); if( $baseInfo['EMP_LV'] != EmployLevel::NO_LEVEL_ID ) { continue; } //给推荐团队添加团队业绩 注:如果些订单特别多的情况,可以分2步。先只计算个人业绩、然后根据个人业绩再计算团队业绩。 //给推荐关系累计增加业绩 $this->loopRelationParentDo($data['USER_ID'], function ($parent) use ($data, $orderCashAmount) { // 给上级会员追加本期业绩到缓存中 CalcCache::nowStandardMonthPerf($parent['PARENT_UID'], $this->_periodNum, [ 'AMOUNT_PSS' => $orderCashAmount, ]); // 把该会员加入到能拿到业绩的会员缓存中 CalcCache::addHasStandardMonthPerfUsers($parent['PARENT_UID'], $this->_periodNum); //获取parent聘级 $parentUserInfo = CalcCache::getUserInfo($parent['PARENT_UID'], $this->_periodNum); if( $parentUserInfo['EMP_LV'] != EmployLevel::NO_LEVEL_ID ) {//如果碰到有聘级的业绩就不在向上累加了 return self::LOOP_FINISH; } }); unset($data, $baseInfo, $orderCashAmount); } unset($insertPerfOrderData, $allData, $snArr); return $this->loopCalcPerfByStandardFXOrder($offset + $this->_limit); } unset($allData); return true; } /** * 计算月业绩表相关的数据并写入数据库 * @param int $offset * @return bool * @throws Exception * @throws \yii\db\Exception */ public function loopCalcMonthPerfTableData(int $offset = 0) { if (!$this->_isCalcMonth) { return true; } echo sprintf("时间:[%s]月业绩,当前offset为:【%s】" . PHP_EOL, date('Y-m-d H:i:s', time()) , $offset); // 从缓存列表里面从底层往上倒序获取会员 // $allData = PerfPeriod::findUseDbCalc()->from(PerfPeriod::tableName() . ' AS PP')->select('PP.USER_ID AS USER_ID, SUM(PP.PV_PCS) AS PV_PCS_SUM,SUM(PP.PV_PSS) AS PV_PSS_SUM,SUM(PP.PV_1L) AS PV_1L_SUM,SUM(PP.PV_2L) AS PV_2L_SUM,SUM(PP.PV_3L) AS PV_3L_SUM,SUM(PP.PV_4L) AS PV_4L_SUM,SUM(PP.PV_5L) AS PV_5L_SUM, SUM(PM.PV_1L_TOTAL) AS PV_1L_TOTAL, SUM(PM.PV_2L_TOTAL) AS PV_2L_TOTAL, SUM(PM.PV_3L_TOTAL) AS PV_3L_TOTAL, SUM(PM.PV_4L_TOTAL) AS PV_4L_TOTAL,SUM(PM.PV_5L_TOTAL) AS PV_5L_TOTAL, SUM(PM.PV_PSS_TOTAL) AS PV_PSS_TOTAL')->leftJoin(PerfMonth::tableName() . ' AS PM', 'PM.USER_ID=PP.USER_ID AND PM.CALC_MONTH=:LAST_CALC_MONTH', ['LAST_CALC_MONTH'=>$this->_lastCalcYearMonth])->where('PP.CALC_MONTH=:CALC_MONTH', [':CALC_MONTH' => $this->_calcYearMonth])->groupBy('PP.USER_ID')->orderBy('PP.USER_ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); $allData = PerfPeriod::findUseDbCalc()->select('USER_ID, SUM(FX_AMOUNT_CASH) AS FX_AMOUNT_CASH_SUM,SUM(PV_PCS) AS PV_PCS_SUM,SUM(PV_PCS_FX) AS PV_PCS_FX_SUM,SUM(PV_PSS) AS PV_PSS_SUM,SUM(PV_1L) AS PV_1L_SUM,SUM(PV_2L) AS PV_2L_SUM,SUM(PV_3L) AS PV_3L_SUM,SUM(PV_4L) AS PV_4L_SUM,SUM(PV_5L) AS PV_5L_SUM,SUM(PV_1L_ZC) AS PV_1L_ZC_SUM,SUM(PV_2L_ZC) AS PV_2L_ZC_SUM,SUM(PV_3L_ZC) AS PV_3L_ZC_SUM,SUM(PV_4L_ZC) AS PV_4L_ZC_SUM,SUM(PV_5L_ZC) AS PV_5L_ZC_SUM')->where('CALC_MONTH=:CALC_MONTH', [':CALC_MONTH' => $this->_calcYearMonth])->groupBy('USER_ID')->orderBy('USER_ID DESC')->offset($offset)->limit($this->_limit)->asArray()->all(); if ($allData) { // 月度业绩表 foreach ($allData as $everyData) { $userId = $everyData['USER_ID']; // $lastMonthData = PerfMonth::find()->select('PV_1L_TOTAL, PV_2L_TOTAL, PV_3L_TOTAL, PV_4L_TOTAL, PV_5L_TOTAL, PV_PSS_TOTAL')->where('USER_ID=:USER_ID AND CALC_MONTH=:LAST_CALC_MONTH', [ // 'USER_ID'=>$userId, // 'LAST_CALC_MONTH'=>$this->_lastCalcYearMonth, // ])->asArray()->one(); //往期业绩 $userLastPerf = CalcCache::userPerf($userId, $this->_periodNum); //本期业绩 $periodPerf = CalcCache::nowPeriodPerf($userId, $this->_periodNum); $userBaseInfo = CalcCache::getUserInfo($userId, $this->_periodNum); $nowMonthPerf = [ 'USER_ID' => $userId, 'FX_AMOUNT_CASH' => $everyData['FX_AMOUNT_CASH_SUM'], 'PV_PCS' => $everyData['PV_PCS_SUM'], 'PV_PCS_FX' => $everyData['PV_PCS_FX_SUM'], 'PV_PSS' => $everyData['PV_PSS_SUM'], 'PV_1L' => $everyData['PV_1L_SUM'], 'PV_2L' => $everyData['PV_2L_SUM'], 'PV_3L' => $everyData['PV_3L_SUM'], 'PV_4L' => $everyData['PV_4L_SUM'], 'PV_5L' => $everyData['PV_5L_SUM'], //总数据,历史+本期。不能用上月加本月,因为上月可能没业绩,上上个月有业绩。 'PV_1L_TOTAL' => $periodPerf['PV_1L'] + $userLastPerf['PV_1L'], 'PV_2L_TOTAL' => $periodPerf['PV_2L'] + $userLastPerf['PV_2L'], 'PV_3L_TOTAL' => $periodPerf['PV_3L'] + $userLastPerf['PV_3L'], 'PV_4L_TOTAL' => $periodPerf['PV_4L'] + $userLastPerf['PV_4L'], 'PV_5L_TOTAL' => $periodPerf['PV_5L'] + $userLastPerf['PV_5L'], 'PV_PSS_TOTAL' => $periodPerf['PV_PSS'] + $userLastPerf['PV_PSS_TOTAL'], ]; // 把会员的月业绩写入缓存中,以便下面的奖金计算从缓冲中获取数据效率高 CalcCache::addHasMonthPerfUsers($userId, $this->_periodNum); CalcCache::nowMonthPerf($userId, $this->_periodNum, $nowMonthPerf); unset($userId, $everyData, $nowMonthPerf, $lastMonthData, $userBaseInfo, $isVip); } unset($allData); $this->loopCalcMonthPerfTableData($offset + $this->_limit); } unset($allData); return true; } /** * 计算聘级 * @param int $offset * @return bool * @throws Exception * @throws \yii\db\Exception */ public function loopCalcEmpLevel(int $offset = 0) { if (!$this->_isCalcMonth) { return true; } echo sprintf("时间:[%s]计算聘级,当前offset为:【%s】" . PHP_EOL, date('Y-m-d H:i:s', time()) , $offset); // 从缓存列表里面从底层往上倒序获取会员 $allData = CalcCache::getUsers($this->_periodNum, $offset, $this->_limit); if ($allData) { // 月度业绩表 foreach ($allData as $userId) { $userInfo = CalcCache::getUserInfo($userId, $this->_periodNum); $nowMonthPerf = CalcCache::nowMonthPerf($userId, $this->_periodNum); $empLevel = $this->checkEmpLevel($userId, $nowMonthPerf, $userInfo['EMP_LV']); //根据用户的级别判断 能否得到级别积分 if( $empLevel['LEVEL_SCORE'] > 0 ) { CalcCache::nowMonthScore($userId, $this->_periodNum, [ 'LEVEL_SCORE' => $empLevel['LEVEL_SCORE'], ]); CalcCache::addHasScoreUsers($userId, $this->_periodNum); } //更新月业绩的聘级和用户信息中的聘级 CalcCache::nowMonthPerf($userId, $this->_periodNum, [ 'EMP_LEVEL' => $empLevel['ID'] ]); //为业绩单更新结算时聘级 // PerfOrder::updateAll(['LAST_EMP_LV'=>$empLevel['ID']],'USER_ID=:USER_ID AND PERIOD_NUM=:PERIOD_NUM',[':USER_ID'=>$userId,':PERIOD_NUM'=>$this->_periodNum]); $userEmpLevel = $this->_empLevelConfig[$userInfo['EMP_LV']]; $userEmpLevelSort = $userEmpLevel['SORT'] ?? EmployLevel::EMP_LEVEL_SORT['NO_LEVEL']; //不降级 if( $empLevel['SORT'] <= $userEmpLevelSort ) continue; $userInfo['EMP_LV'] = $empLevel['ID']; CalcCache::setUserInfo($userId, $this->_periodNum, $userInfo); //可以判断用户是否升级,能否得到升级积分 //因为默认是不降级,直接获得升级积分 $upgradeScore = 0; foreach ($this->_empLevelConfig as $everyEmpLevel) { if( $everyEmpLevel['SORT'] <= $userEmpLevelSort ) continue; if( $everyEmpLevel['SORT'] > $empLevel['SORT'] ) continue; $upgradeScore += $everyEmpLevel['UPGRADE_SCORE']; unset($everyEmpLevel); } if( $upgradeScore > 0 ) { CalcCache::nowMonthScore($userId, $this->_periodNum, [ 'UPGRADE_SCORE' => $upgradeScore ]); CalcCache::addHasScoreUsers($userId, $this->_periodNum); } unset($userId, $empLevel, $nowMonthPerf, $userInfo, $userEmpLevel, $userEmpLevelSort, $upgradeScore); } unset($allData); $this->loopCalcEmpLevel($offset + $this->_limit); } unset($allData); return true; } /** * 计算公司总业绩 * @return bool * @throws Exception */ public function calcPerfCompany() { if (!$this->_isCalcMonth) { return true; } $perfCompany = PerfCompany::findOne(['CALC_MONTH' => $this->_calcYearMonth]); $db = \Yii::$app->db; $transaction = $db->beginTransaction(); try { if (!$perfCompany) { $perfCompany = new PerfCompany(); } $perfCompany->PV = $this->_companyMonthPerf; $perfCompany->CREATED_AT = Date::nowTime(); $perfCompany->CALC_YEAR = $this->_calcYear; $perfCompany->CALC_MONTH = $this->_calcYearMonth; if (!$perfCompany->save()) { throw new Exception(Form::formatErrorsForApi($perfCompany->getErrors())); } $transaction->commit(); } catch (Exception $e) { $transaction->rollBack(); throw new Exception($e->getMessage()); } unset($perfCompany); return true; } /** * 循环有业绩会员,并入库 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopWriteNowPerf($offset = 0) { echo sprintf("时间:[%s]缓存本期业绩数据入库,当前offset为:【%s】" . PHP_EOL, date('Y-m-d H:i:s', time()) , $offset); // 从缓存列表里面从底层往上倒序获取会员 $allData = CalcCache::getHasPerfUsers($this->_periodNum, $offset, $this->_limit); if($allData){ $insertDataPeriodPerf = []; foreach($allData as $userId){ $insertDataPeriodPerf[] = $this->nowPeriodPerfData($userId); unset($userId); } PerfPeriod::batchInsert($insertDataPeriodPerf); unset($insertDataPeriodPerf, $allData); return $this->loopWriteNowPerf($offset + $this->_limit); } unset($allData); return true; } /** * 循环有月业绩会员,并入库 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopWriteMonthPerf($offset = 0) { if(!$this->_isCalcMonth){ return true; } echo sprintf("时间:[%s]缓存本月业绩数据入库,当前offset为:【%s】" . PHP_EOL, date('Y-m-d H:i:s', time()) , $offset); // 从缓存列表里面从底层往上倒序获取会员 $allData = CalcCache::getHasMonthPerfUsers($this->_periodNum, $offset, $this->_limit); if($allData){ $insertDataMonthPerf = []; foreach($allData as $userId){ $insertDataMonthPerf[] = $this->nowMonthPerfData($userId); unset($userId); } PerfMonth::batchInsert($insertDataMonthPerf); unset($insertDataMonthPerf, $allData); return $this->loopWriteMonthPerf($offset + $this->_limit); } unset($allData); return true; } /** * 循环达标业绩会员,并入库 * @param int $offset * @return bool * @throws \yii\db\Exception */ public function loopWriteStandardPerf($offset = 0) { if(!$this->_isCalcMonth){ return true; } echo sprintf("时间:[%s]缓存达标业绩数据入库,当前offset为:【%s】" . PHP_EOL, date('Y-m-d H:i:s', time()) , $offset); // 从缓存列表里面从底层往上倒序获取会员 $allData = CalcCache::getHasStandardMonthPerfUsers($this->_periodNum, $offset, $this->_limit); if($allData){ $insertDataStandardPerf = []; foreach($allData as $userId) { $data = CalcCache::nowStandardMonthPerf($userId, $this->_periodNum); $baseInfo = CalcCache::getUserInfo($userId, $this->_periodNum); $insertDataStandardPerf[] = [ 'ID' => SnowFake::instance()->generateId(), 'USER_ID' => $userId, 'LAST_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_EMP_LV' => $baseInfo['EMP_LV'], 'LAST_STATUS' => $baseInfo['STATUS'], 'AMOUNT_PCS' => $data['AMOUNT_PCS'], 'AMOUNT_PSS' => $data['AMOUNT_PSS'], 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), ]; unset($data, $baseInfo, $userId); } PerfStandard::batchInsert($insertDataStandardPerf); unset($insertDataStandardPerf, $allData); return $this->loopWriteStandardPerf($offset + $this->_limit); } unset($allData); return true; } /** * 本期业绩数据 * @param $userId * @return array */ public function nowPeriodPerfData($userId){ $data = CalcCache::nowPeriodPerf($userId, $this->_periodNum); $baseInfo = CalcCache::getUserInfo($userId, $this->_periodNum); $result = [ 'ID' => SnowFake::instance()->generateId(), 'USER_ID' => $userId, 'LAST_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_EMP_LV' => $baseInfo['EMP_LV'], 'LAST_STATUS' => $baseInfo['STATUS'], 'FX_AMOUNT_CASH' => $data['FX_AMOUNT_CASH'], 'PV_PCS' => $data['PV_PCS'], 'PV_PSS' => $data['PV_PSS'], 'PV_PCS_ZC' => $data['PV_PCS_ZC'], 'PV_PCS_YH' => $data['PV_PCS_YH'], 'PV_PCS_ZG' => $data['PV_PCS_ZG'], 'PV_PCS_LS' => $data['PV_PCS_LS'], 'PV_PCS_FX' => $data['PV_PCS_FX'], 'PV_PCS_FX_CASH' => $data['PV_PCS_FX_CASH'], 'PV_PCS_FX_POINT' => $data['PV_PCS_FX_POINT'], 'PV_1L' => $data['PV_1L'], 'PV_1L_TOUCH' => $data['PV_1L_TOUCH'], 'PV_1L_ZC' => $data['PV_1L_ZC'], 'PV_1L_YH' => $data['PV_1L_YH'], 'PV_1L_ZG' => $data['PV_1L_ZG'], 'PV_1L_LS' => $data['PV_1L_LS'], 'PV_1L_FX' => $data['PV_1L_FX'], 'PV_2L' => $data['PV_2L'], 'PV_2L_TOUCH' => $data['PV_2L_TOUCH'], 'PV_2L_ZC' => $data['PV_2L_ZC'], 'PV_2L_YH' => $data['PV_2L_YH'], 'PV_2L_ZG' => $data['PV_2L_ZG'], 'PV_2L_LS' => $data['PV_2L_LS'], 'PV_2L_FX' => $data['PV_2L_FX'], 'PV_3L' => $data['PV_3L'], 'PV_3L_TOUCH' => $data['PV_3L_TOUCH'], 'PV_3L_ZC' => $data['PV_3L_ZC'], 'PV_3L_YH' => $data['PV_3L_YH'], 'PV_3L_ZG' => $data['PV_3L_ZG'], 'PV_3L_LS' => $data['PV_3L_LS'], 'PV_3L_FX' => $data['PV_3L_FX'], 'PV_4L' => $data['PV_4L'], 'PV_4L_TOUCH' => $data['PV_4L_TOUCH'], 'PV_4L_ZC' => $data['PV_4L_ZC'], 'PV_4L_YH' => $data['PV_4L_YH'], 'PV_4L_ZG' => $data['PV_4L_ZG'], 'PV_4L_LS' => $data['PV_4L_LS'], 'PV_4L_FX' => $data['PV_4L_FX'], 'PV_5L' => $data['PV_5L'], 'PV_5L_TOUCH' => $data['PV_5L_TOUCH'], 'PV_5L_ZC' => $data['PV_5L_ZC'], 'PV_5L_YH' => $data['PV_5L_YH'], 'PV_5L_ZG' => $data['PV_5L_ZG'], 'PV_5L_LS' => $data['PV_5L_LS'], 'PV_5L_FX' => $data['PV_5L_FX'], 'PV_LS_TOUCH' => $data['PV_LS_TOUCH'], 'SURPLUS_1L' => $data['SURPLUS_1L'], 'SURPLUS_2L' => $data['SURPLUS_2L'], 'SURPLUS_3L' => $data['SURPLUS_3L'], 'SURPLUS_4L' => $data['SURPLUS_4L'], 'SURPLUS_5L' => $data['SURPLUS_5L'], 'SURPLUS_LS' => $data['SURPLUS_LS'], 'PERIOD_NUM' => $this->_periodNum, 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), ]; unset($data); return $result; } /** * 本月业绩 * @param $userId * @return array */ public function nowMonthPerfData($userId){ $data = CalcCache::nowMonthPerf($userId, $this->_periodNum); $baseInfo = CalcCache::getUserInfo($userId, $this->_periodNum); $result = [ 'ID' => SnowFake::instance()->generateId(), 'USER_ID' => $userId, 'LAST_DEC_LV' => $baseInfo['DEC_LV'], 'LAST_EMP_LV' => $data['EMP_LEVEL'], 'LAST_STATUS' => $baseInfo['STATUS'], 'FX_AMOUNT_CASH' => $data['FX_AMOUNT_CASH'], 'PV_PCS' => $data['PV_PCS'], 'PV_PCS_FX' => $data['PV_PCS_FX'], 'PV_PSS' => $data['PV_PSS'], 'PV_1L' => $data['PV_1L'], 'PV_2L' => $data['PV_2L'], 'PV_3L' => $data['PV_3L'], 'PV_4L' => $data['PV_4L'], 'PV_5L' => $data['PV_5L'], 'VIP_PV_1L_ZC' => $data['VIP_PV_1L_ZC'], 'VIP_PV_2L_ZC' => $data['VIP_PV_2L_ZC'], 'VIP_PV_3L_ZC' => $data['VIP_PV_3L_ZC'], 'VIP_PV_4L_ZC' => $data['VIP_PV_4L_ZC'], 'VIP_PV_5L_ZC' => $data['VIP_PV_5L_ZC'], 'PV_1L_TOTAL' => $data['PV_1L_TOTAL'], 'PV_2L_TOTAL' => $data['PV_2L_TOTAL'], 'PV_3L_TOTAL' => $data['PV_3L_TOTAL'], 'PV_4L_TOTAL' => $data['PV_4L_TOTAL'], 'PV_5L_TOTAL' => $data['PV_5L_TOTAL'], 'PV_PSS_TOTAL' => $data['PV_PSS_TOTAL'], 'CF_PERCENT' => $data['CF_PERCENT'], 'LX_PERCENT' => $data['LX_PERCENT'], 'FX_STATUS' => $data['FX_STATUS'], 'CALC_MONTH' => $this->_calcYearMonth, 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH), 'CREATED_AT' => Date::nowTime(), ]; unset($data); return $result; } /** * 循环父级并执行回调函数 * @param $userId * @param callable $callbackFunc * @param int $offset * @return bool */ public function loopNetworkParentDo($userId, callable $callbackFunc, int $offset = 0) { $allParents = Cache::getAllNetworkParents($userId); $allData = array_slice($allParents, $offset, $this->_limit); unset($allParents); if ($allData) { foreach ($allData as $data) { $funcResult = $callbackFunc($data); if ($funcResult === self::LOOP_FINISH) { return true; } elseif ($funcResult === self::LOOP_CONTINUE) { continue; } unset($data, $funcResult); } unset($allData); return $this->loopNetworkParentDo($userId, $callbackFunc, $offset + $this->_limit); } return true; } /** * 循环推荐网络的父级 * @param $userId * @param callable $callbackFunc * @param int $offset * @return bool */ public function loopRelationParentDo($userId, callable $callbackFunc, int $offset = 0) { $allParents = Cache::getAllRelationParents($userId); $allData = array_slice($allParents, $offset, $this->_limit); unset($allParents); if ($allData) { foreach ($allData as $data) { $funcResult = $callbackFunc($data); if ($funcResult === self::LOOP_FINISH) { return true; } elseif ($funcResult === self::LOOP_CONTINUE) { continue; } unset($data, $funcResult); } unset($allData); return $this->loopRelationParentDo($userId, $callbackFunc, $offset + $this->_limit); } return true; } /** * ==== 聘级计算开始 ==== */ /** * 查看会员聘级 * @param $userId * @param $nowMonthPerf * @param $userEmpLevelId * @return bool|mixed|\yii\db\ActiveRecord */ public function checkEmpLevel($userId, $nowMonthPerf, $userEmpLevelId) { $empLevel = $this->_empLevelConfig; $userEmpLevel = $empLevel[$userEmpLevelId]; $userEmpLevelSort = $userEmpLevel['SORT'] ?? EmployLevel::EMP_LEVEL_SORT['NO_LEVEL']; $childEmpLevelNumArr = CalcCache::hasEmpLevelNum($userId, $this->_periodNum); // 判断主任到首席总监 $resultLevel = $this->isEmpLevelOther($empLevel, $childEmpLevelNumArr, $userEmpLevelSort); unset($empLevel, $childEmpLevelNumArr); if( empty($resultLevel) ) { //不降级 if ( $userEmpLevelSort < EmployLevel::EMP_LEVEL_SORT['JX_ZR_LEVEL'] ) { //主任 if ($checkLevel = $this->isEmpLevel1($userId, $nowMonthPerf)) { $resultLevel = $checkLevel; } else {// 无聘级会员 $resultLevel = EmployLevel::getLevelFromSort(EmployLevel::EMP_LEVEL_SORT['NO_LEVEL']); } }else { $resultLevel = $userEmpLevel; } } unset($userEmpLevel, $userEmpLevelSort); // 获取到级别以后,给上级的相应人数中追加数量 $parentRecUserId = $userId; $this->loopRelationParentDo($userId, function ($parent) use ($resultLevel, &$parentRecUserId) { if( !$parentRecUserId ) return self::LOOP_FINISH; //判断$parentRecUserId是否为$parent['PARENT_UID']的直推 $parentUid = $parent['PARENT_UID']; $toInfo = CalcCache::getUserInfo($parentRecUserId, $this->_periodNum); if( !isset($toInfo['REC_UID']) ) { echo $parentRecUserId . PHP_EOL; } if( isset($toInfo['REC_UID']) && $parentUid !== $toInfo['REC_UID'] ) { $parentUid = $toInfo['REC_UID']; } unset($toInfo); if( !$parentUid ) CalcCache::hasEmpLevelNum($parentUid, $this->_periodNum, [$parentRecUserId => [$resultLevel['ID'] => 1]]); //每次记录上次的USER_ID $parentRecUserId = $parentUid; }); return $resultLevel; } /** * 是否达到主任 * @param $userId * @param $nowMonthPerf * @return bool|mixed|\yii\db\ActiveRecord * @throws \yii\db\Exception */ public function isEmpLevel1($userId, $nowMonthPerf) { $level1Option = EmployLevel::getLevelFromSort(EmployLevel::EMP_LEVEL_SORT['JX_ZR_LEVEL']); //条件去除最大部门,其它部门累计50万 if( $nowMonthPerf['PV_PSS_TOTAL'] < $level1Option['OTHER_DEPART_PERF'] ) {//本身业绩就小于50万 unset($level1Option); return false; } $oneDeepRelation = CalcCache::getChildrenOneDeepFromRedis($userId, $this->_periodNum); if ( count($oneDeepRelation) <= 1 ) {//只有一个区就不判断了 unset($oneDeepRelation, $level1Option); return false; } $maxPvPSS = 0; $childPvPssTotalSum = 0; foreach ($oneDeepRelation as $childData) { //往期业绩 $userLastPerf = CalcCache::userPerf($childData['USER_ID'], $this->_periodNum); //本期业绩 $periodPerf = CalcCache::nowPeriodPerf($childData['USER_ID'], $this->_periodNum); $pvPcsTotal = $userLastPerf['PV_PCS_ZC'] + $userLastPerf['PV_PCS_FX'] + $periodPerf['PV_PCS']; $pvPssTotal = $userLastPerf['PV_PSS_TOTAL'] + $periodPerf['PV_PSS']; $childPvPssTotal = $pvPcsTotal + $pvPssTotal; unset($userLastPerf, $periodPerf, $pvPcsTotal, $pvPssTotal); $childPvPssTotalSum += $childPvPssTotal; if( $childPvPssTotal >= $maxPvPSS ) { $maxPvPSS = $childPvPssTotal; } unset($childData, $childPvPssTotal); } unset($oneDeepRelation); if( $childPvPssTotalSum - $maxPvPSS >= $level1Option['OTHER_DEPART_PERF'] ) { unset($maxPvPSS, $childPvPssTotalSum); return $level1Option; }else { unset($maxPvPSS, $childPvPssTotalSum, $level1Option); return false; } } /** * 是否达到其他级别 * @param $empLevel * @param $childEmpLevelNumArr * @param $userEmpLevelSort * @return bool|mixed|\yii\db\ActiveRecord */ public function isEmpLevelOther($empLevel, $childEmpLevelNumArr, $userEmpLevelSort) { $resultLevel = []; foreach ($empLevel as $level) { if ($level['SORT'] < EmployLevel::EMP_LEVEL_SORT['JX_ZR_LEVEL']) continue; //不降级 if ($level['SORT'] <= $userEmpLevelSort) continue; // 级别要求有几个区 $locationNum = $level['LOCATION_NUM']; // 级别要求这几个区分别存在级别会员的数量 $minEmpNum = $level['MIN_EMPLOY_NUM']; $minEmpLevel = $level['MIN_EMPLOY_LEVEL']; if( !$minEmpLevel || !isset($empLevel[$minEmpLevel]) || $minEmpNum < 1 ) continue; $minEmpLevelSort = $empLevel[$minEmpLevel]['SORT']; $resultEmpLevelNumArr = array_filter($childEmpLevelNumArr, function ($item, $departUserId) use ($empLevel, $minEmpLevelSort, $minEmpNum) { $tempEmpLevelNum = 0; foreach ($item as $levelIndex => $levelNum) { if ($empLevel[$levelIndex]['SORT'] >= $minEmpLevelSort && $levelNum >= $minEmpNum) { $tempEmpLevelNum += 1; } } return $tempEmpLevelNum >= 1; }, ARRAY_FILTER_USE_BOTH); if (count($resultEmpLevelNumArr) >= $locationNum) { if( $level['SORT'] == EmployLevel::EMP_LEVEL_SORT['SHX_ZJ_LEVEL'] ) { //首席总监还要满足一个条件、任意部门1个高级总监 $gjZjLevelNumArr = array_filter($childEmpLevelNumArr, function ($item, $departUserId) use ($empLevel) { $tempEmpLevelNum = 0; foreach ($item as $levelIndex => $levelNum) { if ($empLevel[$levelIndex]['SORT'] >= EmployLevel::EMP_LEVEL_SORT['GJ_ZJ_LEVEL'] && $levelNum >= 1) { $tempEmpLevelNum += 1; } } return $tempEmpLevelNum >= 1; }, ARRAY_FILTER_USE_BOTH); if( count($gjZjLevelNumArr) >= 1 ) { $resultLevel = $level; } unset($gjZjLevelNumArr); }else { $resultLevel = $level; } } unset($level, $minEmpLevel, $minEmpLevelSort, $resultEmpLevelNumArr); } unset($empLevel, $childEmpLevelNumArr, $userEmpLevelSort); return $resultLevel; } /** * 是否可拿业绩(即注销、关停、停发状态) * @param $userId * @return bool */ public function isHasPerf($userId) { //@todo 所有人都有业绩 return true; } /** * ==== 聘级计算结束 ==== */ /** * 更新百分比并发送 * @param $percent */ private function _updatePercent($percent) { // 把数据写入数据库中 Period::updateAll(['PERF_PERCENT' => $percent], 'PERIOD_NUM=:PERIOD_NUM', [':PERIOD_NUM' => $this->_periodNum]); \Yii::$app->swooleAsyncTimer->pushAsyncPercentToAdmin($percent, ['MODEL' => 'PERIOD', 'ID' => $this->_periodId, 'FIELD' => 'PERF_PERCENT']); } }