//
//  Patcher.swift
//  PadelClub
//
//  Created by Laurent Morvillier on 21/06/2024.
//

import Foundation
import LeStorage

enum PatchError: Error {
    case patchError(message: String)
}

enum Patch: String, CaseIterable {
    case alexisLeDu
    case importDataFromDev
    
    var id: String {
        return "padelclub.app.patch.\(self.rawValue)"
    }
}

class Patcher {
    
    static func applyAllWhenApplicable() {
        for patch in Patch.allCases {
            self.patchIfPossible(patch)
        }
    }
    
    static func patchIfPossible(_ patch: Patch) {
        if UserDefaults.standard.value(forKey: patch.id) == nil {
            do {
                Logger.log(">>> Patches \(patch.rawValue)...")
                try self._applyPatch(patch)
                UserDefaults.standard.setValue(true, forKey: patch.id)
            } catch {
                Logger.error(error)
            }
        }
    }
    
    fileprivate static func _applyPatch(_ patch: Patch) throws {
        switch patch {
        case .alexisLeDu: self._patchAlexisLeDu()
        case .importDataFromDev: try self._importDataFromDev()
        }
    }
    
    fileprivate static func _patchAlexisLeDu() {
        guard StoreCenter.main.userId == "94f45ed2-8938-4c32-a4b6-e4525073dd33" else { return }
        
        let clubs = DataStore.shared.clubs
        StoreCenter.main.resetApiCalls(collection: clubs)
//        clubs.resetApiCalls()
        
        for club in clubs.filter({ $0.creator == "d5060b89-e979-4c19-bf78-e459a6ed5318"}) {
            club.creator = StoreCenter.main.userId
            clubs.writeChangeAndInsertOnServer(instance: club)
        }
        
    }
    
    fileprivate static func _importDataFromDev() throws {
        
        let devServices = Services(url: "https://xlr.alwaysdata.net/roads/")
        guard devServices.hasToken() else {
            return
        }
        guard URLs.api.rawValue == "https://padelclub.app/roads/" else {
            return
        }
        
        guard let userId = StoreCenter.main.userId else {
            return
        }
        
        try StoreCenter.main.migrateToken(devServices)
        
        
        let myClubs: [Club] = DataStore.shared.clubs.filter { $0.creator == userId }
        let clubIds: [String] = myClubs.map { $0.id }

        myClubs.forEach { club in
            DataStore.shared.clubs.insertIntoCurrentService(item: club)
            
            let courts = DataStore.shared.courts.filter { clubIds.contains($0.club) }
            for court in courts {
                DataStore.shared.courts.insertIntoCurrentService(item: court)
            }
        }
        
        DataStore.shared.user.clubs = Array(clubIds)
        DataStore.shared.saveUser()
        
        DataStore.shared.events.insertAllIntoCurrentService()
        DataStore.shared.tournaments.insertAllIntoCurrentService()
        DataStore.shared.dateIntervals.insertAllIntoCurrentService()
        
        for tournament in DataStore.shared.tournaments {
            let store = tournament.tournamentStore
            
            Task { // need to wait for the collections to load
                try await Task.sleep(until: .now + .seconds(2))
                
                store.teamRegistrations.insertAllIntoCurrentService()
                store.rounds.insertAllIntoCurrentService()
                store.groupStages.insertAllIntoCurrentService()
                store.matches.insertAllIntoCurrentService()
                store.playerRegistrations.insertAllIntoCurrentService()
                store.teamScores.insertAllIntoCurrentService()
                
            }
        }
        
    }
    
}
