--[[
============================================================================
ETB - SourceExtractor.lua
============================================================================
In-game helper to extract source data from the Encounter Journal.
Use /etb extract to dump MoP raid loot data for integration.

This extracts itemIDs with their boss/instance associations from the
Encounter Journal API, which can then be merged into SourceDataComplete.lua

Usage:
  /etb extract           -- Extract all MoP raid data
  /etb extract <raidID>  -- Extract specific raid
============================================================================
]]--

local _, ETB = ...

ETB.SourceExtractor = ETB.SourceExtractor or {}
local SE = ETB.SourceExtractor

-- MoP Raid Instance IDs for Encounter Journal
local MOP_RAIDS = {
    { id = 317, name = "Mogu'shan Vaults", instanceID = 1008 },
    { id = 330, name = "Heart of Fear", instanceID = 1009 },
    { id = 320, name = "Terrace of Endless Spring", instanceID = 996 },
    { id = 362, name = "Throne of Thunder", instanceID = 1098 },
    { id = 369, name = "Siege of Orgrimmar", instanceID = 1136 },
}

-- Equipment slot filter for transmog
local TRANSMOG_SLOTS = {
    ["INVTYPE_HEAD"] = true,
    ["INVTYPE_SHOULDER"] = true,
    ["INVTYPE_CLOAK"] = true,
    ["INVTYPE_CHEST"] = true,
    ["INVTYPE_ROBE"] = true,
    ["INVTYPE_WRIST"] = true,
    ["INVTYPE_HAND"] = true,
    ["INVTYPE_WAIST"] = true,
    ["INVTYPE_LEGS"] = true,
    ["INVTYPE_FEET"] = true,
    ["INVTYPE_MAINHAND"] = true,
    ["INVTYPE_WEAPONMAINHAND"] = true,
    ["INVTYPE_WEAPONOFFHAND"] = true,
    ["INVTYPE_WEAPON"] = true,
    ["INVTYPE_2HWEAPON"] = true,
    ["INVTYPE_RANGED"] = true,
    ["INVTYPE_RANGEDRIGHT"] = true,
    ["INVTYPE_SHIELD"] = true,
    ["INVTYPE_HOLDABLE"] = true,
    ["INVTYPE_THROWN"] = true,
}

-- Extract loot from a specific encounter
function SE:ExtractEncounterLoot(journalEncounterID, instanceName, instanceID)
    local results = {}
    
    -- Get encounter info
    local name, description, journalID, rootSectionID, link = EJ_GetEncounterInfo(journalEncounterID)
    if not name then return results end
    
    local encounterID = journalEncounterID -- This maps to our encounterID
    
    -- Get loot count
    local lootIndex = 1
    while true do
        local itemID, _, _, _, _, _, itemLink = EJ_GetLootInfoByIndex(lootIndex)
        if not itemID then break end
        
        -- Check if it's transmog-eligible
        local _, _, _, itemEquipLoc = GetItemInfoInstant(itemID)
        if itemEquipLoc and TRANSMOG_SLOTS[itemEquipLoc] then
            local sourceStr = string.format("B:%s:%s:%d:%d:0",
                name:gsub(":", "-"):gsub("|", "-"),
                instanceName:gsub(":", "-"):gsub("|", "-"),
                instanceID,
                encounterID
            )
            table.insert(results, {
                itemID = itemID,
                sourceStr = sourceStr,
                bossName = name,
                itemLink = itemLink,
            })
        end
        
        lootIndex = lootIndex + 1
    end
    
    return results
end

-- Extract all loot from a raid instance
function SE:ExtractRaidLoot(journalInstanceID, instanceName, instanceID)
    local results = {}
    
    -- Select the instance in the EJ
    EJ_SelectInstance(journalInstanceID)
    
    -- Get all encounters
    local encounterIndex = 1
    while true do
        local name, description, journalEncounterID = EJ_GetEncounterInfoByIndex(encounterIndex)
        if not name then break end
        
        -- Select this encounter
        EJ_SelectEncounter(journalEncounterID)
        
        -- Extract loot
        local encounterLoot = self:ExtractEncounterLoot(journalEncounterID, instanceName, instanceID)
        for _, item in ipairs(encounterLoot) do
            table.insert(results, item)
        end
        
        encounterIndex = encounterIndex + 1
    end
    
    return results
