import os
import json
import pwd
import sys
import yaml

from cfg_checker.common.const import ENV_TYPE_GLOB, ENV_TYPE_SALT
from cfg_checker.common.const import ENV_TYPE_KUBE, ENV_TYPE_LINUX, ENV_LOCAL
from cfg_checker.common.const import supported_envs

from cfg_checker.common.exception import ConfigException
from cfg_checker.common.log import logger_cli

from cfg_checker.common.other import utils, shell
from cfg_checker.common.ssh_utils import ssh_shell_p

from cfg_checker.clients import get_kube_remote

pkg_dir = os.path.dirname(__file__)
pkg_dir = os.path.join(pkg_dir, os.pardir, os.pardir)
pkg_dir = os.path.normpath(pkg_dir)
pkg_dir = os.path.abspath(pkg_dir)

_default_work_folder = os.path.normpath(pkg_dir)


def _extract_salt_return(_raw):
    if not isinstance(_raw, str):
        _json = _raw
        logger_cli.debug("... ambigious return detected")
    else:
        try:
            _json = json.loads(_raw)
        except ValueError:
            _json = _raw
            logger_cli.debug(
                "... return value is not a json: '{}'".format(_raw)
            )

    return _json


def _get_env_value(_key, _default):
    _value = os.environ.get(_key, _default)
    logger_cli.debug("... shell env: {}={}".format(_key, _value))
    return _value


