using Media.JoshHeaps.Net.Models;

namespace Media.JoshHeaps.Net.Services;

public class UserService
{
    private readonly DbExecutor _db;

    public UserService(DbExecutor db)
    {
        _db = db;
    }

    public async Task<UserDashboard?> GetUserDashboardAsync(long userId)
    {
        try
        {
            var query = @"
                SELECT
                    u.id, u.username, u.email, u.email_verified, u.created_at, u.last_login,
                    p.bio, p.avatar_url, p.location, p.website, p.updated_at
                FROM app.users u
                LEFT JOIN app.user_profiles p ON u.id = p.user_id
                WHERE u.id = @userId";

            var dashboard = await _db.ExecuteReaderAsync(query, reader =>
            {
                return new UserDashboard
                {
                    UserId = reader.GetInt64(0),
                    Username = reader.GetString(1),
                    Email = reader.GetString(2),
                    EmailVerified = reader.GetBoolean(3),
                    CreatedAt = reader.GetDateTime(4),
                    LastLogin = reader.IsDBNull(5) ? null : reader.GetDateTime(5),
                    Profile = new UserProfile
                    {
                        UserId = reader.GetInt64(0),
                        Bio = reader.IsDBNull(6) ? null : reader.GetString(6),
                        AvatarUrl = reader.IsDBNull(7) ? null : reader.GetString(7),
                        Location = reader.IsDBNull(8) ? null : reader.GetString(8),
                        Website = reader.IsDBNull(9) ? null : reader.GetString(9),
                        UpdatedAt = reader.IsDBNull(10) ? DateTime.UtcNow : reader.GetDateTime(10)
                    }
                };
            }, new { userId });

            return dashboard;
        }
        catch (Exception)
        {
            return null;
        }
    }

    public async Task<UserProfile?> GetUserProfileAsync(long userId)
    {
        try
        {
            var query = @"
                SELECT user_id, bio, avatar_url, location, website, updated_at
                FROM app.user_profiles
                WHERE user_id = @userId";

            var profile = await _db.ExecuteReaderAsync(query, reader =>
            {
                return new UserProfile
                {
                    UserId = reader.GetInt64(0),
                    Bio = reader.IsDBNull(1) ? null : reader.GetString(1),
                    AvatarUrl = reader.IsDBNull(2) ? null : reader.GetString(2),
                    Location = reader.IsDBNull(3) ? null : reader.GetString(3),
                    Website = reader.IsDBNull(4) ? null : reader.GetString(4),
                    UpdatedAt = reader.GetDateTime(5)
                };
            }, new { userId });

            return profile;
        }
        catch (Exception)
        {
            return null;
        }
    }

    public async Task<bool> UpdateUserProfileAsync(long userId, string? bio, string? avatarUrl, string? location, string? website)
    {
        try
        {
            await _db.ExecuteAsync<object>(
                @"UPDATE app.user_profiles
                  SET bio = @bio, avatar_url = @avatarUrl, location = @location,
                      website = @website, updated_at = @updatedAt
                  WHERE user_id = @userId",
                new { userId, bio, avatarUrl, location, website, updatedAt = DateTime.UtcNow }
            );

            return true;
        }
        catch (Exception)
        {
            return false;
        }
    }
}
