提交代码

This commit is contained in:
zpc 2024-11-15 02:12:27 +08:00
parent 63af05415d
commit 18336f87fb
11 changed files with 372 additions and 7 deletions

View File

@ -7,6 +7,7 @@ using CloudGaming.Code.DataAccess;
using CloudGaming.Code.MiddlewareExtend;
using CloudGaming.DtoModel.Account;
using CloudGaming.DtoModel.Account.Login;
using CloudGaming.DtoModel.Account.User;
using CloudGaming.GameModel.Db.Db_Ext;
using HuanMeng.DotNetCore.AttributeExtend;
@ -57,13 +58,14 @@ public class AccountController : CloudGamingControllerBase
}
/// <summary>
///
/// 获取用户信息
/// </summary>
/// <returns></returns>
[HttpGet]
[Authorize]
public async Task<bool> GetUserInfo()
public async Task<UserInfoDto> GetUserInfo()
{
return true;
AccountBLL account = new AccountBLL(ServiceProvider);
return await account.GetUserInfo();
}
}

View File

@ -4,11 +4,15 @@ using CloudGaming.Code.Account.Contract;
using CloudGaming.Code.Sms;
using CloudGaming.DtoModel.Account;
using CloudGaming.DtoModel.Account.Login;
using CloudGaming.DtoModel.Account.User;
using HuanMeng.DotNetCore.JwtInfrastructure;
using HuanMeng.DotNetCore.Redis;
using HuanMeng.DotNetCore.Utility;
using Microsoft.EntityFrameworkCore.Metadata.Internal;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System;
@ -119,6 +123,16 @@ namespace CloudGaming.Code.Account
var user = await RegisterOrUpdateUserAsync(userId, account, ip);
//注册用户详细信息
var userData = await EnsureUserDataExistsAsync(user.Id, account);
//用户货币
var userCurrency = await EnsureUserCurrencyExistsAsync(user.Id);
if (userCurrency == null)
{
userCurrency = new List<T_User_Currency>();
}
var userCurrencyDic = userCurrency.ToDictionary(it => (UserCurrencyType)it.CurrencyType);
var userInfoKey = GetUserInfoRedisKey(user.Id);
var userInfo = LoadUserInfo(user, userData, userCurrencyDic);
await RedisCache.StringSetAsync(userInfoKey, userInfo, TimeSpan.FromHours(1));
//创建jwt登录
var jwt = GenerateJwtToken(user);
var accountLogIn = new AccountLogInResponse
@ -161,8 +175,6 @@ namespace CloudGaming.Code.Account
private async Task ManageDeviceCacheAsync(int userId, string currentTokenMd5, List<T_User_Token> deviceList)
{
// 获取用户当前所有的登录缓存key
var existingKeys = await RedisServerCache.ScanKeysAsync($"user:login:{userId}:*");
@ -211,7 +223,8 @@ namespace CloudGaming.Code.Account
State = 0,
UserIconUrl = AppConfig.UserConfig.UserIconUrl,
NickName = $"{AppConfig.UserConfig.NickName}{new Random().Next(1000, 9999)}",
Ip = ip
Ip = ip,
IsRealName = false
};
await Dao.DaoUser.Context.T_User.AddAsync(user);
await Dao.DaoUser.Context.SaveChangesAsync();
@ -222,7 +235,7 @@ namespace CloudGaming.Code.Account
user.UpdatedAt = DateTime.Now;
user.Ip = ip;
await Dao.DaoUser.Context.SaveChangesAsync();
return user;
}
@ -245,6 +258,28 @@ namespace CloudGaming.Code.Account
}
return userData;
}
// 确保用户数据存在
private async Task<List<T_User_Currency>> EnsureUserCurrencyExistsAsync(int userId)
{
var userCurrencys = await Dao.DaoUser.Context.T_User_Currency.Where(it => it.UserId == userId).ToListAsync();
if (userCurrencys == null || userCurrencys.Count == 0)
{
userCurrencys ??= new List<T_User_Currency>();
var userCurrency = new T_User_Currency
{
CreateAt = DateTime.Now,
CurrencyMoney = 0,
CurrencyName = UserCurrencyType..ToString(),
CurrencyType = (int)UserCurrencyType.,
UpdateAt = DateTime.Now,
UserId = userId
};
await Dao.DaoUser.Context.T_User_Currency.AddAsync(userCurrency);
await Dao.DaoUser.Context.SaveChangesAsync();
userCurrencys.Add(userCurrency);
}
return userCurrencys;
}
// 生成JWT令牌
private JwtAuthResult GenerateJwtToken(T_User user)
@ -327,5 +362,96 @@ namespace CloudGaming.Code.Account
#endregion
public string GetUserInfoRedisKey(int userId)
{
return $"user:userInfo:{userId}";
}
/// <summary>
///
/// </summary>
/// <returns></returns>
public async Task<UserInfoDto> GetUserInfo()
{
var userId = _UserId;
if (userId == 0)
{
throw MessageBox.Show(ResonseCode.NotFoundRecord, "未找到用户");
}
string key = GetUserInfoRedisKey(userId);
var userInfo = await RedisCache.StringGetAsync<UserInfo>(key);
if (userInfo == null)
{
userInfo = new UserInfo() { };
//用户信息
var user = await Dao.DaoUser.Context.T_User.FirstOrDefaultAsync(it => it.Id == userId);
//用户扩展信息
var userData = await Dao.DaoUser.Context.T_User_Data.FirstOrDefaultAsync(it => it.UserId == userId);
//用户货币
var userCurrency = await Dao.DaoUser.Context.T_User_Currency.Where(it => it.UserId == userId).ToDictionaryAsync(it => (UserCurrencyType)it.CurrencyType);
if (user == null)
{
throw MessageBox.Show(ResonseCode.NotFoundRecord, "未找到用户信息");
}
if (userData == null)
{
throw MessageBox.Show(ResonseCode.NotFoundRecord, "未找到用户扩展信息");
}
userInfo = LoadUserInfo(user, userData, userCurrency);
await RedisCache.StringSetAsync(key, userInfo, TimeSpan.FromHours(1));
}
UserInfoDto userInfoDto = Mapper.Map<UserInfoDto>(userInfo);
return userInfoDto;
}
/// <summary>
/// 加载用户缓存
/// </summary>
/// <param name="key"></param>
/// <param name="user"></param>
/// <param name="userData"></param>
/// <param name="userCurrency"></param>
/// <returns></returns>
private UserInfo LoadUserInfo(T_User? user, T_User_Data? userData, Dictionary<UserCurrencyType, T_User_Currency> userCurrency)
{
var userInfo = new UserInfo() { };
userInfo.NickName = user.NickName;
userInfo.UserId = user.Id;
userInfo.UserIcon = user.UserIconUrl;
userInfo.IsRealName = user.UserRealNameStatus > 0;
userInfo.IsJuveniles = false;
userInfo.UserName = "";
userInfo.IdCard = "";
if (userInfo.IsRealName)
{
userInfo.IsJuveniles = user.UserRealNameStatus == 2;
if (!string.IsNullOrEmpty(user.UserName))
{
// 将用户昵称设置成 "陈*风" 或 "陈*"(如果只有两个字符)
userInfo.UserName = user.UserName.Length <= 2
? user.UserName.Substring(0, 1) + "*"
: user.UserName.Substring(0, 1) + "*" + user.UserName.Substring(user.UserName.Length - 1);
}
// 将用户身份证号设置成 "前四位*后四位"
if (!string.IsNullOrEmpty(user.IDCard) && user.IDCard.Length >= 8)
{
userInfo.IdCard = user.IDCard.Substring(0, 4) + "*********" + user.IDCard.Substring(user.IDCard.Length - 4);
}
}
userInfo.TotalGamingTime = 0;
userInfo.PhoneNum = userData?.PhoneNum ?? "";
userInfo.Email = userData?.Email ?? "";
userInfo.Diamond = (int)userCurrency.GetUserCurrency(UserCurrencyType.);
return userInfo;
}
/// <summary>
/// 实名认证
/// </summary>
/// <returns></returns>
public async Task<bool> RealAuthentication(string userName, string idCard)
{
return true;
}
}
}

