Skip to content

#474: LFRic-Nudging: Part-A: Introduce ability to read nudging datafiles #474

Merged
Matthew Hambley (MatthewHambley) merged 31 commits into
MetOffice:mainfrom
mcdalvi:vn3.1.1_read_nudging_data
Jun 23, 2026
Merged

#474: LFRic-Nudging: Part-A: Introduce ability to read nudging datafiles #474
Matthew Hambley (MatthewHambley) merged 31 commits into
MetOffice:mainfrom
mcdalvi:vn3.1.1_read_nudging_data

Conversation

@mcdalvi

@mcdalvi Mohit Dalvi (mcdalvi) commented Apr 30, 2026

Copy link
Copy Markdown
Contributor

PR Summary

Sci/Tech Reviewer: Thomas Bendall (@tommbendall)
Code Reviewer: Matthew Hambley (@MatthewHambley)

This PR introduces the ability to read in datafiles that will be used for Nudging the Momentum models (Ref: Nudging NWP to AI/ML models - possibly targeting PS49).
The handling of Nudging data is modelled on existing lateral boundary condition handling in LFRic since they are both required to be interpolated from high time resolution file data on every model timestep.
Nudging changes summary:

  • Ability to read in nudging data for temperature, U-wind, V-wind and Log surface pressure (required for vertical remapping to model levels).

  • New [namelist:nudging], which will be active when theta or wind are 'forced by nudging' (in namelist:external_forcing). A corresponding upgrade_macro to add the namelist and I/O related items.

  • Introduce routine create_nudging_fields to create the nudging input fields as '2-D with user-specified (nudge_data) levels'. Corresponding grid_def_nudging.xml and grid_def_nudging_coarse.xml added to lfric_atm/metadata/.

  • Introduce ability to read in nudging data on native ('dynamics') or a coarser grid, with rationalising of routines that create the model fields ('make_spec', 'create_model_data') to accept both aerosol and nudging coarse mesh definitions.

  • Note that the above requires a LFRIC_CORE change to allow defining 3-D coarse grid fields as ''multigrid_ll'' x ndata.

  • Define a nudging_time_axis which will be populated based on the actual number of time records in the specified nudging file.

  • Introduce two new rose-stem tests lfric_atm_nwp_gal9_nudging-C48 that reads nudging files on the model grid and lfric_atm_nwp_gal9_nudging_coarse-C48 that reads in data at a lower resolution (C12) grid. This currently uses nudging data created from ERA5 source, but aim is to expand this to AIFS and other models.

  • At this stage the reference fields are only made available to LFRic and do not modify temperature/ winds.

  • linked #369: Allow coarse-grid fields with ndata levels: vn3.1 read coarse 2d lfric_core#369

Code Quality Checklist

  • I have performed a self-review of my own code
  • My code follows the project's style guidelines
  • Comments have been included that aid understanding and enhance the readability of the code
  • My changes generate no new warnings
  • All automated checks in the CI pipeline have completed successfully

Testing

  • I have tested this change locally, using the LFRic Apps rose-stem suite
  • If any tests fail (rose-stem or CI) the reason is understood and acceptable (e.g. kgo changes)
  • I have added tests to cover new functionality as appropriate (e.g. system tests, unit tests, etc.)
  • Any new tests have been assigned an appropriate amount of compute resource and have been allocated to an appropriate testing group (i.e. the developer tests are for jobs which use a small amount of compute resource and complete in a matter of minutes)

Test Branch: test6_vn3p1_nudging_data

trac.log

Test Suite Results - lfric_apps - test6_vn3p1_nudging_data/run1

Suite Information

