#!/usr/bin/env python
# -*- coding: utf_8 -*-

import os
import json
import traceback
import tempfile
import base64
from hashlib import md5
from application.config import config
from webcreator.log import logger

# 判断目录是否存在,不存在则创建
# if not os.path.exists(os.path.join(config.UPLOAD_ROOT_DIR, config.get("UPLOAD_DIR"))):
#     os.makedirs(os.path.join(config.UPLOAD_ROOT_DIR, config.get("UPLOAD_DIR")))

def checkAccess(path):
    realpath = os.path.realpath(path)
    if not realpath.startswith(config.UPLOAD_ROOT_DIR):
        return False
    return True

def checkPath(path):
    if not path:
        return False, {"code": -1, "data": None, "message": "[%s] arg missed!" % path}

    fpath = os.path.abspath(os.sep.join(
        [os.path.abspath(config.UPLOAD_ROOT_DIR), path]))

    if not checkAccess(fpath):
        return False, {"code": -1, "data": None, "message": "You have no access to [%s]!" % fpath}

    if not os.path.exists(fpath):
        return False, {"code": -1, "data": None, "message": "[%s] is not existed!" % fpath}

    return True, os.path.abspath(fpath)

def saveToFile(saveFile, content):
    try:
        tfn = tempfile.mktemp()
        tf = open(tfn, 'w+b')
        tf.write(content)
        tf.close()
        os.rename(tfn, saveFile)
        return True
    except Exception as e:
        traceback.print_exc()
        logger.error(str(e))
        return False

def getFileInfo(infofile):
    info = dict()
    info.update({
        "isfile": os.path.isfile(infofile),
        "isdir": os.path.isdir(infofile),
        "size": os.path.getsize(infofile),
        "atime": os.path.getatime(infofile),
        "mtime": os.path.getmtime(infofile),
        "ctime": os.path.getctime(infofile),
        "name": os.path.basename(infofile)
    })
    return info

class UploadResource(object):
    def __init__(self):
        super(UploadResource, self).__init__()

    def download(self, data):
        obj = json.loads(data)
        isAccessed, path = checkPath(obj["path"])
        if not isAccessed:
            return {"code": -1, "data": None, "message": "invaild access"}

        if not os.path.isfile(path):
            return {"code": -1, "data": None, "message": "Path [%s] is not a valid file!" % path}

        try:
            with open(path, "rb") as f:
                content = base64.b64encode(f.read())
            md5code = md5(content).hexdigest()

            return {
                "data": {
                    "content": content,
                    "md5": md5code,
                    "filename": os.path.basename(path)
                },
                "code": 0,
                "message": "download file [%s] successfully!" % obj['path']
            }
        except Exception as e:
            traceback.print_exc()
            logger.error(str(e))
            return {
                "data": None,
                "code": -1,
                "message": "upload file [%s] failed!\n %s" % (obj['path'], repr(e))
            }

    def delete(self, data):
        try:
            isAccessed, path = checkPath(data["path"])
            if not isAccessed:
                return {"code": -1, "data": None, "message": "invaild access"}

            if os.path.isfile(path):
                os.remove(path)
                return {"code": 0, "data": None, "message": "delete file [%s] successfully!" % path}
            elif os.path.isdir(path):
                os.rmdir(path)
                return {"code": 0, "data": None, "message": "delete dir [%s] successfully!" % path}
            else:
                return {"code": 0, "data": None, "message": "Path [%s] is not a valid file or path!" % path}
        except Exception as e:
            traceback.print_exc()
            logger.error(str(e))
            return {"code": -1, "data": None, "message": repr(e)}

    def dirlist(self, data):
        obj = json.loads(data)
        isAccessed, path = checkPath(obj["path"])
        if not isAccessed:
            return {"code": -1, "data": None, "message": "invaild access"}

        result = []
        for p in os.listdir(path):
            result.append(getFileInfo(os.path.join(config.UPLOAD_ROOT_DIR, p)))
        return {"code": 0, "result": result, "message": "Get [%s] successfully!" % path}

    def filemd5(self, data):
        obj = json.loads(data)
        isAccessed, path = checkPath(obj["path"])
        if not isAccessed:
            return {"code": -1, "data": None, "message": "invaild access"}

        if not os.path.isfile(path):
            return {"code": -1, "data": None, "message": "Path [%s] is not a valid file!" % path}

        with open(path, "rb") as f:
            filemd5 = md5(f.read()).hexdigest()
        return {"code": 0, "result": filemd5, "message": "Get md5 of [%s] successfully!" % path}

    def fileinfo(self, data):
        obj = json.loads(data)
        isAccessed, path = checkPath(obj["path"])
        if not isAccessed:
            return {"code": -1, "data": None, "message": "invaild access"}

        if not os.path.isfile(path):
            return {"code": -1, "data": None, "message": "Path [%s] is not a valid file!" % path}

        return {"code": 0, "result": getFileInfo(path), "message": "Get md5 of [%s] successfully!" % path}


uploadResource = UploadResource()