Files
Yi.Framework/Yi.Abp.Net8/module/ai-hub/Yi.Framework.AiHub.Application/Services/RechargeService.cs
ccnetcore 4b9f845fae feat: 激活码与VIP充值支持按天计费
- 新增 VIP 天数概念,支持月数与天数组合计算过期时间
- 激活码商品新增 VipDays 配置,并新增 1 天会员试用组合包
- VIP 充值统一按天数计算(1 个月 = 31 天),兼容原有逻辑
- 激活码兑换时支持仅天数或天月组合的 VIP 充值
2025-12-28 17:44:33 +08:00

126 lines
4.8 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
using Mapster;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Volo.Abp.Application.Services;
using Volo.Abp.Users;
using Yi.Framework.AiHub.Application.Contracts.Dtos.Recharge;
using Yi.Framework.AiHub.Application.Contracts.IServices;
using Yi.Framework.AiHub.Domain.Entities;
using Yi.Framework.AiHub.Domain.Managers;
using Yi.Framework.AiHub.Domain.Shared.Consts;
using Yi.Framework.AiHub.Domain.Shared.Enums;
using Yi.Framework.Rbac.Application.Contracts.IServices;
using Yi.Framework.SqlSugarCore.Abstractions;
namespace Yi.Framework.AiHub.Application.Services
{
public class RechargeService : ApplicationService, IRechargeService
{
private readonly ISqlSugarRepository<AiRechargeAggregateRoot> _repository;
private readonly ICurrentUser _currentUser;
private readonly IUserService _userService;
private readonly IRoleService _roleService;
private readonly AiRechargeManager _aiMessageManager;
public RechargeService(
ISqlSugarRepository<AiRechargeAggregateRoot> repository,
ICurrentUser currentUser,
IUserService userService, IRoleService roleService, AiRechargeManager aiMessageManager)
{
_repository = repository;
_currentUser = currentUser;
_userService = userService;
_roleService = roleService;
_aiMessageManager = aiMessageManager;
}
/// <summary>
/// 查询已登录的账户充值记录
/// </summary>
/// <returns></returns>
[Route("recharge/account")]
[Authorize]
public async Task<List<RechargeGetListOutput>> GetListByAccountAsync()
{
var userId = CurrentUser.Id;
var entities = await _repository._DbQueryable.Where(x => x.UserId == userId)
.OrderByDescending(x => x.CreationTime)
.ToListAsync();
var output = entities.Adapt<List<RechargeGetListOutput>>();
return output;
}
/// <summary>
/// 给用户充值VIP
/// </summary>
/// <param name="input">充值输入参数</param>
/// <returns></returns>
[RemoteService(isEnabled:false)]
public async Task RechargeVipAsync(RechargeCreateInput input)
{
DateTime? expireDateTime = null;
// 计算总天数1个月 = 31天
int totalDays = 0;
if (input.Months.HasValue && input.Months.Value > 0)
{
totalDays += input.Months.Value * 31;
}
if (input.Days.HasValue && input.Days.Value > 0)
{
totalDays += input.Days.Value;
}
// 如果有天数,计算过期时间
if (totalDays > 0)
{
// 直接查询该用户最大的过期时间
var maxExpireTime = await _repository._DbQueryable
.Where(x => x.RechargeType == RechargeTypeEnum.Vip)
.Where(x => x.UserId == input.UserId && x.ExpireDateTime.HasValue)
.MaxAsync(x => x.ExpireDateTime);
// 如果最大过期时间大于现在时间,从最大过期时间开始计算
// 否则从当天开始计算
DateTime baseDateTime = maxExpireTime.HasValue && maxExpireTime.Value > DateTime.Now
? maxExpireTime.Value
: DateTime.Now;
// 计算新的过期时间
expireDateTime = baseDateTime.AddDays(totalDays);
}
// 如果总天数为0表示永久VIPExpireDateTime保持为null
// 创建充值记录
var rechargeRecord = new AiRechargeAggregateRoot
{
UserId = input.UserId,
RechargeAmount = input.RechargeAmount,
Content = input.Content,
ExpireDateTime = expireDateTime,
Remark = input.Remark,
ContactInfo = input.ContactInfo,
RechargeType = RechargeTypeEnum.Vip
};
// 保存充值记录到数据库
await _repository.InsertAsync(rechargeRecord);
// 使用UserService给用户添加VIP角色
await _userService.AddUserRoleByRoleCodeAsync(input.UserId,
new List<string>() { AiHubConst.VipRole, "default" });
}
/// <summary>
/// 移除用户vip及角色
/// </summary>
[RemoteService(isEnabled: false)]
public async Task RemoveVipRoleByExpireAsync()
{
var expiredUserIds = await _aiMessageManager.RemoveVipByExpireAsync();
if (expiredUserIds is not null)
{
await _roleService.RemoveUserRoleByRoleCodeAsync(expiredUserIds, AiHubConst.VipRole);
}
}
}
}