View File

@ -1,6 +1,7 @@
using CloudGaming.Code.Account.Contract;
using CloudGaming.Code.Account.Login;
using CloudGaming.DtoModel.Account.Login;
using CloudGaming.DtoModel.Account.User;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
@ -47,5 +48,23 @@ namespace CloudGaming.Code.Account
var propertie = jsonObject.Properties();
return keysToCheck.All(key => propertie.Any(p => string.Equals(p.Name, key, StringComparison.OrdinalIgnoreCase)));
}
/// <summary>
/// 获取用户货币
/// </summary>
/// <param name="curreny"></param>
/// <param name="userCurrencyType"></param>
/// <returns></returns>
public static decimal GetUserCurrency(this Dictionary<UserCurrencyType, T_User_Currency> curreny, UserCurrencyType userCurrencyType)
{
if (curreny != null)
{
if (curreny.TryGetValue(userCurrencyType, out var _currency))
{
return _currency.CurrencyMoney;
}
}
return 0;
}
}
}

View File

@ -3,12 +3,15 @@ using AutoMapper;
using CloudGaming.Code.Cache;
using CloudGaming.Code.Config;
using CloudGaming.Code.DataAccess;
using CloudGaming.DtoModel.Account.User;
using HuanMeng.DotNetCore.JwtInfrastructure.Interface;
using HuanMeng.DotNetCore.Redis;
using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
using Microsoft.IdentityModel.Tokens;
using StackExchange.Redis;
@ -244,5 +247,72 @@ namespace CloudGaming.Code.AppExtend
}
}
#endregion
#region
private RequestUserInfo? _userInfo;
/// <summary>
/// 用户信息
/// </summary>
public RequestUserInfo UserInfo
{
get
{
if (_userInfo == null)
{
var accessToken = HttpContextAccessor.HttpContext.Request.Headers.GetAuthorization();
if (!string.IsNullOrEmpty(accessToken))
{
try
{
var (principal, jwtToken) = JwtAuthManager.DecodeJwtToken(accessToken);
if (jwtToken == null)//|| !jwtToken.Header.Alg.Equals(SecurityAlgorithms.HmacSha256Signature)
{
throw new SecurityTokenException("无效的token");
}
var userIdStr = principal.FindFirst("UserId")?.Value;
if (string.IsNullOrEmpty(userIdStr))
{
throw new SecurityTokenException("无效的token");
}
var nickName = principal.FindFirst("NickName")?.Value;
var userId = int.Parse(userIdStr);
this._userInfo = new RequestUserInfo()
{
UserId = userId,
NickName = nickName
};
}
catch (Exception)
{
_userInfo = new RequestUserInfo()
{
UserId = 0
};
}
}
else
{
_userInfo = new RequestUserInfo()
{
UserId = 0
};
}
}
return _userInfo;
}
}
/// <summary>
/// 用户Id
/// </summary>
public int _UserId
{
get
{
return UserInfo?.UserId ?? 0;
}
}
#endregion
}
}

