-
Notifications
You must be signed in to change notification settings - Fork 12
Remove global access in fv3core and physics tests #60
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
…ics namelist defaults to the _config
… into stencil externals rather than constants
…variables externals
…nly constants into microphysics
…o shared-constants
…o shared-constants
| backend=self.backend, | ||
| ) | ||
|
|
||
| def python_grid(self): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All fv3core import in physics test have been removed except for Grid here. Should we make a new classmethod in GridData that makes the class with serialized data? Or should we retain Grid? We also need a new location for either of them.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Grid's main responsibility is to convert serialized data, which may or may not include some number of halos and may or may not be staggered, into standardized storages that all have 3 halos and a compute origin at (3, 3). For this reason, Grid should continue to be used in the test code, and should probably live with the translate infrastructure.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This makes sense, I had thought that we wanted to get rid of Grid all together. If the plan is to keep it alive within the translate infrastructure, I'll go ahead and reshuffle some things.
| def namelist_to_flatish_dict(nml_input): | ||
| nml = dict(nml_input) | ||
| for name, value in nml.items(): | ||
| if isinstance(value, f90nml.Namelist): | ||
| nml[name] = namelist_to_flatish_dict(value) | ||
| flatter_namelist = {} | ||
| for key, value in nml.items(): | ||
| if isinstance(value, dict): | ||
| for subkey, subvalue in value.items(): | ||
| if subkey in flatter_namelist: | ||
| raise ValueError( | ||
| "Cannot flatten this namelist, duplicate keys: " + subkey | ||
| ) | ||
| flatter_namelist[subkey] = subvalue | ||
| else: | ||
| flatter_namelist[key] = value | ||
| return flatter_namelist |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
namelist_to_flatish_dict should probably go to util since it's used identically in the dycore. This can also live in pace.util.namelist.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Moved to pace.util.namelist
| backend=self.backend, | ||
| ) | ||
|
|
||
| def python_grid(self): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Grid's main responsibility is to convert serialized data, which may or may not include some number of halos and may or may not be staggered, into standardized storages that all have 3 halos and a compute origin at (3, 3). For this reason, Grid should continue to be used in the test code, and should probably live with the translate infrastructure.
| def process_grid_savepoint(serializer, grid_savepoint, rank, *, backend: str): | ||
| grid = make_grid(grid_savepoint, serializer, rank, backend=backend) | ||
| fv3core._config.set_grid(grid) | ||
| def Grid(serializer, grid_savepoint, rank, layout, *, backend: str): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please use a lowercase name, since this isn't returning a class.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed to upper_grid
| grid_rank0 = Grid( | ||
| serializer, grid_savepoint, 0, physics_config.layout, backend=backend | ||
| ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This variable is unused, you should be able to delete it.
|
I’m a little worried that if we duplicate the base translate classes and make small changes, these classes are very complex and may be hard to merge later. Would it be possible to put these in |
rheacangeo
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Epic. As discussed, there are some known circular dependencies that come about from this. But we agree, this PR is large enough, and if everything works, we should merge this and make a new story to address those smaller cycles.
|
|
||
| fv3core.set_backend(args.backend) | ||
| fv3core.set_rebuild(False) | ||
| fv3core.set_validate_args(False) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is validate_args False when this script runs now?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
great catch, changed to False
| from datetime import datetime | ||
| from typing import Any, Dict, List, Tuple | ||
|
|
||
| import f90nml |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
please before merging make sure you run run_standalone (either login to daint, or do it through the performance test jenkins plan on your branch) so we know it still works.
| # references it is updated or removed | ||
| grid = spec.make_grid_from_namelist(namelist, rank) | ||
|
|
||
| grid = spec.make_grid_from_namelist(dycore_config, rank, args.backend) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if this is only referenced by reading serialized input, this could be moved to inside the read_serialized_initial_state method
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
stencil_factory is needed for the baroclinic test case too, so can't be inside read_serialized_initial_state only
fv3core/tests/main/test_config.py
Outdated
| # def test_set_backend(): | ||
| # start_backend = fv3core.get_backend() | ||
| # new_backend = "new_backend" | ||
| # assert new_backend != start_backend | ||
| # fv3core.set_backend(new_backend) | ||
| # assert fv3core.get_backend() == new_backend |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this can be deleted now?
fv3core/tests/main/test_grid.py
Outdated
| domain_compute: Index3D, | ||
| ): | ||
| grid = fv3core.utils.grid.GridIndexing( | ||
| grid = pace.stencils.testing.grid.GridIndexing( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
is GridIndexing in pace.dsl or pace.stencils.testing.grid?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is pace.dsl, updated here and elsewhere
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Very nice seeing the test code make direct use of namelist and stencil_factory instead of relying on Grid for everything.
You can leave refactoring pace.stencils.testing.grid for a follow-on PR, but please make a Jira task. It's not great having every stencil file import from testing, since the idea of putting things there is to indicate the stencil code shouldn't be importing from it.
Very few comments for how much you've updated. Great job!
| import time | ||
|
|
||
| import click | ||
| import f90nml |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't know how to evaluate changes to example scripts like this that aren't in CI. We should consider CI-testing all our examples. For now I'll trust you've run this and it works.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, we should add a plan for this. This script was actually broken for a while and we didn't notice.
|
|
||
|
|
||
| def set_up_namelist(data_directory: str) -> None: | ||
| def set_up_namelist(data_directory: str) -> DynamicalCoreConfig: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you update this function's name and docstring now that it's returning a config and not a namelist? You could name it dycore_config_from_namelist.
| turbulent_kinetic_energy.metadata.gt4py_backend = backend | ||
| cloud_fraction.metadata.gt4py_backend = backend | ||
| u_tendency.metadata.gt4py_backend = backend | ||
| v_tendency.metadata.gt4py_backend = backend |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can pass the gt4py_backend argument when calling Quantity.from_data_array above, instead of overriding it here.
fv3core/fv3core/_config.py
Outdated
| n_sponge: int = NamelistDefaults.n_sponge | ||
|
|
||
| @classmethod | ||
| def from_f90nml(cls, namelist: f90nml.Namelist): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Return value type hints for constructors are particularly important/helpful, because they provide type hinting in the place where they're used. For example, this will make mypy check for any typos in attribute accesses on DynamicalCoreConfig in our untested runfiles.
| n_sponge: int = NamelistDefaults.n_sponge | |
| @classmethod | |
| def from_f90nml(cls, namelist: f90nml.Namelist): | |
| n_sponge: int = NamelistDefaults.n_sponge | |
| @classmethod | |
| def from_f90nml(cls, namelist: f90nml.Namelist) -> "DynamicalCoreConfig": |
| with unittest.mock.patch("pace.util.global_config.get_backend", new=error_func): | ||
| with unittest.mock.patch( | ||
| "fv3core.utils.global_config.is_gpu_backend", new=error_func | ||
| "pace.util.global_config.is_gpu_backend", new=error_func |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Make sure there's a Jira task to delete pace.util.global_config, if we're no longer using it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's being used in two spots in the main tests. Once we get rid of those, we can delete global_config
fv3core/tests/savepoint/conftest.py
Outdated
| def process_grid_savepoint(serializer, grid_savepoint, rank, *, backend: str): | ||
| grid = make_grid(grid_savepoint, serializer, rank, backend=backend) | ||
| fv3core._config.set_grid(grid) | ||
| def upper_grid(serializer, grid_savepoint, rank, layout, *, backend: str): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What is an "upper" grid? Is there a reason for this function when you can directly call make_grid?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It was originally going to be a pytest fixture, but you're right we can just call make_grid directly. Changing this.
| @@ -1,2 +0,0 @@ | |||
| from . import translate_physics | |||
| from .translate_physics import TranslatePhysicsFortranData2Py | |||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why were these removed?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since we no longer need to carry separate translate class infrastructure, we don't need this in physics anymore. If we decide to add TranslatePhysics, it will go here.
| def upper_grid(serializer, grid_savepoint, rank, layout, *, backend: str): | ||
| grid = make_grid(grid_savepoint, serializer, rank, layout, backend=backend) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you call make_grid directly?
I'm a little confused by this network of functions (grid_data, grid_indexing, physics_config, etc.). Instead of calling grid_data(grid), should you directly use grid.grid_data in whatever function is calling these?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
They were supposed to be pytest fixtures, but it's easier to make them instead. I forgot to clean up, deleting all these now.
| stencil_config = pace.dsl.stencil.StencilConfig( | ||
| backend=args.backend, | ||
| rebuild=False, | ||
| validate_args=True, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
change to False please
rheacangeo
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wahoo! I think the Grid object served us well, but good to finalize the shift away from it by untangling the objects we were grabbing from it as an interim step. Lots going on here and this will make many things possible!
mcgibbon
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Make sure there are the 2 Jira tasks for removing global_config and for moving utilities out of pace.stencils.testing.grid, otherwise looks good to me!
* pace-physics -> pySHiELD * Removed pySHiELD locally * Added pySHiELD as submodule * Updating branch to current versions of NDSL and pyFV3 * Updating pyFV3 and pySHiELD for changes to their setup.py files * Updated constraints.txt to match new pySHiELD submodule * Removed local references in constraints.txt * Update pySHiELD * lint * Remove unused mypy * Bad driver `setup,py` * Regenerate `constraints.txt` * Remove local constraints * Lint --------- Co-authored-by: Florian Deconinck <[email protected]>
This PR is a prerequisite to moving namelist to driver. The goal for this PR is to 1) remove global config access, 2) share translate class infrastructure, 3) remove dependencies to
fv3corein physics tests.Changes:
grid,global_config, andcornersfromfv3core.utilstopace.util.testingandpace.util: global_config is removed from most places and can be deleted soon-ishtranslateandparallel_translatetopace.util.testing: they are shared in dycore and physicsNamelistDefaultstopace.util.namelistPhysicsConfigclass: when namelist is moved to the driver, we should add a method to return physics confignamelistandstencil_factorydown to each savepoint classstencil_facotryfrom Grid class