From e77f2c93484b1af70c0ae3ebb2431c014ccd4f5b Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Tue, 18 Feb 2025 12:59:42 -0600 Subject: [PATCH 1/9] changing running order --- workflow/applications/gfs_cycled.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/workflow/applications/gfs_cycled.py b/workflow/applications/gfs_cycled.py index 57176341757..a3ec86f849b 100644 --- a/workflow/applications/gfs_cycled.py +++ b/workflow/applications/gfs_cycled.py @@ -23,11 +23,11 @@ def __init__(self, conf: Configuration): elif ens_run in ['gfs', 'gdas']: self.ens_runs = [ens_run] - # Now construct self.runs the desired XML order (gdas, enkfgdas, gfs, enkfgfs) - self.runs = ["gdas"] # We always have a 'gdas' run - self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 - self.runs.append("gfs") if base['INTERVAL_GFS'] > 0 else 0 + # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) + self.runs = ["gfs"] # We always have a 'gdas' run self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and "gfs" in self.runs else 0 + self.runs.append("gdas") if base['INTERVAL_GFS'] > 0 else 0 + self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 def _get_run_options(self, conf: Configuration) -> Dict[str, Any]: From 40266605d8455f2ccd3592278e12cdbf2201070d Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Tue, 18 Feb 2025 15:51:00 -0600 Subject: [PATCH 2/9] modified gfs_cycled.py --- workflow/applications/gfs_cycled.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/workflow/applications/gfs_cycled.py b/workflow/applications/gfs_cycled.py index a3ec86f849b..27f64035479 100644 --- a/workflow/applications/gfs_cycled.py +++ b/workflow/applications/gfs_cycled.py @@ -24,9 +24,10 @@ def __init__(self, conf: Configuration): self.ens_runs = [ens_run] # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) - self.runs = ["gfs"] # We always have a 'gdas' run + self.runs = [] + self.runs.append ["gfs"] if base['INTERVAL_GFS'] > 0 else 0 self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and "gfs" in self.runs else 0 - self.runs.append("gdas") if base['INTERVAL_GFS'] > 0 else 0 + self.runs.append("gdas") # We always have a 'gdas' run self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 def _get_run_options(self, conf: Configuration) -> Dict[str, Any]: From b56d0c89e9ef81a8e6a1d9fec0a48625678a6583 Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Tue, 18 Feb 2025 18:06:48 -0600 Subject: [PATCH 3/9] modified gfs_cycled.py --- workflow/applications/gfs_cycled.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/workflow/applications/gfs_cycled.py b/workflow/applications/gfs_cycled.py index 27f64035479..790650816fc 100644 --- a/workflow/applications/gfs_cycled.py +++ b/workflow/applications/gfs_cycled.py @@ -25,7 +25,7 @@ def __init__(self, conf: Configuration): # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) self.runs = [] - self.runs.append ["gfs"] if base['INTERVAL_GFS'] > 0 else 0 + self.runs.append ("gfs") if base['INTERVAL_GFS'] > 0 else 0 self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and "gfs" in self.runs else 0 self.runs.append("gdas") # We always have a 'gdas' run self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 From 67c04390c483104e05c440b84218b6a3bf99692f Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Wed, 19 Feb 2025 15:27:04 -0600 Subject: [PATCH 4/9] fixed pynorms errors --- workflow/applications/gfs_cycled.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/workflow/applications/gfs_cycled.py b/workflow/applications/gfs_cycled.py index 790650816fc..d97f19da8fd 100644 --- a/workflow/applications/gfs_cycled.py +++ b/workflow/applications/gfs_cycled.py @@ -25,7 +25,7 @@ def __init__(self, conf: Configuration): # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) self.runs = [] - self.runs.append ("gfs") if base['INTERVAL_GFS'] > 0 else 0 + self.runs.append("gfs") if base['INTERVAL_GFS'] > 0 else 0 self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and "gfs" in self.runs else 0 self.runs.append("gdas") # We always have a 'gdas' run self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 From 5c2530c76a78f3bd2ffce9b6aabdf6ce5a5a1801 Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Wed, 19 Feb 2025 23:51:28 -0600 Subject: [PATCH 5/9] changing double quote into single quote --- workflow/applications/gfs_cycled.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/workflow/applications/gfs_cycled.py b/workflow/applications/gfs_cycled.py index d97f19da8fd..d47578bf18a 100644 --- a/workflow/applications/gfs_cycled.py +++ b/workflow/applications/gfs_cycled.py @@ -25,9 +25,9 @@ def __init__(self, conf: Configuration): # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) self.runs = [] - self.runs.append("gfs") if base['INTERVAL_GFS'] > 0 else 0 - self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and "gfs" in self.runs else 0 - self.runs.append("gdas") # We always have a 'gdas' run + self.runs.append('gfs') if base['INTERVAL_GFS'] > 0 else 0 + self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and 'gfs' in self.runs else 0 + self.runs.append('gdas') # We always have a 'gdas' run self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 def _get_run_options(self, conf: Configuration) -> Dict[str, Any]: From 365e6c5f4f6c2c65e004101a2b85560b7d7dade7 Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Thu, 20 Feb 2025 23:10:41 -0600 Subject: [PATCH 6/9] remove trailing space --- workflow/applications/gfs_cycled.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/workflow/applications/gfs_cycled.py b/workflow/applications/gfs_cycled.py index d47578bf18a..0dd2ce44a46 100644 --- a/workflow/applications/gfs_cycled.py +++ b/workflow/applications/gfs_cycled.py @@ -25,7 +25,7 @@ def __init__(self, conf: Configuration): # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) self.runs = [] - self.runs.append('gfs') if base['INTERVAL_GFS'] > 0 else 0 + self.runs.append('gfs') if base['INTERVAL_GFS'] > 0 else 0 self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and 'gfs' in self.runs else 0 self.runs.append('gdas') # We always have a 'gdas' run self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 From 542469e8e012aaf4dfc75dc1f21b086b7d7fec2f Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Tue, 25 Feb 2025 12:27:25 -0600 Subject: [PATCH 7/9] update gdas hush --- sorc/gdas.cd | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sorc/gdas.cd b/sorc/gdas.cd index 417ed5e686a..7b90ef70f1b 160000 --- a/sorc/gdas.cd +++ b/sorc/gdas.cd @@ -1 +1 @@ -Subproject commit 417ed5e686ae73af7be65350fda20037c5934242 +Subproject commit 7b90ef70f1b55cffc14b0c9d9acd0ebd5c5d7201 From 1c1793a1aa6d31dce5af5a1917afc846f43f3d93 Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Tue, 25 Feb 2025 12:31:35 -0600 Subject: [PATCH 8/9] update ufs_model hash --- sorc/ufs_model.fd | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/sorc/ufs_model.fd b/sorc/ufs_model.fd index 76471dc6b7b..ee3d52d3620 160000 --- a/sorc/ufs_model.fd +++ b/sorc/ufs_model.fd @@ -1 +1 @@ -Subproject commit 76471dc6b7bfc3342416d1a3402f360724f7c0fa +Subproject commit ee3d52d3620565dbf7bc4f47bd039fe6423fa5c1 From bd8a92f2af961644f5909984587df26f8bd586ca Mon Sep 17 00:00:00 2001 From: Mingshi Chen Date: Tue, 25 Feb 2025 12:33:41 -0600 Subject: [PATCH 9/9] remove gfs_cycled.py --- gfs_cycled.py | 332 -------------------------------------------------- 1 file changed, 332 deletions(-) delete mode 100644 gfs_cycled.py diff --git a/gfs_cycled.py b/gfs_cycled.py deleted file mode 100644 index d47578bf18a..00000000000 --- a/gfs_cycled.py +++ /dev/null @@ -1,332 +0,0 @@ -from applications.applications import AppConfig -from typing import Dict, Any -from wxflow import Configuration - - -class GFSCycledAppConfig(AppConfig): - ''' - Class to define GFS cycled configurations - ''' - - def __init__(self, conf: Configuration): - super().__init__(conf) - # Re-read config.base without RUN specified to get the basic settings for - # cycled cases to be able to determine valid runs - base = conf.parse_config('config.base') - - self.ens_runs = [] - - if base.get('DOHYBVAR', False): - ens_run = base.get('EUPD_CYC', 'gdas').lower() - if ens_run in ['both']: - self.ens_runs = ['gfs', 'gdas'] - elif ens_run in ['gfs', 'gdas']: - self.ens_runs = [ens_run] - - # Now construct self.runs the desired XML order (gfs, enkfgfs, gdas, enkfgdas) - self.runs = [] - self.runs.append('gfs') if base['INTERVAL_GFS'] > 0 else 0 - self.runs.append('enkfgfs') if 'gfs' in self.ens_runs and 'gfs' in self.runs else 0 - self.runs.append('gdas') # We always have a 'gdas' run - self.runs.append('enkfgdas') if 'gdas' in self.ens_runs else 0 - - def _get_run_options(self, conf: Configuration) -> Dict[str, Any]: - - run_options = super()._get_run_options(conf) - - for run in self.runs: - base = conf.parse_config('config.base', RUN=run) - - run_options[run]['do_hybvar'] = base.get('DOHYBVAR', False) - run_options[run]['do_hybvar_ocn'] = base.get('DOHYBVAR_OCN', False) - run_options[run]['nens'] = base.get('NMEM_ENS', 0) - if run_options[run]['do_hybvar']: - run_options[run]['lobsdiag_forenkf'] = base.get('lobsdiag_forenkf', False) - - run_options[run]['do_fit2obs'] = base.get('DO_FIT2OBS', True) - run_options[run]['do_jediatmvar'] = base.get('DO_JEDIATMVAR', False) - run_options[run]['do_jediatmens'] = base.get('DO_JEDIATMENS', False) - run_options[run]['do_jediocnvar'] = base.get('DO_JEDIOCNVAR', False) - run_options[run]['do_jedisnowda'] = base.get('DO_JEDISNOWDA', False) - run_options[run]['do_mergensst'] = base.get('DO_MERGENSST', False) - - return run_options - - def _get_app_configs(self, run): - """ - Returns the config files that are involved in the cycled app - """ - options = self.run_options[run] - - configs = ['prep'] - - if options['do_jediatmvar']: - configs += ['prepatmiodaobs', 'atmanlinit', 'atmanlvar', 'atmanlfv3inc', 'atmanlfinal'] - else: - configs += ['anal', 'analdiag'] - - if options['do_jediocnvar']: - configs += ['prepoceanobs', 'marineanlinit', 'marinebmat', 'marineanlvar'] - if options['do_hybvar']: - configs += ['marineanlletkf', 'ocnanalecen'] - configs += ['marineanlchkpt', 'marineanlfinal'] - - if options['do_ocean'] or options['do_ice']: - configs += ['oceanice_products'] - - configs += ['stage_ic', 'sfcanl', 'analcalc', 'fcst', 'upp', 'atmos_products', 'arch_vrfy', 'cleanup'] - - if options['do_archtar']: - configs += ['arch_tars'] - - if options['do_hybvar']: - if options['do_jediatmens']: - configs += ['atmensanlinit', 'atmensanlobs', 'atmensanlsol', - 'atmensanlletkf', 'atmensanlfv3inc', 'atmensanlfinal'] - else: - configs += ['eobs', 'eomg', 'ediag', 'eupd'] - - configs += ['ecen', 'esfc', 'efcs', 'echgres', 'epos', 'earc_vrfy'] - - if options['do_archtar']: - configs += ['earc_tars'] - - if options['do_fit2obs']: - configs += ['fit2obs'] - - if options['do_verfozn']: - configs += ['verfozn'] - - if options['do_verfrad']: - configs += ['verfrad'] - - if options['do_vminmon']: - configs += ['vminmon'] - - if options['do_tracker']: - configs += ['tracker'] - - if options['do_genesis']: - configs += ['genesis'] - - if options['do_genesis_fsu']: - configs += ['genesis_fsu'] - - if options['do_metp']: - configs += ['metp'] - - if options['do_gempak']: - configs += ['gempak'] - if options['do_goes']: - configs += ['npoess'] - - if options['do_bufrsnd']: - configs += ['postsnd'] - - if options['do_awips']: - configs += ['awips', 'fbwind'] - - if options['do_wave']: - configs += ['waveinit', 'wavepostsbs', 'wavepostpnt'] - if options['do_wave_bnd']: - configs += ['wavepostbndpnt', 'wavepostbndpntbll'] - if options['do_gempak']: - configs += ['wavegempak'] - if options['do_awips']: - configs += ['waveawipsbulls', 'waveawipsgridded'] - - if options['do_aero_anl']: - configs += ['aeroanlgenb', 'aeroanlinit', 'aeroanlvar', 'aeroanlfinal'] - if options['do_prep_obs_aero']: - configs += ['prepobsaero'] - - if options['do_jedisnowda']: - configs += ['snowanl'] - if options['do_hybvar']: - configs += ['esnowanl'] - - if options['do_mos']: - configs += ['mos_stn_prep', 'mos_grd_prep', 'mos_ext_stn_prep', 'mos_ext_grd_prep', - 'mos_stn_fcst', 'mos_grd_fcst', 'mos_ext_stn_fcst', 'mos_ext_grd_fcst', - 'mos_stn_prdgen', 'mos_grd_prdgen', 'mos_ext_stn_prdgen', 'mos_ext_grd_prdgen', - 'mos_wx_prdgen', 'mos_wx_ext_prdgen'] - - return configs - - @staticmethod - def _update_base(base_in): - - return base_in - - def get_task_names(self): - """ - Get the task names for each valid run in this cycled configuration. - NOTE: The order of the task names matters in the XML. - This is the place where that order is set. - """ - - # Start with a dictionary of empty task lists for each valid run - task_names = {run: [] for run in self.runs} - - for run in self.runs: - options = self.run_options[run] - - # Common gdas and gfs tasks before fcst - if run in ['gdas', 'gfs']: - task_names[run] += ['prep'] - if options['do_jediatmvar']: - task_names[run] += ['prepatmiodaobs', 'atmanlinit', 'atmanlvar', 'atmanlfv3inc', 'atmanlfinal'] - else: - task_names[run] += ['anal'] - - if options['do_jediocnvar']: - task_names[run] += ['prepoceanobs', 'marineanlinit', 'marinebmat', 'marineanlvar'] - if options['do_hybvar']: - task_names[run] += ['marineanlletkf', 'ocnanalecen'] - task_names[run] += ['marineanlchkpt', 'marineanlfinal'] - - task_names[run] += ['sfcanl', 'analcalc'] - - if options['do_jedisnowda']: - task_names[run] += ['snowanl'] - - wave_prep_tasks = ['waveinit'] - wave_bndpnt_tasks = ['wavepostbndpnt', 'wavepostbndpntbll'] - wave_post_tasks = ['wavepostsbs', 'wavepostpnt'] - - # gdas- and gfs-specific analysis tasks - if run == 'gdas': - if not options['do_jediatmvar']: - task_names[run] += ['analdiag'] - - if options['do_wave']: - task_names[run] += wave_prep_tasks - - if options['do_aero_anl']: - task_names[run] += ['aeroanlgenb'] - - else: - if options['do_wave']: - task_names[run] += wave_prep_tasks - - if options['do_aero_anl']: - task_names[run] += ['aeroanlinit', 'aeroanlvar', 'aeroanlfinal'] - - if options['do_prep_obs_aero']: - task_names[run] += ['prepobsaero'] - - # Staging is gdas-specific - if run == 'gdas': - task_names[run] += ['stage_ic'] - - task_names[run] += ['atmanlupp', 'atmanlprod', 'fcst'] - - # gfs-specific products - if run == 'gfs': - if options['do_ocean']: - task_names[run] += ['ocean_prod'] - - if options['do_ice']: - task_names[run] += ['ice_prod'] - - if options['do_upp']: - task_names[run] += ['atmupp'] - task_names[run] += ['atmos_prod'] - - # GOES post-processing (gfs only) - if run == 'gfs': - if options['do_goes']: - task_names[run] += ['goesupp'] - - # Only fit to obs and verify ozone and radiance during gdas cycles - if run == "gdas": - if options['do_fit2obs']: - task_names[run] += ['fit2obs'] - if options['do_verfozn']: - task_names[run] += ['verfozn'] - if options['do_verfrad']: - task_names[run] += ['verfrad'] - - if options['do_vminmon']: - task_names[run] += ['vminmon'] - - # gfs-only verification/tracking - if run == 'gfs': - if options['do_tracker']: - task_names[run] += ['tracker'] - - if options['do_genesis']: - task_names[run] += ['genesis'] - - if options['do_genesis_fsu']: - task_names[run] += ['genesis_fsu'] - - if options['do_metp']: - task_names[run] += ['metp'] - - if options['do_wave']: - if options['do_wave_bnd']: - task_names[run] += wave_bndpnt_tasks - task_names[run] += wave_post_tasks - # wave gempak and awips jobs are gfs-specific - if run == 'gfs': - if options['do_gempak']: - task_names[run] += ['wavegempak'] - if options['do_awips']: - task_names[run] += ['waveawipsbulls', 'waveawipsgridded'] - - # gdas- and gfs-specific downstream products - if run == 'gdas': - if options['do_gempak']: - task_names[run] += ['gempak', 'gempakmetancdc'] - else: - if options['do_bufrsnd']: - task_names[run] += ['postsnd'] - - if options['do_gempak']: - task_names[run] += ['gempak', 'gempakmeta', 'gempakncdcupapgif'] - if options['do_goes']: - task_names[run] += ['npoess_pgrb2_0p5deg', 'gempakpgrb2spec'] - - if options['do_awips']: - task_names[run] += ['awips_20km_1p0deg', 'fbwind'] - - if options['do_mos']: - task_names[run] += ['mos_stn_prep', 'mos_grd_prep', 'mos_ext_stn_prep', 'mos_ext_grd_prep', - 'mos_stn_fcst', 'mos_grd_fcst', 'mos_ext_stn_fcst', 'mos_ext_grd_fcst', - 'mos_stn_prdgen', 'mos_grd_prdgen', 'mos_ext_stn_prdgen', - 'mos_ext_grd_prdgen', 'mos_wx_prdgen', 'mos_wx_ext_prdgen'] - - # Last items - task_names[run] += ['arch_vrfy'] - if options['do_archtar']: - task_names[run] += ['arch_tars'] - task_names[run] += ['cleanup'] - - # Ensemble tasks - elif 'enkf' in run: - - if options['do_jediatmens']: - task_names[run] += ['atmensanlinit', 'atmensanlfv3inc', 'atmensanlfinal'] - # Only run echgres for the gdas cycle - task_names[run] += ['echgres'] if 'gdas' in run else 0 - if options['lobsdiag_forenkf']: - task_names[run] += ['atmensanlobs', 'atmensanlsol'] - else: - task_names[run] += ['atmensanlletkf'] - - else: - task_names[run] += ['eobs', 'eupd'] - task_names[run].append('echgres') if 'gdas' in run else 0 - task_names[run] += ['ediag'] if options['lobsdiag_forenkf'] else ['eomg'] - - task_names[run].append('esnowanl') if options['do_jedisnowda'] else 0 - task_names[run].append('efcs') if 'gdas' in run else 0 - task_names[run].append('epos') if 'gdas' in run else 0 - - task_names[run] += ['stage_ic', 'ecen', 'esfc'] - if options['do_archtar']: - task_names[run] += ['earc_tars'] - task_names[run] += ['earc_vrfy', 'cleanup'] - - return task_names