import datatypes

class Generator:
    def __init__(self, config, context, factories):
        self.config = config
        self.context = context
        self.factories = factories

    def generate_context(self):
        # files
        self.context['files'] = self.factories['file'].all()

        pages = self.factories['page'].all()
        published_pages = []
        hidden_pages = []
        for lang in self.config['lang']['supported']:
            for slug, page in pages[lang].items():
                if page.status == "published":
                    published_pages.append(page)
                elif page.status == "hidden":
                    hidden_pages.append(page)


        # set context.pages from published_pages as a dict of languages containing dicts of slugs
        all_published_pages = {}
        for lang in self.config['lang']['supported']:
            all_published_pages[lang] = {}
        for page in published_pages:
            if page.slug in all_published_pages[page.lang]:
                raise Exception("duplicate language (",lang,") for slug '", slug ,"'")
            all_published_pages[page.lang][page.slug] = page
        self.context['pages'] = all_published_pages

        # set context.hidden_pages from hidden_pages as a dict of languages containing dicts of slugs
        all_hidden_pages = {}
        for lang in self.config['lang']['supported']:
            all_hidden_pages[lang] = {}
        for page in hidden_pages:
            if page.slug in all_hidden_pages[page.lang]:
                raise Exception("duplicate language (",lang,") for slug '", slug ,"'")
            all_hidden_pages[page.lang][page.slug] = page
        self.context['hidden_pages'] = all_hidden_pages

        # pages_modified
        pages_modified = {}
        for lang in self.config['lang']['supported']:
            lang_pages = []
            for page in published_pages:
                if page.lang == lang:
                    lang_pages.append(page)
            lang_pages.sort()
            lang_pages.reverse()
            pages_modified[lang] = lang_pages
        self.context['pages_modified'] = pages_modified

        # TODO draft pages
        # TODO authors


        # tags
        self.context['tags'] = self.factories['tag'].all()

        # categories
        self.context['categories'] = {}
        for lang in self.config['lang']['supported']:
            self.context['categories'][lang] = {}
            for tag in self.context['tags'][lang].values():
                if tag.is_category:
                    self.context['categories'][lang][tag.name] = tag

        # build_date
        self.context['build_date'] = datatypes.Date("now", self.config)

        # relevant_pages
        relevant_pages_tuple = []
        for page in published_pages:
            if page.relevance['is_relevant']:
                relevant_pages_tuple.append((page.relevance['prio'], page))
        relevant_pages_tuple.sort(key=lambda x: x[0])
        relevant_pages_tuple.reverse()
        relevant_pages = {}
        for lang in self.config['lang']['supported']:
            relevant_pages[lang] = []
        for prio, page in relevant_pages_tuple:
            relevant_pages[page.lang].append(page)
        self.context['relevant_pages'] = relevant_pages
        self.context['relevant_pages_tuple'] = relevant_pages_tuple




    def generate_homepage(self, writer, lang, path):
        page = self.factories['config'].get(lang)['homepage']['page']
        writer.write_template(page.template, path , lang, {'page': page}, page.config)


    def generate_output(self, writer):
        for fname, f in self.context['files'].items():
                #print ("writing binary file: ", fname)
                writer.write_file(f.link.path, f.rawcontents, mode="wb")

        for lang in self.config['lang']['supported']:

            # all published pages
            print(lang, "-> Generatng all published pages.")
            for page in self.context['pages'][lang].values():
                writer.write_template(page.template, page.link.path, lang, {'page': page}, page.config)

            # all hidden pages
            print(lang, "-> Generatng all hidden pages.")
            for page in self.context['hidden_pages'][lang].values():
                #print(page.slug)
                writer.write_template(page.template, page.link.path, lang, {'page': page}, page.config)

            # all tags
            print(lang, "-> Generatng all tags.")
            for tag in self.context['tags'][lang].values():
                writer.write_template('tag.html', tag.link.path, lang, {'tag': tag}, tag.config)

            # homepages for languages
            print(lang, "-> Generatng homepage.")
            self.generate_homepage(writer, lang, lang + "/index.html")

        # homepage
        self.generate_homepage(writer, self.config['lang']['default'], "index.html")