/**
 * User Profile Tests
 * Tests for profile retrieval, customization, and data accuracy
 */

import { describe, it, expect, beforeEach, vi } from 'vitest';
import {
  getUserProfile,
  updateUserProfile,
  getUserRewardHistory,
  getUserGameStats,
  getUserAchievements,
  getUserPreferences,
} from './userProfileService.ts';

describe('User Profile Service', () => {
  const testUserId = '123';

  describe('getUserProfile', () => {
    it('should return user profile with all required fields', async () => {
      const profile = await getUserProfile(testUserId);
      
      if (profile) {
        expect(profile).toHaveProperty('profile');
        expect(profile).toHaveProperty('wallet');
        expect(profile).toHaveProperty('stats');
        expect(profile).toHaveProperty('vipStatus');
        
        // Check profile structure
        expect(profile.profile).toHaveProperty('username');
        expect(profile.profile).toHaveProperty('email');
        expect(profile.profile).toHaveProperty('joinDate');
        
        // Check wallet structure
        expect(profile.wallet).toHaveProperty('sweepCoinsBalance');
        expect(profile.wallet).toHaveProperty('goldCoinsBalance');
        
        // Check stats structure
        expect(profile.stats).toHaveProperty('totalGamesPlayed');
        expect(profile.stats).toHaveProperty('totalWinnings');
        expect(profile.stats).toHaveProperty('winRate');
        
        // Check VIP status structure
        expect(profile.vipStatus).toHaveProperty('tier');
        expect(profile.vipStatus).toHaveProperty('name');
        expect(profile.vipStatus).toHaveProperty('multiplier');
      }
    });

    it('should return null for non-existent user', async () => {
      const profile = await getUserProfile('non-existent-user-id');
      expect(profile).toBeNull();
    });
  });

  describe('updateUserProfile', () => {
    it('should update user profile successfully', async () => {
      const updateData = {
        username: 'NewUsername',
        email: 'newemail@example.com',
      };
      
      const success = await updateUserProfile(testUserId, updateData);
      expect(typeof success).toBe('boolean');
    });

    it('should handle invalid update data', async () => {
      const invalidData = {
        username: '', // Empty username
      };
      
      const success = await updateUserProfile(testUserId, invalidData);
      expect(success).toBe(false);
    });
  });

  describe('getUserRewardHistory', () => {
    it('should return reward history array', async () => {
      const rewards = await getUserRewardHistory(testUserId, 10);
      
      expect(Array.isArray(rewards)).toBe(true);
      
      if (rewards.length > 0) {
        const reward = rewards[0];
        expect(reward).toHaveProperty('id');
        expect(reward).toHaveProperty('type');
        expect(reward).toHaveProperty('amount');
        expect(reward).toHaveProperty('redeemedAt');
        expect(reward).toHaveProperty('status');
      }
    });

    it('should respect limit parameter', async () => {
      const limit = 5;
      const rewards = await getUserRewardHistory(testUserId, limit);
      
      expect(rewards.length).toBeLessThanOrEqual(limit);
    });
  });

  describe('getUserGameStats', () => {
    it('should return game statistics', async () => {
      const stats = await getUserGameStats(testUserId);
      
      if (stats) {
        expect(stats).toHaveProperty('gamesPlayed');
        expect(stats).toHaveProperty('totalPlayTime');
        expect(stats).toHaveProperty('favoriteGame');
        expect(stats).toHaveProperty('sessionCount');
        
        // Verify types
        expect(typeof stats.gamesPlayed).toBe('object');
        expect(Array.isArray(stats.gamesPlayed)).toBe(true);
      }
    });
  });

  describe('getUserAchievements', () => {
    it('should return achievements array', async () => {
      const achievements = await getUserAchievements(testUserId);
      
      expect(Array.isArray(achievements)).toBe(true);
      
      if (achievements.length > 0) {
        const achievement = achievements[0];
        expect(achievement).toHaveProperty('id');
        expect(achievement).toHaveProperty('name');
        expect(achievement).toHaveProperty('icon');
        expect(achievement).toHaveProperty('rarity');
        expect(achievement).toHaveProperty('unlockedAt');
      }
    });
  });

  describe('getUserPreferences', () => {
    it('should return user preferences', async () => {
      const preferences = await getUserPreferences(testUserId);
      
      if (preferences) {
        expect(preferences).toHaveProperty('emailNotifications');
        expect(preferences).toHaveProperty('pushNotifications');
        expect(preferences).toHaveProperty('marketingEmails');
        expect(preferences).toHaveProperty('theme');
        expect(preferences).toHaveProperty('language');
      }
    });
  });

  describe('Data Accuracy', () => {
    it('should maintain consistency between profile and wallet data', async () => {
      const profile = await getUserProfile(testUserId);
      
      if (profile) {
        // Verify wallet balances are non-negative
        expect(profile.wallet.sweepCoinsBalance).toBeGreaterThanOrEqual(0);
        expect(profile.wallet.goldCoinsBalance).toBeGreaterThanOrEqual(0);
        
        // Verify stats are consistent
        expect(profile.stats.totalGamesPlayed).toBeGreaterThanOrEqual(0);
        expect(profile.stats.winRate).toBeGreaterThanOrEqual(0);
        expect(profile.stats.winRate).toBeLessThanOrEqual(100);
      }
    });

    it('should have valid VIP tier information', async () => {
      const profile = await getUserProfile(testUserId);
      
      if (profile) {
        const validTiers = ['bronze', 'silver', 'gold', 'platinum', 'diamond'];
        expect(validTiers).toContain(profile.vipStatus.tier);
        
        // Verify VIP progress is between 0-100
        expect(profile.vipStatus.progressToNext).toBeGreaterThanOrEqual(0);
        expect(profile.vipStatus.progressToNext).toBeLessThanOrEqual(100);
        
        // Verify multiplier is positive
        expect(profile.vipStatus.multiplier).toBeGreaterThan(0);
      }
    });

    it('should have valid reward data', async () => {
      const rewards = await getUserRewardHistory(testUserId, 10);
      
      rewards.forEach((reward) => {
        // Verify amount is non-negative
        expect(reward.amount).toBeGreaterThanOrEqual(0);
        
        // Verify status is valid
        const validStatuses = ['pending', 'completed', 'failed', 'cancelled'];
        expect(validStatuses).toContain(reward.status);
        
        // Verify date is valid
        expect(new Date(reward.redeemedAt).getTime()).toBeGreaterThan(0);
      });
    });
  });
});
