| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293 |
- <?php
- namespace App\Services;
- use App\Support\PromotionRules;
- use Illuminate\Database\Eloquent\Builder;
- use Illuminate\Database\Query\Builder as QueryBuilder;
- use Illuminate\Support\Facades\DB;
- use Illuminate\Support\Facades\Schema;
- /** 会员彩金的展示类型与筛选共用映射,资金账本仍保留原记账类型。 */
- final class MemberBonusLogService
- {
- public const LEDGER_TYPES = ['即充即送', '老用户回归', '余额宝利息', '注册赠送', '优惠活动', '充值返现'];
- private const PROMOTIONS = [
- PromotionRules::LOSS => '净亏邀请',
- PromotionRules::FIRST_DEPOSIT => '首充奖励',
- PromotionRules::WHEEL => '转盘',
- PromotionRules::UPGRADE_INVITE => '邀请升级奖励',
- ];
- private bool $hasPromotions;
- private bool $hasRechargeBonuses;
- public function __construct()
- {
- $this->hasPromotions = Schema::hasTable('promotion_rewards') && Schema::hasTable('promotion_activities');
- $this->hasRechargeBonuses = Schema::hasTable('recharge_bonus_rewards');
- }
- public static function types(): array
- {
- return ['即充即送', '转盘', '老用户回归', '余额宝利息', '净亏邀请', '首充奖励',
- '邀请升级奖励', '充值渠道赠送', '注册赠送', '优惠活动', '充值返现'];
- }
- private function promotionLogs(?int $type = null): QueryBuilder
- {
- return DB::table('promotion_rewards as pr')
- ->join('promotion_activities as pa', 'pa.id', '=', 'pr.activity_id')
- ->whereIn('pa.type', $type === null ? array_keys(self::PROMOTIONS) : [$type])
- ->whereNotNull('pr.credited_log_id')->select('pr.credited_log_id');
- }
- private function rechargeLogs(): QueryBuilder
- {
- return DB::table('recharge_bonus_rewards')->whereNotNull('credited_log_id')->select('credited_log_id');
- }
- public function filter(Builder $query, ?string $type): void
- {
- if ($type === null || $type === '') return;
- $promotionType = array_search($type, self::PROMOTIONS, true);
- if ($promotionType !== false) {
- $query->where('balance_logs.change_type', '优惠活动');
- if ($this->hasPromotions) $query->whereIn('balance_logs.id', $this->promotionLogs($promotionType));
- else $query->whereRaw('1 = 0');
- return;
- }
- if ($type === '充值渠道赠送') {
- $query->where('balance_logs.change_type', '优惠活动');
- if ($this->hasRechargeBonuses) $query->whereIn('balance_logs.id', $this->rechargeLogs());
- else $query->whereRaw('1 = 0');
- // 与展示时一致:独立活动关联优先。
- if ($this->hasPromotions) $query->whereNotIn('balance_logs.id', $this->promotionLogs());
- return;
- }
- $query->where('balance_logs.change_type', $type);
- if ($type === '优惠活动') {
- if ($this->hasPromotions) $query->whereNotIn('balance_logs.id', $this->promotionLogs());
- if ($this->hasRechargeBonuses) $query->whereNotIn('balance_logs.id', $this->rechargeLogs());
- }
- }
- public function decorate(array $rows): array
- {
- $ids = array_column(array_filter($rows, fn ($row) => $row['change_type'] === '优惠活动'), 'id');
- if (!$ids) return $rows;
- $promotions = $this->hasPromotions ? DB::table('promotion_rewards as pr')
- ->join('promotion_activities as pa', 'pa.id', '=', 'pr.activity_id')
- ->whereIn('pr.credited_log_id', $ids)->whereIn('pa.type', array_keys(self::PROMOTIONS))
- ->pluck('pa.type', 'pr.credited_log_id')->all() : [];
- $recharges = $this->hasRechargeBonuses ? array_fill_keys(DB::table('recharge_bonus_rewards')
- ->whereIn('credited_log_id', $ids)->pluck('credited_log_id')->all(), true) : [];
- foreach ($rows as &$row) {
- if ($row['change_type'] !== '优惠活动') continue;
- if (isset($promotions[$row['id']])) $row['change_type'] = self::PROMOTIONS[(int)$promotions[$row['id']]];
- elseif (isset($recharges[$row['id']])) $row['change_type'] = '充值渠道赠送';
- }
- unset($row);
- return $rows;
- }
- }
|