View File

@ -0,0 +1,25 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace CloudGaming.DtoModel.Account.User
{
/// <summary>
/// 请求标头携带的用户信息
/// </summary>
public class RequestUserInfo
{
public RequestUserInfo() { }
/// <summary>
/// 昵称
/// </summary>
public string NickName { get; set; }
/// <summary>
/// 用户id
/// </summary>
public int UserId { get; set; }
}
}

View File

@ -0,0 +1,18 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace CloudGaming.DtoModel.Account.User
{
/// 用户货币类型
/// </summary>
public enum UserCurrencyType
{
/// <summary>
/// 钻石
/// </summary>
= 0
}
}

View File

@ -0,0 +1,68 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace CloudGaming.DtoModel.Account.User
{
/// <summary>
/// 用户信息
/// </summary>
public class UserInfo
{
/// <summary>
/// 用户昵称
/// </summary>
public string NickName { get; set; }
/// <summary>
/// 用户id
/// </summary>
public int UserId { get; set; }
/// <summary>
/// 用户手机号
/// </summary>
public string PhoneNum { get; set; }
/// <summary>
/// 用户邮箱
/// </summary>
public string Email { get; set; }
/// <summary>
/// 用户头像
/// </summary>
public string UserIcon { get; set; }
/// <summary>
/// 用户钻石
/// </summary>
public int Diamond { get; set; }
/// <summary>
/// 总游玩时间(分钟)
/// </summary>
public int TotalGamingTime { get; set; }
/// <summary>
/// 用户是否实名认证
/// </summary>
public bool IsRealName { get; set; }
/// <summary>
/// 是否未成年
/// </summary>
public bool IsJuveniles { get; set; }
/// <summary>
/// 实名认证名称
/// </summary>
public string UserName { get; set; }
/// <summary>
/// 身份证号
/// </summary>
public string IdCard { get; set; }
}
}

View File

@ -0,0 +1,18 @@
using AutoMapper;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace CloudGaming.DtoModel.Account.User
{
/// <summary>
/// 用户信息
/// </summary>
[AutoMap(typeof(UserInfo))]
public class UserInfoDto : UserInfo
{
}
}

View File

@ -134,6 +134,7 @@ public partial class CloudGamingUserContext : MultiTenantDbContext//DbContext
.HasMaxLength(100)
.HasComment("姓名")
.UseCollation("Chinese_PRC_CI_AS");
entity.Property(e => e.UserRealNameStatus).HasComment("用户实名认证状态0未认证1已整整2未成年");
//添加全局筛选器
if (this.TenantInfo != null)
{

View File

@ -78,4 +78,9 @@ public partial class T_User: MultiTenantEntity
/// 是否是测试账号
/// </summary>
public virtual bool? IsTest { get; set; }
/// <summary>
/// 用户实名认证状态0未认证1已整整2未成年
/// </summary>
public virtual int UserRealNameStatus { get; set; }
}

View File

@ -157,6 +157,19 @@ namespace HuanMeng.DotNetCore.Redis
// 将 RedisValue 转换为 T 类型
return JsonConvert.DeserializeObject<T>(value);
}
/// <summary>
/// 数据存放在redis
/// </summary>
/// <param name="database"></param>
/// <param name="key"></param>
/// <param name="value"></param>
/// <param name="expiry"></param>
/// <returns></returns>
public static async Task<bool> StringSetAsync(this IDatabase database, string key, object value, TimeSpan? expiry)
{
return await database.StringSetAsync(key, (value == null ? "" : JsonConvert.SerializeObject(value)), expiry, When.Always);
}
/// <summary>
/// 获取一个key的对象
/// </summary>