Item Value
Suite Name test6_vn3p1_nudging_data/run1
Suite User mohit.dalvi
Workflow Start 2026-06-22T12:02:00
Groups Run developer', 'lfric_atm_azspice_extra
Dependency Reference Main Like
casim MetOffice/casim@2026.03.2 True
jules MetOffice/jules@1ea67b4 True
lfric_apps mcdalvi/lfric_apps@test6_vn3p1_nudging_data False
lfric_core mcdalvi/lfric_core@vn3.1_read_coarse_2d True
moci MetOffice/moci@2026.03.2 True
SimSys_Scripts MetOffice/SimSys_Scripts@3e2998b True
socrates MetOffice/socrates@2026.03.2 True
socrates-spectral MetOffice/socrates-spectral@2026.03.2 True
ukca MetOffice/ukca@1cdb9c2 True

Task Information

✅ succeeded tasks - 1266

Task State
housekeep_azspice waiting
  • I have reviewed my changes for potential security issues
  • Sensitive data is properly handled (if applicable)
  • Authentication and authorisation are properly implemented (if applicable)

Performance Impact

  • Performance of the code has been considered and, if applicable, suitable performance measurements have been conducted

AI Assistance and Attribution

  • Some of the content of this change has been produced with the assistance of Generative AI tool name (e.g., Met Office Github Copilot Enterprise, Github Copilot Personal, ChatGPT GPT-4, etc) and I have followed the Simulation Systems AI policy (including attribution labels)

VsCode - code completion/ snippets.

Documentation

  • Where appropriate I have updated documentation related to this change and confirmed that it builds correctly

PSyclone Approval

  • If you have edited any PSyclone-related code (e.g. PSyKAl-lite, Kernel interface, optimisation scripts, LFRic data structure code) then please contact the TCD Team

Sci/Tech Review

  • I understand this area of code and the changes being added
  • The proposed changes correspond to the pull request description
  • Documentation is sufficient (do documentation papers need updating)
  • Sufficient testing has been completed

(Please alert the code reviewer via a tag when you have approved the SR)

Code Review

  • All dependencies have been resolved
  • Related Issues have been properly linked and addressed
  • CLA compliance has been confirmed
  • Code quality standards have been met
  • Tests are adequate and have passed
  • Documentation is complete and accurate
  • Security considerations have been addressed
  • Performance impact is acceptable

@mcdalvi Mohit Dalvi (mcdalvi) requested review from Matthew Hambley (MatthewHambley) and removed request for a team April 30, 2026 16:20
@mcdalvi Mohit Dalvi (mcdalvi) changed the title LFRic-Nudging: Part-A: Introduce ability to read nudging datafiles : vn3.1.1 read nudging data #74: LFRic-Nudging: Part-A: Introduce ability to read nudging datafiles : vn3.1.1 read nudging data Apr 30, 2026
@mcdalvi Mohit Dalvi (mcdalvi) changed the title #74: LFRic-Nudging: Part-A: Introduce ability to read nudging datafiles : vn3.1.1 read nudging data #474: LFRic-Nudging: Part-A: Introduce ability to read nudging datafiles : vn3.1.1 read nudging data Apr 30, 2026
@DanStoneMO

Copy link
Copy Markdown
Contributor

Is there any chance main could be merged into this branch? I'm currently unable to test the changes with JEDI due to the conflicts

@mcdalvi Mohit Dalvi (mcdalvi) marked this pull request as draft May 1, 2026 09:45
@mcdalvi

Copy link
Copy Markdown
Contributor Author

Apologies, I was not aware creating a PR triggers all this activity ! I have changed it to draft till all my testing is complete.

@mcdalvi Mohit Dalvi (mcdalvi) added Linked Core This PR is linked to a MetOffice/lfric_core PR KGO This PR contains changes to KGO macro This PR contains a metadata upgrade macro labels May 1, 2026
…at are defined in source code; implement upgrade macro
…2bit as done for other azspice runs; remove unused additions to ancil reading code

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

One remaining issue, then we can go to trunk.

Comment on lines +22 to +25
use external_forcing_config_mod, only : theta_forcing_nudging, &
theta_forcing, &
wind_forcing_nudging, &
wind_forcing

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While it's not possible to pass ModelDB to the callback due to a circular dependency, it is possible to pass any configuration you need. Either as primitive values, if there are few of them, or as a namelist type if you need lots of configuration.

