Browse Source

车房奖拆分

kevin_zhangl 3 years ago
parent
commit
0b1c9455ce

+ 1 - 0
backendApi/modules/v1/controllers/UserController.php

@@ -887,6 +887,7 @@ class UserController extends BaseController
             $userInfo['EXCHANGE_POINTS'] = Balance::getBalanceExchangePoints($userInfo['ID']);
             $userInfo['TOURISM_POINTS'] = Balance::getAccountBalance($userInfo['ID'], 'tourism_points');
             $userInfo['GARAGE_POINTS'] = Balance::getAccountBalance($userInfo['ID'], 'garage_points');
+            $userInfo['VILLA_POINTS'] = Balance::getAccountBalance($userInfo['ID'], 'villa_points');
             return static::notice($userInfo);
         }else{
             return static::notice('Member number does not exist', 400);//会员编号不存在

+ 1 - 1
backendEle/src/views/bonus/resend-qy-audit-list.vue

@@ -91,7 +91,7 @@ export default {
       baseDecLevels: baseInfo.decLevels(),
       baseEmpLevels: baseInfo.empLevels(),
       filterStatus:'0',
-      auditStatus: ['未审核', '已审核', '已拒绝'],
+      auditStatus: ['not approved', 'Audited', 'Refused'],// 未审核 已审核 已拒绝
     }
   },
   methods: {

+ 9 - 2
backendEle/src/views/config/bonus-opt.vue

@@ -199,7 +199,7 @@
                 </el-input>
               </template>
             </el-table-column>
-            <el-table-column label="车奖比例">
+            <el-table-column label="车奖比例">
               <template slot-scope="scope">
                 <el-input v-model="scope.row.GARAGE_PERCENT" min="0" max="100">
                   <template slot="append">%</template>
@@ -244,13 +244,20 @@
                               </el-input>
                           </template>
                       </el-table-column>
-                      <el-table-column label="车奖比例">
+                      <el-table-column label="车奖比例">
                           <template slot-scope="scope">
                               <el-input v-model="scope.row.GARAGE_PERCENT" min="0" max="100">
                                   <template slot="append">%</template>
                               </el-input>
                           </template>
                       </el-table-column>
+                      <el-table-column label="房奖比例">
+                          <template slot-scope="scope">
+                              <el-input v-model="scope.row.VILLA_PERCENT" min="0" max="100">
+                                  <template slot="append">%</template>
+                              </el-input>
+                          </template>
+                      </el-table-column>
                   </el-table>
               </div>
               <div class="panel-footer">

+ 1 - 1
backendEle/src/views/finance/perf-audit-list.vue

@@ -206,7 +206,7 @@
           SURPLUS_5L: null,
         },
 
