import atexit
import grp
import os
import pwd
import time
import tempfile

_default_time_format = "%Y-%m-%d %H:%M:%S.%f%z"
_temp_files = {}


def remove_file(filename):
    os.remove(filename)
    # open('filename', 'w').close()


def write_str_to_file(filename, _str):
    with open(filename, 'w') as fo:
        fo.write(_str)


def append_str_to_file(filename, _str):
    with open(filename, 'a') as fa:
        fa.write(_str)


def write_lines_to_file(filename, source_list):
    with open(filename, 'w') as fw:
        fw.write("\n".join(source_list) + "\n")


def append_lines_to_file(filename, source_list):
    _buf = "\n".join(source_list)
    with open(filename, 'a') as fw:
        fw.write(_buf + "\n")


def append_line_to_file(filename, _str):
    with open(filename, 'a') as fa:
        fa.write(_str+'\n')


def read_file(filename):
    _buf = None
    with open(filename, 'rb') as fr:
        _buf = fr.read()
    return _buf


def read_file_as_lines(filename):
    _list = []
    with open(filename, 'rt') as fr:
        for line in fr:
            _list.append(line.rstrip())
    return _list


def get_file_info_fd(fd, time_format=_default_time_format):

    def format_time(unixtime):
        return time.strftime(
            time_format,
            time.gmtime(unixtime)
        )

    (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime) = \
        os.fstat(fd.fileno())

    _dict = {
        'fd': fd.fileno(),
        'mode': oct(mode & 0o777),
        'device': hex(dev),
        'inode': ino,
        'hard_links': nlink,
        'owner_id': uid,
        'owner_name': pwd.getpwuid(uid).pw_name,
        'owner_group_name': grp.getgrgid(gid).gr_name,
        'owner_group_id': gid,
        'size': size,
        'access_time': format_time(atime),
        'modification_time': format_time(mtime),
        'creation_time': format_time(ctime)
    }

    return _dict


def get_gzipped_file(url):
    # imports
    from io import BytesIO
    from requests import get
    import gzip
    # download a file
    _bytes = BytesIO(get(url).content)
    with gzip.GzipFile(fileobj=_bytes) as gz:
        return gz.read()


def ensure_folder_exists(_folder):
    if not os.path.exists(_folder):
        # it is not exists, create it
        os.mkdir(_folder)
        return "... folder '{}' created".format(_folder)
    else:
        return "... folder exists at '{}'".format(_folder)


def ensure_folder_removed(_folder):
    if os.path.exists(_folder):
        os.rmdir(_folder)
        return "... folder '{}' removed".format(_folder)
    else:
        return "... folder '{}' not exists".format(_folder)


def _cleanup_temp_files():
    global _temp_files
    for temp_file in _temp_files.values():
        try:
            os.remove(temp_file)
        except OSError:
            pass
    _temp_files = {}


def create_temp_file_with_content(content, mode=None):
    if len(_temp_files) == 0:
        atexit.register(_cleanup_temp_files)
    # Because we may change context several times, try to remember files we
    # created and reuse them at a small memory cost.
    content_key = hash(content)
    if content_key in _temp_files:
        return _temp_files[content_key]

    # new file, create it
    _, name = tempfile.mkstemp()
    _temp_files[content_key] = name
    with open(name, 'wb') as fd:
        fd.write(content.encode() if isinstance(content, str) else content)

    # set mode for the file
    if mode:
        os.chmod(name, mode)

    return name