This is not an ideal solution as it bloats the callback's argument list but it at least makes the problem explicit. The problem still exists when fetching from global scope, it is just obfuscated. It is more important that we move away from global scope configuration and I think we would rather see our problems than not.

As of yesterday the location of the callback has changed so you will have to merge your branch up to head of trunk before making any changes.

Ideally this would be done by creating a new branch from your development branch and merging that up to head of trunk. This leaves a branch based on a release tag, which the GC group can use, should they care to, and one which can actually merge onto trunk. Unfortunately it doesn't seem to be possible to change the source branch of a pull request.

Instead please add a comment to this pull request with the hash of the head-of-branch before you merge up. This can be used to retrieve the version against the release tag.

@mcdalvi

Copy link
Copy Markdown
Contributor Author

Latest working commit for dev branch before merging main: 7818d2d

@github-actions github-actions Bot removed the cla-modified The CLA has been modified as part of this PR - added by GA label Jun 17, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change now looks to be ready for trunk.

@mcdalvi

Copy link
Copy Markdown
Contributor Author

This change now looks to be ready for trunk.

Thanks Matthew Hambley (@MatthewHambley) . Just adding a reminder here about the test input files to be placed in BIGDATA

@cjohnson-pi

Copy link
Copy Markdown
Contributor

#502 has now been committed and I expect this to cause a conflict with this PR. In #502 I split create_model_data into create_model_data and create_physics_model_data. Ideally the changes on this ticket should go into create_physics_model_data and then there should not be any change in the linear_model.

@mcdalvi

Copy link
Copy Markdown
Contributor Author

#502 has now been committed and I expect this to cause a conflict with this PR. In #502 I split create_model_data into create_model_data and create_physics_model_data. Ideally the changes on this ticket should go into create_physics_model_data and then there should not be any change in the linear_model.

I will merge with main to resolve conflicts, but I believe the external_forcing with nudging is independant of physics. In fact we have had to move some existing code sections out of #ifdef UM_PHYSICS.
Thomas Bendall (@tommbendall) ?

@tommbendall

Copy link
Copy Markdown
Contributor

#502 has now been committed and I expect this to cause a conflict with this PR. In #502 I split create_model_data into create_model_data and create_physics_model_data. Ideally the changes on this ticket should go into create_physics_model_data and then there should not be any change in the linear_model.

I will merge with main to resolve conflicts, but I believe the external_forcing with nudging is independant of physics. In fact we have had to move some existing code sections out of #ifdef UM_PHYSICS. Thomas Bendall (Thomas Bendall (@tommbendall)) ?

cjohnson-pi thanks for flagging the conflict! Good question Mohit Dalvi (@mcdalvi) -- I think it could be argued either way. I'd probably lean towards us adding the new fields to the new create_physics_model_data routine? From a dynamical core point-of-view I see external_forcing as physics schemes that are owned by gungho.

@mcdalvi

Copy link
Copy Markdown
Contributor Author

#502 has now been committed and I expect this to cause a conflict with this PR. In #502 I split create_model_data into create_model_data and create_physics_model_data. Ideally the changes on this ticket should go into create_physics_model_data and then there should not be any change in the linear_model.

I will merge with main to resolve conflicts, but I believe the external_forcing with nudging is independant of physics. In fact we have had to move some existing code sections out of #ifdef UM_PHYSICS. Thomas Bendall (Thomas Bendall (Thomas Bendall (@tommbendall))) ?

cjohnson-pi thanks for flagging the conflict! Good question Mohit Dalvi (Mohit Dalvi (@mcdalvi)) -- I think it could be argued either way. I'd probably lean towards us adding the new fields to the new create_physics_model_data routine? From a dynamical core point-of-view I see external_forcing as physics schemes that are owned by gungho.

