From 9e3a1222176f9bad4a6bd96ec81073ade4c0511f Mon Sep 17 00:00:00 2001 From: Eric Sinsky - NOAA <48259628+EricSinsky-NOAA@users.noreply.github.com> Date: Thu, 1 May 2025 15:50:54 -0400 Subject: [PATCH] Add support for 24hr-averaged ocn/ice products (#3535) Add full capability to produce 24-hr ocean and ice products. In particular, fixing a bug where the CICE history files are missing when `cycle` is not `t00z` and when `FHOUT_ICE` is `24`. This fix has been made possible since the changes from [UFSWM PR #2437](https://github.com/ufs-community/ufs-weather-model/pull/2437) have been merged and the GW PR #3145 updated the UFSWM hash to include these UFSWM updates for global-workflow. Resolves #2674 --- .gitignore | 4 ++++ parm/config/gefs/yaml/defaults.yaml | 4 ++-- parm/config/gfs/config.oceanice_products | 2 +- parm/post/oceanice_products_gefs.yaml | 4 ++-- .../{oceanice_products.yaml => oceanice_products_gfs.yaml} | 2 +- sorc/gfs_utils.fd | 2 +- sorc/link_workflow.sh | 2 +- ush/forecast_postdet.sh | 6 +++++- ush/parsing_namelists_CICE.sh | 7 ++++++- 9 files changed, 23 insertions(+), 10 deletions(-) rename parm/post/{oceanice_products.yaml => oceanice_products_gfs.yaml} (97%) diff --git a/.gitignore b/.gitignore index 1fa7bbf34ef..bc540c083b8 100644 --- a/.gitignore +++ b/.gitignore @@ -74,7 +74,11 @@ parm/post/gfs parm/post/gefs parm/post/sfs parm/post/ocean.csv +parm/post/ocean_gefs.csv +parm/post/ocean_gfs.csv parm/post/ice.csv +parm/post/ice_gefs.csv +parm/post/ice_gfs.csv parm/post/ocnicepost.nml.jinja2 parm/ufs/noahmptable.tbl parm/ufs/model_configure.IN diff --git a/parm/config/gefs/yaml/defaults.yaml b/parm/config/gefs/yaml/defaults.yaml index d918d12ebcf..ac9c9553ed3 100644 --- a/parm/config/gefs/yaml/defaults.yaml +++ b/parm/config/gefs/yaml/defaults.yaml @@ -15,8 +15,8 @@ base: FCST_BREAKPOINTS: "48" REPLAY_ICS: "NO" FHOUT_GFS: 6 - FHOUT_OCN_GFS: 6 - FHOUT_ICE_GFS: 6 + FHOUT_OCN_GFS: 24 + FHOUT_ICE_GFS: 24 HPSSARCH: "NO" LOCALARCH: "NO" USE_OCN_ENS_PERTURB_FILES: "NO" diff --git a/parm/config/gfs/config.oceanice_products b/parm/config/gfs/config.oceanice_products index a618cbe10c2..6cce26997ce 100644 --- a/parm/config/gfs/config.oceanice_products +++ b/parm/config/gfs/config.oceanice_products @@ -10,7 +10,7 @@ source "${EXPDIR}/config.resources" oceanice_products # Maximum number of rocoto tasks per member export MAX_TASKS=25 -export OCEANICEPRODUCTS_CONFIG="${PARMgfs}/post/oceanice_products.yaml" +export OCEANICEPRODUCTS_CONFIG="${PARMgfs}/post/oceanice_products_gfs.yaml" # No. of forecast hours to process in a single job export NFHRS_PER_GROUP=3 diff --git a/parm/post/oceanice_products_gefs.yaml b/parm/post/oceanice_products_gefs.yaml index 3cf63643a5c..bf90952643c 100644 --- a/parm/post/oceanice_products_gefs.yaml +++ b/parm/post/oceanice_products_gefs.yaml @@ -10,7 +10,7 @@ ocnicepost: copy: - ["{{ EXECgfs }}/ocnicepost.x", "{{ DATA }}/"] - ["{{ PARMgfs }}/post/ocnicepost.nml.jinja2", "{{ DATA }}/"] - - ["{{ PARMgfs }}/post/{{ component }}.csv", "{{ DATA }}/"] + - ["{{ PARMgfs }}/post/{{ component }}_gefs.csv", "{{ DATA }}/{{ component }}.csv"] - ["{{ FIXgfs }}/mom6/post/{{ model_grid }}/tripole.{{ model_grid }}.Bu.to.Ct.bilinear.nc", "{{ DATA }}/"] - ["{{ FIXgfs }}/mom6/post/{{ model_grid }}/tripole.{{ model_grid }}.Cu.to.Ct.bilinear.nc", "{{ DATA }}/"] - ["{{ FIXgfs }}/mom6/post/{{ model_grid }}/tripole.{{ model_grid }}.Cv.to.Ct.bilinear.nc", "{{ DATA }}/"] @@ -57,7 +57,7 @@ ice: sinvar: "" cosvar: "" angvar: "ANGLET" - subset: ['hi_h', 'hs_h', 'aice_h', 'Tsfc_h', 'uvel_h', 'vvel_h', 'frzmlt_h', 'albsni_h', 'mlt_onset_h', 'frz_onset_h'] + subset: ['hi_1', 'hs_1', 'aice_1', 'Tsfc_1', 'uvel_1', 'vvel_1', 'frzmlt_1', 'albsni_1', 'mlt_onset_1', 'frz_onset_1'] data_in: copy: - ["{{ COMIN_ICE_HISTORY }}/{{ RUN }}.ice.t{{ current_cycle | strftime('%H') }}z.{{ interval }}hr_avg.f{{ '%03d' % forecast_hour }}.nc", "{{ DATA }}/ice.nc"] diff --git a/parm/post/oceanice_products.yaml b/parm/post/oceanice_products_gfs.yaml similarity index 97% rename from parm/post/oceanice_products.yaml rename to parm/post/oceanice_products_gfs.yaml index 8d4ca0401fc..d6ea35e00c1 100644 --- a/parm/post/oceanice_products.yaml +++ b/parm/post/oceanice_products_gfs.yaml @@ -10,7 +10,7 @@ ocnicepost: copy: - ["{{ EXECgfs }}/ocnicepost.x", "{{ DATA }}/"] - ["{{ PARMgfs }}/post/ocnicepost.nml.jinja2", "{{ DATA }}/"] - - ["{{ PARMgfs }}/post/{{ component }}.csv", "{{ DATA }}/"] + - ["{{ PARMgfs }}/post/{{ component }}_gfs.csv", "{{ DATA }}/{{ component }}.csv"] - ["{{ FIXgfs }}/mom6/post/{{ model_grid }}/tripole.{{ model_grid }}.Bu.to.Ct.bilinear.nc", "{{ DATA }}/"] - ["{{ FIXgfs }}/mom6/post/{{ model_grid }}/tripole.{{ model_grid }}.Cu.to.Ct.bilinear.nc", "{{ DATA }}/"] - ["{{ FIXgfs }}/mom6/post/{{ model_grid }}/tripole.{{ model_grid }}.Cv.to.Ct.bilinear.nc", "{{ DATA }}/"] diff --git a/sorc/gfs_utils.fd b/sorc/gfs_utils.fd index 2bf341a3d76..ff41e3ce4fb 160000 --- a/sorc/gfs_utils.fd +++ b/sorc/gfs_utils.fd @@ -1 +1 @@ -Subproject commit 2bf341a3d760d36b86e43187227d34189107e8a5 +Subproject commit ff41e3ce4fbf211e65e9366a0ea68ffdbe651022 diff --git a/sorc/link_workflow.sh b/sorc/link_workflow.sh index 0efcb75c99b..aab6108a0b2 100755 --- a/sorc/link_workflow.sh +++ b/sorc/link_workflow.sh @@ -154,7 +154,7 @@ for dir in gfs gefs sfs do ${LINK_OR_COPY} "${HOMEgfs}/sorc/upp.fd/parm/${dir}" . done -for file in ice.csv ocean.csv ocnicepost.nml.jinja2; do +for file in ice_gfs.csv ice_gefs.csv ocean_gfs.csv ocean_gefs.csv ocnicepost.nml.jinja2; do ${LINK_OR_COPY} "${HOMEgfs}/sorc/gfs_utils.fd/parm/ocnicepost/${file}" . done diff --git a/ush/forecast_postdet.sh b/ush/forecast_postdet.sh index 4244d5d69c9..8349d6dbaf5 100755 --- a/ush/forecast_postdet.sh +++ b/ush/forecast_postdet.sh @@ -719,10 +719,14 @@ CICE_postdet() { source_file="iceh_inst.${vdatestr}.nc" dest_file="${RUN}.ice.t${cyc}z.inst.f${fhr3}.nc" ;; - gfs|enkfgfs|gefs|sfs) + gfs|enkfgfs|sfs) source_file="iceh_$(printf "%0.2d" "${FHOUT_ICE}")h.${vdatestr}.nc" dest_file="${RUN}.ice.t${cyc}z.${interval}hr_avg.f${fhr3}.nc" ;; + gefs) + source_file="iceh.${vdatestr}.nc" + dest_file="${RUN}.ice.t${cyc}z.${interval}hr_avg.f${fhr3}.nc" + ;; *) echo "FATAL ERROR: Unsupported RUN ${RUN} in CICE postdet" exit 10 diff --git a/ush/parsing_namelists_CICE.sh b/ush/parsing_namelists_CICE.sh index 16c89ee80d5..b2b0a97aca3 100755 --- a/ush/parsing_namelists_CICE.sh +++ b/ush/parsing_namelists_CICE.sh @@ -70,7 +70,12 @@ local CICE_RESTART_FORMAT="pnetcdf2" local CICE_DUMPFREQ="y" # "h","d","m" or "y" for restarts at intervals of "hours", "days", "months" or "years" local CICE_DUMPFREQ_N=10000 # Set this to a really large value, as cice, mom6 and cmeps restart interval is controlled by ufs.configure local CICE_DIAGFREQ=$(( 86400 / DT_CICE )) # frequency of diagnostic output in timesteps, recommended for 1x per day -local CICE_HISTFREQ_N="0, 0, ${FHOUT_ICE}, 0, 1" +if [[ "${RUN}" == "gefs" ]]; then + local CICE_DIAGFREQ1=$((( FHOUT_ICE * 3600 )/ DT_CICE )) # Number of timesteps within FHOUT_ICE + local CICE_HISTFREQ_N="0, 0, 0, ${CICE_DIAGFREQ1}, 1" +else + local CICE_HISTFREQ_N="0, 0, ${FHOUT_ICE}, 0, 1" +fi local CICE_hist_suffix="'x','x','x','x','x'" if [[ "${RUN}" =~ "gdas" ]]; then local CICE_HIST_AVG=".false., .false., .false., .false., .false." # DA needs instantaneous