PHP 用户成长体系

wen PHP项目 6

本文目录导读:

PHP 用户成长体系

  1. 系统架构设计
  2. 任务系统实现
  3. 等级展示组件
  4. 使用示例
  5. 最佳实践建议

我来为你详细介绍PHP用户成长体系的完整设计方案和实现代码。

系统架构设计

数据库表结构

-- 用户表
CREATE TABLE `users` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `username` varchar(50) NOT NULL,
  `email` varchar(100) DEFAULT NULL,
  `current_level` int(11) DEFAULT '1',
  `current_exp` int(11) DEFAULT '0',
  `total_exp` int(11) DEFAULT '0',
  `created_at` timestamp DEFAULT CURRENT_TIMESTAMP,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB;
-- 等级配置表
CREATE TABLE `level_config` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `level` int(11) NOT NULL,
  `level_name` varchar(50) NOT NULL,
  `min_exp` int(11) NOT NULL,
  `max_exp` int(11) NOT NULL,
  `benefits` text,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB;
-- 经验记录表
CREATE TABLE `exp_records` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `user_id` int(11) NOT NULL,
  `exp_change` int(11) NOT NULL,
  `reason` varchar(100) NOT NULL,
  `created_at` timestamp DEFAULT CURRENT_TIMESTAMP,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB;
-- 成长任务表
CREATE TABLE `growth_tasks` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `task_name` varchar(100) NOT NULL,
  `task_type` varchar(50) NOT NULL,
  `exp_reward` int(11) NOT NULL,
  `daily_limit` int(11) DEFAULT '0',
  `weekly_limit` int(11) DEFAULT '0',
  `status` tinyint(1) DEFAULT '1',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB;

核心类设计

<?php
/**
 * 用户成长体系核心类
 */
class GrowthSystem {
    private $db;
    private $userId;
    public function __construct($db, $userId) {
        $this->db = $db;
        $this->userId = $userId;
    }
    /**
     * 添加经验值
     * @param int $exp 经验值
     * @param string $reason 原因
     * @return bool|array
     */
    public function addExp($exp, $reason = '') {
        if ($exp <= 0) return false;
        try {
            $this->db->beginTransaction();
            // 获取当前用户信息
            $user = $this->getUserInfo();
            $newExp = $user['current_exp'] + $exp;
            $newTotalExp = $user['total_exp'] + $exp;
            // 计算新等级
            $newLevel = $this->calculateLevel($newTotalExp);
            // 更新用户信息
            $updateSql = "UPDATE users SET 
                          current_exp = ?,
                          total_exp = ?,
                          current_level = ?
                          WHERE id = ?";
            $stmt = $this->db->prepare($updateSql);
            $stmt->execute([$newExp, $newTotalExp, $newLevel, $this->userId]);
            // 记录经验变化
            $this->logExpChange($exp, $reason);
            // 检查是否升级
            $isLevelUp = ($newLevel > $user['current_level']);
            $this->db->commit();
            return [
                'success' => true,
                'level_up' => $isLevelUp,
                'new_level' => $newLevel,
                'current_exp' => $newExp,
                'total_exp' => $newTotalExp
            ];
        } catch (Exception $e) {
            $this->db->rollBack();
            return ['success' => false, 'error' => $e->getMessage()];
        }
    }
    /**
     * 获取用户成长信息
     */
    public function getUserGrowthInfo() {
        $user = $this->getUserInfo();
        $levelConfig = $this->getLevelConfig($user['current_level']);
        // 计算进度
        $levelProgress = 0;
        if ($levelConfig) {
            $range = $levelConfig['max_exp'] - $levelConfig['min_exp'];
            $current = $user['current_exp'] - $levelConfig['min_exp'];
            $levelProgress = ($range > 0) ? round(($current / $range) * 100, 2) : 100;
        }
        return [
            'user_id' => $user['id'],
            'current_level' => $user['current_level'],
            'level_name' => $levelConfig ? $levelConfig['level_name'] : '',
            'current_exp' => $user['current_exp'],
            'total_exp' => $user['total_exp'],
            'next_level_exp' => $levelConfig ? $levelConfig['max_exp'] - $user['current_exp'] : 0,
            'level_progress' => $levelProgress,
            'level_benefits' => $levelConfig ? json_decode($levelConfig['benefits'], true) : []
        ];
    }
    /**
     * 计算等级
     */
    private function calculateLevel($totalExp) {
        $sql = "SELECT MAX(level) as level FROM level_config WHERE min_exp <= ?";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$totalExp]);
        $result = $stmt->fetch(PDO::FETCH_ASSOC);
        return $result['level'] ?: 1;
    }
    /**
     * 获取等级配置
     */
    private function getLevelConfig($level) {
        $sql = "SELECT * FROM level_config WHERE level = ?";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$level]);
        return $stmt->fetch(PDO::FETCH_ASSOC);
    }
    /**
     * 记录经验变化
     */
    private function logExpChange($exp, $reason) {
        $sql = "INSERT INTO exp_records (user_id, exp_change, reason) VALUES (?, ?, ?)";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$this->userId, $exp, $reason]);
    }
    /**
     * 获取用户信息
     */
    private function getUserInfo() {
        $sql = "SELECT * FROM users WHERE id = ?";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$this->userId]);
        return $stmt->fetch(PDO::FETCH_ASSOC);
    }
}

任务系统实现

<?php
/**
 * 任务系统类
 */
