| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326 |
- <?php
- namespace App\Module\Promotion\Logics;
- use App\Module\Promotion\Enums\TALENT_LEVEL;
- use App\Module\Promotion\Models\PromotionTalentConfig;
- use App\Module\Promotion\Models\PromotionUserTalent;
- use Illuminate\Support\Facades\DB;
- use Illuminate\Support\Facades\Log;
- use Illuminate\Support\Facades\Redis;
- /**
- * 达人等级逻辑类
- *
- * 处理用户达人等级的核心业务逻辑,包括计算达人等级、更新达人等级、
- * 获取达人等级配置等功能。该类仅供内部使用,不对外提供服务。
- */
- class TalentLogic
- {
- /**
- * @var ReferralLogic
- */
- protected $referralLogic;
- /**
- * 构造函数
- *
- * @param ReferralLogic $referralLogic
- */
- public function __construct(ReferralLogic $referralLogic)
- {
- $this->referralLogic = $referralLogic;
- }
- /**
- * 获取用户的达人等级信息
- *
- * @param int $userId 用户ID
- * @return PromotionUserTalent|null
- */
- public function getUserTalent(int $userId): ?PromotionUserTalent
- {
- // 尝试从缓存获取
- $cacheKey = "promotion:user:{$userId}:talent";
- $cachedData = Redis::get($cacheKey);
- if ($cachedData !== null) {
- $talentData = json_decode($cachedData, true);
- $talent = new PromotionUserTalent();
- $talent->fill($talentData);
- return $talent;
- }
- // 从数据库获取
- $talent = PromotionUserTalent::where('user_id', $userId)->first();
- // 如果不存在,创建一个默认的达人等级记录
- if (!$talent) {
- $talent = $this->createDefaultTalent($userId);
- }
- // 缓存结果
- if ($talent) {
- Redis::setex($cacheKey, 86400, json_encode($talent->toArray())); // 缓存1天
- }
- return $talent;
- }
- /**
- * 创建默认的达人等级记录
- *
- * @param int $userId 用户ID
- * @return PromotionUserTalent|null
- */
- public function createDefaultTalent(int $userId): ?PromotionUserTalent
- {
- try {
- $talent = new PromotionUserTalent();
- $talent->user_id = $userId;
- $talent->talent_level = TALENT_LEVEL::NONE;
- $talent->direct_count = 0;
- $talent->promotion_count = 0;
- $talent->save();
- return $talent;
- } catch (\Exception $e) {
- Log::error("创建默认达人等级记录失败: " . $e->getMessage());
- return null;
- }
- }
- /**
- * 更新用户的达人等级
- *
- * @param int $userId 用户ID
- * @param int $talentLevel 达人等级
- * @return bool
- */
- public function updateTalentLevel(int $userId, int $talentLevel): bool
- {
- try {
- $talent = $this->getUserTalent($userId);
- if (!$talent) {
- return false;
- }
- // 如果等级没有变化,无需更新
- if ($talent->talent_level == $talentLevel) {
- return true;
- }
- $talent->talent_level = $talentLevel;
- $result = $talent->save();
- if ($result) {
- // 清除缓存
- Redis::del("promotion:user:{$userId}:talent");
- }
- return $result;
- } catch (\Exception $e) {
- Log::error("更新达人等级失败: " . $e->getMessage());
- return false;
- }
- }
- /**
- * 更新用户的团队统计数据
- *
- * @param int $userId 用户ID
- * @return bool
- */
- public function updatePromotionCounts(int $userId): bool
- {
- try {
- $talent = $this->getUserTalent($userId);
- if (!$talent) {
- return false;
- }
- // 计算直推人数
- $directCount = $this->referralLogic->countDirectReferrals($userId);
- // 计算团队总人数
- $promotionCount = $this->referralLogic->countPromotionMembers($userId);
- // 更新数据
- $talent->direct_count = $directCount;
- $talent->promotion_count = $promotionCount;
- $result = $talent->save();
- if ($result) {
- // 清除缓存
- Redis::del("promotion:user:{$userId}:talent");
- }
- return $result;
- } catch (\Exception $e) {
- Log::error("更新团队统计数据失败: " . $e->getMessage());
- return false;
- }
- }
- /**
- * 检查并更新用户的达人等级
- *
- * @param int $userId 用户ID
- * @return bool
- */
- public function checkAndUpdateTalentLevel(int $userId): bool
- {
- try {
- // 更新团队统计数据
- $this->updatePromotionCounts($userId);
- // 获取用户的达人信息
- $talent = $this->getUserTalent($userId);
- if (!$talent) {
- return false;
- }
- // 获取所有达人等级配置
- $configs = $this->getAllTalentConfigs();
- // 计算应该的达人等级
- $newLevel = TALENT_LEVEL::NONE;
- foreach ($configs as $config) {
- if ($talent->direct_count >= $config->direct_count_required &&
- $talent->promotion_count >= $config->promotion_count_required) {
- $newLevel = $config->level;
- }
- }
- // 如果等级有变化,更新达人等级
- if ($talent->talent_level != $newLevel) {
- return $this->updateTalentLevel($userId, $newLevel);
- }
- return true;
- } catch (\Exception $e) {
- Log::error("检查并更新达人等级失败: " . $e->getMessage());
- return false;
- }
- }
- /**
- * 获取达人等级配置
- *
- * @param int $level 等级
- * @return PromotionTalentConfig|null
- */
- public function getTalentConfig(int $level): ?PromotionTalentConfig
- {
- // 尝试从缓存获取
- $cacheKey = "promotion:talent_config:{$level}";
- $cachedData = Redis::get($cacheKey);
- if ($cachedData !== null) {
- $configData = json_decode($cachedData, true);
- $config = new PromotionTalentConfig();
- $config->fill($configData);
- return $config;
- }
- // 从数据库获取
- $config = PromotionTalentConfig::where('level', $level)->first();
- // 缓存结果
- if ($config) {
- Redis::setex($cacheKey, 86400 * 7, json_encode($config->toArray())); // 缓存7天
- }
- return $config;
- }
- /**
- * 获取所有达人等级配置
- *
- * @return array
- */
- public function getAllTalentConfigs(): array
- {
- // 尝试从缓存获取
- $cacheKey = "promotion:talent_configs";
- $cachedData = Redis::get($cacheKey);
- if ($cachedData !== null) {
- $configsData = json_decode($cachedData, true);
- $configs = [];
- foreach ($configsData as $configData) {
- $config = new PromotionTalentConfig();
- $config->fill($configData);
- $configs[] = $config;
- }
- return $configs;
- }
- // 从数据库获取
- $configs = PromotionTalentConfig::orderBy('level')->get()->toArray();
- // 缓存结果
- Redis::setex($cacheKey, 86400 * 7, json_encode($configs)); // 缓存7天
- return $configs;
- }
- /**
- * 获取达人等级分成比例
- *
- * @param int $level 等级
- * @return float
- */
- public function getTalentProfitRate(int $level): float
- {
- $config = $this->getTalentConfig($level);
- if (!$config) {
- return 0.0;
- }
- return $config->profit_rate;
- }
- /**
- * 获取达人等级权益
- *
- * @param int $level 等级
- * @return array
- */
- public function getTalentBenefits(int $level): array
- {
- $config = $this->getTalentConfig($level);
- if (!$config || empty($config->benefits)) {
- return [];
- }
- return is_array($config->benefits) ? $config->benefits : json_decode($config->benefits, true);
- }
- /**
- * 批量更新用户的达人等级
- *
- * @param array $userIds 用户ID数组
- * @return int 成功更新的数量
- */
- public function batchUpdateTalentLevels(array $userIds): int
- {
- $successCount = 0;
- foreach ($userIds as $userId) {
- if ($this->checkAndUpdateTalentLevel($userId)) {
- $successCount++;
- }
- }
- return $successCount;
- }
- }
|