diff --git a/parm/config/gefs/config.base b/parm/config/gefs/config.base index acfc39db33..65bca1b377 100644 --- a/parm/config/gefs/config.base +++ b/parm/config/gefs/config.base @@ -248,6 +248,10 @@ export FHOUT_WAV=3 export FHMAX_HF_WAV=120 export FHOUT_HF_WAV=1 export FHMAX_WAV=${FHMAX_GFS} +export FHMAX_WAV_GFS=${FHMAX_GFS} +export FHMAX_HF_GFS=$(( FHMAX_HF_GFS > FHMAX_GFS ? FHMAX_GFS : FHMAX_HF_GFS )) +export FHMAX_WAV_GFS=$(( FHMAX_WAV_GFS > FHMAX_GFS ? FHMAX_GFS : FHMAX_WAV_GFS )) +export FHMAX_HF_WAV=$(( FHMAX_HF_WAV > FHMAX_WAV_GFS ? FHMAX_WAV_GFS : FHMAX_HF_WAV )) export ILPOST=1 # gempak output frequency up to F120 export FHMIN_ENKF=${FHMIN_GFS} diff --git a/parm/config/gfs/config.base b/parm/config/gfs/config.base index 91f353360f..46e27b4541 100644 --- a/parm/config/gfs/config.base +++ b/parm/config/gfs/config.base @@ -311,6 +311,10 @@ export FHMAX_HF_WAV=120 export FHOUT_HF_WAV=1 export FHMAX_WAV=${FHMAX:-9} export FHMAX_WAV_GFS=${FHMAX_GFS} +export FHMAX_HF_GFS=$(( FHMAX_HF_GFS > FHMAX_GFS ? FHMAX_GFS : FHMAX_HF_GFS )) +export FHMAX_WAV=$(( FHMAX_WAV > FHMAX ? FHMAX : FHMAX_WAV )) +export FHMAX_WAV_GFS=$(( FHMAX_WAV_GFS > FHMAX_GFS ? FHMAX_GFS : FHMAX_WAV_GFS )) +export FHMAX_HF_WAV=$(( FHMAX_HF_WAV > FHMAX_WAV_GFS ? FHMAX_WAV_GFS : FHMAX_HF_WAV )) # TODO: Change gempak to use standard out variables (#2348) export ILPOST=${FHOUT_HF_GFS} # gempak output frequency up to F120 diff --git a/scripts/exgfs_wave_post_gridded_sbs.sh b/scripts/exgfs_wave_post_gridded_sbs.sh index b0cca34bd1..a241a00d88 100755 --- a/scripts/exgfs_wave_post_gridded_sbs.sh +++ b/scripts/exgfs_wave_post_gridded_sbs.sh @@ -217,219 +217,189 @@ source "${USHgfs}/preamble.sh" set +x echo ' Making command file for sbs grib2 and GRID Interpolation ' set_trace - -# 1.a.2 Loop over forecast time to generate post files -# When executed side-by-side, serial mode (cfp when run after the fcst step) -# Contingency for RERUN=YES - if [ "${RERUN-NO}" = "YES" ]; then - fhr=$((FHRUN + FHMIN_WAV)) - if [ $FHMAX_HF_WAV -gt 0 ] && [ $FHOUT_HF_WAV -gt 0 ] && [ $fhr -lt $FHMAX_HF_WAV ]; then - FHINCG=$FHOUT_HF_WAV - else - FHINCG=$FHOUT_WAV - fi - fhr=$((fhr + FHINCG)) - else - fhr=$FHMIN_WAV - fi + fhr=$(( 10#${FHR3} )) fhrg=$fhr - sleep_interval=10 - iwaitmax=120 # Maximum loop cycles for waiting until wave component output file is ready (fails after max) - while [ $fhr -le $FHMAX_WAV ]; do + ymdh=$($NDATE $fhr ${PDY}${cyc}) + YMD=$(echo $ymdh | cut -c1-8) + HMS="$(echo $ymdh | cut -c9-10)0000" + YMDHMS=${YMD}${HMS} + FH3=$(printf %03i $fhr) - ymdh=$($NDATE $fhr ${PDY}${cyc}) - YMD=$(echo $ymdh | cut -c1-8) - HMS="$(echo $ymdh | cut -c9-10)0000" - YMDHMS=${YMD}${HMS} - FH3=$(printf %03i $fhr) - - fcmdnow=cmdfile.${FH3} - fcmdigrd=icmdfile.${FH3} - mkdir output_$YMDHMS - cd output_$YMDHMS - rm -f ${fcmdnow} ${fcmdigrd} - touch ${fcmdnow} ${fcmdigrd} + fcmdnow=cmdfile.${FH3} + fcmdigrd=icmdfile.${FH3} + mkdir output_$YMDHMS + cd output_$YMDHMS + rm -f ${fcmdnow} ${fcmdigrd} + touch ${fcmdnow} ${fcmdigrd} # Create instances of directories for gridded output - export GRIBDATA=${DATA}/output_$YMDHMS - export GRDIDATA=${DATA}/output_$YMDHMS + export GRIBDATA=${DATA}/output_$YMDHMS + export GRDIDATA=${DATA}/output_$YMDHMS # Gridded data (main part, need to be run side-by-side with forecast - - if [ $fhr = $fhrg ] - then - for wavGRD in ${waveGRD}; do - gfile="${COMIN_WAVE_HISTORY}/${WAV_MOD_TAG}.out_grd.${wavGRD}.${YMD}.${HMS}" - if ! wait_for_file "${gfile}" "${sleep_interval}" "${iwaitmax}"; then - echo " FATAL ERROR : NO RAW FIELD OUTPUT FILE out_grd.${grdID}" - echo "${WAV_MOD_TAG} post ${grdID} ${PDY} ${cycle} : field output missing." + + if [ $fhr = $fhrg ] + then + for wavGRD in ${waveGRD}; do + gfile="${COMIN_WAVE_HISTORY}/${WAV_MOD_TAG}.out_grd.${wavGRD}.${YMD}.${HMS}" + if [[ ! -s "${gfile}" ]]; then + echo " FATAL ERROR : NO RAW FIELD OUTPUT FILE ${gfile}" err=3; export err; "${errchk}" exit "${err}" fi - ${NLN} "${gfile}" "./out_grd.${wavGRD}" - done - - if [ "$DOGRI_WAV" = 'YES' ] - then - nigrd=1 - for grdID in $waveinterpGRD - do - ymdh_int=$($NDATE -${WAVHINDH} $ymdh); dt_int=3600.; n_int=9999 ; - echo "${USHgfs}/wave_grid_interp_sbs.sh $grdID $ymdh_int $dt_int $n_int > grint_$grdID.out 2>&1" >> ${fcmdigrd}.${nigrd} - if [ "$DOGRB_WAV" = 'YES' ] - then - gribFL=\'$(echo ${OUTPARS_WAV})\' - case $grdID in - glo_15mxt) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - reg025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - glo_025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - glo_100) GRDNAME='global' ; GRDRES=1p00 ; GRIDNR=255 ; MODNR=11 ;; - glo_200) GRDNAME='global' ; GRDRES=2p00 ; GRIDNR=255 ; MODNR=11 ;; - glo_500) GRDNAME='global' ; GRDRES=5p00 ; GRIDNR=255 ; MODNR=11 ;; - glo_30mxt) GRDNAME='global' ; GRDRES=0p50 ; GRIDNR=255 ; MODNR=11 ;; - glo_30m) GRDNAME='global' ; GRDRES=0p50 ; GRIDNR=255 ; MODNR=11 ;; - at_10m) GRDNAME='atlocn' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; - ep_10m) GRDNAME='epacif' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; - wc_10m) GRDNAME='wcoast' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; - ak_10m) GRDNAME='alaska' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; - esac - echo "${USHgfs}/wave_grib2_sbs.sh $grdID $GRIDNR $MODNR $ymdh $fhr $GRDNAME $GRDRES $gribFL > grib_$grdID.out 2>&1" >> ${fcmdigrd}.${nigrd} - fi - echo "${GRIBDATA}/${fcmdigrd}.${nigrd}" >> ${fcmdnow} - chmod 744 ${fcmdigrd}.${nigrd} - nigrd=$((nigrd+1)) - done - fi + ${NLN} "${gfile}" "./out_grd.${wavGRD}" + done - if [ "$DOGRB_WAV" = 'YES' ] - then - for grdID in ${wavepostGRD} # First concatenate grib files for sbs grids - do + if [ "$DOGRI_WAV" = 'YES' ] + then + nigrd=1 + for grdID in $waveinterpGRD + do + ymdh_int=$($NDATE -${WAVHINDH} $ymdh); dt_int=3600.; n_int=9999 ; + echo "${USHgfs}/wave_grid_interp_sbs.sh $grdID $ymdh_int $dt_int $n_int > grint_$grdID.out 2>&1" >> ${fcmdigrd}.${nigrd} + if [ "$DOGRB_WAV" = 'YES' ] + then gribFL=\'$(echo ${OUTPARS_WAV})\' case $grdID in - aoc_9km) GRDNAME='arctic' ; GRDRES=9km ; GRIDNR=255 ; MODNR=11 ;; - ant_9km) GRDNAME='antarc' ; GRDRES=9km ; GRIDNR=255 ; MODNR=11 ;; - glo_10m) GRDNAME='global' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; - gnh_10m) GRDNAME='global' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; - gsh_15m) GRDNAME='gsouth' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - glo_15m) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - ao_20m) GRDNAME='arctic' ; GRDRES=0p33 ; GRIDNR=255 ; MODNR=11 ;; - so_20m) GRDNAME='antarc' ; GRDRES=0p33 ; GRIDNR=255 ; MODNR=11 ;; - glo_15mxt) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - reg025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - glo_025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; - glo_100) GRDNAME='global' ; GRDRES=1p00 ; GRIDNR=255 ; MODNR=11 ;; - glo_200) GRDNAME='global' ; GRDRES=2p00 ; GRIDNR=255 ; MODNR=11 ;; - glo_500) GRDNAME='global' ; GRDRES=5p00 ; GRIDNR=255 ; MODNR=11 ;; - gwes_30m) GRDNAME='global' ; GRDRES=0p50 ; GRIDNR=255 ; MODNR=10 ;; + glo_15mxt) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + reg025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + glo_025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + glo_100) GRDNAME='global' ; GRDRES=1p00 ; GRIDNR=255 ; MODNR=11 ;; + glo_200) GRDNAME='global' ; GRDRES=2p00 ; GRIDNR=255 ; MODNR=11 ;; + glo_500) GRDNAME='global' ; GRDRES=5p00 ; GRIDNR=255 ; MODNR=11 ;; + glo_30mxt) GRDNAME='global' ; GRDRES=0p50 ; GRIDNR=255 ; MODNR=11 ;; + glo_30m) GRDNAME='global' ; GRDRES=0p50 ; GRIDNR=255 ; MODNR=11 ;; + at_10m) GRDNAME='atlocn' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; + ep_10m) GRDNAME='epacif' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; + wc_10m) GRDNAME='wcoast' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; + ak_10m) GRDNAME='alaska' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; esac - echo "${USHgfs}/wave_grib2_sbs.sh $grdID $GRIDNR $MODNR $ymdh $fhr $GRDNAME $GRDRES $gribFL > grib_$grdID.out 2>&1" >> ${fcmdnow} - done - fi - + echo "${USHgfs}/wave_grib2_sbs.sh $grdID $GRIDNR $MODNR $ymdh $fhr $GRDNAME $GRDRES $gribFL > grib_$grdID.out 2>&1" >> ${fcmdigrd}.${nigrd} + fi + echo "${GRIBDATA}/${fcmdigrd}.${nigrd}" >> ${fcmdnow} + chmod 744 ${fcmdigrd}.${nigrd} + nigrd=$((nigrd+1)) + done fi - if [ ${CFP_MP:-"NO"} = "YES" ]; then - nfile=0 - ifile=0 - iline=1 - ifirst='yes' - nlines=$( wc -l ${fcmdnow} | awk '{print $1}' ) - while [ $iline -le $nlines ]; do - line=$( sed -n ''$iline'p' ${fcmdnow} ) - if [ -z "$line" ]; then - break - else - if [ "$ifirst" = 'yes' ]; then - echo "#!/bin/sh" > cmdmfile.$nfile - echo "$nfile cmdmfile.$nfile" >> cmdmprog - chmod 744 cmdmfile.$nfile - fi - echo $line >> cmdmfile.$nfile - nfile=$(( nfile + 1 )) - if [ $nfile -eq $NTASKS ]; then - nfile=0 - ifirst='no' - fi - iline=$(( iline + 1 )) - fi + if [ "$DOGRB_WAV" = 'YES' ] + then + for grdID in ${wavepostGRD} # First concatenate grib files for sbs grids + do + gribFL=\'$(echo ${OUTPARS_WAV})\' + case $grdID in + aoc_9km) GRDNAME='arctic' ; GRDRES=9km ; GRIDNR=255 ; MODNR=11 ;; + ant_9km) GRDNAME='antarc' ; GRDRES=9km ; GRIDNR=255 ; MODNR=11 ;; + glo_10m) GRDNAME='global' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; + gnh_10m) GRDNAME='global' ; GRDRES=0p16 ; GRIDNR=255 ; MODNR=11 ;; + gsh_15m) GRDNAME='gsouth' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + glo_15m) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + ao_20m) GRDNAME='arctic' ; GRDRES=0p33 ; GRIDNR=255 ; MODNR=11 ;; + so_20m) GRDNAME='antarc' ; GRDRES=0p33 ; GRIDNR=255 ; MODNR=11 ;; + glo_15mxt) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + reg025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + glo_025) GRDNAME='global' ; GRDRES=0p25 ; GRIDNR=255 ; MODNR=11 ;; + glo_100) GRDNAME='global' ; GRDRES=1p00 ; GRIDNR=255 ; MODNR=11 ;; + glo_200) GRDNAME='global' ; GRDRES=2p00 ; GRIDNR=255 ; MODNR=11 ;; + glo_500) GRDNAME='global' ; GRDRES=5p00 ; GRIDNR=255 ; MODNR=11 ;; + gwes_30m) GRDNAME='global' ; GRDRES=0p50 ; GRIDNR=255 ; MODNR=10 ;; + esac + echo "${USHgfs}/wave_grib2_sbs.sh $grdID $GRIDNR $MODNR $ymdh $fhr $GRDNAME $GRDRES $gribFL > grib_$grdID.out 2>&1" >> ${fcmdnow} done fi - wavenproc=$(wc -l ${fcmdnow} | awk '{print $1}') - wavenproc=$(echo $((${wavenproc}<${NTASKS}?${wavenproc}:${NTASKS}))) + fi + + if [ ${CFP_MP:-"NO"} = "YES" ]; then + nfile=0 + ifile=0 + iline=1 + ifirst='yes' + nlines=$( wc -l ${fcmdnow} | awk '{print $1}' ) + while [ $iline -le $nlines ]; do + line=$( sed -n ''$iline'p' ${fcmdnow} ) + if [ -z "$line" ]; then + break + else + if [ "$ifirst" = 'yes' ]; then + echo "#!/bin/sh" > cmdmfile.$nfile + echo "$nfile cmdmfile.$nfile" >> cmdmprog + chmod 744 "cmdmfile.$nfile" + fi + echo $line >> "cmdmfile.$nfile" + nfile=$(( nfile + 1 )) + if [ "$nfile" -eq "$NTASKS" ]; then + nfile=0 + ifirst='no' + fi + iline=$(( iline + 1 )) + fi + done + fi + + wavenproc=$(wc -l ${fcmdnow} | awk '{print $1}') + wavenproc=$(echo $((${wavenproc}<${NTASKS}?${wavenproc}:${NTASKS}))) + + set +x + echo ' ' + echo " Executing the grib2_sbs scripts at : $(date)" + echo ' ------------------------------------' + echo ' ' + set_trace + + if [ "$wavenproc" -gt '1' ] + then + if [ ${CFP_MP:-"NO"} = "YES" ]; then + ${wavempexec} -n ${wavenproc} ${wave_mpmd} cmdmprog + else + ${wavempexec} ${wavenproc} ${wave_mpmd} ${fcmdnow} + fi + exit=$? + else + chmod 744 ${fcmdnow} + ./${fcmdnow} + exit=$? + fi + if [ "$exit" != '0' ] + then set +x echo ' ' - echo " Executing the grib2_sbs scripts at : $(date)" - echo ' ------------------------------------' + echo '*************************************' + echo '*** FATAL ERROR: CMDFILE FAILED ***' + echo '*************************************' + echo ' See Details Below ' echo ' ' set_trace + err=4; export err;${errchk} + exit "$err" + fi - if [ "$wavenproc" -gt '1' ] - then - if [ ${CFP_MP:-"NO"} = "YES" ]; then - ${wavempexec} -n ${wavenproc} ${wave_mpmd} cmdmprog - else - ${wavempexec} ${wavenproc} ${wave_mpmd} ${fcmdnow} - fi - exit=$? - else - chmod 744 ${fcmdnow} - ./${fcmdnow} - exit=$? - fi + rm -f out_grd.* # Remove large binary grid output files - if [ "$exit" != '0' ] - then + cd $DATA + + + if [ "$fhr" = "$fhrg" ] + then +# Check if grib2 file created + ENSTAG="" + if [ ${waveMEMB} ]; then ENSTAG=".${membTAG}${waveMEMB}" ; fi + gribchk="${RUN}wave.${cycle}${ENSTAG}.${GRDNAME}.${GRDRES}.f${FH3}.grib2" + if [ ! -s ${COMOUT_WAVE_GRID}/${gribchk} ]; then set +x echo ' ' - echo '*************************************' - echo '*** FATAL ERROR: CMDFILE FAILED ***' - echo '*************************************' + echo '********************************************' + echo "*** FATAL ERROR: $gribchk not generated " + echo '********************************************' echo ' See Details Below ' echo ' ' set_trace - err=4; export err;${errchk} - exit $err - fi - - rm -f out_grd.* # Remove large binary grid output files - - cd $DATA - - FHINCG=$(( DTFLD_WAV / 3600 )) - if [ $fhr = $fhrg ] - then -# Check if grib2 file created - ENSTAG="" - if [ ${waveMEMB} ]; then ENSTAG=".${membTAG}${waveMEMB}" ; fi - gribchk="${RUN}wave.${cycle}${ENSTAG}.${GRDNAME}.${GRDRES}.f${FH3}.grib2" - if [ ! -s ${COMOUT_WAVE_GRID}/${gribchk} ]; then - set +x - echo ' ' - echo '********************************************' - echo "*** FATAL ERROR: $gribchk not generated " - echo '********************************************' - echo ' See Details Below ' - echo ' ' - set_trace - err=5; export err;${errchk} - exit $err - fi - if [ $FHMAX_HF_WAV -gt 0 ] && [ $FHOUT_HF_WAV -gt 0 ] && [ $fhr -lt $FHMAX_HF_WAV ]; then - FHINCG=$FHOUT_HF_WAV - else - FHINCG=$FHOUT_WAV - fi - fhrg=$((fhr+FHINCG)) + err=5; export err;${errchk} + exit "$err" fi - echo $fhrg - - fhr=$fhrg #loop with out_grd stride - - done + fi # --------------------------------------------------------------------------- # # 7. Ending output diff --git a/workflow/rocoto/gefs_tasks.py b/workflow/rocoto/gefs_tasks.py index 468ce01008..ca29bcdf1e 100644 --- a/workflow/rocoto/gefs_tasks.py +++ b/workflow/rocoto/gefs_tasks.py @@ -316,13 +316,14 @@ def wavepostsbs(self): wave_post_envars = self.envars.copy() postenvar_dict = {'ENSMEM': '#member#', 'MEMDIR': 'mem#member#', + 'FHR3': '#fhr#', } for key, value in postenvar_dict.items(): wave_post_envars.append(rocoto.create_envar(name=key, value=str(value))) resources = self.get_resource('wavepostsbs') - task_name = f'gefs_wave_post_grid_mem#member#' + task_name = f'gefs_wave_post_grid_mem#member#_f#fhr#' task_dict = {'task_name': task_name, 'resources': resources, 'dependency': dependencies, @@ -334,11 +335,21 @@ def wavepostsbs(self): 'maxtries': '&MAXTRIES;' } - member_var_dict = {'member': ' '.join([str(mem).zfill(3) for mem in range(0, self.nmem + 1)])} - member_metatask_dict = {'task_name': 'gefs_wave_post_grid', - 'task_dict': task_dict, - 'var_dict': member_var_dict - } + fhrs = self._get_forecast_hours('gefs', self._configs['wavepostsbs'], 'wave') + is_replay = self._configs['wavepostsbs']['REPLAY_ICS'] + if is_replay: + fhrs = [fhr for fhr in fhrs if fhr not in [0, 1, 2]] + + fhr_var_dict = {'fhr': ' '.join([f"{fhr:03d}" for fhr in fhrs])} + + fhr_metatask_dict = {'task_name': f'gefs_wave_post_grid_#member#', + 'task_dict': task_dict, + 'var_dict': fhr_var_dict} + + member_var_dict = {'member': ' '.join([f"{mem:03d}" for mem in range(0, self.nmem + 1)])} + member_metatask_dict = {'task_name': f'gefs_wave_post_grid', + 'task_dict': fhr_metatask_dict, + 'var_dict': member_var_dict} task = rocoto.create_task(member_metatask_dict) @@ -467,7 +478,7 @@ def wavepostpnt(self): def extractvars(self): deps = [] if self.options['do_wave']: - dep_dict = {'type': 'task', 'name': 'gefs_wave_post_grid_mem#member#'} + dep_dict = {'type': 'metatask', 'name': 'gefs_wave_post_grid_#member#'} deps.append(rocoto.add_dependency(dep_dict)) if self.options['do_ocean']: dep_dict = {'type': 'metatask', 'name': 'gefs_ocean_prod_#member#'} diff --git a/workflow/rocoto/gfs_tasks.py b/workflow/rocoto/gfs_tasks.py index 616248c110..535f5ce844 100644 --- a/workflow/rocoto/gfs_tasks.py +++ b/workflow/rocoto/gfs_tasks.py @@ -1172,6 +1172,7 @@ def _atmosoceaniceprod(self, component: str): fhrs.remove(0) fhr_var_dict = {'fhr': ' '.join([f"{fhr:03d}" for fhr in fhrs])} + if component in ['ocean']: fhrs_next = fhrs[1:] + [fhrs[-1] + (fhrs[-1] - fhrs[-2])] fhr_var_dict['fhr_next'] = ' '.join([f"{fhr:03d}" for fhr in fhrs_next]) @@ -1184,17 +1185,23 @@ def _atmosoceaniceprod(self, component: str): return task def wavepostsbs(self): + deps = [] dep_dict = {'type': 'metatask', 'name': f'{self.run}_fcst'} deps.append(rocoto.add_dependency(dep_dict)) dependencies = rocoto.create_dependency(dep=deps) + wave_post_envars = self.envars.copy() + postenvar_dict = {'FHR3': '#fhr#'} + for key, value in postenvar_dict.items(): + wave_post_envars.append(rocoto.create_envar(name=key, value=str(value))) + resources = self.get_resource('wavepostsbs') - task_name = f'{self.run}_wavepostsbs' + task_name = f'{self.run}_wavepostsbs_f#fhr#' task_dict = {'task_name': task_name, 'resources': resources, 'dependency': dependencies, - 'envars': self.envars, + 'envars': wave_post_envars, 'cycledef': self.run.replace('enkf', ''), 'command': f'{self.HOMEgfs}/jobs/rocoto/wavepostsbs.sh', 'job_name': f'{self.pslot}_{task_name}_@H', @@ -1202,7 +1209,14 @@ def wavepostsbs(self): 'maxtries': '&MAXTRIES;' } - task = rocoto.create_task(task_dict) + fhrs = self._get_forecast_hours('gfs', self._configs['wavepostsbs'], 'wave') + + fhr_metatask_dict = {'fhr': ' '.join([f"{fhr:03d}" for fhr in fhrs])} + metatask_dict = {'task_name': f'{self.run}_wavepostsbs', + 'task_dict': task_dict, + 'var_dict': fhr_metatask_dict} + + task = rocoto.create_task(metatask_dict) return task @@ -1286,7 +1300,7 @@ def wavepostpnt(self): def wavegempak(self): deps = [] - dep_dict = {'type': 'task', 'name': f'{self.run}_wavepostsbs'} + dep_dict = {'type': 'metatask', 'name': f'{self.run}_wavepostsbs'} deps.append(rocoto.add_dependency(dep_dict)) dependencies = rocoto.create_dependency(dep=deps) @@ -1309,7 +1323,7 @@ def wavegempak(self): def waveawipsbulls(self): deps = [] - dep_dict = {'type': 'task', 'name': f'{self.run}_wavepostsbs'} + dep_dict = {'type': 'metatask', 'name': f'{self.run}_wavepostsbs'} deps.append(rocoto.add_dependency(dep_dict)) dep_dict = {'type': 'task', 'name': f'{self.run}_wavepostpnt'} deps.append(rocoto.add_dependency(dep_dict)) @@ -1334,7 +1348,7 @@ def waveawipsbulls(self): def waveawipsgridded(self): deps = [] - dep_dict = {'type': 'task', 'name': f'{self.run}_wavepostsbs'} + dep_dict = {'type': 'metatask', 'name': f'{self.run}_wavepostsbs'} deps.append(rocoto.add_dependency(dep_dict)) dependencies = rocoto.create_dependency(dep=deps) @@ -2271,7 +2285,7 @@ def arch(self): dep_dict = {'type': 'metatask', 'name': f'{self.run}_atmos_prod'} deps.append(rocoto.add_dependency(dep_dict)) if self.options['do_wave']: - dep_dict = {'type': 'task', 'name': f'{self.run}_wavepostsbs'} + dep_dict = {'type': 'metatask', 'name': f'{self.run}_wavepostsbs'} deps.append(rocoto.add_dependency(dep_dict)) dep_dict = {'type': 'task', 'name': f'{self.run}_wavepostpnt'} deps.append(rocoto.add_dependency(dep_dict)) diff --git a/workflow/rocoto/tasks.py b/workflow/rocoto/tasks.py index 2aee48835f..c0496a4996 100644 --- a/workflow/rocoto/tasks.py +++ b/workflow/rocoto/tasks.py @@ -152,6 +152,12 @@ def _get_forecast_hours(run, config, component='atmos') -> List[str]: local_config['FHOUT_GFS'] = config['FHOUT_ICE_GFS'] local_config['FHOUT'] = config['FHOUT_ICE'] + if component in ['wave']: + local_config['FHOUT_HF_GFS'] = config['FHOUT_HF_WAV'] + local_config['FHMAX_HF_GFS'] = config['FHMAX_HF_WAV'] + local_config['FHOUT_GFS'] = config['FHOUT_WAV'] + local_config['FHOUT'] = config['FHOUT_WAV'] + fhmin = local_config['FHMIN'] # Get a list of all forecast hours @@ -163,8 +169,8 @@ def _get_forecast_hours(run, config, component='atmos') -> List[str]: elif run in ['gfs', 'gefs']: fhmax = local_config['FHMAX_GFS'] fhout = local_config['FHOUT_GFS'] - fhmax_hf = local_config['FHMAX_HF_GFS'] fhout_hf = local_config['FHOUT_HF_GFS'] + fhmax_hf = local_config['FHMAX_HF_GFS'] fhrs_hf = range(fhmin, fhmax_hf + fhout_hf, fhout_hf) fhrs = list(fhrs_hf) + list(range(fhrs_hf[-1] + fhout, fhmax + fhout, fhout))