class TaskSystem {
    private $db;
    private $userId;
    private $growth;
    public function __construct($db, $userId) {
        $this->db = $db;
        $this->userId = $userId;
        $this->growth = new GrowthSystem($db, $userId);
    }
    /**
     * 完成任务
     */
    public function completeTask($taskId) {
        // 检查任务
        $task = $this->getTask($taskId);
        if (!$task || $task['status'] != 1) {
            return ['success' => false, 'error' => '任务不存在或已禁用'];
        }
        // 检查每日/每周限制
        if (!$this->checkTaskLimit($taskId, $task)) {
            return ['success' => false, 'error' => '任务次数已达上限'];
        }
        // 记录任务完成
        $this->recordTaskCompletion($taskId);
        // 发放经验奖励
        $result = $this->growth->addExp($task['exp_reward'], '完成任务:' . $task['task_name']);
        return array_merge(['success' => true], $result);
    }
    /**
     * 检查任务限制
     */
    private function checkTaskLimit($taskId, $task) {
        $today = date('Y-m-d');
        $weekStart = date('Y-m-d', strtotime('monday this week'));
        // 检查每日限制
        if ($task['daily_limit'] > 0) {
            $sql = "SELECT COUNT(*) as count FROM task_records 
                    WHERE task_id = ? AND user_id = ? AND DATE(completed_at) = ?";
            $stmt = $this->db->prepare($sql);
            $stmt->execute([$taskId, $this->userId, $today]);
            $dailyCount = $stmt->fetch(PDO::FETCH_ASSOC)['count'];
            if ($dailyCount >= $task['daily_limit']) {
                return false;
            }
        }
        // 检查每周限制
        if ($task['weekly_limit'] > 0) {
            $sql = "SELECT COUNT(*) as count FROM task_records 
                    WHERE task_id = ? AND user_id = ? AND completed_at >= ?";
            $stmt = $this->db->prepare($sql);
            $stmt->execute([$taskId, $this->userId, $weekStart]);
            $weeklyCount = $stmt->fetch(PDO::FETCH_ASSOC)['count'];
            if ($weeklyCount >= $task['weekly_limit']) {
                return false;
            }
        }
        return true;
    }
    /**
     * 记录任务完成
     */
    private function recordTaskCompletion($taskId) {
        $sql = "INSERT INTO task_records (task_id, user_id) VALUES (?, ?)";
        $stmt = $this->db->prepare($sql);
        $stmt->execute([$taskId, $this->userId]);
    }
}

等级展示组件

<?php
/**
 * 等级展示组件
 */
class LevelDisplay {
    /**
     * 生成等级进度条HTML
     */
    public static function renderProgress($growthInfo) {
        $html = '<div class="level-progress">';
        $html .= '<span class="level-badge">Lv.' . $growthInfo['current_level'] . ' ' . 
                 $growthInfo['level_name'] . '</span>';
        $html .= '<div class="progress-bar">';
        $html .= '<div class="progress-fill" style="width: ' . 
                 $growthInfo['level_progress'] . '%"></div>';
        $html .= '</div>';
        $html .= '<span class="progress-text">' . 
                 $growthInfo['level_progress'] . '%</span>';
        $html .= '</div>';
        return $html;
    }
    /**
     * 生成等级权益卡片
     */
    public static function renderBenefits($levelBenefits) {
        if (empty($levelBenefits)) return '';
        $html = '<div class="level-benefits">';
        foreach ($levelBenefits as $benefit) {
            $html .= '<div class="benefit-item">';
            $html .= '<i class="' . $benefit['icon'] . '"></i>';
            $html .= '<span>' . $benefit['description'] . '</span>';
            $html .= '</div>';
        }
        $html .= '</div>';
        return $html;
    }
}

使用示例

<?php
// 初始化数据库连接
$pdo = new PDO('mysql:host=localhost;dbname=test;charset=utf8', 'root', 'password');
// 创建用户成长对象
$userId = 1; // 假设用户ID为1
$growth = new GrowthSystem($pdo, $userId);
// 添加经验值
$result = $growth->addExp(100, '每日签到');
if ($result['success']) {
    // 检查是否升级
    if ($result['level_up']) {
        echo "恭喜升级到 Lv." . $result['new_level'] . "!";
    }
}
// 获取成长信息
$info = $growth->getUserGrowthInfo();
echo "当前等级:" . $info['level_name'] . "<br>";
echo "升级进度:" . $info['level_progress'] . "%<br>";
// 完成任务
$taskSystem = new TaskSystem($pdo, $userId);
$result = $taskSystem->completeTask(1); // 完成任务ID为1的任务
if ($result['success']) {
    echo "任务完成,获得经验奖励!";
}
// 显示进度条
echo LevelDisplay::renderProgress($info);

最佳实践建议

经验值设计原则

  • 递增曲线:等级越高,升级所需经验越多
  • 多维度激励:结合登录、消费、互动等多个维度
  • 防刷机制:设置每日/每周上限

性能优化

// 使用Redis缓存等级配置
class GrowthCache {
    private $redis;
    public function getLevelConfig($level) {
        $cacheKey = "level_config:{$level}";
        $data = $this->redis->get($cacheKey);
        if (!$data) {
            // 从数据库加载
            $data = $this->loadFromDB($level);
            $this->redis->setex($cacheKey, 3600, $data);
        }
        return $data;
    }
}

扩展建议

  • 增加排行榜功能
  • 引入特权体系(VIP)
  • 设置经验值有效期
  • 增加成长值兑换功能

这个成长体系设计包含了完整的用户等级、经验值、任务系统,可以根据实际需求进行调整和扩展。

抱歉,评论功能暂时关闭!