from __future__ import print_function

"""This file and its contents are licensed under the Apache License 2.0. Please see the included NOTICE for copyright information and LICENSE for a copy of the license.
"""
""" Version Lib
Copyright (C) 2019 Maxim Tkachenko 

This library automatically generates version of package based on git.
If 'git desc' is successful it will write version to __version__.py:git_version.  
If 'git desc' is fail it will read __version__.py:git_version.

ATTENTION: do not include version_.py to git! It will affect git commit always!
"""
from subprocess import STDOUT, CalledProcessError, check_output as run
import os
import sys
import logging
import json

VERSION_FILE = "version_.py"


def _write_py(info):
    # go to current dir to package __init__.py
    cwd = os.getcwd()
    d = os.path.dirname(__file__)
    d = d if d else "."
    os.chdir(d)

    info_str = json.dumps(info)

    # write txt
    with open(VERSION_FILE, "w") as f:
        os.chdir(cwd)  # back current dir
        f.write(
            "info = %s\n" % info_str + "\n# This file is automatically generated by version.py"
            "\n# Do not include it to git!\n"
        )


def _read_py():
    # go to current dir to package __init__.py
    cwd = os.getcwd()
    d = os.path.dirname(__file__)
    d = d if d else "."
    sys.path.append(d)
    os.chdir(d)

    # read version
    try:
        version_module = __import__(os.path.splitext(VERSION_FILE)[0])
        return version_module.info
    except ImportError as e:
        logging.warning("Can't read version file: " + VERSION_FILE)
        logging.warning(e)
        return {}
    finally:
        os.chdir(cwd)  # back current dir


# get commit info: message, date, hash, branch
def get_git_commit_info(skip_os=True):

    cwd = os.getcwd()
    d = os.path.dirname(__file__)
    d = d if d else "."
    os.chdir(d)

    try:
        # take version from git
        try:
            desc = run(
                "git describe --long --tags --always --dirty", stderr=STDOUT, shell=True
            ).decode("utf-8")
            info = {
                "message": run("git show -s --format=%s", stderr=STDOUT, shell=True)
                .strip()
                .decode("utf8"),
                "commit": run("git show -s --format=%H", stderr=STDOUT, shell=True)
                .strip()
                .decode("utf8"),
                "date": run("git show -s --format=%ai", stderr=STDOUT, shell=True)
                .strip()
                .decode("utf8"),
                "branch": run("git rev-parse --abbrev-ref HEAD", stderr=STDOUT, shell=True)
                .strip()
                .decode("utf8"),
            }
        except CalledProcessError:
            return _read_py()

        # create package version
        version = desc.lstrip("v").rstrip().replace("-", "+", 1).replace("-", ".")
        # take OS name
        if not skip_os:
            keys = ("ID=", "VERSION_ID=", "RELEASE=")
            with open("/etc/os-release") as f:
                os_version = "".join(
                    str(s).split("=", 1)[1].rstrip().strip('"').replace(".", "")
                    for s in f
                    if str(s).startswith(keys)
                )
                version += "." + os_version
        info["version"] = version

        _write_py(info)
        return info

    except Exception as e:
        raise e

    finally:
        os.chdir(cwd)  # back current dir


def get_git_version(skip_os=True):
    info = get_git_commit_info(skip_os)
    return info.get("version", "")


# get only tag from git
def get_short_version():
    version = get_git_version()
    return version.split("+")[0]


if __name__ == "__main__":
    # init version_.py file
    get_git_version()
