import 'dart:convert';
import 'package:flutter_secure_storage/flutter_secure_storage.dart';
import 'http_service.dart';
import '../constants/api_constants.dart';
import '../models/puzzle_models.dart';

class PuzzleService {
  static const FlutterSecureStorage _storage = FlutterSecureStorage();
  static const String _gameStateKey = 'wordle_game_state';

  static Future<DailyChallenge?> getDailyChallenge() async {
    try {
      final response = await HttpService.get(ApiConstants.dailyChallengeEndpoint);
      
      if (response.statusCode == 200) {
        final dailyChallengeResponse = DailyChallengeResponse.fromJson(
          jsonDecode(response.body)
        );
        return dailyChallengeResponse.data;
      } else {
        print('Failed to get daily challenge: ${response.statusCode}');
        return null;
      }
    } catch (e) {
      print('Error getting daily challenge: $e');
      return null;
    }
  }

  static Future<bool> submitAttempt({
    required int attempts,
    required bool solved,
  }) async {
    try {
      final attempt = PuzzleAttempt(attempts: attempts, solved: solved);
      final response = await HttpService.post(
        ApiConstants.puzzleAttemptEndpoint,
        attempt.toJson(),
      );
      
      if (response.statusCode == 200 || response.statusCode == 201) {
        final responseData = jsonDecode(response.body);
        return responseData['status'] ?? false;
      } else {
        print('Failed to submit attempt: ${response.statusCode}');
        return false;
      }
    } catch (e) {
      print('Error submitting attempt: $e');
      return false;
    }
  }

  static Future<void> saveGameState(GameState gameState) async {
    try {
      await _storage.write(
        key: _gameStateKey,
        value: jsonEncode(gameState.toJson()),
      );
    } catch (e) {
      print('Error saving game state: $e');
    }
  }

  static Future<GameState?> loadGameState() async {
    try {
      final gameStateString = await _storage.read(key: _gameStateKey);
      if (gameStateString != null) {
        final gameState = GameState.fromJson(jsonDecode(gameStateString));
        
        // Check if it's the same day - if not, return null to start fresh
        final today = DateTime.now().toIso8601String().substring(0, 10);
        if (gameState.gameDate != today) {
          await clearGameState();
          return null;
        }
        
        return gameState;
      }
      return null;
    } catch (e) {
      print('Error loading game state: $e');
      return null;
    }
  }

  static Future<void> clearGameState() async {
    try {
      await _storage.delete(key: _gameStateKey);
    } catch (e) {
      print('Error clearing game state: $e');
    }
  }

  static String getTodayDateString() {
    return DateTime.now().toIso8601String().substring(0, 10);
  }

  static Future<LeaderboardResponse> getLeaderboard() async {
    try {
      final response = await HttpService.get(ApiConstants.puzzleLeaderboardEndpoint);
      
      if (response.statusCode == 200) {
        return LeaderboardResponse.fromJson(jsonDecode(response.body));
      } else {
        print('Failed to get leaderboard: ${response.statusCode}');
        return LeaderboardResponse(
          status: false, 
          message: 'Failed to load leaderboard',
          data: null,
        );
      }
    } catch (e) {
      print('Error getting leaderboard: $e');
      return LeaderboardResponse(
        status: false, 
        message: 'Error loading leaderboard',
        data: null,
      );
    }
  }

  static String formatSolveTime(DateTime solveTime) {
    final now = DateTime.now();
    final today = DateTime(now.year, now.month, now.day);
    final solveDate = DateTime(solveTime.year, solveTime.month, solveTime.day);
    
    if (solveDate == today) {
      // Format as time today (e.g., "2:36 PM")
      final hour = solveTime.hour > 12 ? solveTime.hour - 12 : solveTime.hour == 0 ? 12 : solveTime.hour;
      final minute = solveTime.minute.toString().padLeft(2, '0');
      final period = solveTime.hour >= 12 ? 'PM' : 'AM';
      return '$hour:$minute $period today';
    } else {
      // Format as full date if not today
      return '${solveTime.day}/${solveTime.month}/${solveTime.year}';
    }
  }
}