Skip to content

Commit

Permalink
Merge pull request #224 from billsacks/filename_add_day
Browse files Browse the repository at this point in the history
Allow adding a day to streams' file name date specifier

### Description of changes

This is needed for the new presaero 24-hour cplhist files, where the first file name has a date stamp of 0001-01-02.

This can be leveraged by changing the file specifier for a stream – such as the presaero stream – to have a filename_advance_days="1" attribute like this:

```xml
<file first_year="$DATM_YR_START" last_year="$DATM_YR_END" filename_advance_days="1">$DATM_CPLHIST_DIR/$DATM_CPLHIST_CASE.cpl.ha2x1d.%ymd.nc</file>
```

### Specific notes

Contributors other than yourself, if any: @olyson 

CDEPS Issues Fixed (include github issue #): none

Are there dependencies on other component PRs (if so list): No

Are changes expected to change answers (bfb, different to roundoff, more substantial): No

Any User Interface Changes (namelist or namelist defaults changes): None

Testing performed (e.g. aux_cdeps, CESM prealpha, etc): Manual testing

Hashes used for testing: CTSM at tag ctsm5.1.dev120, with its corresponding externals
  • Loading branch information
billsacks authored Apr 17, 2023
2 parents 69e5502 + d4d0809 commit f2f773c
Show file tree
Hide file tree
Showing 2 changed files with 68 additions and 3 deletions.
54 changes: 51 additions & 3 deletions cime_config/stream_cdeps.py
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,14 @@ def create_stream_xml(self, stream_names, case, streams_xml_file, data_list_file
stream_year_last = int(value)
year_first = max(stream_year_first, data_year_first)
year_last = min(stream_year_last, data_year_last)
stream_datafiles = self._sub_paths(stream_datafiles, year_first, year_last)
if 'filename_advance_days' in child.xml_element.attrib:
filename_advance_days = int(child.xml_element.get('filename_advance_days'))
else:
filename_advance_days = 0
stream_datafiles = self._sub_paths(stream_name,
stream_datafiles,
year_first, year_last,
filename_advance_days)
stream_datafiles = stream_datafiles.strip()
#endif
if stream_vars[node_name]:
Expand Down Expand Up @@ -427,7 +434,33 @@ def _days_in_month(month, year=1):
next_month_start = datetime.date(next_year, next_month, 1)
return (next_month_start - month_start).days

def _sub_paths(self, filenames, year_start, year_end):
@classmethod
def _add_day(cls, year, month, day):
"""Given a year, month and day, add 1 day
Returns a new tuple, (adjusted_year, adjusted_month, adjusted_day)
Assumes a no-leap calendar
>>> StreamCDEPS._add_day(1999, 1, 1)
(1999, 1, 2)
>>> StreamCDEPS._add_day(1999, 1, 31)
(1999, 2, 1)
>>> StreamCDEPS._add_day(1999, 12, 31)
(2000, 1, 1)
"""
adjusted_year = year
adjusted_month = month
adjusted_day = day + 1
if adjusted_day > cls._days_in_month(month):
adjusted_day = 1
adjusted_month = adjusted_month + 1
if adjusted_month > 12:
adjusted_month = 1
adjusted_year = adjusted_year + 1
return (adjusted_year, adjusted_month, adjusted_day)

def _sub_paths(self, stream_name, filenames, year_start, year_end, filename_advance_days):
"""Substitute indicators with given values in a list of filenames.
Replace any instance of the following substring indicators with the
Expand All @@ -447,13 +480,24 @@ def _sub_paths(self, filenames, year_start, year_end):
also that we use a no-leap calendar, i.e. every month has the same
number of days every year.
filename_advance_days is an integer specifying the number of days to add to the date
portion of the file name when using %ymd. Currently only values of 0 or 1 are
supported. This is typically 0 but can be 1 to indicate that the dates have a
one-day offset, starting with day 2 in the first year and ending with day 1 in the
year following the last year. This can be the case, for example, for daily coupler
history files.
The difference between this function and `_sub_fields` is that this
function is intended to be used for file names (especially from the
`strm_datfil` defaults), whereas `_sub_fields` is intended for use on
variable names.
Returns a string (filenames separated by newlines).
"""
expect(filename_advance_days == 0 or filename_advance_days == 1,
"Bad filename_advance_days attribute ({}) for {}: must be 0 or 1".format(
filename_advance_days, stream_name))

lines = [line for line in filenames.split("\n") if line]
new_lines = []
for line in lines:
Expand All @@ -470,7 +514,11 @@ def _sub_paths(self, filenames, year_start, year_end):
for month in range(1, 13):
days = self._days_in_month(month)
for day in range(1, days+1):
date_string = (year_format + "-{:02d}-{:02d}").format(year, month, day)
if filename_advance_days == 1:
(adjusted_year, adjusted_month, adjusted_day) = self._add_day(year, month, day)
else:
(adjusted_year, adjusted_month, adjusted_day) = (year, month, day)
date_string = (year_format + "-{:02d}-{:02d}").format(adjusted_year, adjusted_month, adjusted_day)
new_line = line.replace(match.group(0), date_string)
new_lines.append(new_line)
elif match.group('month'):
Expand Down
17 changes: 17 additions & 0 deletions cime_config/stream_definition_v2.0.xsd
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,22 @@
<xs:attribute name="compset" type="xs:string"/>
<xs:attribute name="version" type="xs:string"/>

<!-- For file names with the %ymd specifier, this attribute can be set
to 1 to indicate that the dates have a one-day offset, starting
with day 2 in the first year and ending with day 1 in the year
following the last year. This can be the case, for example, for
daily coupler history files. (The absence of this attribute is
equivalent to a value of 0. Currently only values of 0 and 1 are
supported, though we may extend that in the future if needed.)
-->
<xs:attribute name="filename_advance_days">
<xs:simpleType>
<xs:restriction base="xs:integer">
<xs:pattern value="0|1"/>
</xs:restriction>
</xs:simpleType>
</xs:attribute>

<!-- ======================== -->
<!-- simple elements -->
<!-- ======================== -->
Expand Down Expand Up @@ -166,6 +182,7 @@
<xs:attribute ref="first_year"/>
<xs:attribute ref="last_year"/>
<xs:attribute ref="model_grid"/>
<xs:attribute ref="filename_advance_days"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
Expand Down

0 comments on commit f2f773c

Please sign in to comment.