using System.Text.Json.Serialization;
using Tiku.Domain.Tenancy;

namespace Tiku.Application.Auth;

/// <summary>
/// 认证令牌对。
/// </summary>
/// <param name="AccessToken">用于访问 API 的 JWT access token。</param>
/// <param name="RefreshToken">用于刷新会话的 refresh token，服务端只保存哈希。</param>
/// <param name="AccessTokenExpiresAt">access token 过期时间。</param>
/// <param name="RefreshTokenExpiresAt">refresh token 过期时间。</param>
public sealed record AuthTokenPair(
    string AccessToken,
    string RefreshToken,
    DateTimeOffset AccessTokenExpiresAt,
    DateTimeOffset RefreshTokenExpiresAt);

/// <summary>
/// 当前登录租户成员摘要。
/// </summary>
/// <param name="TenantId">租户 ID。</param>
/// <param name="TenantName">租户名称。</param>
/// <param name="Role">当前用户在租户内的角色。</param>
/// <param name="Status">租户成员状态。</param>
public sealed record TenantMembershipSummary(
    Guid TenantId,
    string TenantName,
    TenantRole Role,
    MembershipStatus Status);

/// <summary>
/// 登录成功后的应用层用户信息。
/// </summary>
/// <param name="UserId">用户 ID。</param>
/// <param name="Phone">手机号。</param>
/// <param name="Email">邮箱。</param>
/// <param name="Name">用户显示名称。</param>
/// <param name="Realm">当前令牌的 tenant 或 platform 授权域。</param>
/// <param name="Tenant">当前登录租户成员摘要。</param>
/// <param name="Tokens">认证令牌对。</param>
public sealed record AuthenticatedUser(
    Guid UserId,
    string? Phone,
    string? Email,
    string? Name,
    AuthRealm Realm,
    TenantMembershipSummary? Tenant,
    AuthTokenPair Tokens);

public enum AuthenticationStatus
{
    [JsonStringEnumMemberName("authenticated")]
    Authenticated,
    [JsonStringEnumMemberName("password_change_required")]
    PasswordChangeRequired
}

public sealed record AuthenticationResult(
    AuthenticationStatus Status,
    AuthenticatedUser? User = null,
    string? ChallengeToken = null,
    DateTimeOffset? ChallengeExpiresAt = null);

public sealed record PasswordLoginRequest(
    AuthRealm Realm,
    Guid? TenantId,
    string Phone,
    string Password,
    string? IpAddress,
    string? UserAgent);

public sealed record SmsLoginRequest(
    AuthRealm Realm,
    Guid? TenantId,
    string Phone,
    string Code,
    string? IpAddress,
    string? UserAgent);

public sealed record WechatLoginRequest(
    AuthRealm Realm,
    Guid? TenantId,
    string Code,
    string? IpAddress,
    string? UserAgent);

public sealed record RefreshSessionRequest(
    string RefreshToken,
    string? IpAddress,
    string? UserAgent);

public sealed record LogoutSessionRequest(
    string RefreshToken);

public sealed record PasswordChangeChallengeRequest(
    string ChallengeToken,
    string NewPassword,
    string? IpAddress,
    string? UserAgent);

public sealed record SmsSendResult(
    Guid VerificationId,
    DateTimeOffset ExpiresAt);

public sealed record SendSmsCodeRequest(
    Guid TenantId,
    string Phone,
    SmsPurpose Purpose,
    string? IpAddress,
    string? UserAgent,
    string? DeviceId = null);