Thanks for the clarification Tom, will merge in the changes accordingly.

@mcdalvi

Copy link
Copy Markdown
Contributor Author

Unfortunately, some changes in response to #502 have failed in other developer tests over the weekend. I will try to fix these today.

@mcdalvi

Copy link
Copy Markdown
Contributor Author

#502 has now been committed and I expect this to cause a conflict with this PR. In #502 I split create_model_data into create_model_data and create_physics_model_data. Ideally the changes on this ticket should go into create_physics_model_data and then there should not be any change in the linear_model.

I will merge with main to resolve conflicts, but I believe the external_forcing with nudging is independant of physics. In fact we have had to move some existing code sections out of #ifdef UM_PHYSICS. Thomas Bendall (Thomas Bendall (Thomas Bendall (Thomas Bendall (@tommbendall)))) ?

cjohnson-pi thanks for flagging the conflict! Good question Mohit Dalvi (Mohit Dalvi (Mohit Dalvi (@mcdalvi))) -- I think it could be argued either way. I'd probably lean towards us adding the new fields to the new create_physics_model_data routine? From a dynamical core point-of-view I see external_forcing as physics schemes that are owned by gungho.

Thanks for the clarification Tom, will merge in the changes accordingly.

cjohnson-pi Thomas Bendall (@tommbendall) : The call to create_nudging_fields requires the field_mapper argument. This is initialised in 'create_model_data' so has to be passed out from there and in to the new 'create_physics_model_data' routine. This is working for gungho and lfric_atm but also means updating the call to 'create_model_data' in other driver routines (jedi_lfric, linear, t1_test, shallow_water, ..) Is there any other way of acccessing field_mapper, or an equivalent ?

…reate_physics_model_data* routine; needs field_mapper to be made available from the original routine
@tommbendall

Copy link
Copy Markdown
Contributor

#502 has now been committed and I expect this to cause a conflict with this PR. In #502 I split create_model_data into create_model_data and create_physics_model_data. Ideally the changes on this ticket should go into create_physics_model_data and then there should not be any change in the linear_model.

I will merge with main to resolve conflicts, but I believe the external_forcing with nudging is independant of physics. In fact we have had to move some existing code sections out of #ifdef UM_PHYSICS. Thomas Bendall (Thomas Bendall (Thomas Bendall (Thomas Bendall (Thomas Bendall (@tommbendall))))) ?

cjohnson-pi thanks for flagging the conflict! Good question Mohit Dalvi (Mohit Dalvi (Mohit Dalvi (Mohit Dalvi (@mcdalvi)))) -- I think it could be argued either way. I'd probably lean towards us adding the new fields to the new create_physics_model_data routine? From a dynamical core point-of-view I see external_forcing as physics schemes that are owned by gungho.

Thanks for the clarification Tom, will merge in the changes accordingly.

cjohnson-pi Thomas Bendall (Thomas Bendall (@tommbendall)) : The call to create_nudging_fields requires the field_mapper argument. This is initialised in 'create_model_data' so has to be passed out from there and in to the new 'create_physics_model_data' routine. This is working for gungho and lfric_atm but also means updating the call to 'create_model_data' in other driver routines (jedi_lfric, linear, t1_test, shallow_water, ..) Is there any other way of acccessing field_mapper, or an equivalent ?

Ah apologies, I think I hadn't followed that this would be a problem. In that case I think we should call create_nudging_fields from create_model_data (and not create_physics_model_data). And now I've looked more carefully, that matches what happens with other physics prognostics and IAU fields so I think makes more sense. Sorry for the confusion!

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Still approved.

@MatthewHambley Matthew Hambley (MatthewHambley) merged commit c646410 into MetOffice:main Jun 23, 2026
7 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

KGO This PR contains changes to KGO Linked Core This PR is linked to a MetOffice/lfric_core PR macro This PR contains a metadata upgrade macro

Projects

None yet

Development

Successfully merging this pull request may close these issues.

10 participants