using Dpz.Core.EnumLibrary;
namespace Dpz.Core.Public.ViewModel.Response;
/// <summary>
/// 账号会话信息
/// </summary>
public class AccountSessionResponse
{
/// <summary>
/// 会话记录 ID
/// </summary>
public required string Id { get; set; }
/// <summary>
/// 账号
/// </summary>
public required string Account { get; set; }
/// <summary>
/// 会话 ID
/// </summary>
public required string SessionId { get; set; }
/// <summary>
/// 登录 IP 地址
/// </summary>
public string? IpAddress { get; set; }
/// <summary>
/// 客户端原始 User-Agent
/// </summary>
public string? UserAgent { get; set; }
/// <summary>
/// 设备名称
/// </summary>
public string? DeviceName { get; set; }
/// <summary>
/// 设备类型(如 mobile、desktop、tablet)
/// </summary>
public string? DeviceType { get; set; }
/// <summary>
/// 浏览器名称
/// </summary>
public string? BrowserName { get; set; }
/// <summary>
/// 浏览器版本
/// </summary>
public string? BrowserVersion { get; set; }
/// <summary>
/// 操作系统名称
/// </summary>
public string? OsName { get; set; }
/// <summary>
/// 操作系统版本
/// </summary>
public string? OsVersion { get; set; }
/// <summary>
/// 客户端平台标识
/// </summary>
public string? Platform { get; set; }
/// <summary>
/// 屏幕宽度(像素)
/// </summary>
public int? ScreenWidth { get; set; }
/// <summary>
/// 屏幕高度(像素)
/// </summary>
public int? ScreenHeight { get; set; }
/// <summary>
/// 客户端语言
/// </summary>
public string? Language { get; set; }
/// <summary>
/// 定位纬度
/// </summary>
public double? Latitude { get; set; }
/// <summary>
/// 定位经度
/// </summary>
public double? Longitude { get; set; }
/// <summary>
/// 定位精度(米)
/// </summary>
public double? LocationAccuracy { get; set; }
/// <summary>
/// 定位来源(如 GPS、IP)
/// </summary>
public string? LocationSource { get; set; }
/// <summary>
/// 所在国家
/// </summary>
public string? Country { get; set; }
/// <summary>
/// 所在省份/地区
/// </summary>
public string? Region { get; set; }
/// <summary>
/// 所在城市
/// </summary>
public string? City { get; set; }
/// <summary>
/// 时区
/// </summary>
public string? TimeZone { get; set; }
/// <summary>
/// 网络运营商(ISP)
/// </summary>
public string? Isp { get; set; }
/// <summary>
/// 定位信息更新时间
/// </summary>
public DateTime? LocationUpdatedTime { get; set; }
/// <summary>
/// 登录方式
/// </summary>
public LoginMethod Method { get; set; }
/// <summary>
/// 是否已撤销
/// </summary>
public bool Revoked { get; set; }
/// <summary>
/// 撤销时间
/// </summary>
public DateTime? RevokedTime { get; set; }
/// <summary>
/// 创建时间
/// </summary>
public DateTime CreateTime { get; set; }
/// <summary>
/// 最近活跃时间
/// </summary>
public DateTime LastActiveTime { get; set; }
/// <summary>
/// 是否为当前会话
/// </summary>
public bool IsCurrent { get; set; }
/// <summary>
/// 设备显示名称
/// </summary>
public string Device =>
string.IsNullOrWhiteSpace(DeviceName) ? ToDeviceName(UserAgent) : DeviceName;
/// <summary>
/// 登录方式的中文名称
/// </summary>
public string MethodName =>
Method switch
{
LoginMethod.Password => "密码登录",
LoginMethod.Passkey => "Passkey 登录",
_ => Method.ToString(),
};
/// <summary>
/// 会话状态的中文名称(已撤销/活跃)
/// </summary>
public string StatusName => Revoked ? "已撤销" : "活跃";
/// <summary>
/// 是否处于有效(未撤销)状态
/// </summary>
public bool IsSuccess => !Revoked;
private static string ToDeviceName(string? userAgent)
{
if (string.IsNullOrWhiteSpace(userAgent))
{
return "未知设备";
}
return userAgent.Length <= 96 ? userAgent : $"{userAgent[..96]}...";
}
}
⚠⚠ 以下内容为AI分析的结果,请根据实际情况进行判断。
这是一个基于 C# 的响应视图模型(Response ViewModel),用于向客户端返回“账号会话信息”。在用户登录后,系统会记录一条会话记录,本类定义了该记录的完整数据结构、格式化字段和状态判断逻辑。下面分部分说明:
1. 命名空间与引用
using Dpz.Core.EnumLibrary;
namespace Dpz.Core.Public.ViewModel.Response;
- 使用了
Dpz.Core.EnumLibrary中的LoginMethod枚举(表示登录方式)。 - 命名空间表明这是一个在公开响应中使用的视图模型。
2. 类的主要用途
AccountSessionResponse 用于描述一个账号的登录会话信息,包含:
- 会话标识与账号
- 登录时的 IP、User-Agent、设备、浏览器、操作系统等客户端信息
- 地理位置信息
- 登录方式、是否被撤销、创建和活跃时间
- 派生出来的展示字段(设备名称、登录方式中文名、状态中文名等)
典型应用场景:用户查看自己“所有登录的会话”列表,或用于实现“会话管理/吊销”功能。
3. 各部分代码详解
3.1 会话基础信息
public required string Id { get; set; }
public required string Account { get; set; }
public required string SessionId { get; set; }
required是 C# 11 特性,强制在初始化时必须提供这些属性。Id表示会话记录的数据库主键。Account是登录账号(可能是用户名/邮箱等)。SessionId是实际会话令牌对应的标识。
3.2 客户端环境信息
public string? IpAddress { get; set; }
public string? UserAgent { get; set; }
public string? DeviceName { get; set; }
public string? DeviceType { get; set; }
public string? BrowserName { get; set; }
public string? BrowserVersion { get; set; }
public string? OsName { get; set; }
public string? OsVersion { get; set; }
public string? Platform { get; set; }
public int? ScreenWidth { get; set; }
public int? ScreenHeight { get; set; }
public string? Language { get; set; }
- 所有可空类型
?表示该字段可缺失(可能未采集到)。 - 包含浏览器、操作系统、平台、屏幕分辨率、语言等信息。
- 这些数据通常由前端 JS 收集后随着登录请求发送,或从 User-Agent 解析而来。
3.3 地理位置信息
public double? Latitude { get; set; }
public double? Longitude { get; set; }
public double? LocationAccuracy { get; set; }
public string? LocationSource { get; set; }
public string? Country { get; set; }
public string? Region { get; set; }
public string? City { get; set; }
public string? TimeZone { get; set; }
public string? Isp { get; set; }
public DateTime? LocationUpdatedTime { get; set; }
- 经纬度、精度、来源说明(如 GPS 或 IP 定位)。
- 国家、地区、城市、时区、网络运营商(ISP)。
- 记录定位信息最后一次更新时间,可用于时效判断。
3.4 登录与状态信息
public LoginMethod Method { get; set; }
public bool Revoked { get; set; }
public DateTime? RevokedTime { get; set; }
public DateTime CreateTime { get; set; }
public DateTime LastActiveTime { get; set; }
public bool IsCurrent { get; set; }
Method: 使用枚举LoginMethod,包含密码登录、Passkey 登录等。Revoked: 表示该会话是否已被用户主动撤销。RevokedTime: 撤销的时间(如果已撤销)。CreateTime: 会话创建时间。LastActiveTime: 最近一次活跃时间,用于判断是否活跃。IsCurrent: 是否为当前正在使用的会话。
4. 计算属性(只读派生属性)
4.1 设备显示名称
public string Device =>
string.IsNullOrWhiteSpace(DeviceName) ? ToDeviceName(UserAgent) : DeviceName;
- 若
DeviceName为空,则通过ToDeviceName(UserAgent)从 User-Agent 中生成一个展示名称。 - 否则直接使用
DeviceName。
4.2 登录方式中文名
public string MethodName =>
Method switch
{
LoginMethod.Password => "密码登录",
LoginMethod.Passkey => "Passkey 登录",
_ => Method.ToString(),
};
- 根据
LoginMethod枚举值映射为中文名称。 _是默认分支,会输出枚举原本的字符串形式。
4.3 状态中文名
public string StatusName => Revoked ? "已撤销" : "活跃";
- 简单根据布尔值输出中文状态。
4.4 是否有效状态
public bool IsSuccess => !Revoked;
- 取反
Revoked,用于快速判断该会话是否仍在有效状态,方便调用方做逻辑判断。
5. 私有辅助方法
private static string ToDeviceName(string? userAgent)
{
if (string.IsNullOrWhiteSpace(userAgent))
return "未知设备";
return userAgent.Length <= 96 ? userAgent : $"{userAgent[..96]}...";
}
- 当
DeviceName为空时,此方法将完整的 User-Agent 字符串作为设备名返回。 - 如果 User-Agent 过长(超过 96 字符),则截取前 96 个字符并加省略号,避免 UI 展示过长。
- 如果 User-Agent 也为空,则返回“未知设备”。
6. 整体设计思想
该类是典型的 响应模型(Response Model),集成了数据存储字段和展示派生属性。它让后端可以直接返回丰富的会话信息,前端无需再做额外处理即可渲染界面。required 和可空类型确保了数据完整性;派生属性和私有方法则进一步封装了格式化逻辑,使得调用方代码更加简洁清晰。
AI 正在分析代码…
评论加载中...