import json
import string

from funcs import logThis

def getName(user : str):
    logThis("Getting name for "+user+"'s character")
    with open("resources/swcharacters.json", "r") as f:
        data = json.load(f)
    
    if user in data:
        logThis("Name is "+data[user]["Name"])
        return data[user]["Name"]
    else:
        logThis("Just using "+user)
        return user

def setUpDict(cmd : dict):
    logThis("Setting up a dictionary in a nice way")
    if bool(cmd):
        keys = list(cmd)
        values = list(cmd.values())
        result = ""
        if type(values[0]) is dict:
            return ", ".join(values)
        else:
            for x in range(len(keys)):
                if type(keys[x]) is list:
                    if x%3 != 2:
                        result += "**" + keys[x] + "**" + ": " + ", ".join(values[x]) + " "
                    else:
                        result += "**" + keys[x] + "**" + ": " + ", ".join(values[x]) + "\n"
                else:
                    if x%3 != 2:
                        result += "**" + keys[x] + "**" + ": " + str(values[x]) + " "
                    else:
                        result += "**" + keys[x] + "**" + ": " + str(values[x]) + "\n"
            logThis("Returning a dictionary, but well formatted")
            return result
    else:
        logThis("Couldn't find anything")
        return "There doesn't seem to be anything here..."

def lookUp(data : dict, key : str, cmd : str = ""):
    if cmd == " ":
        cmd = ""
    elif cmd != "":
        while cmd[0] == " ":
            cmd = cmd[1:]
            if cmd == "":
                break

    logThis("Looking up "+key)
    if key in data:
        logThis(key+" exists")
        if cmd == "":
            if type(data[key]) is dict and key != "Weapons":
                return setUpDict(data[key])
            elif key == "Weapons":
                logThis("Does this even get used? I'm too scared to delete it")
                if bool(data[key]):
                    logThis("Found "+(", ".join(list(data[key]))))
                    return ", ".join(list(data[key]))
                else:
                    logThis("There is nothing here")
                    return "There doesn't seem to be anything here..."
            else:
                if str(data[key]) != "":
                    logThis("Returning "+str(data[key]))
                    return data[key]
                else:
                    logThis("There was nothing there")
                    return "There doesn't seem to be anything here"
        elif cmd[0] == '+':
            logThis("Trying to add to "+key)
            try:
                cmd = cmd[1:]
                while cmd[0] == ' ':
                    cmd = cmd[1:]
            except:
                logThis("Yeah, that fucked up")
                return "Can't do that"

            if type(data[key]) is int:
                try:
                    newValue = data[key] + int(cmd)
                    data[key] = newValue
                    logThis("Added "+cmd+" to "+key)
                    return data
                except:
                    logThis("Couldn't add "+cmd+" to "+key)
                    return "Can't add that"
            elif type(data[key]) is list:
                    try:
                        data[key].append(cmd)
                        logThis("Added "+cmd+" to "+key)
                        return data
                    except:
                        logThis("Couldn't add "+cmd+" to "+key)
                        return "Can't add that"
            else:
                logThis("Yeah, I can't add that to "+key)
                return "Can't add that"

        elif cmd[0] == '-':
            logThis("Trying to remove/subtract from "+key)
            try:
                cmd = cmd[1:]
                while cmd[0] == ' ':
                    cmd = cmd[1:]
            except:
                logThis("Yeah, that fucked up")
                return "Can't do that"
            
            if type(data[key]) is int:
                try:
                    newValue = data[key] - int(cmd)
                    data[key] = newValue
                    logThis("Subtracted "+cmd+" from "+key)
                    return data
                except:
                    logThis("Couldn't subtract "+cmd+" from "+key)
                    return "Can't remove that"
            elif type(data[key]) is list:
                    try:
                        data[key].remove(cmd)
                        logThis("Removed "+cmd+" from "+key)
                        return data
                    except:
                        logThis("Couldn't remove "+cmd+" from "+key)
                        return "Can't remove that"
            else:
                logThis("Yeah, I can't remove/subtract that from "+key)
                return "Can't remove that"
        else:
            while cmd[0] == ' ':
                cmd = cmd[1:]

            if type(data[key]) is dict:
                newKey = cmd.split(" ")[0]
                cmd = cmd[len(newKey):]
                if cmd != "":
                    while cmd[0] == " ":
                        cmd = cmd[1:]
                        if cmd == "":
                            break
                logThis("Looking up "+newKey+" in "+key)
                lookUpResult = lookUp(data[key],newKey,cmd)
                if type(lookUpResult) is dict:
                    data[key] = lookUpResult
                    return data
                else:
                    return lookUpResult
            elif type(data[key]) != list:
                logThis("Trying to change "+key+" to "+cmd)
                try:
                    cmd = type(data[key])(cmd)
                    data[key] = cmd
                    logThis("Did that")
                    return data
                except:
                    logThis("No. That did not work")
                    return "Wrong data type"
            else:
                logThis("Yeah, that didn't work")
                return "Wrong data type"
    else:
        logThis("Couldn't find "+key)
        logThis("Testing to see if it's a multi-word key")
        cmd = key + " " + cmd
        words = cmd.split(" ")
        search = ""
        i = 0
        while search not in data:
            try:
                search += " " + words[i]
                i += 1
            except:
                logThis("It wasn't. "+search+" doesn't exist")
                return search + " doesn't exist"
            if search[0] == " ":
                search = search[1:]
        logThis("Yeah! Did that! The key was "+search)

        cmd = cmd[len(search):]
        if cmd != "":
            while cmd[0] == " ":
                cmd = cmd[1:]
                if cmd == "":
                    break

        if cmd == "":
            logThis("Returning "+search)
            return setUpDict(data[search])
        else:
            newKey = cmd.split(" ")[0]
            cmd = cmd[len(newKey):]
            if cmd != "":
                while cmd[0] == " ":
                    cmd = cmd[1:]
                    if cmd == "":
                        break
            lookUpResult = lookUp(data[search],newKey,cmd)
            if type(lookUpResult) is dict:
                data[search] = lookUpResult
                return data
            else:
                return lookUpResult