class CheckerConfiguration(object):
    @staticmethod
    def load_nodes_list():
        _file = _get_env_value('SALT_NODE_LIST_FILE', None)
        if _file:
            _v, _ = utils.get_nodes_list(
                os.path.join(pkg_dir, _file),
                env_sting=_get_env_value('CFG_ALL_NODES', None)
            )
            return _v
        else:
            return None

    def _detect(self, _type):
        logger_cli.debug("... detecting '{}'".format(_type))
        if _type is None:
            raise ConfigException("# Unexpected supported env type")
        elif _type == ENV_TYPE_SALT:
            # Detect salt env
            _detect_cmd = ["curl", "-s"]
            _detect_cmd.append(
                "http://" + self.mcp_host + ':' + self.salt_port
            )
            # Try to call salt API on target host
            _r = None
            logger_cli.debug("... detecting env type '{}'".format(_type))
            if self.env_name == ENV_LOCAL:
                _r = shell(" ".join(_detect_cmd))
            else:
                _r = ssh_shell_p(
                    " ".join(_detect_cmd),
                    self.ssh_host,
                    username=self.ssh_user,
                    keypath=self.ssh_key,
                    piped=False,
                    use_sudo=self.ssh_uses_sudo,
                    silent=True
                )
            # Parse return
            _r = _extract_salt_return(_r)

            if len(_r) < 1:
                return False
            elif _r["return"] == "Welcome":
                return True
            else:
                return False
        elif _type == ENV_TYPE_KUBE:
            _kube = get_kube_remote(self)
            if not _kube.initialized:
                logger_cli.debug(
                    "... failed to init kube using '{}'".format(
                        _kube.kConfigPath
                    )
                )
                return False
            else:
                logger_cli.debug(
                    "... config loaded from '{}'".format(
                        _kube.kConfigPath
                    )
                )
            try:
                _vApi = _kube.get_versions_api()
                _v = _vApi.get_code()
                if hasattr(_v, "platform") and \
                        hasattr(_v, "major") and \
                        hasattr(_v, "minor"):
                    logger_cli.info(
                        "# Kube server found: {}:{} on '{}'".format(
                            _v.major,
                            _v.minor,
                            _kube.kConfigPath
                        )
                    )
                    return True
                else:
                    return False
            except Exception as e:
                logger_cli.debug(
                    "... kube env error: '{}' ".format(
                        str(e)
                    )
                )
                return False
        elif _type == ENV_TYPE_LINUX:
            # Detect Linux env
            from platform import system, release
            _s = system()
            _r = release()
            logger_cli.debug("... running on {} {}".format(_s, _r))
            if _s in ['Linux', 'Darwin']:
                return True
            else:
                return False
        else:
            raise ConfigException(
                "# Env type of '{}' is not supported".format(
                    _type
                )
            )

    def _detect_types(self):
        """Try to detect env type based on the name
        """
        self.detected_envs = []
        logger_cli.info('# Detecting env types')
        for _env in supported_envs:
            if self._detect(_env):
                logger_cli.info("# '{}' found".format(_env))
                self.detected_envs.append(_env)
            else:
                logger_cli.info("# '{}' not found".format(_env))

        return

    def _init_mcp_values(self):
        """Load values from environment variables or put default ones
        """
        # filter vars and preload if needed
        self.salt_vars = []
        self.kube_vars = []
        for _key, _value in self.vars:
            if _key in os.environ:
                logger_cli.info(
                    "-> Using env var '{}={}'".format(_key, os.environ[_key])
                )
            if _key.startswith(ENV_TYPE_GLOB):
                os.environ[_key] = _value
            elif _key.startswith(ENV_TYPE_SALT):
                self.salt_vars.append([_key, _value])
            elif _key.startswith(ENV_TYPE_KUBE):
                self.kube_vars.append([_key, _value])
            else:
                logger_cli.warn(
                    "Unsupported config variable: '{}={}'".format(
                        _key,
                        _value
                    )
                )
        self.name = "CheckerConfig"
        self.working_folder = _get_env_value(
            'CFG_TESTS_WORK_DIR',
            _default_work_folder
        )
        self.date_format = "%Y-%m-%d %H:%M:%S.%f%z"
        self.default_tz = "UTC"

        self.pkg_versions_map = 'versions_map.csv'

        # self.ssh_uses_sudo = False
        self.ssh_key = _get_env_value('MCP_SSH_KEY', None)
        self.ssh_user = _get_env_value('MCP_SSH_USER', None)
        self.ssh_host = _get_env_value('MCP_SSH_HOST', None)
        self.ssh_connect_timeout = int(
            _get_env_value('MCP_SSH_TIMEOUT', "15")
        )

        self.mcp_host = _get_env_value('MCP_ENV_HOST', None)
        self.salt_port = _get_env_value('MCP_SALT_PORT', '6969')
        self.threads = int(_get_env_value('MCP_THREADS', "5"))
        self.script_execution_timeout = int(
            _get_env_value('MCP_SCRIPT_RUN_TIMEOUT', "300")
        )

        self.skip_nodes = utils.node_string_to_list(_get_env_value(
            'CFG_SKIP_NODES',
            None
        ))
        # prebuild user data and folder path
        self.pw_user = pwd.getpwuid(os.getuid())
        if self.env_name == "local":
            pass
        else:
            if not self.ssh_key and not self.force_no_key:
                raise ConfigException(
                    "Please, supply a key for the cluster's master node. "
                    "Use MCP_SSH_KEY, see 'etc/example.env'"
                )

    def _init_env_values(self):
        if ENV_TYPE_SALT in self.detected_envs:
            for _key, _value in self.salt_vars:
                if _key not in os.environ:
                    os.environ[_key] = _value

            self.salt_user = _get_env_value('SALT_USER', 'salt')
            self.salt_timeout = _get_env_value('SALT_TIMEOUT', 30)
            self.salt_file_root = _get_env_value(
                'SALT_FILE_ROOT',
                "/usr/share/salt-formulas/env/"
            )
            self.salt_scripts_folder = _get_env_value(
                'SALT_SCRIPTS_FOLDER',
                'cfg_checker_scripts'
            )
        elif ENV_TYPE_KUBE in self.detected_envs:
            for _key, _value in self.kube_vars:
                if _key not in os.environ:
                    os.environ[_key] = _value

            self.kube_config_root = _get_env_value('KUBE_CONFIG_ROOT', "/root")
            self.kube_scripts_folder = _get_env_value(
                'KUBE_SCRIPTS_FOLDER',
                "cfg-checker-scripts"
            )
            self.kube_node_user = _get_env_value(
                'KUBE_NODE_USER',
                'ubuntu'
            )
            self.kube_node_keypath = _get_env_value(
                'KUBE_NODE_KEYPATH',
                None
            )
            # Warn user only if Kube env is detected locally
            if self.env_name == ENV_LOCAL:
                if not os.path.exists(self.kube_config_path):
                    logger_cli.warn(
                        "Kube config path not found on local env: '{}'".format(
                            self.kube_config_path
                        )
                    )
                # On local envs, KUBE_NODE_KEYPATH is mandatory and is
                # provided to give cfg-checker access to kube nodes
                if not self.kube_node_keypath and not self.force_no_key:
                    raise ConfigException(
                        "Please, supply a key for the cluster nodes. "
                        "Use KUBE_NODE_KEYPATH, see 'etc/example.env'. "
                        "Consider checking KUBE_NODE_USER as well"
                    )
                self.kube_node_homepath = os.path.join(
                    '/home',
                    self.kube_node_user
                )
            else:
                # Init key for nodes
                # KUBE_NODE_KEYPATH is provided in case of node keys would be
                # different to master node key, which is supplied
                # using MCP_SSH_KEY (mandatory) and, for the most cases,
                # should be the same for remote envs
                if not self.kube_node_keypath and not self.force_no_key:
                    logger_cli.debug(
                        "... using MCP_SSH_KEY as node keys. "
                        "Supply KUBE_NODE_KEYPATH to update."
                    )
                    self.kube_node_keypath = self.ssh_key
                self.kube_node_homepath = self.homepath

    def _init_env(self, config_path, env_name=None):
        """Inits the environment vars from the env file
        Uses simple validation for the values and names

        Keyword Arguments:
            env_name {str} -- environment name to search configuration
                files in etc/<env_name>.env (default: {None})
            env_type {str} -- environment type to use: salt/kube

        Raises:
            ConfigException -- on IO error when loading env file
            ConfigException -- on env file failed validation
        """
        # detect kubeconfig placement
        _env_kubeconf_path = _get_env_value('KUBECONFIG', None)
        if not os.path.exists(self.kube_config_path):
            logger_cli.debug(
                "... kubeconfig not detected at '{}'".format(
                    self.kube_config_path
                )
            )
            # not exists, get KUBECONFIG var
            if _env_kubeconf_path:
                # get the env var path
                self.kube_config_path = _env_kubeconf_path
                logger_cli.debug(
                    "... KUBECONFIG var points to '{}'".format(
                        self.kube_config_path
                    )
                )
                self.kube_config_detected = True
            else:
                logger_cli.debug("... KUBECONFIG env var not found")
                # do not change it from default
                # self.kube_config_path = None
                self.kube_config_detected = False
        else:
            logger_cli.debug(
                "... kubeconfig detected at '{}'".format(
                    self.kube_config_path
                )
            )
            self.kube_config_detected = True

        # try to load values from KUBECONF
        _kube_conf = None
        if self.kube_config_path and self.kube_config_detected:
            with open(self.kube_config_path) as kF:
                _kube_conf = yaml.load(kF, Loader=yaml.SafeLoader)
            # extract host ip
            try:
                _server = _kube_conf["clusters"][0]["cluster"]["server"]
            except KeyError as e:
                logger_cli.debug(
                    "... failed to extract server ip: "
                    "no '{}' key in 'clusters/[0]/cluster/server".format(e)
                )
            except IndexError:
                logger_cli.debug(
                    "... failed to extract server ip: empty cluster list"
                )
            _ip = _server.split(':')
            self.remote_ip = _ip[1].replace('/', '')
            logger_cli.debug("... detected ip: '{}'".format(self.remote_ip))

        # load env file as init os.environment with its values
        if os.path.isfile(config_path):
            with open(config_path) as _f:
                _list = _f.read().splitlines()
            logger_cli.info(
                "# Loading env vars from '{}'".format(
                    config_path
                )
            )
        else:
            raise ConfigException(
                "# Failed to load enviroment vars from '{}'".format(
                    config_path
                )
            )
        self.vars = []
        for index in range(len(_list)):
            _line = _list[index]
            # skip comments
            if _line.strip().startswith('#'):
                continue
            # validate
            _errors = []
            if len(_line) < 1:
                _errors.append("Line {}: empty".format(index))
            elif _line.find('=') < 0 or _line.count('=') > 1:
                _errors.append("Line {}: {}".format(index, _line))
            else:
                # save values
                _t = _line.split('=')
                self.vars.append([_t[0], _t[1]])
        # if there was errors, report them
        if _errors:
            raise ConfigException(
                "# Environment file failed validation in lines: {}".format(
                    "\n".join(_errors)
                )
            )
        else:
            logger_cli.debug(
                "... loaded total of '{}' vars".format(
                    len(_list)
                )
            )
            self.env_name = env_name

    def __init__(self, args):
        """Base configuration class. Only values that are common for all scripts
        """
        self.ssh_uses_sudo = args.sudo
        self.ssh_direct = args.ssh_direct
        self.kube_config_path = args.kube_config
        self.debug = args.debug
        self.insecure = args.insecure
        self.force_no_key = args.force_no_key
        # Make sure we running on Python 3
        if sys.version_info[0] < 3 and sys.version_info[1] < 5:
            logger_cli.error("# ERROR: Python 3.5+ is required")
            sys.exit(1)
        else:
            logger_cli.debug("### Python version is {}.{}".format(
                sys.version_info[0],
                sys.version_info[1]
            ))

        # if env name is default, check var too
        if args.env_name == ENV_LOCAL:
            _env = _get_env_value('MCP_ENV', None)
            _env = _env if _env else args.env_name
            _env_config_path = os.path.join(pkg_dir, 'etc', _env + '.env')
        else:
            _env = args.env_name
            _env_config_path = args.env_config
        logger_cli.debug(
            "... env is '{}', config path is '{}'".format(
                _env,
                _env_config_path
            )
        )

        # Init environment variables from file, validate
        logger_cli.debug(
            "... init environment values from '{}'".format(_env_config_path)
        )
        self._init_env(_env_config_path, env_name=_env)
        # Load Common vars for any type of the env
        logger_cli.debug("... loading common variables")
        self._init_mcp_values()
        # Detect env types present
        self._detect_types()
        # handle forced env type var
        logger_cli.debug("... handling forced env types")
        _forced_type = _get_env_value('MCP_TYPE_FORCE', None)
        if _forced_type in supported_envs:
            self.detected_envs.append(_forced_type)
        elif _forced_type is not None:
            logger_cli.warn(
                "Unsupported forced type of '{}'".format(
                    _forced_type
                )
            )
        # Check if any of the envs detected
        if len(self.detected_envs) < 1:
            if _env is None:
                raise ConfigException("No environment types detected locally")
            else:
                raise ConfigException(
                    "No environment types detected at '{}'".format(
                                self.mcp_host
                            )
                )
        # initialize path to folders
        if self.env_name == ENV_LOCAL:
            # names and folders
            self.user = self.pw_user.pw_name
            self.homepath = self.pw_user.pw_dir
        else:
            # names and folders in case of remote env
            self.user = self.ssh_user
            self.homepath = os.path.join('/home', self.ssh_user)
        logger_cli.debug("... system user for ssh is '{}'".format(self.user))
        logger_cli.debug("... system home path is '{}'".format(self.homepath))

        # Init vars that is specific to detected envs only
        logger_cli.debug("... loading detected environment type vars")
        self._init_env_values()