end

-- Extract all MoP raid data
function SE:ExtractAllMoPData()
    if not EJ_SelectTier then
        print("|cFFFF0000[ETB]|r Encounter Journal API not available")
        return {}
    end
    
    local allResults = {}
    
    -- Select MoP tier (tier 5 in most clients)
    EJ_SelectTier(5) -- MoP
    
    for _, raid in ipairs(MOP_RAIDS) do
        print("|cFF00FF00[ETB]|r Extracting: " .. raid.name)
        local raidLoot = self:ExtractRaidLoot(raid.id, raid.name, raid.instanceID)
        for _, item in ipairs(raidLoot) do
            allResults[item.itemID] = item
        end
    end
    
    return allResults
end

-- Generate Lua code from extracted data
function SE:GenerateLuaCode(data)
    local output = "-- MoP Raid Items (extracted from Encounter Journal)\n"
    output = output .. "-- Add these to SourceDataComplete.lua\n\n"
    
    -- Group by raid
    local byRaid = {}
    for itemID, info in pairs(data) do
        local raidName = info.sourceStr:match("B:[^:]+:([^:]+):")
        byRaid[raidName] = byRaid[raidName] or {}
        table.insert(byRaid[raidName], {itemID = itemID, info = info})
    end
    
    -- Output grouped
    for raidName, items in pairs(byRaid) do
        output = output .. "-- " .. raidName .. "\n"
        table.sort(items, function(a, b) return a.itemID < b.itemID end)
        for _, item in ipairs(items) do
            output = output .. string.format('SDC.SOURCES[%d] = "%s"  -- %s\n',
                item.itemID, item.info.sourceStr, item.info.bossName)
        end
        output = output .. "\n"
    end
    
    return output
end

-- Print to chat (limited)
function SE:PrintResults(data)
    local count = 0
    for _ in pairs(data) do count = count + 1 end
    
    print("|cFF00FF00[ETB]|r Extracted " .. count .. " transmog items from MoP raids")
    print("|cFF00FF00[ETB]|r Use /etb extractsave to save to SavedVariables")
end

-- Save to SavedVariables for export
function SE:SaveToSavedVariables(data)
    ETB_ExtractedSources = ETB_ExtractedSources or {}
    
    local luaCode = self:GenerateLuaCode(data)
    ETB_ExtractedSources.mopRaids = luaCode
    ETB_ExtractedSources.timestamp = date("%Y-%m-%d %H:%M:%S")
    ETB_ExtractedSources.count = 0
    for _ in pairs(data) do ETB_ExtractedSources.count = ETB_ExtractedSources.count + 1 end
    
    print("|cFF00FF00[ETB]|r Saved " .. ETB_ExtractedSources.count .. " items to ETB_ExtractedSources")
    print("|cFF00FF00[ETB]|r /reload and check SavedVariables/ETB.lua")
end

-- Command handler
function SE:HandleCommand(args)
    if not EJ_SelectTier then
        print("|cFFFF0000[ETB]|r Encounter Journal not available in this client")
        return
    end
    
    local cmd = args[1]
    
    if cmd == "save" or cmd == "extractsave" then
        local data = self:ExtractAllMoPData()
        self:SaveToSavedVariables(data)
    else
        local data = self:ExtractAllMoPData()
        self:PrintResults(data)
        print("|cFFFFFF00[ETB]|r Run '/etb extract save' to save for export")
    end
end

-- Register with commands
if ETB.Commands then
    ETB.Commands:RegisterSubCommand("extract", function(args)
        SE:HandleCommand(args)
    end, "Extract MoP raid source data from Encounter Journal")
end