def characterSheet(character : dict):
    logThis("Setting up a character sheet for "+character["Name"])
    divider = "--------------------\n"
    name = character["Name"]
    textf = ""
    if character["Force-rating"] != 0:
        textf = "\n**Force Rating**: "+str(character["Force-rating"])

    text1 = "**Species**: "+character["Species"]+"\n**Career**: "+character["Career"]+"\n**Specialization Trees**: "+", ".join(character["Specialization-trees"])+textf+"\n**Soak**: "+str(character["Soak"])
    text2 = "\n\n**Wounds**: "+str(character["Wounds"])+"/"+str(character["Wound-threshold"])+"\n**Strain**: "+str(character["Strain"])+"/"+str(character["Strain-threshold"])
    text3 = setUpDict(character["Characteristics"])
    text4 = setUpDict(character["Skills"])
    text5 = ""
    text6 = ""
    text7 = ""
    text8 = ""

    if bool(character["Talents"]):
        text5 = "**Talents**: "+", ".join(list(character["Talents"]))+"\n\n"

    if bool(character["Force-powers"]):
        text6 = "**Force Powers**: "+", ".join(list(character["Force-powers"]))+"\n\n"

    text7 = "**Equipment**: "+", ".join(character["Equipment"])+"\n**Credits**: "+str(character["Credits"])+"\n**Weapons**: "+", ".join(list(character["Weapons"]))+"\n"+divider
    
    if bool(character["Obligations"]):
        text8 = "**Obligations**: "+",".join(list(character["Obligations"]))

    return name, text1+text2+"\n\n"+text3+divider+text4+"\n"+divider+text5+text6+text7+text8

