#!/usr/bin/python
#
#/**************************************************************************
# * Copyright 2017-2018 IoT.bzh
# *
# * author: Romain Forlot <romain.forlot@iot.bzh>
# *
# * Licensed under the Apache License, Version 2.0 (the "License");
# * you may not use this file except in compliance with the License.
# * You may obtain a copy of the License at
# *
# *     http://www.apache.org/licenses/LICENSE-2.0
# *
# * Unless required by applicable law or agreed to in writing, software
# * distributed under the License is distributed on an "AS IS" BASIS,
# * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# * See the License for the specific language governing permissions and
# * limitations under the License.
# **************************************************************************/

import os
import json
import logging
import inspect
import fnmatch
import argparse
import subprocess

PARSER = argparse.ArgumentParser(
    description='Lists available and installed SDKs')
PARSER.add_argument('-debug', dest='debug', action='store_true',
                    help='Output debug log messages')

ARGS = PARSER.parse_args()

if ARGS.debug:
    logging.basicConfig(level=logging.DEBUG,
                        format='%(asctime)s:%(levelname)s: %(message)s')
else:
    logging.basicConfig(level=logging.INFO,
                        format='%(asctime)s:%(levelname)s: %(message)s')

SCRIPT_PATH = os.path.dirname(os.path.abspath(
    inspect.getfile(inspect.currentframe())))

ENV = subprocess.check_output(
    [os.path.join(SCRIPT_PATH, './_env-init.sh'), '-print']).splitlines()

for elt in ENV:
    k, v = elt.split('=', 1)
    if k == 'SDK_ROOT_DIR':
        SDK_ROOT_DIR = v
    elif k == 'SDK_ENV_SETUP_FILENAME':
        SDK_ENV_SETUP_FILENAME = v

if SDK_ROOT_DIR is None:
    logging.error('No SDK_ROOT_DIR environment variable found.')
    exit(1)
elif SDK_ENV_SETUP_FILENAME is None:
    SDK_ENV_SETUP_FILENAME = 'environment-setup*'

# Get list of available SDKs
SDK_DB_FILEPATH = os.path.join(SDK_ROOT_DIR, "sdks_latest.json")

if not os.path.exists(SDK_DB_FILEPATH):
    DB_UPDATE_FILEPATH = os.path.join(SCRIPT_PATH, 'db-update')
    os.system(DB_UPDATE_FILEPATH + " " + SDK_DB_FILEPATH)

SDK_DB_JSON = json.load(open(SDK_DB_FILEPATH, 'r'))

for one_sdk in SDK_DB_JSON:
    one_sdk['status'] = 'Not Installed'

INSTALLED_SDK = []
for root, dirs, files in os.walk(SDK_ROOT_DIR):
    depth = root[len(SDK_ROOT_DIR) + len(os.path.sep):].count(os.path.sep)
    # Limit the walking depth of processed directories
    if depth >= 4:
        dirs[:] = []
    # Only process SDK dir matching profile/version/arch or
    # profile/version/arch/tag
    elif depth != 2 and depth != 3:
        continue
    EF, VF = '', ''
    for one_file in files:
        if fnmatch.fnmatch(one_file, SDK_ENV_SETUP_FILENAME):
            EF = os.path.join(root, one_file)
        if fnmatch.fnmatch(one_file, 'version-*'):
            VF = os.path.join(root, one_file)
    if EF != '' and VF != '':
        logging.debug('Adding installed SDK ' + root)
        INSTALLED_SDK.append({'ENV_FILE': EF, 'VERSION_FILE': VF})
    elif (EF == '' and VF != '') or (EF != '' and VF == ''):
        logging.debug(
            'WARNING SDK ignored : root=%s, EnvFile=%s, VersFile=%s', root, EF, VF)

for one_sdk in INSTALLED_SDK:
    logging.debug("Processing %s", one_sdk['ENV_FILE'])
    PROFILE = one_sdk['ENV_FILE'].split('/')[3]
    VERSION = one_sdk['ENV_FILE'].split('/')[4]
    ARCH = one_sdk['ENV_FILE'].split('/')[5]
    DIR = os.path.dirname(one_sdk['ENV_FILE'])
    if PROFILE == '' or VERSION == '' or ARCH == '' or DIR == '':
        logging.debug('Path not compliant, skipping')
        continue

    SDK_DATE = ''
    for line in open(one_sdk['VERSION_FILE']).readlines():
        if line.startswith('Timestamp'):
            D = line.split(':')[1]
            if D:
                D = D.strip()
                SDK_DATE = '{}-{}-{} {}:{}'.format(
                    D[0:4], D[4:6], D[6:8], D[8:10], D[10:12])
                logging.debug('Found date: %s', SDK_DATE)

    found = False
    for sdk in SDK_DB_JSON:
        if sdk['profile'] == PROFILE and sdk['version'] == VERSION and sdk['arch'] == ARCH:
            if sdk['status'] == 'Installed':
                continue
            found = True
            sdk['status'] = 'Installed'
            sdk['date'] = SDK_DATE
            sdk['setupFile'] = one_sdk['ENV_FILE']
            sdk['path'] = DIR
            break

    if not found:
        logging.debug('Not found in database, add: ' +
                      PROFILE + '-' + ARCH + '-' + VERSION)
        NEW_SDK = {
            'name': PROFILE + '-' + ARCH + '-' + VERSION,
            'description': 'AGL SDK ' + ARCH + ' (version ' + VERSION + ')',
            'profile': PROFILE,
            'version': VERSION,
            'arch': ARCH,
            'path': DIR,
            'url': "",
            'status': "Installed",
            'date': SDK_DATE,
            'size': "",
            'md5sum': "",
            'setupFile': one_sdk['ENV_FILE']
        }
        SDK_DB_JSON.append(NEW_SDK)

print(json.dumps(SDK_DB_JSON))