1010
1111CONFIG = None
1212
13+
1314class HHRebalancingModuleConfig (BaseModel ):
1415 """
1516 Configuration for Household Rebalancing module
1617 """
18+
1719 control_table : str
1820 control_col : str
1921 geoid_col : str
2022
23+
2124class EmploymentModuleConfig (BaseModel ):
2225 simultaneous_calibration_config : Optional [SimultaneousCalibrationConfig ] = None
2326 enter_model_calibration_procedure : Optional [CalibrationConfig ] = None
@@ -29,24 +32,31 @@ def check_calibration_config_exclusivity(self):
2932 enter_cal = self .enter_model_calibration_procedure is not None
3033 exit_cal = self .exit_model_calibration_procedure is not None
3134 if sim_cal and (enter_cal or exit_cal ):
32- raise ValueError (f"Simultaneous calibration cannot be used at the same time as " + \
33- f"individual model calibration. Simultaneous selected: { sim_cal } , " + \
34- f"EnterModel selected: { enter_cal } , ExitModel selected: { exit_cal } " )
35+ raise ValueError (
36+ f"Simultaneous calibration cannot be used at the same time as "
37+ + f"individual model calibration. Simultaneous selected: { sim_cal } , "
38+ + f"EnterModel selected: { enter_cal } , ExitModel selected: { exit_cal } "
39+ )
3540 return self
3641
42+
3743class HHReorgModuleConfig (BaseModel ):
3844 simultaneous_calibration_config : Optional [SimultaneousCalibrationConfig ] = None
3945 geoid_col : Optional [str ] = None
4046
47+
4148class MortalityModuleConfig (BaseModel ):
4249 calibration_procedure : Optional [CalibrationConfig ] = None
4350
51+
4452class BirthModuleConfig (BaseModel ):
4553 calibration_procedure : Optional [CalibrationConfig ] = None
4654
55+
4756class KidsMovingModuleConfig (BaseModel ):
4857 geoid_col : str
4958
59+
5060class AgingModuleConfig (BaseModel ):
5161 #: Age at which a person qualifies as senior
5262 senior_age : int = 65
@@ -56,6 +66,7 @@ class DEMOSConfig(BaseModel):
5666 """
5767 Global configuration for DEMOS. Individual fields in this class control the configuration of each module.
5868 """
69+
5970 random_seed : int
6071
6172 #: Year represented in synthetic population input
@@ -82,32 +93,44 @@ class DEMOSConfig(BaseModel):
8293
8394 # Module-specific config
8495 aging_module_config : AgingModuleConfig = Field (default_factory = AgingModuleConfig )
85- employment_module_config : EmploymentModuleConfig = Field (default_factory = EmploymentModuleConfig )
86- hh_reorg_module_config : HHReorgModuleConfig = Field (default_factory = HHReorgModuleConfig )
87- mortality_module_config : MortalityModuleConfig = Field (default_factory = MortalityModuleConfig )
96+ employment_module_config : EmploymentModuleConfig = Field (
97+ default_factory = EmploymentModuleConfig
98+ )
99+ hh_reorg_module_config : HHReorgModuleConfig = Field (
100+ default_factory = HHReorgModuleConfig
101+ )
102+ mortality_module_config : MortalityModuleConfig = Field (
103+ default_factory = MortalityModuleConfig
104+ )
88105 birth_module_config : BirthModuleConfig = Field (default_factory = BirthModuleConfig )
89- hh_rebalancing_module_config : HHRebalancingModuleConfig = Field (default_factory = HHRebalancingModuleConfig )
90- kids_moving_module_config : KidsMovingModuleConfig = Field (default_factory = KidsMovingModuleConfig )
91-
106+ hh_rebalancing_module_config : HHRebalancingModuleConfig = Field (
107+ default_factory = HHRebalancingModuleConfig
108+ )
109+ kids_moving_module_config : KidsMovingModuleConfig = Field (
110+ default_factory = KidsMovingModuleConfig
111+ )
112+
92113 def model_post_init (self , __context ) -> None :
93114 if self .output_fname is None :
94- self .output_fname = f"{ self .output_dir } /demos_output_{ self .forecast_year } .h5"
115+ self .output_fname = (
116+ f"{ self .output_dir } /demos_output_{ self .forecast_year } .h5"
117+ )
95118 os .makedirs (self .output_dir , exist_ok = True )
96119 logger .info (f"Output file set to default: { self .output_fname } " )
97-
120+
98121 if self .output_tables is None :
99122 self .output_tables = []
100-
123+
101124 if self .initialize_empty_tables is None :
102125 self .initialize_empty_tables = []
103-
126+
104127 # Load all table datasources
105128 for t in self .tables :
106129 t .load_into_orca ()
107130
108131 for n in self .initialize_empty_tables :
109132 orca .add_table (n , pd .DataFrame ())
110-
133+
111134 if self .modules is None :
112135 self .modules = [
113136 "aging" ,
@@ -118,21 +141,27 @@ def model_post_init(self, __context) -> None:
118141 "birth_model" ,
119142 "education_model" ,
120143 "household_rebalancing" ,
121- "update_income"
144+ "update_income" ,
122145 ]
123-
124146
125- @model_validator (mode = ' after' )
147+ @model_validator (mode = " after" )
126148 def require_persons_and_households (self ):
127149 loaded_table_names = [t .table_name for t in self .tables ]
128- if "persons" not in loaded_table_names or "households" not in loaded_table_names :
129- raise ValueError (f"Both 'persons' and 'households' tables are required. Tables defined: { loaded_table_names } " )
150+ if (
151+ "persons" not in loaded_table_names
152+ or "households" not in loaded_table_names
153+ ):
154+ raise ValueError (
155+ f"Both 'persons' and 'households' tables are required. Tables defined: { loaded_table_names } "
156+ )
130157 return self
131158
159+
132160def load_config_file (dir : str ) -> DEMOSConfig :
133161 global CONFIG
134162 CONFIG = DEMOSConfig (** toml .load (dir ))
135163
164+
136165def get_config ():
137166 global CONFIG
138167 if CONFIG is None :
0 commit comments