def charData(user : str,cmd : str):
    with open("resources/swcharacters.json", "r") as f:
        data = json.load(f)

    key = string.capwords(cmd.split(" ")[0])
    cmd = cmd[len(key):]
    if cmd == " ":
        cmd = ""
    elif cmd != "":
        while cmd[0] == " ":
            cmd = cmd[1:]
            if cmd == "":
                break
    
    logThis("Looking for "+user+"'s character")
    if user in data:
        logThis("Foundt it! Looking for "+key+" in the data")
        if key in data[user]:
            logThis("Found it!")
            if type(data[user][key]) is dict:
                logThis("It's a dictionary!")
                if cmd == "":
                    logThis("Retrieving data")
                    if key == "Weapons":
                        if bool(data[user][key]):
                            logThis("Returning a list of weapons")
                            return ", ".join(list(data[user][key]))
                        else:
                            logThis("The character doesn't have any weapons. Which is probably for the best. Like, who just walks around with weapons?")
                            return "There doesn't seem to be anything there..."
                    else:
                        return setUpDict(data[user][key])
                elif cmd[0] == "+":
                    logThis("Gonna add something!!!")
                    try:
                        cmd = cmd[1:]
                        while cmd[0] == ' ':
                            cmd = cmd[1:]
                    except:
                        logThis("Nope. That didn't happen")
                        return "Can't do that"
                    
                    if (key == "Talents" or key == "Force-powers") and "," in cmd:
                        cmd = cmd.split(",")
                        while cmd[1][0] == " ":
                            cmd[1] = cmd[1][1:]
                        logThis("Adding "+cmd[0]+" to "+key)
                        data[user][key][cmd[0]] = cmd[1]
                        with open("resources/swcharacters.json", "w") as f:
                            json.dump(data,f,indent = 4)
                        return cmd[0]+" added to "+key+" for " + data[user]["Name"]
                    
                    elif key == "Obligations" and "," in cmd:
                        cmd = cmd.split(",")
                        while cmd[1][0] == " ":
                            cmd[1] = cmd[1][1:]
                        logThis("Adding "+cmd[0]+" to "+key)
                        try:
                            data[user][key][cmd[0]] = int(cmd[1])
                        except:
                            logThis("Fucked that up")
                            return "Wrong data type"
                        with open("resources/swcharacters.json", "w") as f:
                            json.dump(data,f,indent = 4)
                        return cmd[0]+" added to "+key+" for " + data[user]["Name"]

                    elif key == "Weapons":
                        with open("resources/swtemplates.json", "r") as f:
                            templates = json.load(f)
                        newWeapon = templates["Weapon"]
                        logThis("Adding "+cmd+" to "+key)
                        data[user][key][cmd] = newWeapon
                        
                        with open("resources/swcharacters.json", "w") as f:
                            json.dump(data,f,indent = 4)
                        return cmd+" added to weapons for " + data[user]["Name"]
                    
                    else:
                        logThis("That's not happening")
                        return "Can't add that"

                elif cmd[0] == "-":
                    logThis("Gonna subtract/remove something")
                    try:
                        cmd = cmd[1:]
                        while cmd[0] == ' ':
                            cmd = cmd[1:]
                    except:
                        logThis("AAAAAAAAAAAA")
                        return "Can't do that"
                    
                    if key == "Talents" or key == "Force-powers" or key == "Weapons" or key == "Obligations":
                        logThis("Trying to remove "+cmd+" from "+key)
                        if cmd in data[user][key]:
                            del data[user][key][cmd]
                            with open("resources/swcharacters.json", "w") as f:
                                json.dump(data,f,indent = 4)
                            logThis("I did that")
                            return cmd+" removed from "+key+" from "+data[user]["Name"]
                        else:
                            logThis("Welp. I fucked that up")
                            return "Can't remove that"
                    else:
                        logThis("Urgh!")
                        return "Can't remove that"

                else:
                    logThis("Looking up "+cmd+" in "+key)
                    if key == "Talents" or key == "Force-powers":
                        newKey = cmd
                        newcmd = ""
                    else:
                        newKey = string.capwords(cmd.split(" ")[0])
                        newcmd = cmd[len(newKey):]

                    lookUpResult = lookUp(data[user][key],newKey,newcmd)

                    if type(lookUpResult) is dict:
                        data[user][key] = lookUpResult
                        with open("resources/swcharacters.json", "w") as f:
                            json.dump(data,f,indent = 4)
                        return "Changed " + data[user]["Name"] + "'s " + key
                    else:
                        return lookUpResult
            else:
                if cmd == "":
                    logThis("Retrieving data")
                    if type(data[user][key]) is list:
                        return key+":\n"+", ".join(data[user][key])
                    else:
                        return data[user][key]
                elif cmd[0] == '+':
                    logThis("Adding")
                    try:
                        cmd = cmd[1:]
                        while cmd[0] == ' ':
                            cmd = cmd[1:]
                    except:
                        logThis("Error message")
                        return "Can't do that"

                    if type(data[user][key]) is int:
                        try:
                            logThis("Adding "+cmd+" to "+key)
                            beforeData = data[user][key]
                            data[user][key] = beforeData+ int(cmd)
                            with open("resources/swcharacters.json", "w") as f:
                                json.dump(data,f,indent = 4)
                            return "Added " + cmd + " to " + data[user]["Name"] + "'s " + key
                        except:
                            logThis("BITCH SANDWICH")
                            return "Can't add that"
                    elif type(data[user][key]) is list:
                        try:
                            logThis("Adding "+cmd+" to "+key)
                            data[user][key].append(cmd)
                            with open("resources/swcharacters.json", "w") as f:
                                json.dump(data,f,indent = 4)
                            return "Added " + cmd + " to " + data[user]["Name"] + "'s " + key
                        except:
                            logThis("tstststststs")
                            return "Can't add that"
                    else:
                        logThis("Help")
                        return "Can't add that"
                elif cmd[0] == '-':
                    logThis("Removing/subtracting")
                    try:
                        cmd = cmd[1:]
                        while cmd[0] == ' ':
                            cmd = cmd[1:]
                    except:
                        logThis("lalalala")
                        return "Can't do that"

                    if type(data[user][key]) is int:
                        try:
                            logThis("Subtracting "+cmd+" from "+key)
                            beforeData = data[user][key]
                            data[user][key] = beforeData - int(cmd)
                            with open("resources/swcharacters.json", "w") as f:
                                json.dump(data,f,indent = 4)
                            return "Subtracted " + cmd + " from " + data[user]["Name"] + "'s " + key
                        except:
                            logThis("Tried it. Didn't want to")
                            return "Can't remove that"
                    elif type(data[user][key]) is list:
                        try:
                            logThis("removing "+cmd+" from "+key)
                            beforeData = data[user][key]
                            try:
                                data[user][key].remove(cmd)
                            except:
                                logThis("They can only remove stuff that's actually in the list")
                                return "Not in list"
                            with open("resources/swcharacters.json", "w") as f:
                                json.dump(data,f,indent = 4)
                            return "Removed " + cmd + " from " + data[user]["Name"] + "'s " + key
                        except:
                            logThis("nah")
                            return "Can't remove that"
                    else:
                        logThis("nyope")
                        return "Can't remove that"
                else:
                    logThis("Changing "+key+" to "+cmd)
                    if type(data[user][key]) is int:
                        try:
                            data[user][key] = int(cmd)
                        except:
                            return "Can't do that"
                    elif type(data[user][key]) is str:
                        data[user][key] = cmd
                    else:
                        logThis("I don't wanna tho")
                        return "Can't do that"

                    with open("resources/swcharacters.json", "w") as f:
                            json.dump(data,f,indent = 4)
                    return "Changed " + data[user]["Name"] + "'s " + key +" to " + cmd
        else:
            logThis(key+" isn't in there")
            return "Couldn't find that data. Are you sure you spelled it correctly?"
    else:
        logThis(user+" doesn't have a character")
        return "You don't have a character. You can make one with !swchar"

