# -*- coding: utf-8 -*-
#/usr/bin/env python
# Program to read NEMO output temperature field file (netCDF3),
# Initial Requirements:
# 1) convert it to netcdf4 and write one output variable per file.
# 2) Output files should also pass CF checker + CMIP conventions (possibly OGC).
# 3) Mars attributes should be clearly identified 
# 4) time should be handled (forecast time, assimilation window etc)
#
# Modified program to alter the split level/time fields created from cdo on
# the output of convert_nemo_to_1_variable_all_levels_and_timesteps.py.
# these files are 1 field/level/timestep per netcdf4 file. Uses CDO because
# it already has the timestep/level splitting capability built in.
# Dependencies:
#    netCDF4 python module
#    nco tools (ncks,ncatted)

# It may be necessary to remove this dependency on nco/cdo by coding this functionality in a 
# (local) C program.
#
# K Marsh 23/9/15

from netCDF4 import Dataset
import glob
import subprocess
import getopt
import sys,os

def runcmd(run_cmd):
    print "in run cmd: ", run_cmd
    process_obj = subprocess.Popen(run_cmd, shell=True, stdout = subprocess.PIPE)
    output, err = process_obj.communicate()
    print "*** Running  command ***\n",
    print "output:", type(output)
    print output
    if err:
        print "Error:", err
    return
            
def main():
    """
    input files are stored in a list created by glob.glob()
    Process the filenames and split each file into 1 2 field per record,
    naming the output files accordingly. Also need to set the mars attributes
    explicitly to indicate these are single times and levels. 

    """
    options, remainder = getopt.getopt(sys.argv[1:],'c:')
    print options,remainder
    if len(options) ==0:
        print "Option required; Exiting"
        sys.exit()
    for opt, arg in options:
        print opt,arg
        if opt in ('-c'):
           cf_cfg_fname = arg
           print "Config file is ",cf_cfg_fname
        else:
            print "Config file required; Exiting"
            sys.exit()
    try:
        cfg_file=open(cf_cfg_fname,"r")
    except:
        print "File to process does not exit; Exiting"
        sys.exit()

    lines=cfg_file.readlines()
    for line in lines:
#        print line
        if line.startswith("#"): # comment line: 
            continue
        elif line.startswith("\'"): # "Env: " line
            option, value = line.split("=")
            o=option.strip()
            v=value.strip()
            os.environ[o] ="$"+o+":"+v            
        else:
            print line
            option, value = line.split("=")
            o=option.strip()
            v=value.strip()
            if o == "files_to_process":
                files_to_process=v
            elif o == "path_to_ncks":
                path_to_ncks=v
            elif o == "path_to_ncatted":
                 path_to_ncatted = v
            else:
                print "Unmatched option"
    cfg_file.close()
#
# Process the input file list; this assumes that these files have a regular structure
#

    try:
        fnames = glob.glob(files_to_process)
        print "Files are: ",fnames
    except:
       print "Error creating file name list; Exiting"   
       sys.exit()
    if len(fnames) == 0:
       print "File name list is empty; Exiting"
       sys.exit() 
    time_steps = []
    level_steps = []
    time_step_counter = 0
    level_step_counter = 0
    for fname in fnames:
        dsin = Dataset(fname)
        try:
            print fname
            print (os.path.isfile(fname))
            dsin = Dataset(fname)
        except:
            print "NetCDF file to process cannot be opened; Exiting"
#python            sys.exit()
        time_steps[:] = dsin.variables['time'][:]
        level_steps[:] = dsin.variables['deptht'][:]
        print "Time Steps ", time_steps
        print "Vertical Levels ", level_steps
        for time_step in range(len(time_steps)):
            time_step_counter = time_step_counter + 1
            print "time_steps[time_step]", time_steps[time_step]
            time = int(time_steps[time_step])/(60 * 60)
            for level_step in range(len(level_steps)):
                level_step_counter = level_step_counter + 1
                level = level_steps[level_step]
                print "output strings are: ", time, level_step
                temp_level_str = "_T" + str(time_step) + "_L" + str(level_step + 1) + ".nc"
                fname_out = (fname.replace("split_data", "split_data/split_nco")).replace(".nc", temp_level_str)
                print fname_out
                cmd = path_to_ncks + " -O -d time," + str(time_step) + " -d deptht," + str(level_step) + " " + fname+" " + fname_out
                print cmd 
                runcmd(cmd)
                cmd = path_to_ncatted +" -O -a mars_step,data,m,c," + str(time) + " " + fname_out
                print cmd
                runcmd(cmd)
                cmd = path_to_ncatted +" -O -a mars_levelist,data,m,c," + str(level_step+1) + " " + fname_out
                print cmd
                runcmd(cmd)
                cmd = path_to_ncatted + " -O -a valid_min,deptht,m,f," + str(level) + " " + fname_out
                print cmd
                runcmd(cmd)
                cmd = path_to_ncatted + " -O -a valid_max,deptht,m,f," + str(level) + " " + fname_out
                print cmd
                runcmd(cmd)
                cmd = path_to_ncks + " -4 "+fname_out+" "+fname_out+"4"
                runcmd(cmd)
#
# break out of processing loop if only want first 3 levels for testing
#
                if level_step_counter == 3: 
                    break
#
# break out of processing loop if only want first timestep for testing
#
            if time_step_counter == 1: 
                break

if __name__ == "__main__":
    main()




