#! /usr/bin/env python
# coding: utf-8

from multiprocessing import Pool
import argparse
import importlib
import logging

import level2


# check third-party packages
for name in ['numpy', 'netCDF4', 'cartopy', 'shapely']:
    try:
        importlib.import_module(name)
    except ImportError:
        print('Missing third-party package `%s`.' % name)
        sys.exit(1)


def multi_main(args):
    level2.main(*args)


def main():

    parser = argparse.ArgumentParser(description='Create Level-2 data')

    # instrument
    parser.add_argument('--instrument', type=str,
            help='name of satellite instrument')

    # output
    parser.add_argument('--output_path', metavar='path', type=str, required=True,
            help='output path')
    parser.add_argument('--dont_overwrite', required=False, action='store_true',
            help='do not overwrite existing files'
    )

    # cosmo input
    parser.add_argument('--cosmo_path', type=str, required=True, help='path to COSMO 2D files')
    parser.add_argument('--cosmo_vars', type=str, nargs='+',
            help='list of COSMO variables that will be included')
    parser.add_argument('--overpass_time', type=str, required=False, default=None,
            help='time of overpass (overwrites overpass time from orbit calculator')


    # albedo
    parser.add_argument('--albedo_path', type=str, help='path to MODIS albedo file')
    parser.add_argument('--albedo_vars', type=str, default=level2.config.albedo_vars,
            nargs='+',
            help='list of variables included from MODIS albedo filename'
    )

    # orbit
    parser.add_argument('--orbit_path', metavar='path', type=str,
            help='path to netCDF file with orbit parameters')

    parser.add_argument('--orbit_number', type=int, nargs='+', default=[0],
            help='orbit number(s), if two numbers use range(start, stop)')

    parser.add_argument('--longitude_equator', type=float, default=0.0,
            help='longitude of equator overpass of first orbit on ascending node'
    )

    parser.add_argument('--compute_orbit', action='store_true',
            help='if given compute orbit using SRON orbit simulator'
    )
    parser.add_argument('--do_shift_orbit', required=False, action='store_true',
            help='shift longitude of ground pixels (not fully implemented)'
    )

    # multi-core
    parser.add_argument('--nproc', type=int, default=1, help='number of processes')

    # logging
    parser.add_argument('--log_level', type=str, default='DEBUG',
            choices=['CRITICAL', 'ERROR', 'WARNING', 'INFO', 'DEBUG'], help='logging level')
    parser.add_argument('--log_filename', type=str, default=None, help='file for log output')


    # parse arguments
    args = parser.parse_args()

    # set logger
    level2.misc.set_logger(args.log_filename, args.log_level)


    output_path = args.output_path
    orbit_path = args.orbit_path

    # COSMO 2D fields
    if args.cosmo_vars and args.cosmo_path is None:
        logging.error('COSMO variables given but no COSMO_PATH')
        sys.exit(1)


    if len(args.orbit_number) == 2:
        orbits = range(*args.orbit_number)
    else:
        orbits = args.orbit_number

    if args.nproc == 1:
        for number in orbits:
            level2.main(
                    args.instrument,
                    args.output_path,
                    args.dont_overwrite,
                    args.cosmo_path,
                    args.cosmo_vars,
                    level2.config.cosmo_attrs,
                    args.albedo_path,
                    args.albedo_vars,
                    level2.config.albedo_attrs,
                    args.overpass_time,
                    args.compute_orbit,
                    args.orbit_path,
                    number,
                    args.longitude_equator,
                    args.do_shift_orbit
            )
    else:
        arguments = [(
                    args.instrument,
                    args.output_path,
                    args.dont_overwrite,
                    args.cosmo_path,
                    args.cosmo_vars,
                    level2.config.cosmo_attrs,
                    args.albedo_path,
                    args.albedo_vars,
                    level2.config.albedo_attrs,
                    args.overpass_time,
                    args.compute_orbit,
                    args.orbit_path,
                    number,
                    args.longitude_equator,
                    args.do_shift_orbit
            )
            for number in orbits
        ]
        pool = Pool(processes=args.nproc)
        pool.map(multi_main, arguments)



if __name__ == '__main__':
    main()







