#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import argparse
import sys
from pathlib import Path

sys.path.append(str(Path(__file__).parent.parent))

from ndop import search_filter, get_ndop_shp_data, get_ndop_csv_data, get_search_pars, read_config, login, store_config

def args_parser():
    """
    Parse command line arguments
    """
    parser = argparse.ArgumentParser(
        description=('Download data (.csv, .shp) from NDOP based on input '
                    'parametres. Unlike the offical web filter, its possible '
                    'to input polygon layer for search in area and amount of '
                    'results is not limited. Login can be stored in '
                    'configuration file ".ndop.cfg".')
    )

    parser.add_argument(
        '--user', help='login (user name or email)'
    )
    parser.add_argument(
        '--password', help='ISOP password'
    )
    parser.add_argument(
        '-s', help='store login and password in "{}"'
        .format(Path(Path.home(),".ndop.cfg")), action='store_true'
    )
    parser.add_argument(
        '--output', help='path with output filenames prefix',
        default=str(Path(Path.cwd(),"data"))
    )
    parser.add_argument(
        '-loc_only', help='downloads only spatial data without tables'
        '(faster, but only localisations with id)',
        action='store_true'
    )

    parser.add_argument(
        '--taxon', help='taxon name (i.e. "mantis religiosa")'
    )

    parser.add_argument(
        '--region', help='region of iterest (i.e. town , protected area)'
    )
    parser.add_argument(
        '--polygon', help='path to poygon layer (EPSG:5514) that define the'
        'search area. Function takes first feature of the layer'
    )

    parser.add_argument(
        '--month_from', help='get data only from a certain month in season '
        '(number)'
    )
    parser.add_argument(
        '--month_to', help='get data only to a certain month in season '
        '(number)'
    )
    parser.add_argument(
        '--date_from', help='get data from a certain date (d.m.yyyy)'
    )
    parser.add_argument(
        '--date_to', help='get data only to a certain date (d.m.yyyy)'
    )

    parser.add_argument(
        '--author', help='author surname and firstname (i.e. "Kaláb Oto")'
    )
    parser.add_argument(
        '--project', help='for data obtained from specific project'
    )
    parser.add_argument(
        '--source', help='general source of data (i.e. "ND - Databáze BioLog")'
    )
    parser.add_argument(
        '--d_source', help='specific, more detailed source of data'
    )

    parser.add_argument(
        '--config',
        help='path to the config file with login and password.'
        ' Default file path is: "{}"'.format(Path(Path.home(),
        ".ndop.cfg")), default=Path(Path.home(), ".ndop.cfg")
    )

    if len(sys.argv)==1:
        parser.print_help(sys.stderr)
        sys.exit(1)
    
    args = parser.parse_args()

    if args.user and args.password:
        if args.s:
            store_config(args.user, args.password)
    elif args.user and not args.password or \
          not args.user and args.password:
         fail("Input username and password")
    elif args.config:
         if not Path.is_file(Path(args.config)):
             fail("Configuration file {} not found".format(args.config))
         else:
              args.user, args.password = read_config(args.config)
    elif Path.is_file(Path.home(), '.ndop.cfg'):
             args.user, args.password = read_config(Path(Path.home(),
             '.ndop.cfg'))
    else:
         fail("There is no username and password or config file")  

    return args

def poly (polygon):
    """
    Parse geometry of polygon layers first feature to NDOP input format
    """
    import fiona

    shape = fiona.open(polygon)
    first = next(iter(shape))
    bb = shape.bounds

    polygon = '{},"xmin":{},"xmax":{},"ymin":{},"ymax":{} {}'.format(
        str(first['geometry']).replace("(","[").replace(")","]") \
        .replace("'","\"")[:-1],
        bb[0],bb[2],bb[1],bb[3],"}"
    )

    return polygon

def main():

    args = args_parser()
    if args.polygon:
        polygon = poly(args.polygon)
    else:
        polygon = None
    search_parameters = get_search_pars(args.author, args.taxon,
                                        args.region, polygon,
                                        args.date_to, args.date_from,
                                        args.month_to, args.month_from,
                                        args.project, args.d_source, 
                                        args.source)

    if type(search_parameters) is not dict:
        pass

    else:
        s = login(args.user, args.password)
        table_payload, num_rec = search_filter(s,search_parameters)
        get_ndop_shp_data(s,args.output)
        if not args.loc_only:
            get_ndop_csv_data(s,num_rec,table_payload,args.output)

if __name__ == "__main__":

    main()
