def logprint(logname, category, level='INFO', backupCount=15):
    """
        Print logs by datetime.

        logname
          string, file name
        category
          string, category path of logs file in log directory
        level
          string, restrict whether logs to be printed or not
        backupCount
          int, how many backups can be reserved
        
    """
    path = os.path.join(CFG.dir, category.strip('/'), logname.strip('/') + '.log')
    print "log path:", path
    if not os.path.exists(path[:path.rindex('/')]):
        os.makedirs(path[:path.rindex('/')])
    # Initialize logger
    logger = logging.getLogger(logname)
    frt = logging.Formatter('%(asctime)s - %(levelname)s - %(message)s')

    hdr = logging.StreamHandler(sys.stdout)
    hdr.setFormatter(frt)
    hdr._name = '##_sh_##'
    if not hdr._name in CFG.exist:
        logger.addHandler(hdr)
        CFG.exist.append(hdr._name)

    hdr = TimedRotatingFileHandler(path, 'D', 1, backupCount)
    hdr.setFormatter(frt)
    hdr._name = '##_rfh_##'
    if not hdr._name in CFG.exist:
        logger.addHandler(hdr)
        CFG.exist.append(hdr._name)


    if level.upper() == 'NOTEST':
        level == logging.NOTSET
    elif level.upper() == 'DEBUG':
        level == logging.DEBUG
    elif level.upper() == 'WARNING':
        level == logging.WARNING
    elif level.upper() == 'ERROR':
        level == logging.ERROR
    elif level.upper() == 'CRITICAL':
        level == logging.CRITICAL
    else:
        level == logging.INFO
    logger.setLevel(level)

    def _wraper(*args, **kwargs):
        if not CFG.debug:
            return
        if not args:
            return
            
        for hdr in CFG.handlers:
            if not hdr._name in CFG.exist:
                logger.addHandler(hdr)
                CFG.exist.append(hdr._name)

        encoding = 'utf8' if os.name == 'posix' else 'gbk'
        args = [_cu(a, encoding) for a in args]

        prefix = ''

        pl = kwargs.get('printlevel', 'info').upper()
        if pl == 'DEBUG':
            try:
                logger.debug(*args, **kwargs)
            except:
                t, v, b = sys.exc_info()
                err_messages = traceback.format_exception(t, v, b)
                print 'Error: %s' % ','.join(err_messages)
        elif pl == 'WARNING':
            try:
                logger.warning(*args, **kwargs)
            except:
                t, v, b = sys.exc_info()
                err_messages = traceback.format_exception(t, v, b)
                print 'Error: %s' % ','.join(err_messages)
        elif pl == 'ERROR':
            try:
                logger.error(*args, **kwargs)
            except:
                t, v, b = sys.exc_info()
                err_messages = traceback.format_exception(t, v, b)
                print 'Error: %s' % ','.join(err_messages)
        elif pl == 'CRITICAL':
            try:
                logger.critical(*args, **kwargs)
            except:
                t, v, b = sys.exc_info()
                err_messages = traceback.format_exception(t, v, b)
                print 'Error: %s' % ','.join(err_messages)
        else:
            try:
                logger.info(*args, **kwargs)
            except:
                t, v, b = sys.exc_info()
                err_messages = traceback.format_exception(t, v, b)
                print 'Error: %s' % ','.join(err_messages)
    return _wraper, logger