294 lines
7.5 KiB
JavaScript
294 lines
7.5 KiB
JavaScript
const express = require('express');
|
|
const router = express.Router();
|
|
const { getDB } = require('../database');
|
|
const { agentAuth } = require('../middleware/agentAuth');
|
|
const { logger } = require('../config/logger');
|
|
|
|
/**
|
|
* 获取代理统计数据
|
|
* GET /api/agent/stats
|
|
*/
|
|
router.get('/stats', agentAuth, async (req, res) => {
|
|
try {
|
|
const agentId = req.agent.id;
|
|
|
|
// 获取下级用户统计
|
|
const [userStats] = await getDB().execute(`
|
|
SELECT
|
|
COUNT(*) as total_users,
|
|
COUNT(CASE WHEN DATE(created_at) = CURDATE() THEN 1 END) as today_new_users,
|
|
COUNT(CASE WHEN last_login_at >= DATE_SUB(NOW(), INTERVAL 7 DAY) THEN 1 END) as active_users,
|
|
CAST(COALESCE(SUM(balance), 0) AS DECIMAL(10,2)) as total_balance
|
|
FROM agent_merchants
|
|
WHERE agent_id = ?
|
|
`, [agentId]);
|
|
|
|
// 获取佣金统计
|
|
const [commissionStats] = await getDB().execute(`
|
|
SELECT
|
|
CAST(COALESCE(SUM(commission_amount), 0) AS DECIMAL(10,2)) as total_commission,
|
|
CAST(COALESCE(SUM(CASE WHEN DATE(created_at) = CURDATE() THEN commission_amount ELSE 0 END), 0) AS DECIMAL(10,2)) as today_commission,
|
|
CAST(COALESCE(SUM(CASE WHEN status = 'paid' THEN commission_amount ELSE 0 END), 0) AS DECIMAL(10,2)) as paid_commission,
|
|
CAST(COALESCE(SUM(CASE WHEN status = 'pending' THEN commission_amount ELSE 0 END), 0) AS DECIMAL(10,2)) as pending_commission
|
|
FROM agent_commission_records
|
|
WHERE agent_id = ?
|
|
`, [agentId]);
|
|
|
|
// 获取转账统计
|
|
const [transferStats] = await getDB().execute(`
|
|
SELECT
|
|
COUNT(*) as total_transfers,
|
|
COUNT(CASE WHEN DATE(created_at) = CURDATE() THEN 1 END) as today_transfers,
|
|
CAST(COALESCE(SUM(amount), 0) AS DECIMAL(10,2)) as total_amount,
|
|
CAST(COALESCE(SUM(CASE WHEN DATE(created_at) = CURDATE() THEN amount ELSE 0 END), 0) AS DECIMAL(10,2)) as today_amount
|
|
FROM transfers t
|
|
INNER JOIN agent_merchants am ON (t.from_user_id = am.merchant_id OR t.to_user_id = am.merchant_id)
|
|
WHERE am.agent_id = ?
|
|
`, [agentId]);
|
|
|
|
const stats = {
|
|
users: userStats[0] || {
|
|
total_users: 0,
|
|
today_new_users: 0,
|
|
active_users: 0,
|
|
total_balance: '0.00'
|
|
},
|
|
commissions: commissionStats[0] || {
|
|
total_commission: '0.00',
|
|
today_commission: '0.00',
|
|
paid_commission: '0.00',
|
|
pending_commission: '0.00'
|
|
},
|
|
transfers: transferStats[0] || {
|
|
total_transfers: 0,
|
|
today_transfers: 0,
|
|
total_amount: '0.00',
|
|
today_amount: '0.00'
|
|
}
|
|
};
|
|
|
|
res.json({
|
|
success: true,
|
|
data: stats
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('获取代理统计数据失败', {
|
|
error: error.message,
|
|
stack: error.stack,
|
|
agentId: req.agent?.id
|
|
});
|
|
|
|
res.status(500).json({
|
|
success: false,
|
|
message: '获取统计数据失败'
|
|
});
|
|
}
|
|
});
|
|
|
|
/**
|
|
* 获取用户增长趋势数据
|
|
* GET /api/agent/user-growth-trend
|
|
*/
|
|
router.get('/user-growth-trend', agentAuth, async (req, res) => {
|
|
try {
|
|
const agentId = req.agent.id;
|
|
const { days = 7 } = req.query;
|
|
|
|
const [trendData] = await getDB().execute(`
|
|
SELECT
|
|
DATE(created_at) as date,
|
|
COUNT(*) as count
|
|
FROM agent_merchants
|
|
WHERE agent_id = ?
|
|
AND created_at >= DATE_SUB(CURDATE(), INTERVAL ? DAY)
|
|
GROUP BY DATE(created_at)
|
|
ORDER BY date ASC
|
|
`, [agentId, parseInt(days)]);
|
|
|
|
res.json({
|
|
success: true,
|
|
data: trendData
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('获取用户增长趋势失败', {
|
|
error: error.message,
|
|
stack: error.stack,
|
|
agentId: req.agent?.id
|
|
});
|
|
|
|
res.status(500).json({
|
|
success: false,
|
|
message: '获取趋势数据失败'
|
|
});
|
|
}
|
|
});
|
|
|
|
/**
|
|
* 获取佣金收入趋势数据
|
|
* GET /api/agent/commission-trend
|
|
*/
|
|
router.get('/commission-trend', agentAuth, async (req, res) => {
|
|
try {
|
|
const agentId = req.agent.id;
|
|
const { days = 7 } = req.query;
|
|
|
|
const [trendData] = await getDB().execute(`
|
|
SELECT
|
|
DATE(created_at) as date,
|
|
CAST(COALESCE(SUM(commission_amount), 0) AS DECIMAL(10,2)) as amount
|
|
FROM agent_commission_records
|
|
WHERE agent_id = ?
|
|
AND created_at >= DATE_SUB(CURDATE(), INTERVAL ? DAY)
|
|
GROUP BY DATE(created_at)
|
|
ORDER BY date ASC
|
|
`, [agentId, parseInt(days)]);
|
|
|
|
res.json({
|
|
success: true,
|
|
data: trendData
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('获取佣金趋势失败', {
|
|
error: error.message,
|
|
stack: error.stack,
|
|
agentId: req.agent?.id
|
|
});
|
|
|
|
res.status(500).json({
|
|
success: false,
|
|
message: '获取趋势数据失败'
|
|
});
|
|
}
|
|
});
|
|
|
|
/**
|
|
* 获取佣金类型分布数据
|
|
* GET /api/agent/commission-distribution
|
|
*/
|
|
router.get('/commission-distribution', agentAuth, async (req, res) => {
|
|
try {
|
|
const agentId = req.agent.id;
|
|
|
|
const [distributionData] = await getDB().execute(`
|
|
SELECT
|
|
commission_type as type,
|
|
COUNT(*) as count,
|
|
CAST(COALESCE(SUM(commission_amount), 0) AS DECIMAL(10,2)) as amount
|
|
FROM agent_commission_records
|
|
WHERE agent_id = ?
|
|
GROUP BY commission_type
|
|
ORDER BY amount DESC
|
|
`, [agentId]);
|
|
|
|
res.json({
|
|
success: true,
|
|
data: distributionData
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('获取佣金分布失败', {
|
|
error: error.message,
|
|
stack: error.stack,
|
|
agentId: req.agent?.id
|
|
});
|
|
|
|
res.status(500).json({
|
|
success: false,
|
|
message: '获取分布数据失败'
|
|
});
|
|
}
|
|
});
|
|
|
|
/**
|
|
* 获取最新下级用户
|
|
* GET /api/agent/recent-users
|
|
*/
|
|
router.get('/recent-users', agentAuth, async (req, res) => {
|
|
try {
|
|
const agentId = req.agent.id;
|
|
const { limit = 10 } = req.query;
|
|
|
|
const [recentUsers] = await getDB().execute(`
|
|
SELECT
|
|
u.id,
|
|
u.username,
|
|
u.real_name,
|
|
u.phone,
|
|
u.avatar,
|
|
u.balance,
|
|
u.created_at,
|
|
am.created_at as join_date
|
|
FROM agent_merchants am
|
|
LEFT JOIN users u ON am.merchant_id = u.id
|
|
WHERE am.agent_id = ?
|
|
ORDER BY am.created_at DESC
|
|
LIMIT ?
|
|
`, [agentId, parseInt(limit)]);
|
|
|
|
res.json({
|
|
success: true,
|
|
data: recentUsers
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('获取最新用户失败', {
|
|
error: error.message,
|
|
stack: error.stack,
|
|
agentId: req.agent?.id
|
|
});
|
|
|
|
res.status(500).json({
|
|
success: false,
|
|
message: '获取最新用户失败'
|
|
});
|
|
}
|
|
});
|
|
|
|
/**
|
|
* 获取最新佣金记录
|
|
* GET /api/agent/recent-commissions
|
|
*/
|
|
router.get('/recent-commissions', agentAuth, async (req, res) => {
|
|
try {
|
|
const agentId = req.agent.id;
|
|
const { limit = 10 } = req.query;
|
|
|
|
const [recentCommissions] = await getDB().execute(`
|
|
SELECT
|
|
acr.id,
|
|
acr.commission_type,
|
|
acr.commission_amount,
|
|
acr.status,
|
|
acr.created_at,
|
|
u.username,
|
|
u.real_name
|
|
FROM agent_commission_records acr
|
|
LEFT JOIN users u ON acr.merchant_id = u.id
|
|
WHERE acr.agent_id = ?
|
|
ORDER BY acr.created_at DESC
|
|
LIMIT ?
|
|
`, [agentId, parseInt(limit)]);
|
|
|
|
res.json({
|
|
success: true,
|
|
data: recentCommissions
|
|
});
|
|
|
|
} catch (error) {
|
|
logger.error('获取最新佣金失败', {
|
|
error: error.message,
|
|
stack: error.stack,
|
|
agentId: req.agent?.id
|
|
});
|
|
|
|
res.status(500).json({
|
|
success: false,
|
|
message: '获取最新佣金失败'
|
|
});
|
|
}
|
|
});
|
|
|
|
module.exports = router; |