def replaceSpaces(cmd : str):
    withSpaces = ["Specialization Trees","Wound Threshold","Strain Threshold","Defense - Ranged","Defense - Melee","Force Rating","Core Worlds","Outer Rim","Piloting - Planetary","Piloting - Space","Ranged - Heavy","Ranged - Light","Lightsaber Characteristic","Critical Injuries","Force Powers"]
    withoutSpaces = ["Specialization-trees","Wound-threshold","Strain-threshold","Defense-ranged","Defense-melee","Force-rating","Core-worlds","Outer-rim","Piloting-planetary","Piloting-space","Ranged-heavy","Ranged-light","Lightsaber-characteristic","Critical-injuries","Force-powers"]

    for x in range(len(withoutSpaces)):
        cmd = cmd.replace(withSpaces[x],withoutSpaces[x])
    
    return cmd

def replaceWithSpaces(cmd : str):
    withSpaces = ["Specialization Trees","Wound Threshold","Strain Threshold","Defense - Ranged","Defense - Melee","Force Rating","Core Worlds","Outer Rim","Piloting - Planetary","Piloting - Space","Ranged - Heavy","Ranged - light","Lightsaber Characteristic","Critical Injuries","Force Powers"]
    withoutSpaces = ["Specialization-trees","Wound-threshold","Strain-threshold","Defense-ranged","Defense-melee","Force-rating","Core-worlds","Outer-rim","Piloting-planetary","Piloting-space","Ranged-heavy","Ranged-light","Lightsaber-characteristic","Critical-injuries","Force-powers"]

    for x in range(len(withoutSpaces)):
        cmd = cmd.replace(withoutSpaces[x],withSpaces[x])
    
    return cmd

def parseChar(user : str, cmd : str):

    cmd = replaceSpaces(cmd)

    with open("resources/swcharacters.json", "r") as f:
        data = json.load(f)

    if cmd == " ":
        cmd = ""
    elif cmd != "":
        while cmd[0] == " ":
            cmd = cmd[1:]
            if cmd == "":
                break
    
    if cmd == "":
        if user in data:
            text1, text2 = characterSheet(data[user])
            return text1, replaceWithSpaces(text2)
        else:
            logThis("Makin' a character for "+user)
            with open("resources/swtemplates.json", "r") as f:
                templates = json.load(f)
            newChar = templates["Character"]
            data[user] = newChar
            with open("resources/swcharacters.json", "w") as f:
                json.dump(data,f,indent = 4)
            return "", "Character for " + user + " created"
    else:
        if cmd == "Purge":
            logThis("Deleting "+user+"'s character")
            del data[user]
            with open("resources/swcharacters.json", "w") as f:
                json.dump(data,f,indent = 4)
                return "", "Character for " + user + " deleted"
        return "", replaceWithSpaces(str(charData(user,cmd)))

def lightsaberChar(user : str):
    with open("resources/swcharacters.json", "r") as f:
        data = json.load(f)

    if user in data:
        return data[user]["Lightsaber-characteristic"]

def userHasChar(user : str):
    with open("resources/swcharacters.json", "r") as f:
        data = json.load(f)

    return user in data

