#
# Copyright OpenEmbedded Contributors
#
# SPDX-License-Identifier: GPL-2.0-only
#

import logging
import os
import stat
import sys
import shutil
import json

import bb.utils
import bb.process

from bblayers.common import LayerPlugin

logger = logging.getLogger('bitbake-layers')

sys.path.insert(0, os.path.dirname(os.path.dirname(__file__)))

import oe.buildcfg

def plugin_init(plugins):
    return BuildConfPlugin()

class BuildConfPlugin(LayerPlugin):
    notes_fixme = """FIXME: Please place here the description of this build configuration.
It will be shown to the users when they set up their builds via TEMPLATECONF.
"""

    def _save_conf(self, templatename, templatepath, oecorepath, relpaths_to_oecore):
        confdir = os.path.join(os.environ["BBPATH"], "conf")
        destdir = os.path.join(templatepath, "conf", "templates", templatename)
        os.makedirs(destdir, exist_ok=True)

        with open(os.path.join(confdir, "local.conf")) as src:
            with open(os.path.join(destdir, "local.conf.sample"), 'w') as dest:
                dest.write(src.read())

        with open(os.path.join(confdir, "bblayers.conf")) as src:
            with open(os.path.join(destdir, "bblayers.conf.sample"), 'w') as dest:
                bblayers_data = src.read()

                for (abspath, relpath) in relpaths_to_oecore:
                    bblayers_data = bblayers_data.replace(abspath, "##OEROOT##/" + relpath)
                dest.write(bblayers_data)

        with open(os.path.join(destdir, "conf-notes.txt"), 'w') as dest:
            dest.write(self.notes_fixme)

        logger.info("""Configuration template placed into {}
Please review the files in there, and particularly provide a configuration description in {}
You can try out the configuration with
TEMPLATECONF={} . {}/oe-init-build-env build-try-{}"""
.format(destdir, os.path.join(destdir, "conf-notes.txt"), destdir, oecorepath, templatename))

    def do_save_build_conf(self, args):
        """ Save the currently active build configuration (conf/local.conf, conf/bblayers.conf) as a template into a layer.\n This template can later be used for setting up builds via TEMPLATECONF. """
        repos = {}
        layers = oe.buildcfg.get_layer_revisions(self.tinfoil.config_data)
        targetlayer = None
        oecore = None

        for l in layers:
            if os.path.abspath(l[0]) == os.path.abspath(args.layerpath):
                targetlayer = l[0]
            if l[1] == 'meta':
                oecore = os.path.dirname(l[0])

        if not targetlayer:
            logger.error("Layer {} not in one of the currently enabled layers:\n{}".format(args.layerpath, "\n".join([l[0] for l in layers])))
        elif not oecore:
            logger.error("Openembedded-core not in one of the currently enabled layers:\n{}".format("\n".join([l[0] for l in layers])))
        else:
            relpaths_to_oecore = [(l[0], os.path.relpath(l[0], start=oecore)) for l in layers]
            self._save_conf(args.templatename, targetlayer, oecore, relpaths_to_oecore)

    def register_commands(self, sp):
        parser_build_conf = self.add_command(sp, 'save-build-conf', self.do_save_build_conf, parserecipes=False)
        parser_build_conf.add_argument('layerpath',
            help='The path to the layer where the configuration template should be saved.')
        parser_build_conf.add_argument('templatename',
            help='The name of the configuration template.')
