import csv
import os
import requests
import zipfile
from io import BytesIO
from pathlib import Path
from nltk.corpus import wordnet


def get_noun_list(output_dir: Path = Path("../data")) -> list[str]:
    nounlist = output_dir / "nounlist.csv"
    if not nounlist.exists():
        # URL of the ZIP file
        url = "https://www.kaggle.com/api/v1/datasets/download/leite0407/list-of-nouns"

        # Create the data directory if it doesn't exist
        os.makedirs(output_dir, exist_ok=True)

        # Download the ZIP file
        print("Downloading the ZIP file...")
        response = requests.get(url, stream=True)

        if response.status_code == 200:
            print("Download complete. Extracting svg_files...")
            with zipfile.ZipFile(BytesIO(response.content)) as zip_ref:
                zip_ref.extractall(output_dir)
            print(f"Files extracted to {output_dir}")
        else:
            raise Exception(f"Failed to download the file. Status code: {response.status_code}")

    with open(nounlist, mode='r', encoding='utf-8') as csv_file:
        reader = csv.reader(csv_file)
        return [row[0] for row in reader if row]  # Skip empty rows



def get_banned_wordlist(output_dir: Path) -> list[str]:
    banned_word_file = output_dir / "banned_words.txt"

    if not banned_word_file.exists():
        print("getting banned words")
        # Sources of banned words
        sources = [
            "https://raw.githubusercontent.com/LDNOOBW/List-of-Dirty-Naughty-Obscene-and-Otherwise-Bad-Words/master/en",
            "https://www.cs.cmu.edu/~biglou/resources/bad-words.txt"
        ]

        banned_words = set()

        # Download and combine
        for url in sources:
            response = requests.get(url)
            if response.status_code == 200:
                banned_words.update(response.text.splitlines())

        # Save to banned_words.txt
        with open(banned_word_file, "w") as file:
            file.write("\n".join(sorted(banned_words)))

        print("saved banned words")

    with open(banned_word_file, "r") as file:
        banned_words = file.read().splitlines()
        if len(banned_words) <= 0:
            raise Exception("no banned words")
        return  banned_words


def filter_banned_words_list(noun_list: list[str], banned_words: list[str]) -> list[str]:
    filtered_list = set(noun_list) - set(banned_words)
    print(f"Removed {len(noun_list) - len(filtered_list)} words")
    return list(filtered_list)


def filter_nonimageable_words(nouns: list[str]) -> list[str]:
    return [noun for noun in nouns if is_imageable(noun)]


def is_imageable(noun):
    # Get all the noun synsets for the given word
    synsets = wordnet.synsets(noun, pos=wordnet.NOUN)
    if not synsets:
        return False

    # The canonical synset for "physical_entity"
    physical_entity = wordnet.synset('physical_entity.n.01')

    for syn in synsets:
        # Traverse up the hypernym tree
        for ancestor in syn.closure(lambda s: s.hypernyms()):
            if ancestor == physical_entity:
                return True

    return False


if __name__ == "__main__":
    #nounlist = get_noun_list(Path("../data"))
    #banned_words = get_banned_wordlist(Path("../data"))
    #print(len(nounlist))
    #print(len( banned_words))
    #filtered_words = filter_banned_words_list(noun_list=nounlist, banned_words=banned_words)
    #print(len(filtered_words))

    #imageable = filter_nonimageable_words(filtered_words)
    #print(len(imageable))
    #print(f"imageable: {len(filtered_words) - len(imageable)}")
    #with open("../data/imageable.txt", "w") as fp:
    #    fp.write("\n".join(imageable))
    print(is_imageable("destiny"))