-        auditStatus: ['未审核', '已审核', '已拒绝'],
+        auditStatus: ['not approved', 'Audited', 'Refused'],// 未审核 已审核 已拒绝
       }
     },
     methods: {

+ 5 - 1
common/config/params.php

@@ -215,7 +215,11 @@ return [
         ],
         'garage_points' => [
             'name' => 'garage_points',
-            'label' => 'Car/Villa points balance',//车房积分余额
+            'label' => 'Car points balance',//名车积分余额
+        ],
+        'villa_points' => [
+            'name' => 'villa_points',
+            'label' => 'Villa points balance',//豪宅积分余额
         ],
     ],
     'auditStatus' => [

+ 186 - 43
common/helpers/bonus/BonusCalc.php

@@ -31,6 +31,7 @@ use common\models\CalcBonusQY;
 use common\models\CalcBonusStandard;
 use common\models\CalcBonusTG;
 use common\models\CalcBonusTourism;
+use common\models\CalcBonusVilla;
 use common\models\CalcBonusVIP;
 use common\models\CalcBonusXF;
 use common\models\CalcBonusYC;
@@ -303,9 +304,14 @@ class BonusCalc extends BaseObject {
 //            echo('计算旅游奖' . ($this->_sysConfig['openTourism']['VALUE'] ? '完成' : '关闭') . ',耗时:' . round($t21 - $t20, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL);
 //            $this->_updatePercent(68);
 
-            $this->calcBonusGarage();
+            $this->calcBonusVilla();
             $t22 = microtime(true);
-            echo('计算车房奖' . ($this->_sysConfig['openGarage']['VALUE'] ? '完成' : '关闭').',耗时:' . round($t22 - $t21, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL . PHP_EOL);
+            echo('计算房奖' . ($this->_sysConfig['openVilla']['VALUE'] ? '完成' : '关闭').',耗时:' . round($t22 - $t21, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL . PHP_EOL);
+            $this->_updatePercent(69);
+
+            $this->calcBonusGarage();
+            $t23 = microtime(true);
+            echo('计算车奖' . ($this->_sysConfig['openGarage']['VALUE'] ? '完成' : '关闭').',耗时:' . round($t23 - $t22, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL . PHP_EOL);
             $this->_updatePercent(69);
 
 
@@ -347,7 +353,7 @@ class BonusCalc extends BaseObject {
             echo('结算全部完成,共耗时:' . round($t35 - $t34, 3) . ',内存使用:' . (round(memory_get_usage() / 1024 / 1024, 3)) . 'MB' . PHP_EOL . PHP_EOL);
         } catch (\Exception $e) {
             $this->errorCalcTask();
-            $this->addError('calc', $e->getFile() . '  ' . $e->getLine() . '  ' . $e->getMessage());
+            $this->addError('calc', sprintf('File【%s】, Line【%s】, Msg【%s】', $e->getFile(), $e->getLine(), $e->getMessage()));
             return false;
         }
         return true;
@@ -449,6 +455,7 @@ class BonusCalc extends BaseObject {
             ScoreMonth::pageDeleteAll('PERIOD_NUM='.$this->_periodNum);
             CalcBonusTourism::pageDeleteAll('PERIOD_NUM='.$this->_periodNum);
             CalcBonusGarage::pageDeleteAll('PERIOD_NUM='.$this->_periodNum);
+            CalcBonusVilla::pageDeleteAll('PERIOD_NUM='.$this->_periodNum);
         }
     }
 
@@ -1662,14 +1669,13 @@ class BonusCalc extends BaseObject {
         $mate = $bonusConfig['VALUE'] / 100;
         // 会员级别
         $minDecLevel = $config['OPTIONS']['declarationLevel'] ?? [];
-        // 会员聘级
-        $minEmpLevel = $config['OPTIONS']['employLevel'] ?? [];
-
         // 月度公司总PV
         $monthTotalPV = PerfMonth::find()
             ->yearMonth($this->_calcYearMonth)
             ->where('CALC_MONTH=:CALC_MONTH', [':CALC_MONTH' => $this->_calcYearMonth])
             ->sum('PV_PCS');
+        // 用于分发的奖金总数
+        $transferAmount = $monthTotalPV * $mate;
 
         // 基于蓝星奖结果计算符合获奖条件的会员StarDirector
         $userStarDirector = CalcBonusBS::find()
@@ -1694,6 +1700,8 @@ class BonusCalc extends BaseObject {
         // 合并用户ID,去重
         $bonusUsers = array_unique(array_merge(array_keys($userStarDirectorObj), array_keys($userStarCrownObj)));
 
+        // 奖金点数综合
+        $bonusPointComplex = 0;
         $insertBonusData = [];
         foreach($bonusUsers as $userId) {
             // 计算奖金:取starDirectorPoint和startCrownPoint的大个值
@@ -1701,47 +1709,163 @@ class BonusCalc extends BaseObject {
             $startCrownPoint = $this->_starCrownLevelConfig[$userStarCrownObj[$userId]['LAST_STAR_LV']]['TOURISM_PERCENT'] ?? 0;
             // 奖金比例:
             $bonusPoint = max($starDirectorPoint, $startCrownPoint);
-            // 计算奖金
-            $amount = Tool::formatPrice(($monthTotalPV * $mate * $bonusPoint) / 100);
-            if ($amount <= 0) {
-                continue;
-            }
-
-            // 会员级别+聘级都达到要求才会发放奖金
-            if (in_array($userStarDirectorObj[$userId]['LAST_DEC_LV'], $minDecLevel)) {
-                // 放入缓存
-                CalcCache::tourismBonus($userId, $this->_periodNum, $amount);
-                // 加入月奖的会员
-                CalcCache::addHasMonthBonusUsers($userId, $this->_periodNum);
-            }
 
             $insertBonusData[] = [
                 'ID' => SnowFake::instance()->generateId(),
                 'USER_ID' => $userId,
-                'LEVEL_ID' => $userStarDirectorObj[$userId]['LEVEL_ID'],
                 'LAST_DEC_LV' => $userStarDirectorObj[$userId]['LAST_DEC_LV'],
                 'LAST_EMP_LV' => $userStarDirectorObj[$userId]['LAST_EMP_LV'],
                 'LAST_STATUS' => $userStarDirectorObj[$userId]['LAST_STATUS'],
                 'LAST_STAR_LV' => $userStarCrownObj[$userId]['LAST_STAR_LV'],
-                'AMOUNT_STANDARD' => $amount,
+                'AMOUNT_STANDARD' => 0,
                 'POINT' => $bonusPoint,
                 'PERIOD_NUM' => $this->_periodNum,
                 'CALC_YEAR' => $this->_calcYear,
                 'CALC_MONTH' => $this->_calcYearMonth,
                 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH),
                 'CREATED_AT' => Date::nowTime(),
+                'PERF' => $monthTotalPV,
+                'TRANSFER_RATE' => $mate,
+                'TRANSFER_AMOUNT' => Tool::formatPrice($transferAmount),
+                'CAP_AMOUNT' => 0,
+                'POINT_COMPLEX' => 0,
             ];
+
+            $bonusPointComplex += $bonusPoint;
         }
 
         // 数据写入总表
         if ($insertBonusData) {
+            foreach ($insertBonusData as &$bonusData) {
+                // 计算奖金
+                $amount = Tool::formatPrice($transferAmount * ($bonusData['POINT'] / $bonusPointComplex));
+                if ($amount <= 0) {
+                    continue;
+                }
+
+                // 会员级别达到要求才会发放奖金
+                if ($bonusData['LAST_DEC_LV'] == $minDecLevel) {
+                    // 放入缓存
+                    CalcCache::tourismBonus($bonusData['USER_ID'], $this->_periodNum, $amount);
+                    // 加入月奖的会员
+                    CalcCache::addHasMonthBonusUsers($bonusData['USER_ID'], $this->_periodNum);
+                }
+
+                $bonusData['AMOUNT'] = $amount;
+                $bonusData['POINT_COMPLEX'] = $bonusPointComplex;
+            }
+
             CalcBonusTourism::batchInsert($insertBonusData);
         }
 
         return true;
     }
 
-    // 执行车房奖的计算
+    // 执行房奖的计算
+    public function calcBonusVilla() {
+        // 月结,如果不是月结点,则直接退出
+        if (!$this->_isCalcMonth) {
+            return true;
+        }
+
+        $bonusConfig = $this->_sysConfig['openVilla'];
+        // 达标条件:聘级、级别、奖项比例
+        $config = json_decode($bonusConfig['OPTIONS'], true);
+        // 奖金总比例
+        $mate = $bonusConfig['VALUE'] / 100;
+        // 个人奖金封顶
+        $capBonus = intval($this->_sysConfig['openVillaCap']['VALUE'] ?? 0);
+        // 会员级别
+        $minDecLevel = $config['declarationLevel'] ?? [];
+
+        // 月度公司总PV
+        $monthTotalPV = PerfMonth::find()
+            ->yearMonth($this->_calcYearMonth)
+            ->where('CALC_MONTH=:CALC_MONTH', [':CALC_MONTH' => $this->_calcYearMonth])
+            ->sum('PV_PCS');
+        // 用于分发的奖金总数
+        $transferAmount = $monthTotalPV * $mate;
+
+        // 基于团队奖/绩效奖结果计算会员的StarCrown.StarCrown基于周期计算,一个月会产生多次,取月周期中的最高星级
+        $subQuery = CalcBonusQY::find()
+            ->yearMonth($this->_calcYearMonth)
+            ->where('CALC_MONTH = :CALC_MONTH AND LAST_STAR_LV <> :NO_STAR_LV', [':CALC_MONTH' => $this->_calcYearMonth, ':NO_STAR_LV' => StarCrownLevel::NO_LEVEL_ID])
+            ->select('USER_ID,LAST_DEC_LV,LAST_EMP_LV,LAST_STAR_LV,LAST_STATUS,LEVEL_NAME,SORT')
+            ->joinWith(['starCrown' => function($query) {
+                $query->select(['LEVEL_NAME', 'SORT']);
+            }])
+            ->having(1)
+            ->orderBy('USER_ID ASC, SORT DESC');
+        $userStarCrownObj = (new Query())->from(['u' => $subQuery])->select('USER_ID,LAST_DEC_LV,LAST_EMP_LV,LAST_STAR_LV,LAST_STATUS,LEVEL_NAME,SORT')->groupBy('USER_ID')->indexBy('USER_ID')->all();
+
+        // 奖金点数综合
+        $bonusPointComplex = 0;
+        $insertBonusData = [];
+        foreach($userStarCrownObj as $item) {
+            // 奖金比例
+            $bonusPoint = $this->_starCrownLevelConfig[$item['LAST_STAR_LV']]['VILLA_PERCENT'] ?? 0;
+            if (!$bonusPoint) {
+                continue;
+            }
+
+            $insertBonusData[] = [
+                'ID' => SnowFake::instance()->generateId(),
+                'USER_ID' => $item['USER_ID'],
+                'LAST_DEC_LV' => $item['LAST_DEC_LV'],
+                'LAST_EMP_LV' => $item['LAST_EMP_LV'],
+                'LAST_STATUS' => $item['LAST_STATUS'],
+                'LAST_STAR_LV' => $item['LAST_STAR_LV'],
+                'AMOUNT' => 0,
+                'POINT' => $bonusPoint,
+                'PERIOD_NUM' => $this->_periodNum,
+                'CALC_YEAR' => $this->_calcYear,
+                'CALC_MONTH' => $this->_calcYearMonth,
+                'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH),
+                'CREATED_AT' => Date::nowTime(),
+                'PERF' => $monthTotalPV,
+                'TRANSFER_RATE' => $mate,
+                'TRANSFER_AMOUNT' => Tool::formatPrice($transferAmount),
+                'CAP_AMOUNT' => 0,
+                'POINT_COMPLEX' => 0,
+            ];
+
+            $bonusPointComplex += $bonusPoint;
+        }
+
+        // 数据写入总表
+        if ($insertBonusData) {
+            // 计算个人奖金
+            foreach ($insertBonusData as &$bonusData) {
+                // 计算奖金
+                $amount = Tool::formatPrice($transferAmount * ($bonusData['POINT'] / $bonusPointComplex));
+                if ($amount <= 0) {
+                    continue;
+                }
+                // 封顶前奖金数
+                $capAmount = $amount;
+                // 奖金数不能大于封顶值
+                $amount = ($amount > $capBonus) ? $capBonus : $amount;
+
+                // 会员级别达到要求才会发放奖金
+                if ($bonusData['LAST_DEC_LV'] == $minDecLevel) {
+                    // 放入缓存
+                    CalcCache::villaBonus($bonusData['USER_ID'], $this->_periodNum, $amount);
+                    // 加入月奖的会员
+                    CalcCache::addHasMonthBonusUsers($bonusData['USER_ID'], $this->_periodNum);
+                }
+
+                $bonusData['AMOUNT'] = $amount;
+                $bonusData['CAP_AMOUNT'] = $capAmount;
+                $bonusData['POINT_COMPLEX'] = $bonusPointComplex;
+            }
+
+            CalcBonusVilla::batchInsert($insertBonusData);
+        }
+
+        return true;
+    }
+
+    // 执行车奖的计算
     public function calcBonusGarage() {
         // 月结,如果不是月结点,则直接退出
         if (!$this->_isCalcMonth) {
@@ -1754,9 +1878,7 @@ class BonusCalc extends BaseObject {
         // 奖金总比例
         $mate = $bonusConfig['VALUE'] / 100;
         // 会员级别
-        $minDecLevel = $config['OPTIONS']['declarationLevel'] ?? [];
-        // 会员聘级
-        $minEmpLevel = $config['OPTIONS']['employLevel'] ?? [];
+        $minDecLevel = $config['declarationLevel'] ?? [];
         // 个人奖金封顶
         $capBonus = intval($this->_sysConfig['openGarageCap']['VALUE'] ?? 0);
 
@@ -1765,6 +1887,8 @@ class BonusCalc extends BaseObject {
             ->yearMonth($this->_calcYearMonth)
             ->where('CALC_MONTH=:CALC_MONTH', [':CALC_MONTH' => $this->_calcYearMonth])
             ->sum('PV_PCS');
+        // 用于分发的奖金总数
+        $transferAmount = $monthTotalPV * $mate;
 
         // 基于蓝星奖结果计算符合获奖条件的会员StarDirector
         $userStarDirector = CalcBonusBS::find()
@@ -1792,6 +1916,8 @@ class BonusCalc extends BaseObject {
         $bonusUsers = array_unique(array_merge(array_keys($userStarDirectorObj), array_keys($userStarCrownObj)));
         sort($bonusUsers);
 
+        // 奖金点数综合
+        $bonusPointComplex = 0;
         $insertBonusData = [];
         foreach($bonusUsers as $userId) {
             // 计算奖金:取starDirectorPoint和startCrownPoint的大个值
@@ -1799,42 +1925,57 @@ class BonusCalc extends BaseObject {
             $startCrownPoint = !isset($userStarCrownObj[$userId]['LAST_STAR_LV']) ? 0: ($this->_starCrownLevelConfig[$userStarCrownObj[$userId]['LAST_STAR_LV']]['GARAGE_PERCENT'] ?? 0);
             // 奖金比例:
             $bonusPoint = max($starDirectorPoint, $startCrownPoint);
-            // 计算奖金
-            $amount = Tool::formatPrice(($monthTotalPV * $mate * $bonusPoint) / 100);
-            if ($amount <= 0) {
-                continue;
-            }
-            // 奖金数不能大于封顶值
-            $amount = ($amount > $capBonus) ? $capBonus : $amount;
-
-            // 会员级别+聘级都达到要求才会发放奖金
-            if (isset($userStarDirectorObj[$userId]) && in_array($userStarDirectorObj[$userId]['LAST_DEC_LV'], $minDecLevel)) {
-                // 放入缓存
-                CalcCache::garageBonus($userId, $this->_periodNum, $amount);
-                // 加入月奖的会员
-                CalcCache::addHasMonthBonusUsers($userId, $this->_periodNum);
-            }
 
             $insertBonusData[] = [
                 'ID' => SnowFake::instance()->generateId(),
                 'USER_ID' => $userId,
-                'LEVEL_ID' => $userStarDirectorObj[$userId]['LEVEL_ID'] ?? '',
                 'LAST_DEC_LV' => $userStarDirectorObj[$userId]['LAST_DEC_LV'] ?? ($userStarCrownObj[$userId]['LAST_DEC_LV'] ?? ''),
                 'LAST_EMP_LV' => $userStarDirectorObj[$userId]['LAST_EMP_LV'] ?? ($userStarCrownObj[$userId]['LAST_EMP_LV'] ?? ''),
                 'LAST_STATUS' => $userStarDirectorObj[$userId]['LAST_STATUS'] ?? ($userStarCrownObj[$userId]['LAST_STATUS'] ?? 1),
                 'LAST_STAR_LV' => $userStarCrownObj[$userId]['LAST_STAR_LV'] ?? '',
-                'AMOUNT' => $amount,
+                'AMOUNT' => 0,
                 'POINT' => $bonusPoint,
                 'PERIOD_NUM' => $this->_periodNum,
                 'CALC_YEAR' => $this->_calcYear,
                 'CALC_MONTH' => $this->_calcYearMonth,
                 'P_CALC_MONTH' => Date::ociToDate($this->_calcYearMonth, Date::OCI_TIME_FORMAT_SHORT_MONTH),
                 'CREATED_AT' => Date::nowTime(),
+                'PERF' => $monthTotalPV,
+                'TRANSFER_RATE' => $mate,
+                'TRANSFER_AMOUNT' => Tool::formatPrice($transferAmount),
+                'CAP_AMOUNT' => 0,
+                'POINT_COMPLEX' => 0,
             ];
+
+            $bonusPointComplex += $bonusPoint;
         }
 
         // 数据写入总表
         if ($insertBonusData) {
+            foreach ($insertBonusData as &$bonusData) {
+                // 计算奖金
+                $amount = Tool::formatPrice($transferAmount * ($bonusData['POINT'] / $bonusPointComplex));
+                if ($amount <= 0) {
+                    continue;
+                }
+                // 封顶前奖金数
+                $capAmount = $amount;
+                // 奖金数不能大于封顶值
+                $amount = ($amount > $capBonus) ? $capBonus : $amount;
+
+                // 会员级别达到要求才会发放奖金
+                if ($bonusData['LAST_DEC_LV'] == $minDecLevel) {
+                    // 放入缓存
+                    CalcCache::garageBonus($bonusData['USER_ID'], $this->_periodNum, $amount);
+                    // 加入月奖的会员
+                    CalcCache::addHasMonthBonusUsers($bonusData['USER_ID'], $this->_periodNum);
+                }
+
+                $bonusData['AMOUNT'] = $amount;
+                $bonusData['CAP_AMOUNT'] = $capAmount;
+                $bonusData['POINT_COMPLEX'] = $bonusPointComplex;
+            }
+
             CalcBonusGarage::batchInsert($insertBonusData);
         }
 
@@ -3499,6 +3640,7 @@ class BonusCalc extends BaseObject {
         $perfData = CalcCache::nowPeriodPerf($userId, $this->_periodNum);
         $tourismBonus = CalcCache::tourismBonus($userId, $this->_periodNum);
         $garageBonus = CalcCache::garageBonus($userId, $this->_periodNum);
+        $villaBonus = CalcCache::villaBonus($userId, $this->_periodNum);
         $empLv = $baseInfo['EMP_LV'];
 //        if($this->_isCalcMonth){
 //            $empLv = $this->nowMonthPerfData($userId)['LAST_EMP_LV'];
@@ -3675,7 +3817,8 @@ class BonusCalc extends BaseObject {
             'ORI_CAPPED_BONUS_QY' => $bonus['ORI_CAPPED_BONUS_QY'], // 团队奖封顶前的奖金
 
             'BONUS_TOURISM' => $tourismBonus, // 旅游奖
-            'BONUS_GARAGE' => $garageBonus, // 车房奖
+            'BONUS_VILLA' => $villaBonus, // 房奖
+            'BONUS_GARAGE' => $garageBonus, // 车奖
 
             //以下没有用
             'BONUS_FW' => 0,

+ 14 - 2
common/helpers/bonus/BonusSend.php

@@ -192,7 +192,7 @@ class BonusSend extends BaseObject {
             echo('全部奖金发放完成,耗时:'.round($t7 - $t1, 3).',内存使用:'.(round(memory_get_usage()/1024/1024, 3)).'MB'.PHP_EOL);
             $this->_updatePercent(100);
         } catch (\Exception $e) {
-            $this->addError('sendBonus', $e->getMessage());
+            $this->addError('sendBonus', sprintf('File【%s】, Line【%s】, Msg【%s】', $e->getFile(), $e->getLine(), $e->getMessage()));
             return false;
         }
         if (count($this->_errors) > 0) {
@@ -367,7 +367,7 @@ class BonusSend extends BaseObject {
                             'BONUS_ISSUE' => true,
                         ]);
                     }
-                    // 车
+                    // 车奖
                     if ($data['BONUS_GARAGE'] > 0) {
                         Balance::changeUserBonus($data['USER_ID'], 'garage_points', $data['BONUS_GARAGE'], [
                             'CALC_ID' => $data['ID'],
@@ -379,6 +379,18 @@ class BonusSend extends BaseObject {
                             'BONUS_ISSUE' => true,
                         ]);
                     }
+                    // 房奖
+                    if ($data['BONUS_VILLA'] > 0) {
+                        Balance::changeUserBonus($data['USER_ID'], 'villa_points', $data['BONUS_VILLA'], [
+                            'CALC_ID' => $data['ID'],
+                            'REMARK' => 'From Period ' . $periodNum,
+                            'PERIOD_NUM' => $periodNum,
+                            'VILLA_POINTS' => $data['BONUS_VILLA'],
+                            'DEAL_TYPE_ID' => DealType::VILLA_SEND,
+                            'SORT' => $key * 10,
+                            'BONUS_ISSUE' => true,
+                        ]);
+                    }
 
                     //发放重消积分
 //                    if ($data['RECONSUME_POINTS'] > 0) {

+ 22 - 0
common/helpers/bonus/CalcCache.php

@@ -51,6 +51,7 @@ class CalcCache {
     const REDIS_KEY_PREFIX_YC_BONUS = 'calc:yc:bonus_';
     const REDIS_KEY_PREFIX_FW_BONUS = 'calc:fw:bonus_';
     const REDIS_KEY_PREFIX_TOURISM_BONUS = 'calc:tourism:bonus_';
+    const REDIS_KEY_PREFIX_VILLA_BONUS = 'calc:villa:bonus_';
     const REDIS_KEY_PREFIX_GARAGE_BONUS = 'calc:garage:bonus_';
     const REDIS_KEY_PREFIX_HAS_PERF_USER = 'calc:hasPerfUser_';
     const REDIS_KEY_PREFIX_HAS_MONTH_PERF_USER = 'calc:hasMonthPerfUser_';
@@ -1600,6 +1601,27 @@ class CalcCache {
         return $value;
     }
 
+    public static function villaBonus($userId, $periodNum, $bonus = 0.00) {
+        $cacheKey = self::REDIS_KEY_PREFIX_VILLA_BONUS . $periodNum;
+
+        $value = 0.00;
+        if( $bonus > 0 ) {
+            Yii::$app->redis->hset($cacheKey, $userId, $bonus);
+            $value = $bonus;
+            //加入有奖金的会员中
+            self::addHasBonusUsers($userId, $periodNum);
+        }else {
+            $cacheValue = \Yii::$app->redis->hget($cacheKey, $userId);
+            if ($cacheValue) {
+                $value = $cacheValue;
+            }
+            unset($cacheValue);
+        }
+
+        unset($cacheKey, $userId, $periodNum, $bonus);
+        return $value;
+    }
+
     public static function garageBonus($userId, $periodNum, $bonus = 0.00) {
         $cacheKey = self::REDIS_KEY_PREFIX_GARAGE_BONUS . $periodNum;
 

+ 1 - 1
common/helpers/bonus/PerfCalc.php

@@ -192,7 +192,7 @@ class PerfCalc {
             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', $e->getMessage());
+            $this->addError('calc', sprintf('File【%s】, Line【%s】, Msg【%s】', $e->getFile(), $e->getLine(), $e->getMessage()));
             return false;
         }
         return true;

+ 21 - 1
common/helpers/user/Balance.php

@@ -19,6 +19,7 @@ use common\models\FlowGaragePoints;
 use common\models\FlowLX;
 use common\models\FlowReconsumePoints;
 use common\models\FlowTourismPoints;
+use common\models\FlowVillaPoints;
 use common\models\InvoiceFlow;
 use common\models\Period;
 use common\models\DeclarationLevel;
@@ -46,6 +47,7 @@ class Balance {
     const INVOICE_BALANCE_LOCK_KEY = 'Invoice';
     const TOURISM_POINTS_BALANCE_LOCK_KEY = 'tourismPoints';
     const GARAGE_POINTS_BALANCE_LOCK_KEY = 'garagePoints';
+    const VILLA_POINTS_BALANCE_LOCK_KEY = 'villaPoints';
 
     const BALANCE_TYPE = [
         'exchange' => [
@@ -62,10 +64,16 @@ class Balance {
         ],
         'garage_points' => [
             'id'    => 'garage_points',
-            'title' => '车积分',
+            'title' => '车积分',
             'attr'  => 'GARAGE_POINTS',
             'pv'    => false,
         ],
+        'villa_points' => [
+            'id'    => 'villa_points',
+            'title' => '房奖积分',
+            'attr'  => 'VILLA_POINTS',
+            'pv'    => false,
+        ],
     ];
 
     /**
@@ -286,6 +294,9 @@ class Balance {
             case 'GARAGE_POINTS':
                 $lockKey = self::GARAGE_POINTS_BALANCE_LOCK_KEY . $userId;
                 break;
+            case 'VILLA_POINTS':
+                $lockKey = self::VILLA_POINTS_BALANCE_LOCK_KEY . $userId;
+                break;
             default:
                 throw new Exception('流水类型错误');
         }
@@ -353,6 +364,9 @@ class Balance {
                 if (isset($params['GARAGE_POINTS'])) {
                     $paramData['GARAGE_POINTS_TOTAL'] = new Expression('GARAGE_POINTS_TOTAL + '.$params['GARAGE_POINTS']);
                 }
+                if (isset($params['VILLA_POINTS'])) {
+                    $paramData['VILLA_POINTS_TOTAL'] = new Expression('VILLA_POINTS_TOTAL + '.$params['VILLA_POINTS']);
+                }
                 if (isset($params['RECONSUME_POINTS_TOTAL'])) {
                     $paramData['RECONSUME_POINTS_TOTAL'] = new Expression('RECONSUME_POINTS_TOTAL + ' . ($issueBonus ? $params['RECONSUME_POINTS_TOTAL'] * $exchangeRate : $params['RECONSUME_POINTS_TOTAL']));
                     //$oneUserBonusModel->RECONSUME_POINTS_TOTAL += $params['RECONSUME_POINTS_TOTAL'];
@@ -478,6 +492,9 @@ class Balance {
                 if (isset($params['GARAGE_POINTS'])) {
                     $paramData['GARAGE_POINTS_TOTAL'] = $params['GARAGE_POINTS'];
                 }
+                if (isset($params['VILLA_POINTS'])) {
+                    $paramData['VILLA_POINTS_TOTAL'] = $params['VILLA_POINTS'];
+                }
                 if (isset($params['RECONSUME_POINTS_TOTAL'])) {
 //                    $paramData['RECONSUME_POINTS_TOTAL'] = new Expression('RECONSUME_POINTS_TOTAL + '.$params['RECONSUME_POINTS_TOTAL']);
                     $paramData['RECONSUME_POINTS_TOTAL'] = ($issueBonus ? $params['RECONSUME_POINTS_TOTAL'] * $exchangeRate : $params['RECONSUME_POINTS_TOTAL']);
@@ -608,6 +625,9 @@ class Balance {
             } elseif (strtolower($type) == 'garage_points') {
                 $flowInsertData['LAST_STAR_LV'] = $userInfo['LAST_STAR_LV'];
                 FlowGaragePoints::insertOne($flowInsertData);
+            } elseif (strtolower($type) == 'villa_points') {
+                $flowInsertData['LAST_STAR_LV'] = $userInfo['LAST_STAR_LV'];
+                FlowVillaPoints::insertOne($flowInsertData);
             }
 
             unset($flowInsertData, $userInfo, $oneUserBonus);

+ 5 - 1
common/models/BalanceAudit.php

@@ -60,7 +60,11 @@ class BalanceAudit extends \common\components\ActiveRecord
 //        ],
         'garage_points' => [
             'name' => 'garage_points',
-            'label' => 'Car/Villa points',//车房积分
+            'label' => 'Car points',// 车奖积分
+        ],
+        'villa_points' => [
+            'name' => 'villa_points',
+            'label' => 'Villa points',// 房奖积分
         ],
     ];
 

+ 6 - 4
common/models/CalcBonus.php

@@ -105,7 +105,8 @@ use Yii;
  * @property string $BONUS_BS 蓝星奖金(即新的管理奖)
  * @property string $ORI_BONUS_BS 蓝星原奖金(即新的管理奖,原奖金)
  * @property string $BONUS_TOURISM 旅游奖奖金
- * @property string $BONUS_GARAGE 车房奖奖金
+ * @property string $BONUS_VILLA 房奖奖金
+ * @property string $BONUS_GARAGE 车奖奖金
  */
 class CalcBonus extends \common\components\ActiveRecord
 {
@@ -125,7 +126,7 @@ class CalcBonus extends \common\components\ActiveRecord
         return [
             [['USER_ID', 'LAST_USER_NAME', 'LAST_REAL_NAME', 'LAST_MOBILE', 'LAST_SYSTEM_ID','LAST_LOCATION', 'PERIOD_NUM', 'CALC_YEAR', 'CALC_MONTH', 'CALCULATED_AT', 'P_CALC_MONTH', 'CREATED_AT'], 'required'],
             [['LAST_STATUS', 'LAST_PERIOD_AT', 'LAST_CREATED_AT', 'LAST_PROVINCE', 'LAST_CITY', 'LAST_COUNTY', 'LAST_IS_DIRECT_SELLER', 'LAST_LOCATION', 'PERIOD_NUM', 'CALC_YEAR', 'CALC_MONTH', 'CALCULATED_AT', 'IS_SENT', 'SENT_AT', 'CREATED_AT'], 'integer'],
-            [['ORI_BONUS_BS','EXCHANGE_POINTS','BONUS_BS','BONUS_QY', 'BONUS_YC', 'BONUS_VIP', 'BONUS_FX', 'BONUS_LS', 'BONUS_FW', 'BONUS_BT', 'BONUS_BT_PROD', 'BONUS_BT_TOOL', 'DEDUCT_ZR', 'BONUS_FL', 'BONUS_CF', 'BONUS_LX', 'SHOULD_QY', 'SHOULD_DEDUCT_ZR', 'PV_1L', 'QY_1L', 'SURPLUS_1L', 'PV_2L', 'QY_2L', 'SURPLUS_2L', 'PV_3L', 'QY_3L', 'SURPLUS_3L', 'PV_4L', 'QY_4L', 'SURPLUS_4L', 'PV_5L', 'QY_5L', 'SURPLUS_5L', 'PV_PCS', 'PV_LS_TOUCH', 'SURPLUS_LS', 'QY_LS', 'PV_TOUCH', 'BONUS_REAL', 'BONUS_TOTAL', 'BONUS_INCOME', 'ORI_BONUS_QY','ORI_BONUS_QY_BD','ORI_BONUS_QY_FX','ORI_BONUS_YC', 'ORI_BONUS_VIP','ORI_BONUS_STANDARD','BONUS_BD','ORI_BONUS_BD','BONUS_TG','ORI_BONUS_TG','BONUS_XF','ORI_BONUS_XF','BONUS_YJ','ORI_BONUS_YJ','ORI_BONUS_YJ_BD','ORI_BONUS_YJ_FX','BONUS_GX','ORI_BONUS_GX','REAL_BONUS_GX','BONUS_GL','ORI_BONUS_GL','REAL_BONUS_GL','ORI_BONUS_GL_BD','ORI_BONUS_GL_FX','RECONSUME_POINTS','MANAGE_TAX', 'BONUS_TOURISM', 'BONUS_GARAGE'], 'number'],
+            [['ORI_BONUS_BS','EXCHANGE_POINTS','BONUS_BS','BONUS_QY', 'BONUS_YC', 'BONUS_VIP', 'BONUS_FX', 'BONUS_LS', 'BONUS_FW', 'BONUS_BT', 'BONUS_BT_PROD', 'BONUS_BT_TOOL', 'DEDUCT_ZR', 'BONUS_FL', 'BONUS_CF', 'BONUS_LX', 'SHOULD_QY', 'SHOULD_DEDUCT_ZR', 'PV_1L', 'QY_1L', 'SURPLUS_1L', 'PV_2L', 'QY_2L', 'SURPLUS_2L', 'PV_3L', 'QY_3L', 'SURPLUS_3L', 'PV_4L', 'QY_4L', 'SURPLUS_4L', 'PV_5L', 'QY_5L', 'SURPLUS_5L', 'PV_PCS', 'PV_LS_TOUCH', 'SURPLUS_LS', 'QY_LS', 'PV_TOUCH', 'BONUS_REAL', 'BONUS_TOTAL', 'BONUS_INCOME', 'ORI_BONUS_QY','ORI_BONUS_QY_BD','ORI_BONUS_QY_FX','ORI_BONUS_YC', 'ORI_BONUS_VIP','ORI_BONUS_STANDARD','BONUS_BD','ORI_BONUS_BD','BONUS_TG','ORI_BONUS_TG','BONUS_XF','ORI_BONUS_XF','BONUS_YJ','ORI_BONUS_YJ','ORI_BONUS_YJ_BD','ORI_BONUS_YJ_FX','BONUS_GX','ORI_BONUS_GX','REAL_BONUS_GX','BONUS_GL','ORI_BONUS_GL','REAL_BONUS_GL','ORI_BONUS_GL_BD','ORI_BONUS_GL_FX','RECONSUME_POINTS','MANAGE_TAX', 'BONUS_TOURISM', 'BONUS_GARAGE', 'BONUS_VILLA'], 'number'],
             [['ID', 'USER_ID', 'LAST_DEC_LV', 'LAST_EMP_LV', 'LAST_SUB_COM_ID', 'LAST_SYSTEM_ID', 'LAST_STAR_LV'], 'string', 'max' => 32],
             [['LAST_USER_NAME', 'LAST_REC_USER_NAME', 'LAST_CON_USER_NAME'], 'string', 'max' => 16],
             [['LAST_REAL_NAME', 'LAST_REC_REAL_NAME', 'LAST_CON_REAL_NAME'], 'string', 'max' => 128],
@@ -243,7 +244,8 @@ class CalcBonus extends \common\components\ActiveRecord
             'BONUS_BS_ABBR' => '蓝星业绩奖',
             'ORI_BONUS_BS_ABBR' => '蓝星业绩奖原奖金',
             'BONUS_TOURISM' => '旅游奖奖金',
-            'BONUS_GARAGE' => '车房奖奖金',
+            'BONUS_GARAGE' => '车奖奖金',
+            'BONUS_VILLA' => '房奖奖金',
         ];
     }
 
@@ -259,7 +261,7 @@ class CalcBonus extends \common\components\ActiveRecord
         $periodYearMonths = Period::getNearlyPeriodYearMonth($num);
         $allBonus = [];
         foreach($periodYearMonths as $data){
-            $allBonus[] = static::findUseSlaves()->yearMonth($data['yearMonth'])->select('USER_ID,BONUS_QY, BONUS_YC, BONUS_FX, BONUS_LS, BONUS_FW, BONUS_BT, BONUS_BT_PROD, BONUS_BT_TOOL, DEDUCT_ZR, BONUS_FL, BONUS_CF, BONUS_LX, SHOULD_QY,BONUS_TOURISM,BONUS_GARAGE')->where('USER_ID=:USER_ID AND PERIOD_NUM=:PERIOD_NUM AND IS_SENT=1', [':USER_ID'=>$userId, ':PERIOD_NUM'=>$data['periodNum']])->asArray()->one();
+            $allBonus[] = static::findUseSlaves()->yearMonth($data['yearMonth'])->select('USER_ID,BONUS_QY, BONUS_YC, BONUS_FX, BONUS_LS, BONUS_FW, BONUS_BT, BONUS_BT_PROD, BONUS_BT_TOOL, DEDUCT_ZR, BONUS_FL, BONUS_CF, BONUS_LX, SHOULD_QY,BONUS_TOURISM,BONUS_GARAGE,BONUS_VILLA')->where('USER_ID=:USER_ID AND PERIOD_NUM=:PERIOD_NUM AND IS_SENT=1', [':USER_ID'=>$userId, ':PERIOD_NUM'=>$data['periodNum']])->asArray()->one();
         }
         return $allBonus;
     }

+ 6 - 1
common/models/CalcBonusGarage.php

@@ -14,13 +14,18 @@ use Yii;
  * @property string $LAST_STAR_LV 结算时会员星级
  * @property int $LAST_STATUS 结算时状态
  * @property string $AMOUNT 奖金金额
- * @property string $POINT 奖金比例
+ * @property string $POINT 会员提点
  * @property int $PERIOD_NUM 结算期数
  * @property int $CALC_YEAR 所在结算年
  * @property int $CALC_MONTH 所在结算月
  * @property string $P_CALC_MONTH 表分区的日期索引
  * @property string $LOGS 日志
  * @property int $CREATED_AT 创建时间
+ * @property string $PERF 总业绩
+ * @property string $TRANSFER_RATE 奖金总划拨比
+ * @property string $TRANSFER_AMOUNT 划拨奖金
+ * @property string $CAP_AMOUNT 封顶前奖金
+ * @property string $POINT_COMPLEX 总点数
  */
 class CalcBonusGarage extends \common\components\ActiveRecord
 {

+ 5 - 0
common/models/CalcBonusTourism.php

@@ -21,6 +21,11 @@ use Yii;
  * @property string $P_CALC_MONTH 表分区的日期索引
  * @property string $LOGS 日志
  * @property int $CREATED_AT 创建时间
+ * @property string $PERF 总业绩
+ * @property string $TRANSFER_RATE 奖金总划拨比
+ * @property string $TRANSFER_AMOUNT 划拨奖金
+ * @property string $CAP_AMOUNT 封顶前奖金
+ * @property string $POINT_COMPLEX 总点数
  */
 class CalcBonusTourism extends \common\components\ActiveRecord
 {

+ 78 - 0
common/models/CalcBonusVilla.php

@@ -0,0 +1,78 @@
+<?php
+
+namespace common\models;
+
+use Yii;
+
+/**
+ * This is the model class for table "{{%CALC_BONUS_VILLA}}".
+ *
+ * @property string $ID
+ * @property string $USER_ID 会员ID
+ * @property string $LAST_DEC_LV 结算时会员级别
+ * @property string $LAST_EMP_LV 结算时会员聘级
+ * @property string $LAST_STAR_LV 结算时会员星级
+ * @property int $LAST_STATUS 结算时状态
+ * @property string $AMOUNT 奖金金额
+ * @property string $POINT 会员提点
+ * @property int $PERIOD_NUM 结算期数
+ * @property int $CALC_YEAR 所在结算年
+ * @property int $CALC_MONTH 所在结算月
+ * @property string $P_CALC_MONTH 表分区的日期索引
+ * @property string $LOGS 日志
+ * @property int $CREATED_AT 创建时间
+ * @property string $PERF 月总业绩
+ * @property string $TRANSFER_RATE 奖金总划拨比
+ * @property string $TRANSFER_AMOUNT 划拨奖金
+ * @property string $CAP_AMOUNT 封顶前奖金
+ * @property string $POINT_COMPLEX 总点数
+ */
+class CalcBonusVilla extends \common\components\ActiveRecord
+{
+    /**
+     * @inheritdoc
+     */
+    public static function tableName()
+    {
+        return '{{%CALC_BONUS_VILLA}}';
+    }
+
+    /**
+     * @inheritdoc
+     */
+    public function rules()
+    {
+        return [
+            [['USER_ID', 'PERIOD_NUM', 'CALC_YEAR', 'CALC_MONTH', 'P_CALC_MONTH', 'CREATED_AT'], 'required'],
+            [['AMOUNT', 'POINT'], 'number'],
+            [['LAST_STATUS', 'PERIOD_NUM', 'CALC_YEAR', 'CALC_MONTH', 'CREATED_AT'], 'integer'],
+            [['ID', 'USER_ID', 'LAST_DEC_LV', 'BONUS_TYPE', 'LAST_STAR_LV'], 'string', 'max' => 32],
+            [['P_CALC_MONTH'], 'safe'],
+            [['LOGS'], 'string', 'max' => 2000],
+            [['ID'], 'unique'],
+        ];
+    }
+
+    /**
+     * @inheritdoc
+     */
+    public function attributeLabels()
+    {
+        return [
+            'ID' => 'ID',
+            'USER_ID' => '会员ID',
+            'LAST_DEC_LV' => '结算时会员级别',
+            'LAST_EMP_LV' => '结算时会员聘级',
+            'LAST_STAR_LV' => '结算时会员星级',
+            'LAST_STATUS' => '结算时状态',
+            'AMOUNT' => '奖金金额',
+            'POINT' => '奖金比例',
+            'PERIOD_NUM' => '结算期数',
+            'CALC_YEAR' => '所在结算年',
+            'CALC_MONTH' => '所在结算月',
+            'P_CALC_MONTH' => '表分区的日期索引',
+            'CREATED_AT' => '创建时间',
+            'LOGS' => '日志',
+        ];
+    }
+}

+ 6 - 3
common/models/DealType.php

@@ -48,11 +48,14 @@ class DealType extends \common\components\ActiveRecord
     CONST RECONSUME_POINTS_EXCHANGE = 'YA627DTHN81OBO7NIQ1OP8N3PGZX5C66';//复消积分兑换
     CONST EXCHANGE_POINTS_EXCHANGE = '316872011148300288';//兑换积分兑换
     CONST TOURISM_SEND = '364305038266470400';// 旅游奖奖金发放
-    CONST GARAGE_SEND = '364305160249413632';// 车房奖奖金发放
+    CONST GARAGE_SEND = '364305160249413632';// 车奖奖金发放
+    CONST VILLA_SEND = '390992293622059008';// 房奖奖金发放
     CONST TOURISM_POINTS_EXCHANGE = '365343018452127744'; // 旅游积分兑换
-    CONST GARAGE_POINTS_EXCHANGE = '365343060634243072'; // 车房积分兑换
+    CONST GARAGE_POINTS_EXCHANGE = '365343060634243072'; // 车奖积分兑换
+    CONST VILLA_POINTS_EXCHANGE = '390992212424527872'; // 房奖积分兑换
     CONST TOURISM_POINTS_ADJUST = '365753533326299136'; // 旅游积分余额调整
-    CONST GARAGE_POINTS_ADJUST = '365753643942678528'; // 车房积分余额调整
+    CONST GARAGE_POINTS_ADJUST = '365753643942678528'; // 车奖积分余额调整
+    CONST VILLA_POINTS_ADJUST = '390990784847024128'; // 房奖积分余额调整
 
     /**
      * {@inheritdoc}

+ 81 - 0
common/models/FlowVillaPoints.php

@@ -0,0 +1,81 @@
+<?php
+
+namespace common\models;
+
+use Yii;
+
+/**
+ * This is the model class for table "{{%FLOW_VILLA_POINTS}}".
+ *
+ * @property string $ID
+ * @property string $USER_ID 会员ID
+ * @property string $CALC_ID 奖金结算表ID
+ * @property string $AMOUNT 金额
+ * @property string $TOTAL 当前总金额
+ * @property int $IS_INCR 是否增加
+ * @property string $REMARK 备注
+ * @property string $ADMIN_NAME 操作人名称
+ * @property int $PERIOD_NUM 所在期数
+ * @property int $CALC_MONTH 所在结算月
+ * @property string $P_MONTH 表分区的日期索引
+ * @property int $CREATED_AT 创建时间
+ * @property int $DELETED 是否删除
+ * @property int $DELETED_AT 删除时间
+ * @property int $SORT 排序
+ * @property string $TRANSFER_SN 转账流水号
+ */
+class FlowVillaPoints extends \common\components\ActiveRecord
+{
+    const INCR_REDUCE = 0;      // 减少
+    const INCR_ADD = 1;         // 增加
+    const INCR_FREEZE = 2;      // 冻结
+    const INCR_UNFREEZE = 3;    // 解冻
+
+    /**
+     * @inheritdoc
+     */
+    public static function tableName()
+    {
+        return '{{%FLOW_VILLA_POINTS}}';
+    }
+
+    /**
+     * @inheritdoc
+     */
+    public function rules()
+    {
+        return [
+            [['USER_ID', 'REMARK', 'PERIOD_NUM', 'CALC_MONTH', 'P_MONTH', 'CREATED_AT'], 'required'],
+            [['AMOUNT', 'TOTAL'], 'number'],
+            [['IS_INCR', 'PERIOD_NUM', 'CALC_MONTH', 'CREATED_AT', 'DELETED', 'DELETED_AT', 'SORT'], 'integer'],
+            [['ID', 'USER_ID', 'CALC_ID', 'ADMIN_NAME', 'TRANSFER_SN', 'LAST_STAR_LV'], 'string', 'max' => 32],
+            [['REMARK'], 'string', 'max' => 255],
+            [['ID'], 'unique'],
+        ];
+    }
+
+    /**
+     * @inheritdoc
+     */
+    public function attributeLabels()
+    {
+        return [
+            'ID' => 'ID',
+            'USER_ID' => '会员ID',
+            'CALC_ID' => '结算表ID',
+            'AMOUNT' => '交易金额',
+            'TOTAL' => '当前总金额',
+            'IS_INCR' => '是否增加',
+            'REMARK' => '备注',
+            'ADMIN_NAME' => '操作人名称',
+            'PERIOD_NUM' => '所在期数',
+            'CALC_MONTH' => '所在结算月',
+            'P_MONTH' => '表分区的日期索引',
+            'CREATED_AT' => '创建时间',
+            'DELETED' => '是否删除',
+            'DELETED_AT' => '删除时间',
+            'SORT' => '排序',
+            'TRANSFER_SN' => '转账流水号',
+        ];
+    }
+}

+ 1 - 1
common/models/PerfOrder.php

@@ -45,7 +45,7 @@ class PerfOrder extends \common\components\ActiveRecord
     const STATUS_NORMAL = 1; //正常
     const STATUS_CLOSED = 2; //置废
     const STATUS_NAME = [
-      self::STATUS_NORMAL=>'已审核',
+      self::STATUS_NORMAL=>'Audited',//已审核
       self::STATUS_CLOSED=>'置废',
     ];
     /**

+ 18 - 3
common/models/ShopGoods.php

@@ -55,9 +55,14 @@ class ShopGoods extends \common\components\ActiveRecord
         ],
         5 => [
             'id' => 5,
-            'name' => 'Car/Villa Fund',
+            'name' => 'Car Fund',
             'label' => 'garage_points',
         ],
+        6 => [
+            'id' => 6,
+            'name' => 'Villa Fund',
+            'label' => 'villa_points',
+        ],
         7 => [
             'id' => 7,
             'name' => 'PayStack',
@@ -112,11 +117,18 @@ class ShopGoods extends \common\components\ActiveRecord
 //        ],
         [
             'id' => 5,
-            'name' => 'Car/Villa Fund Products',
+            'name' => 'Car Fund Products',
             'sell_type' => [
                 self::SALE_TYPE[5]
             ]
         ],
+        [
+            'id' => 6,
+            'name' => 'Villa Fund Products',
+            'sell_type' => [
+                self::SALE_TYPE[6]
+            ]
+        ],
     ];
     /**
      * @inheritdoc
@@ -226,7 +238,10 @@ class ShopGoods extends \common\components\ActiveRecord
 //                'name'=>'Travel Bonus'
 //            ],
             'garage_points' => [
-                'name' => 'Car/Villa Fund'
+                'name' => 'Car Fund'
+            ],
+            'villa_points' => [
+                'name' => 'Villa Fund'
             ],
             'pay_stack' => [
                 'name' => 'PayStack'

+ 10 - 5
common/models/UserBonus.php

@@ -31,7 +31,8 @@ use common\libs\logging\operate\valueType\Config as ValueTypeConfig;
  * @property string $DEDUCT_ZR_TOTAL 责任业绩扣除累计
  * @property string $FL_TOTAL 形象店货补累计
  * @property string $TOURISM_POINTS_TOTAL 旅游积分累积
- * @property string $GARAGE_POINTS_TOTAL 车房积分累积
+ * @property string $GARAGE_POINTS_TOTAL 车奖积分累积
+ * @property string $VILLA_POINTS_TOTAL 房奖积分累积
  * @property int $VER 乐观锁标识
  * @property int $CREATED_AT 创建时间
  * @property int $BD_TOTAL 服务奖累计
@@ -72,7 +73,7 @@ class UserBonus extends \common\components\ActiveRecord
     {
         return [
             [['USER_ID', 'CREATED_AT'], 'required'],
-            [['BS_TOTAL','ORI_BS_TOTAL','BS','BONUS', 'BONUS_FREEZE', 'CF', 'LX', 'QY_TOTAL', 'YC_TOTAL', 'VIP_TOTAL', 'FX_TOTAL', 'LS_TOTAL', 'FW_TOTAL', 'BT_TOTAL', 'BT_PROD_TOTAL', 'BT_TOOL_TOTAL', 'CF_TOTAL', 'LX_TOTAL', 'DEDUCT_ZR_TOTAL', 'FL_TOTAL', 'BD_TOTAL','TG_TOTAL','YJ_TOTAL','GX_TOTAL','GL_TOTAL', 'ORI_QY_TOTAL','ORI_YC_TOTAL','ORI_YC_TOTAL','ORI_BD_TOTAL','ORI_TG_TOTAL','ORI_YJ_TOTAL','ORI_GX_TOTAL','ORI_GL_TOTAL','RECONSUME_POINTS','MANAGE_TAX', 'RECONSUME_POINTS_EXPIRED', 'RECONSUME_POINTS_TOTAL', 'BONUS_TOTAL', 'TOURISM_POINTS', 'GARAGE_POINTS'], 'number'],
+            [['BS_TOTAL','ORI_BS_TOTAL','BS','BONUS', 'BONUS_FREEZE', 'CF', 'LX', 'QY_TOTAL', 'YC_TOTAL', 'VIP_TOTAL', 'FX_TOTAL', 'LS_TOTAL', 'FW_TOTAL', 'BT_TOTAL', 'BT_PROD_TOTAL', 'BT_TOOL_TOTAL', 'CF_TOTAL', 'LX_TOTAL', 'DEDUCT_ZR_TOTAL', 'FL_TOTAL', 'BD_TOTAL','TG_TOTAL','YJ_TOTAL','GX_TOTAL','GL_TOTAL', 'ORI_QY_TOTAL','ORI_YC_TOTAL','ORI_YC_TOTAL','ORI_BD_TOTAL','ORI_TG_TOTAL','ORI_YJ_TOTAL','ORI_GX_TOTAL','ORI_GL_TOTAL','RECONSUME_POINTS','MANAGE_TAX', 'RECONSUME_POINTS_EXPIRED', 'RECONSUME_POINTS_TOTAL', 'BONUS_TOTAL', 'TOURISM_POINTS', 'GARAGE_POINTS', 'VILLA_POINTS'], 'number'],
             [['VER', 'CREATED_AT'], 'integer'],
             [['ID','USER_ID'], 'string', 'max' => 32],
             [['USER_ID'], 'unique'],
@@ -129,8 +130,10 @@ class UserBonus extends \common\components\ActiveRecord
             'ORI_BS_TOTAL' => '蓝星原奖金累计',
             'TOURISM' => '旅游积分',
             'TOURISM_TOTAL' => '旅游积分累计',
-            'GARAGE' => '车房积分',
-            'GARAGE_TOTAL' => '车房积分累计',
+            'GARAGE' => '车奖积分',
+            'GARAGE_TOTAL' => '车奖积分累计',
+            'VILLA' => '房奖积分',
+            'VILLA_TOTAL' => '房奖积分累计',
         ];
     }
 
@@ -145,7 +148,8 @@ class UserBonus extends \common\components\ActiveRecord
             'CF' => '车房养老奖',
             'LX' => '领袖分红奖',
             'TOURISM' => '旅游积分',
-            'GARAGE' => '车房积分',
+            'GARAGE' => '车奖积分',
+            'VILLA' => '房奖积分',
         ];
     }
 
@@ -173,6 +177,7 @@ class UserBonus extends \common\components\ActiveRecord
                 'LX' => 0,
                 'TOURISM' => 0,
                 'GARAGE' => 0,
+                'VILLA' => 0,
             ];
         }
         return $data;

+ 2 - 0
common/models/forms/OrderForm.php

@@ -689,6 +689,8 @@ class OrderForm extends Model
             Balance::changeUserBonus(\Yii::$app->user->id, 'tourism_points', -abs($this->_payAmount), ['DEAL_TYPE_ID' => DealType::TOURISM_POINTS_EXCHANGE,'REMARK' => '会员旅游换积分兑换']);
         } else if ($this->payType == 'garage_points') {
             Balance::changeUserBonus(\Yii::$app->user->id, 'garage_points', -abs($this->_payAmount), ['DEAL_TYPE_ID' => DealType::GARAGE_POINTS_EXCHANGE,'REMARK' => '会员名车积分兑换']);
+        }  else if ($this->payType == 'villa_points') {
+            Balance::changeUserBonus(\Yii::$app->user->id, 'villa_points', -abs($this->_payAmount), ['DEAL_TYPE_ID' => DealType::VILLA_POINTS_EXCHANGE,'REMARK' => '会员房奖积分兑换']);
         } else if ($this->payType == 'reconsume_points') {
             Balance::changeUserBonus(\Yii::$app->user->id,'reconsume_points', -abs($this->_payAmount),['DEAL_TYPE_ID' => DealType::RECONSUME_POINTS_EXCHANGE,'REMARK' => '会员复销积分兑换']);
         }

+ 18 - 6
frontendApi/modules/v1/controllers/BonusController.php

@@ -25,6 +25,7 @@ use common\models\FlowGaragePoints;
 use common\models\FlowLX;
 use common\models\FlowReconsumePoints;
 use common\models\FlowTourismPoints;
+use common\models\FlowVillaPoints;
 use common\models\FlowWallet;
 use common\models\PerfMonth;
 use common\models\Period;
@@ -46,7 +47,7 @@ class BonusController extends BaseController {
      */
     public function actionIndex() {
         $userId = \Yii::$app->user->id;
-        $data = UserBonus::findUseSlaves()->select('BONUS,RECONSUME_POINTS,EXCHANGE_POINTS,TOURISM_POINTS,GARAGE_POINTS')->where('USER_ID=:USER_ID', [':USER_ID' => $userId])->asArray()->one();
+        $data = UserBonus::findUseSlaves()->select('BONUS,RECONSUME_POINTS,EXCHANGE_POINTS,TOURISM_POINTS,GARAGE_POINTS,VILLA_POINTS')->where('USER_ID=:USER_ID', [':USER_ID' => $userId])->asArray()->one();
         if (!$data) {
             $data = [
                 'BONUS' => 0,
@@ -54,6 +55,7 @@ class BonusController extends BaseController {
                 'EXCHANGE_POINTS' => 0,
                 'TOURISM_POINTS' => 0,
                 'GARAGE_POINTS' => 0,
+                'VILLA_POINTS' => 0,
             ];
         }
         $data['CASH'] = 0;
@@ -75,7 +77,8 @@ class BonusController extends BaseController {
 //        $wallet[] = ['walletType' => 'point', 'walletName' => '会员积分', 'amount' => Tool::formatPrice($data['RECONSUME_POINTS'])];
 //        $wallet[] = ['walletType' => 'exchange', 'walletName' => 'Exchange points', 'amount' => Tool::formatPrice($data['EXCHANGE_POINTS'])];//兑换点数
 //        $wallet[] = ['walletType' => 'tourism_points', 'walletName' => 'Travel points', 'amount' => Tool::formatPrice($data['TOURISM_POINTS'])];//旅游积分
-        $wallet[] = ['walletType' => 'garage_points', 'walletName' => 'Car/Villa points', 'amount' => Tool::formatPrice($data['GARAGE_POINTS'])];//名车积分
+        $wallet[] = ['walletType' => 'garage_points', 'walletName' => 'Car points', 'amount' => Tool::formatPrice($data['GARAGE_POINTS'])];//车奖积分
+        $wallet[] = ['walletType' => 'villa_points', 'walletName' => 'Villa points', 'amount' => Tool::formatPrice($data['VILLA_POINTS'])];//房奖积分
 //        if ($showCFLX) {
 //            $wallet[] = ['walletType' => 'cf', 'walletName' => '福利积分一', 'amount' => Tool::formatPrice($data['CF'])];
 //            $wallet[] = ['walletType' => 'lx', 'walletName' => '福利积分二', 'amount' => Tool::formatPrice($data['LX'])];
@@ -107,7 +110,7 @@ class BonusController extends BaseController {
      */
     public function actionWalletFlow(){
         $walletType = \Yii::$app->request->get('walletType');
-        if(!in_array($walletType,['bonus', 'cash', 'exchange', 'tourism_points', 'garage_points'])) return static::notice('错误的账户类型',400);
+        if(!in_array($walletType,['bonus', 'cash', 'exchange', 'tourism_points', 'garage_points', 'villa_points'])) return static::notice('walletType error',400);
         $dealType = \Yii::$app->request->get('dealType');
         $createAt = \Yii::$app->request->get('createAt');
         $remark = \Yii::$app->request->get('remark');
@@ -179,13 +182,22 @@ class BonusController extends BaseController {
                 'select' => 'AMOUNT,TOTAL,IS_INCR,REMARK,REMARK_IS_SHOW,PERIOD_NUM,CALC_MONTH,CREATED_AT,DEAL_TYPE_ID,DEAL_TYPE_IS_PRESET',
                 'orderBy' => 'CREATED_AT DESC',
             ]);
+        } else if ($walletType == 'villa_points') {
+            $dealLists = FlowVillaPoints::find()->groupBy('DEAL_TYPE_ID')->select('DEAL_TYPE_ID')->where('USER_ID=:USER_ID',[':USER_ID'=>\Yii::$app->user->id])->asArray()->all();
+            $data = FlowVillaPoints::lists($condition, $params, [
+                'useSlaves' => true,
+                'select' => 'AMOUNT,TOTAL,IS_INCR,REMARK,REMARK_IS_SHOW,PERIOD_NUM,CALC_MONTH,CREATED_AT,DEAL_TYPE_ID,DEAL_TYPE_IS_PRESET',
+                'orderBy' => 'CREATED_AT DESC',
+            ]);
+        } else {
+            return static::notice('walletType error',400);
         }
 
         if($data) {
             if($walletType != 'cash') {
                 foreach ($data['list'] as $key => $value) {
                     if ($value['DEAL_TYPE_IS_PRESET'] == 0) {
-                        $data['list'][$key]['DEAL_TYPE_NAME'] = $value['AMOUNT'] > 0 ? '增加' : '减少';
+                        $data['list'][$key]['DEAL_TYPE_NAME'] = $value['AMOUNT'] > 0 ? 'increase' : 'reduce'; // 增加 减少
                     } else {
                         $data['list'][$key]['DEAL_TYPE_NAME'] = DealType::getAllTypesForShow()[$value['DEAL_TYPE_ID']]['TYPE_NAME'] ?? '';
                     }
@@ -202,8 +214,8 @@ class BonusController extends BaseController {
                 if(!$value['DEAL_TYPE_ID']) continue;
                 $dealType = DealType::getAllTypesForShow()[$value['DEAL_TYPE_ID']];
                 if($dealType['IS_PRESET']==0){
-                    $dealTypes['1'] = '增加';
-                    $dealTypes['2'] = '扣除';
+                    $dealTypes['1'] = 'increase';// 增加
+                    $dealTypes['2'] = 'reduce';// 扣除
                 }else{
                     $dealLists[$key]['DEAL_TYPE_NAME'] = $dealType['TYPE_NAME']??'';
                     $dealTypes[$value['DEAL_TYPE_ID']] = $dealLists[$key]['DEAL_TYPE_NAME'];

+ 5 - 1
frontendApi/modules/v1/controllers/ShopController.php

@@ -477,7 +477,11 @@ class ShopController extends BaseController {
 //            ],
             [
                 'name' => '5',
-                'label' => 'Car/Villa Fund Products',//车房积分商品
+                'label' => 'Car Fund Products',//车奖积分商品
+            ],
+            [
+                'name' => '6',
+                'label' => 'Villa Fund Products',//房奖积分商品
             ],
         ];
         return static::notice($data);

+ 1 - 1
frontendEle/src/utils/tool.js

@@ -82,7 +82,7 @@ let tool = {
       userInfo.logout()
     }
     if (todo || status === 402) {
-      message = todo ? '长时间未进行操作,请重新登录':(message === 'Connection not operated for too long' ? '长时间未进行操作,请重新登录' : message)
+      message = todo ? 'No operation has been performed for a long time,please log in again.':(message === 'Connection not operated for too long' ? 'No operation has been performed for a long time,please log in again.' : message) // 长时间未进行操作,请重新登录
       userInfo.logout()
     }
     return {message, todo, status}

+ 1 - 1
frontendEle/src/views/shop/index.vue

@@ -49,7 +49,7 @@
                       <el-table-column label="Inventory" prop="STORE_NUMS"><!--库存-->
                       </el-table-column>
 
-                      <el-table-column label="Quantity"  width="155"><!--数量-->
+                      <el-table-column label="Qty"  width="155"><!--数量-->
                         <template slot-scope="scope">
                           <el-input-number size="mini" v-model="numList[scope.$index]"  :min="0" :max="Number(scope.row.STORE_NUMS)" @change="(val)=>{handleInputNumber(val, scope.row)}"></el-input-number>
                         </template>

+ 8 - 1
frontendEle/src/views/shop/order.vue

@@ -130,10 +130,17 @@
 
             <div v-if="category_type === 5">
               <div class="sum_box">
-                <div>Car House bonus</div><!-- 名车积分 -->
+                <div>Car bonus</div><!-- 名车积分 -->
                 <div>{{ balance.garage_points }}</div>
               </div>
             </div>
+
+            <div v-if="category_type === 6">
+              <div class="sum_box">
+                <div>Villa bonus</div><!-- 豪宅积分 -->
+                <div>{{ balance.villa_points }}</div>
+              </div>
+            </div>
           </div>
         </div>
 

+ 118 - 0
sql/upgrade/1729.sql

@@ -0,0 +1,118 @@
+-- 更新车奖配置
+UPDATE `AR_CONFIG` SET `TITLE` = '是否开启车奖',`OPTIONS` = '{"declarationLevel":"67ABCE0ECE705575E055736AECE8644D"}',`VALUE` = '2' WHERE `CONFIG_NAME` = 'openGarage' LIMIT 1;
+UPDATE `AR_CONFIG` SET `TITLE` = '车奖个人封顶值' WHERE `CONFIG_NAME` = 'openGarageCap' LIMIT 1;
+
+-- 增加房奖配置
+INSERT INTO `AR_CONFIG` (`CONFIG_NAME`, `TITLE`, `UNIT`, `INPUT_TYPE`, `OPTIONS`, `VALUE`, `TYPE`, `SORT`, `CREATED_AT`, `UPDATED_AT`) VALUES ('openVilla', '是否开启房奖', NULL, 8, '{"declarationLevel":"67ABCE0ECE705575E055736AECE8644D"}', '2', 'bonus', 44, 1521085263, 1657872447);
+INSERT INTO `AR_CONFIG` (`CONFIG_NAME`, `TITLE`, `UNIT`, `INPUT_TYPE`, `OPTIONS`, `VALUE`, `TYPE`, `SORT`, `CREATED_AT`, `UPDATED_AT`) VALUES ('openVillaCap', '房奖个人封顶值', '$', 1, '', '10000', 'bonus', 44, 1521085263, 1657872447);
+
+
+-- 星级表增加房奖比例
+ALTER TABLE `AR_STAR_LEVEL` ADD COLUMN `VILLA_PERCENT` decimal(16,2) NOT NULL DEFAULT 0.00 COMMENT '房奖比例' AFTER `TOURISM_PERCENT`;
+ALTER TABLE `AR_STAR_LEVEL` MODIFY COLUMN `GARAGE_PERCENT` decimal(16,2) NOT NULL DEFAULT 0.00 COMMENT '车奖比例';
+
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 1.0 WHERE ID = 'E0B75B89C94F35EF8EE0054FA34B759C';
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 1.5 WHERE ID = '7FEBE5DE95D530578915F4072E7CD842';
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 2.0 WHERE ID = '391691E01CD5373F8D23F01FAD750222';
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 2.5 WHERE ID = '8ACAEA736F5331B79283C895F36084E5';
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 3.0 WHERE ID = 'CE46B39D07633217AA5711438649D1D6';
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 3.5 WHERE ID = '24396B85E74A3005947F1F90EBA5F5CF';
+UPDATE `AR_STAR_LEVEL` SET `VILLA_PERCENT` = 4.0 WHERE ID = '8C253968EB6F3F3FA5BE84F63136FFFA';
+
+
+ALTER TABLE `AR_CALC_BONUS_GARAGE` DROP COLUMN `LEVEL_ID`;
+ALTER TABLE `AR_CALC_BONUS_TOURISM` DROP COLUMN `LEVEL_ID`;
+
+-- 增加业绩奖金字段
+ALTER TABLE `AR_CALC_BONUS_GARAGE` ADD COLUMN `PERF` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '月总业绩' AFTER `POINT`;
+ALTER TABLE `AR_CALC_BONUS_GARAGE` ADD COLUMN `TRANSFER_RATE` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '奖金总划拨比' AFTER `PERF`;
+ALTER TABLE `AR_CALC_BONUS_GARAGE` ADD COLUMN `TRANSFER_AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '划拨奖金' AFTER `TRANSFER_RATE`;
+ALTER TABLE `AR_CALC_BONUS_GARAGE` ADD COLUMN `CAP_AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '封顶前奖金' AFTER `TRANSFER_AMOUNT`;
+ALTER TABLE `AR_CALC_BONUS_GARAGE` ADD COLUMN `POINT_COMPLEX` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '总点数' AFTER `CAP_AMOUNT`;
+ALTER TABLE `AR_CALC_BONUS_GARAGE` CHANGE COLUMN `POINT` `POINT` decimal(10,4) NOT NULL DEFAULT 0.0000 COMMENT '奖金比例';
+
+ALTER TABLE `AR_CALC_BONUS_TOURISM` ADD COLUMN `PERF` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '月总业绩' AFTER `POINT`;
+ALTER TABLE `AR_CALC_BONUS_TOURISM` ADD COLUMN `TRANSFER_RATE` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '奖金总划拨比' AFTER `PERF`;
+ALTER TABLE `AR_CALC_BONUS_TOURISM` ADD COLUMN `TRANSFER_AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '划拨奖金' AFTER `TRANSFER_RATE`;
+ALTER TABLE `AR_CALC_BONUS_TOURISM` ADD COLUMN `CAP_AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '封顶前奖金' AFTER `TRANSFER_AMOUNT`;
+ALTER TABLE `AR_CALC_BONUS_TOURISM` ADD COLUMN `POINT_COMPLEX` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '总点数' AFTER `CAP_AMOUNT`;
+ALTER TABLE `AR_CALC_BONUS_TOURISM` CHANGE COLUMN `POINT` `POINT` decimal(10,4) NOT NULL DEFAULT 0.0000 COMMENT '奖金比例';
+
+
+-- 新增车奖结算记录表
+CREATE TABLE `AR_CALC_BONUS_VILLA` (
+    `ID` varchar(32) COLLATE utf8mb4_bin NOT NULL,
+    `USER_ID` varchar(32) COLLATE utf8mb4_bin NOT NULL COMMENT '会员ID',
+    `LAST_DEC_LV` varchar(32) COLLATE utf8mb4_bin DEFAULT '' COMMENT '结算时会员等级',
+    `LAST_EMP_LV` varchar(32) COLLATE utf8mb4_bin DEFAULT '' COMMENT '计算时会员聘级',
+    `LAST_STAR_LV` varchar(32) CHARACTER SET utf8mb4 DEFAULT '' COMMENT '计算时会员星级',
+    `LEVEL_ID` varchar(32) CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci DEFAULT '' COMMENT '会员最新聘级.聘级ID,对应AR_EMPLOY_LEVEL表主键',
+    `LAST_STATUS` tinyint(1) NOT NULL DEFAULT 0 COMMENT '结算时状态',
+    `AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '奖金数',
+    `POINT` decimal(10,4) NOT NULL DEFAULT 0.0000 COMMENT '奖金比例',
+    `PERF` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '月总业绩',
+    `TRANSFER_RATE` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '奖金总划拨比',
+    `TRANSFER_AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '划拨奖金',
+    `CAP_AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '封顶前奖金',
+    `POINT_COMPLEX` decimal(10,4) NOT NULL DEFAULT 0.0000 COMMENT '总点数',
+    `PERIOD_NUM` int(10) NOT NULL COMMENT '结算期数',
+    `CALC_YEAR` int(10) NOT NULL COMMENT '结算年份',
+    `CALC_MONTH` int(10) NOT NULL COMMENT '结算月份',
+    `P_CALC_MONTH` date NOT NULL,
+    `LOGS` varchar(2000) COLLATE utf8mb4_bin DEFAULT '',
+    `CREATED_AT` int(10) NOT NULL COMMENT '创建时间',
+    KEY `USER_ID` (`USER_ID`),
+    KEY `PERIOD_NUM` (`PERIOD_NUM`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin COMMENT='房奖结算记录';
+
+
+-- 奖金总表增加房奖列
+ALTER TABLE `AR_CALC_BONUS` ADD COLUMN `BONUS_VILLA` decimal(16,3) NOT NULL DEFAULT 0.000 COMMENT '房奖奖金' AFTER `BONUS_GARAGE`;
+
+
+-- 增加房奖流水
+CREATE TABLE `AR_FLOW_VILLA_POINTS` (
+    `ID` varchar(32) COLLATE utf8mb4_bin NOT NULL,
+    `USER_ID` varchar(32) COLLATE utf8mb4_bin NOT NULL,
+    `LAST_DEC_LV` varchar(32) COLLATE utf8mb4_bin DEFAULT '',
+    `LAST_EMP_LV` varchar(32) COLLATE utf8mb4_bin DEFAULT '',
+    `LAST_STAR_LV` varchar(32) COLLATE utf8mb4_bin DEFAULT '',
+    `LAST_STATUS` tinyint(1) NOT NULL DEFAULT 0,
+    `CALC_ID` varchar(32) COLLATE utf8mb4_bin DEFAULT NULL,
+    `AMOUNT` decimal(16,3) NOT NULL DEFAULT 0.000,
+    `AMOUNT_STANDARD` float(16,2) NOT NULL DEFAULT 0.00 COMMENT '奖金数额-标准数值',
+    `EXCHANGE_RATE` float(10,4) NOT NULL DEFAULT 0.0000 COMMENT '汇率',
+    `TOTAL` decimal(16,3) NOT NULL DEFAULT 0.000,
+    `IS_INCR` tinyint(1) NOT NULL DEFAULT 1,
+    `REMARK` varchar(255) COLLATE utf8mb4_bin NOT NULL,
+    `REMARK_IS_SHOW` tinyint(1) NOT NULL DEFAULT 1,
+    `DEAL_TYPE_ID` varchar(32) COLLATE utf8mb4_bin DEFAULT NULL,
+    `DEAL_TYPE_IS_PRESET` tinyint(1) NOT NULL DEFAULT 1,
+    `ADMIN_NAME` varchar(32) COLLATE utf8mb4_bin DEFAULT NULL,
+    `PERIOD_NUM` int(10) NOT NULL,
+    `CALC_MONTH` int(10) NOT NULL,
+    `P_MONTH` date NOT NULL,
+    `CREATED_AT` int(10) NOT NULL,
+    `DELETED` tinyint(1) NOT NULL DEFAULT 0,
+    `DELETED_AT` int(10) NOT NULL DEFAULT 0,
+    `TRANSFER_SN` varchar(32) COLLATE utf8mb4_bin DEFAULT '',
+    `SORT` int(10) NOT NULL DEFAULT 0,
+    `AUTO_SORT` int(10) NOT NULL DEFAULT 0,
+    PRIMARY KEY (`ID`) USING BTREE,
+    KEY `IDX_USER_ID` (`USER_ID`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin ROW_FORMAT=DYNAMIC COMMENT='房奖积分流水';
+
+
+ALTER TABLE `AR_USER_BONUS` ADD COLUMN `VILLA_POINTS` decimal(16,2) NOT NULL DEFAULT 0.00 COMMENT '房奖积分';
+ALTER TABLE `AR_USER_BONUS` ADD COLUMN `VILLA_POINTS_TOTAL` decimal(16,2) NOT NULL DEFAULT 0.00 COMMENT '房奖积分累计';
+
+
+ALTER TABLE `AR_DEAL_TYPE` CHANGE COLUMN `COMMENT` `COMMENT` varchar(255) COLLATE utf8mb4_bin NOT NULL DEFAULT '' COMMENT '说明';
+
+UPDATE `AR_DEAL_TYPE` SET `TYPE_NAME` = 'Adjust car points balance',`COMMENT` = '车奖积分余额调整' WHERE `ID` = '365753643942678528' LIMIT 1;
+UPDATE `AR_DEAL_TYPE` SET `TYPE_NAME` = 'Car points exchange',`COMMENT` = '车奖积分兑换' WHERE `ID` = '365343060634243072' LIMIT 1;
+UPDATE `AR_DEAL_TYPE` SET `TYPE_NAME` = 'Car points grant',`COMMENT` = '车奖积分发放' WHERE `ID` = '364305160249413632' LIMIT 1;
+
+INSERT INTO `AR_DEAL_TYPE` (`ID`, `TYPE_NAME`, `COMMENT`, `CREATE_ADMIN`, `UPDATE_ADMIN`, `CREATE_REMARK`, `UPDATE_REMARK`, `IS_PRESET`, `IS_ENABLE`, `CREATED_AT`, `UPDATED_AT`, `SORT_ORDER`) VALUES ('390990784847024128', 'Adjust villa points balance', '房奖积分余额调整', '354832362066022400', NULL, '', NULL, 0, 1, 1658467551, 0, 1);
+INSERT INTO `AR_DEAL_TYPE` (`ID`, `TYPE_NAME`, `COMMENT`, `CREATE_ADMIN`, `UPDATE_ADMIN`, `CREATE_REMARK`, `UPDATE_REMARK`, `IS_PRESET`, `IS_ENABLE`, `CREATED_AT`, `UPDATED_AT`, `SORT_ORDER`) VALUES ('390992212424527872', 'Villa points exchange', '房奖积分兑换', '354832362066022400', NULL, '', NULL, 0, 1, 1658467892, 0, 1);
+INSERT INTO `AR_DEAL_TYPE` (`ID`, `TYPE_NAME`, `COMMENT`, `CREATE_ADMIN`, `UPDATE_ADMIN`, `CREATE_REMARK`, `UPDATE_REMARK`, `IS_PRESET`, `IS_ENABLE`, `CREATED_AT`, `UPDATED_AT`, `SORT_ORDER`) VALUES ('390992293622059008', 'Villa points grant', '房奖积分发放', '354832362066022400', NULL, '', NULL, 0, 1, 1658467910, 0, 1);