source: flex_extract.git/python/getMARSdata.py @ 991df6a

ctbtodev
Last change on this file since 991df6a was 991df6a, checked in by Anne Philipp <anne.philipp@…>, 6 years ago

finished documentation (except plot_retrieved)

  • Property mode set to 100755
File size: 8.5 KB
Line 
1#!/usr/bin/env python
2# -*- coding: utf-8 -*-
3#************************************************************************
4# TODO AP
5# - add function docstrings!!!!
6#************************************************************************
7#*******************************************************************************
8# @Author: Anne Fouilloux (University of Oslo)
9#
10# @Date: October 2014
11#
12# @Change History:
13#
14#    November 2015 - Leopold Haimberger (University of Vienna):
15#        - moved the getEIdata program into a function "getMARSdata"
16#        - moved the AgurmentParser into a seperate function
17#        - adatpted the function for the use in flex_extract
18#        - renamed file to getMARSdata
19#
20#    February 2018 - Anne Philipp (University of Vienna):
21#        - applied PEP8 style guide
22#        - added structured documentation
23#        - minor changes in programming style for consistence
24#        - added function main and moved function calls vom __main__ there
25#          (necessary for better documentation with docstrings for later
26#          online documentation)
27#        - use of UIFiles class for file selection and deletion
28
29#
30# @License:
31#    (C) Copyright 2014-2018.
32#
33#    This software is licensed under the terms of the Apache Licence Version 2.0
34#    which can be obtained at http://www.apache.org/licenses/LICENSE-2.0.
35#
36# @Program Functionality:
37#    This program can be used as a module in the whole flex_extract process
38#    or can be run by itself to just extract MARS data from ECMWF. To do so,
39#    a couple of necessary parameters has to be passed with the program call.
40#    See documentation for more details.
41#
42# @Program Content:
43#    - main
44#    - getMARSdata
45#
46#*******************************************************************************
47
48# ------------------------------------------------------------------------------
49# MODULES
50# ------------------------------------------------------------------------------
51import os
52import sys
53import datetime
54import inspect
55try:
56    ecapi=True
57    import ecmwfapi
58except ImportError:
59    ecapi=False
60
61# add path to pythonpath so that python finds its buddies
62localpythonpath = os.path.dirname(os.path.abspath(
63    inspect.getfile(inspect.currentframe())))
64if localpythonpath not in sys.path:
65    sys.path.append(localpythonpath)
66
67# software specific classes and modules from flex_extract
68from ControlFile import ControlFile
69from Tools import myerror, normalexit, \
70                          interpret_args_and_control
71from ECFlexpart import ECFlexpart
72from UIOFiles import UIOFiles
73
74# ------------------------------------------------------------------------------
75# FUNCTION
76# ------------------------------------------------------------------------------
77def main():
78    '''
79    @Description:
80        If getMARSdata is called from command line, this function controls
81        the program flow and calls the argumentparser function and
82        the getMARSdata function for retrieving EC data.
83
84    @Input:
85        <nothing>
86
87    @Return:
88        <nothing>
89    '''
90    args, c = interpret_args_and_control()
91    getMARSdata(args, c)
92    normalexit(c)
93
94    return
95
96def getMARSdata(args, c):
97    '''
98    @Description:
99        Retrieves the EC data needed for a FLEXPART simulation.
100        Start and end dates for retrieval period is set. Retrievals
101        are divided into smaller periods if necessary and datechunk parameter
102        is set.
103
104    @Input:
105        args: instance of ArgumentParser
106            Contains the commandline arguments from script/program call.
107
108        c: instance of class ControlFile
109            Contains all the parameters of CONTROL file, which are e.g.:
110            DAY1(start_date), DAY2(end_date), DTIME, MAXSTEP, TYPE, TIME,
111            STEP, CLASS(marsclass), STREAM, NUMBER, EXPVER, GRID, LEFT,
112            LOWER, UPPER, RIGHT, LEVEL, LEVELIST, RESOL, GAUSS, ACCURACY,
113            OMEGA, OMEGADIFF, ETA, ETADIFF, DPDETA, SMOOTH, FORMAT,
114            ADDPAR, WRF, CWC, PREFIX, ECSTORAGE, ECTRANS, ECFSDIR,
115            MAILOPS, MAILFAIL, GRIB2FLEXPART, FLEXPARTDIR, BASETIME
116            DATE_CHUNK, DEBUG, INPUTDIR, OUTPUTDIR, FLEXPART_ROOT_SCRIPTS
117
118            For more information about format and content of the parameter
119            see documentation.
120
121    @Return:
122        <nothing>
123    '''
124
125    if not os.path.exists(c.inputdir):
126        os.makedirs(c.inputdir)
127
128    print("Retrieving EC data!")
129    print("start date %s " % (c.start_date))
130    print("end date %s " % (c.end_date))
131
132    if ecapi:
133        server = ecmwfapi.ECMWFService("mars")
134    else:
135        server = False
136
137    c.ecapi = ecapi
138    print 'ecapi: ', c.ecapi
139
140    # set start date of retrieval period
141    start = datetime.date(year=int(c.start_date[:4]),
142                          month=int(c.start_date[4:6]),
143                          day=int(c.start_date[6:]))
144    startm1 = start - datetime.timedelta(days=1)
145    if c.basetime == '00':
146        start = startm1
147
148    # set end date of retrieval period
149    end = datetime.date(year=int(c.end_date[:4]),
150                        month=int(c.end_date[4:6]),
151                        day=int(c.end_date[6:]))
152    if c.basetime == '00' or c.basetime == '12':
153        endp1 = end + datetime.timedelta(days=1)
154    else:
155        endp1 = end + datetime.timedelta(days=2)
156
157    # set time period of one single retrieval
158    datechunk = datetime.timedelta(days=int(c.date_chunk))
159
160    # --------------  flux data ------------------------------------------------
161    print 'removing old flux content of ' + c.inputdir
162    tobecleaned = UIOFiles('*_acc_*.' + str(os.getppid()) + '.*.grb')
163    tobecleaned.listFiles(c.inputdir)
164    tobecleaned.deleteFiles()
165
166    # if forecast for maximum one day (upto 23h) are to be retrieved,
167    # collect accumulation data (flux data)
168    # with additional days in the beginning and at the end
169    # (used for complete disaggregation of original period)
170    if c.maxstep < 24:
171        day = startm1
172        while day < endp1:
173            # retrieve MARS data for the whole period
174            flexpart = ECFlexpart(c, fluxes=True)
175            tmpday = day + datechunk - datetime.timedelta(days=1)
176            if tmpday < endp1:
177                dates = day.strftime("%Y%m%d") + "/to/" + \
178                        tmpday.strftime("%Y%m%d")
179            else:
180                dates = day.strftime("%Y%m%d") + "/to/" + \
181                        end.strftime("%Y%m%d")
182
183            print "retrieve " + dates + " in dir " + c.inputdir
184
185            try:
186                flexpart.retrieve(server, dates, c.inputdir)
187            except IOError:
188                myerror(c, 'MARS request failed')
189
190            day += datechunk
191
192    # if forecast data longer than 24h are to be retrieved,
193    # collect accumulation data (flux data)
194    # with the exact start and end date
195    # (disaggregation will be done for the
196    # exact time period with boundary conditions)
197    else:
198        day = start
199        while day <= end:
200            # retrieve MARS data for the whole period
201            flexpart = ECFlexpart(c, fluxes=True)
202            tmpday = day + datechunk - datetime.timedelta(days=1)
203            if tmpday < end:
204                dates = day.strftime("%Y%m%d") + "/to/" + \
205                        tmpday.trftime("%Y%m%d")
206            else:
207                dates = day.strftime("%Y%m%d") + "/to/" + \
208                        end.strftime("%Y%m%d")
209
210            print "retrieve " + dates + " in dir " + c.inputdir
211
212            try:
213                flexpart.retrieve(server, dates, c.inputdir)
214            except IOError:
215                myerror(c, 'MARS request failed')
216
217            day += datechunk
218
219    # --------------  non flux data --------------------------------------------
220    print 'removing old non flux content of ' + c.inputdir
221    tobecleaned = UIOFiles('*__*.' + str(os.getppid()) + '.*.grb')
222    tobecleaned.listFiles(c.inputdir)
223    tobecleaned.deleteFiles()
224
225    day = start
226    while day <= end:
227            # retrieve all non flux MARS data for the whole period
228            flexpart = ECFlexpart(c, fluxes=False)
229            tmpday = day + datechunk - datetime.timedelta(days=1)
230            if tmpday < end:
231                dates = day.strftime("%Y%m%d") + "/to/" + \
232                        tmpday.strftime("%Y%m%d")
233            else:
234                dates = day.strftime("%Y%m%d") + "/to/" + \
235                        end.strftime("%Y%m%d")
236
237            print "retrieve " + dates + " in dir " + c.inputdir
238
239            try:
240                flexpart.retrieve(server, dates, c.inputdir)
241            except IOError:
242                myerror(c, 'MARS request failed')
243
244            day += datechunk
245
246    return
247
248if __name__ == "__main__":
249    main()
250
Note: See TracBrowser for help on using the repository browser.
hosted by ZAMG