import os
import logging 
from collections import namedtuple


from lxml import etree

from .config import get_packages

from .cmake_helper import get_data_path


ArmarXProxyInfo = namedtuple('ArmarXProxyInfo', ['package_name', 'fullname',
                                                 'include_path', 'default_name', 'type'])

logger = logging.getLogger(__name__)



def get_ice_default_name(cls) -> str:
    mapping = build_mapping()
    fullname = f'{cls.__module__}.{cls.__name__}'
    if mapping.get(fullname, None):
        variant_info = mapping[fullname]
        default_name = variant_info.default_name
    else:
        default_name = cls.__name__
        default_name = default_name.rstrip('Prx')
        default_name = default_name.rstrip('Interface')
    return default_name



def _load_variant_info(armarx_package_name: str):
    mapping = dict()
    data_path = get_data_path(armarx_package_name)
    if not data_path:
        logger.warning('unable to get data path for package %s', armarx_package_name)
        return mapping
    variant_path = os.path.join(data_path[0], armarx_package_name,
                                'VariantInfo-{}.xml'.format(armarx_package_name))
    if not os.path.isfile(variant_path):
        logger.warning('variant info does not exists for package %s', armarx_package_name)
        return mapping
    tree = etree.parse(variant_path)
    start_pos = len(armarx_package_name + '/interface/')
    for definition_type in ['Proxy', 'Topic', 'Class']:
        for nav in tree.xpath('//VariantInfo/Lib/' + definition_type):
            fullname = nav.get('typeName').replace('::', '.')
            if not '.' in fullname:
                fullname = f'armarx.{fullname}'
            slice_include_path = nav.get('include')[start_pos:-2] + '.ice'
            if definition_type == 'Class':
                proxy_default_name = ''
            else:
                proxy_default_name = nav.get('propertyDefaultValue')

            mapping[fullname] = ArmarXProxyInfo(armarx_package_name, fullname,
                                                slice_include_path, proxy_default_name,
                                                definition_type)
            # also make the interface available.
            # the suffix Prx is autogenerated from the slice definition
    return mapping


def build_mapping():
    global_mapping = dict()
    armarx_packages = get_packages()
    for package_name in armarx_packages.split(','):
        global_mapping.update(_load_variant_info(package_name))
    return global_mapping


slice_mapping = build_mapping()

