roms-tools 3.2.0__py3-none-any.whl → 3.3.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (202) hide show
  1. roms_tools/__init__.py +1 -1
  2. roms_tools/plot.py +38 -30
  3. roms_tools/setup/boundary_forcing.py +2 -2
  4. roms_tools/setup/grid.py +13 -5
  5. roms_tools/setup/initial_conditions.py +5 -5
  6. roms_tools/setup/{datasets.py → lat_lon_datasets.py} +23 -804
  7. roms_tools/setup/nesting.py +262 -90
  8. roms_tools/setup/river_datasets.py +527 -0
  9. roms_tools/setup/river_forcing.py +2 -2
  10. roms_tools/setup/surface_forcing.py +4 -4
  11. roms_tools/setup/tides.py +1 -1
  12. roms_tools/setup/topography.py +4 -6
  13. roms_tools/setup/utils.py +263 -2
  14. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_east/c/0/0/0 +0 -0
  15. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_north/c/0/0/0 +0 -0
  16. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_west/c/0/0/0 +0 -0
  17. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_east/c/0/0/0 +0 -0
  18. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_north/c/0/0/0 +0 -0
  19. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_west/c/0/0/0 +0 -0
  20. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_east/c/0/0/0 +0 -0
  21. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_north/c/0/0/0 +0 -0
  22. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_west/c/0/0/0 +0 -0
  23. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_east/c/0/0/0 +0 -0
  24. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_north/c/0/0/0 +0 -0
  25. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_west/c/0/0/0 +0 -0
  26. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_east/c/0/0/0 +0 -0
  27. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_north/c/0/0/0 +0 -0
  28. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_west/c/0/0/0 +0 -0
  29. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_east/c/0/0/0 +0 -0
  30. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_north/c/0/0/0 +0 -0
  31. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_west/c/0/0/0 +0 -0
  32. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_east/c/0/0/0 +0 -0
  33. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_north/c/0/0/0 +0 -0
  34. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_west/c/0/0/0 +0 -0
  35. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_east/c/0/0/0 +0 -0
  36. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_north/c/0/0/0 +0 -0
  37. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_west/c/0/0/0 +0 -0
  38. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_east/c/0/0/0 +0 -0
  39. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_north/c/0/0/0 +0 -0
  40. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_west/c/0/0/0 +0 -0
  41. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_east/c/0/0/0 +0 -0
  42. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_north/c/0/0/0 +0 -0
  43. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_west/c/0/0/0 +0 -0
  44. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_east/c/0/0/0 +0 -0
  45. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_north/c/0/0/0 +0 -0
  46. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_west/c/0/0/0 +0 -0
  47. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_east/c/0/0/0 +0 -0
  48. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_north/c/0/0/0 +0 -0
  49. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_west/c/0/0/0 +0 -0
  50. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_east/c/0/0/0 +0 -0
  51. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_north/c/0/0/0 +0 -0
  52. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_west/c/0/0/0 +0 -0
  53. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_east/c/0/0/0 +0 -0
  54. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_north/c/0/0/0 +0 -0
  55. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_west/c/0/0/0 +0 -0
  56. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_east/c/0/0/0 +0 -0
  57. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_north/c/0/0/0 +0 -0
  58. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_west/c/0/0/0 +0 -0
  59. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_east/c/0/0/0 +0 -0
  60. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_north/c/0/0/0 +0 -0
  61. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_west/c/0/0/0 +0 -0
  62. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/SiO3_east/c/0/0/0 +0 -0
  63. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/SiO3_north/c/0/0/0 +0 -0
  64. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/SiO3_west/c/0/0/0 +0 -0
  65. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatC_east/c/0/0/0 +0 -0
  66. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatC_north/c/0/0/0 +0 -0
  67. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatC_west/c/0/0/0 +0 -0
  68. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_east/c/0/0/0 +0 -0
  69. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_north/c/0/0/0 +0 -0
  70. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_west/c/0/0/0 +0 -0
  71. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_east/c/0/0/0 +0 -0
  72. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_north/c/0/0/0 +0 -0
  73. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_west/c/0/0/0 +0 -0
  74. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_east/c/0/0/0 +0 -0
  75. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_north/c/0/0/0 +0 -0
  76. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_west/c/0/0/0 +0 -0
  77. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_east/c/0/0/0 +0 -0
  78. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_north/c/0/0/0 +0 -0
  79. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_west/c/0/0/0 +0 -0
  80. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_east/c/0/0/0 +0 -0
  81. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_north/c/0/0/0 +0 -0
  82. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_west/c/0/0/0 +0 -0
  83. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_east/c/0/0/0 +0 -0
  84. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_north/c/0/0/0 +0 -0
  85. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_west/c/0/0/0 +0 -0
  86. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_east/c/0/0/0 +0 -0
  87. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_north/c/0/0/0 +0 -0
  88. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_west/c/0/0/0 +0 -0
  89. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_east/c/0/0/0 +0 -0
  90. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_north/c/0/0/0 +0 -0
  91. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_west/c/0/0/0 +0 -0
  92. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_east/c/0/0/0 +0 -0
  93. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_north/c/0/0/0 +0 -0
  94. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_west/c/0/0/0 +0 -0
  95. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_east/c/0/0/0 +0 -0
  96. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_north/c/0/0/0 +0 -0
  97. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_west/c/0/0/0 +0 -0
  98. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_east/c/0/0/0 +0 -0
  99. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_north/c/0/0/0 +0 -0
  100. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_west/c/0/0/0 +0 -0
  101. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_east/c/0/0/0 +0 -0
  102. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_north/c/0/0/0 +0 -0
  103. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_west/c/0/0/0 +0 -0
  104. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_east/c/0/0/0 +0 -0
  105. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_north/c/0/0/0 +0 -0
  106. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_west/c/0/0/0 +0 -0
  107. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zarr.json +406 -406
  108. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_east/c/0/0/0 +0 -0
  109. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_north/c/0/0/0 +0 -0
  110. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_west/c/0/0/0 +0 -0
  111. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_east/c/0/0/0 +0 -0
  112. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_north/c/0/0/0 +0 -0
  113. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_south/c/0/0/0 +0 -0
  114. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_west/c/0/0/0 +0 -0
  115. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_east/c/0/0/0 +0 -0
  116. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_north/c/0/0/0 +0 -0
  117. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_south/c/0/0/0 +0 -0
  118. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_west/c/0/0/0 +0 -0
  119. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_east/c/0/0/0 +0 -0
  120. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_north/c/0/0/0 +0 -0
  121. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_south/c/0/0/0 +0 -0
  122. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_west/c/0/0/0 +0 -0
  123. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_east/c/0/0 +0 -0
  124. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_north/c/0/0 +0 -0
  125. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_south/c/0/0 +0 -0
  126. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_west/c/0/0 +0 -0
  127. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_east/c/0/0/0 +0 -0
  128. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_north/c/0/0/0 +0 -0
  129. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_south/c/0/0/0 +0 -0
  130. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_west/c/0/0/0 +0 -0
  131. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_east/c/0/0 +0 -0
  132. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_north/c/0/0 +0 -0
  133. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_south/c/0/0 +0 -0
  134. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_west/c/0/0 +0 -0
  135. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/zarr.json +182 -182
  136. roms_tools/tests/test_setup/test_data/grid.zarr/h/c/0/0 +0 -0
  137. roms_tools/tests/test_setup/test_data/grid.zarr/zarr.json +191 -191
  138. roms_tools/tests/test_setup/test_data/grid_that_straddles_dateline.zarr/h/c/0/0 +0 -0
  139. roms_tools/tests/test_setup/test_data/grid_that_straddles_dateline.zarr/zarr.json +210 -210
  140. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/ALK/c/0/0/0/0 +0 -0
  141. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/ALK_ALT_CO2/c/0/0/0/0 +0 -0
  142. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DIC/c/0/0/0/0 +0 -0
  143. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DIC_ALT_CO2/c/0/0/0/0 +0 -0
  144. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOC/c/0/0/0/0 +0 -0
  145. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOCr/c/0/0/0/0 +0 -0
  146. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DON/c/0/0/0/0 +0 -0
  147. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DONr/c/0/0/0/0 +0 -0
  148. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOP/c/0/0/0/0 +0 -0
  149. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOPr/c/0/0/0/0 +0 -0
  150. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/Fe/c/0/0/0/0 +0 -0
  151. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/Lig/c/0/0/0/0 +0 -0
  152. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/NH4/c/0/0/0/0 +0 -0
  153. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/NO3/c/0/0/0/0 +0 -0
  154. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/O2/c/0/0/0/0 +0 -0
  155. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/PO4/c/0/0/0/0 +0 -0
  156. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/SiO3/c/0/0/0/0 +0 -0
  157. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatC/c/0/0/0/0 +0 -0
  158. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatChl/c/0/0/0/0 +0 -0
  159. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatFe/c/0/0/0/0 +0 -0
  160. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatP/c/0/0/0/0 +0 -0
  161. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatSi/c/0/0/0/0 +0 -0
  162. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazC/c/0/0/0/0 +0 -0
  163. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazChl/c/0/0/0/0 +0 -0
  164. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazFe/c/0/0/0/0 +0 -0
  165. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazP/c/0/0/0/0 +0 -0
  166. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/salt/c/0/0/0/0 +0 -0
  167. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spC/c/0/0/0/0 +0 -0
  168. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spCaCO3/c/0/0/0/0 +0 -0
  169. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spChl/c/0/0/0/0 +0 -0
  170. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spFe/c/0/0/0/0 +0 -0
  171. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spP/c/0/0/0/0 +0 -0
  172. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/temp/c/0/0/0/0 +0 -0
  173. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/u/c/0/0/0/0 +0 -0
  174. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/ubar/c/0/0/0 +0 -0
  175. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/v/c/0/0/0/0 +0 -0
  176. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/vbar/c/0/0/0 +0 -0
  177. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/zarr.json +182 -182
  178. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/zooC/c/0/0/0/0 +0 -0
  179. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/salt/c/0/0/0/0 +0 -0
  180. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/temp/c/0/0/0/0 +0 -0
  181. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/u/c/0/0/0/0 +0 -0
  182. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/ubar/c/0/0/0 +0 -0
  183. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/v/c/0/0/0/0 +0 -0
  184. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/vbar/c/0/0/0 +0 -0
  185. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/zarr.json +187 -187
  186. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/u_Im/c/0/0/0 +0 -0
  187. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/u_Re/c/0/0/0 +0 -0
  188. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/v_Im/c/0/0/0 +0 -0
  189. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/v_Re/c/0/0/0 +0 -0
  190. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/zarr.json +66 -66
  191. roms_tools/tests/test_setup/test_grid.py +14 -0
  192. roms_tools/tests/test_setup/test_initial_conditions.py +1 -1
  193. roms_tools/tests/test_setup/{test_datasets.py → test_lat_lon_datasets.py} +22 -61
  194. roms_tools/tests/test_setup/test_nesting.py +119 -31
  195. roms_tools/tests/test_setup/test_river_datasets.py +48 -0
  196. roms_tools/tests/test_setup/test_surface_forcing.py +1 -1
  197. roms_tools/tests/test_setup/test_utils.py +1 -1
  198. {roms_tools-3.2.0.dist-info → roms_tools-3.3.0.dist-info}/METADATA +1 -1
  199. {roms_tools-3.2.0.dist-info → roms_tools-3.3.0.dist-info}/RECORD +202 -200
  200. {roms_tools-3.2.0.dist-info → roms_tools-3.3.0.dist-info}/WHEEL +0 -0
  201. {roms_tools-3.2.0.dist-info → roms_tools-3.3.0.dist-info}/licenses/LICENSE +0 -0
  202. {roms_tools-3.2.0.dist-info → roms_tools-3.3.0.dist-info}/top_level.txt +0 -0
roms_tools/setup/utils.py CHANGED
@@ -4,10 +4,10 @@ import time
4
4
  import typing
5
5
  from collections.abc import Sequence
6
6
  from dataclasses import asdict, fields, is_dataclass
7
- from datetime import datetime
7
+ from datetime import datetime, timedelta
8
8
  from enum import StrEnum
9
9
  from pathlib import Path
10
- from typing import Any, Literal
10
+ from typing import Any, Literal, TypeAlias
11
11
 
12
12
  import cftime
13
13
  import numba as nb
@@ -31,6 +31,8 @@ yaml.SafeDumper.add_multi_representer(
31
31
  HEADER_SZ = 96
32
32
  HEADER_CHAR = "="
33
33
 
34
+ RawDataSource: TypeAlias = dict[str, str | Path | list[str | Path] | bool]
35
+
34
36
 
35
37
  def log_the_separator() -> None:
36
38
  """Log a separator line using HEADER_CHAR repeated HEADER_SZ times."""
@@ -1963,3 +1965,262 @@ def validate_names(
1963
1965
  names = names[:max_to_plot]
1964
1966
 
1965
1967
  return names
1968
+
1969
+
1970
+ def check_dataset(
1971
+ ds: xr.Dataset,
1972
+ dim_names: dict[str, str],
1973
+ var_names: dict[str, str],
1974
+ opt_var_names: dict[str, str] | None = None,
1975
+ ) -> None:
1976
+ """Check if the dataset contains the specified variables and dimensions.
1977
+
1978
+ Parameters
1979
+ ----------
1980
+ ds : xr.Dataset
1981
+ The xarray Dataset to check.
1982
+ dim_names: Dict[str, str], optional
1983
+ Dictionary specifying the names of dimensions in the dataset.
1984
+ var_names: Dict[str, str]
1985
+ Dictionary of variable names that are required in the dataset.
1986
+ opt_var_names : Optional[Dict[str, str]], optional
1987
+ Dictionary of optional variable names.
1988
+ These variables are not strictly required, and the function will not raise an error if they are missing.
1989
+ Default is None, meaning no optional variables are considered.
1990
+
1991
+
1992
+ Raises
1993
+ ------
1994
+ ValueError
1995
+ If the dataset does not contain the specified variables or dimensions.
1996
+ """
1997
+ missing_dims = [dim for dim in dim_names.values() if dim not in ds.dims]
1998
+ if missing_dims:
1999
+ raise ValueError(
2000
+ f"Dataset does not contain all required dimensions. The following dimensions are missing: {missing_dims}"
2001
+ )
2002
+
2003
+ missing_vars = [var for var in var_names.values() if var not in ds.data_vars]
2004
+ if missing_vars:
2005
+ raise ValueError(
2006
+ f"Dataset does not contain all required variables. The following variables are missing: {missing_vars}"
2007
+ )
2008
+
2009
+ if opt_var_names:
2010
+ missing_optional_vars = [
2011
+ var for var in opt_var_names.values() if var not in ds.data_vars
2012
+ ]
2013
+ if missing_optional_vars:
2014
+ logging.warning(
2015
+ f"Optional variables missing (but not critical): {missing_optional_vars}"
2016
+ )
2017
+
2018
+
2019
+ def select_relevant_times(
2020
+ ds: xr.Dataset,
2021
+ time_dim: str,
2022
+ start_time: datetime,
2023
+ end_time: datetime | None = None,
2024
+ climatology: bool = False,
2025
+ allow_flex_time: bool = False,
2026
+ ) -> xr.Dataset:
2027
+ """
2028
+ Select a subset of the dataset based on time constraints.
2029
+
2030
+ This function supports two main use cases:
2031
+
2032
+ 1. **Time range selection (start_time + end_time provided):**
2033
+ - Returns all records strictly between `start_time` and `end_time`.
2034
+ - Ensures at least one record at or before `start_time` and one record at or
2035
+ after `end_time` are included, even if they fall outside the strict range.
2036
+
2037
+ 2. **Initial condition selection (start_time provided, end_time=None):**
2038
+ - Delegates to `_select_initial_time`, which reduces the dataset to exactly one
2039
+ time entry.
2040
+ - If `allow_flex_time=True`, a +24-hour buffer around `start_time` is allowed,
2041
+ and the closest timestamp is chosen.
2042
+ - If `allow_flex_time=False`, requires an exact timestamp match.
2043
+
2044
+ Additional behavior:
2045
+ - If `climatology=True`, the dataset must contain exactly 12 time steps. If valid,
2046
+ the climatology dataset is returned without further filtering.
2047
+ - If the dataset uses `cftime` datetime objects, these are converted to
2048
+ `np.datetime64` before filtering.
2049
+
2050
+ Parameters
2051
+ ----------
2052
+ ds : xr.Dataset
2053
+ The dataset to filter. Must contain a valid time dimension.
2054
+ time_dim : str
2055
+ Name of the time dimension in `ds`.
2056
+ start_time : datetime
2057
+ Start time for filtering.
2058
+ end_time : datetime or None
2059
+ End time for filtering. If `None`, the function assumes an initial condition
2060
+ use case and selects exactly one timestamp.
2061
+ climatology : bool, optional
2062
+ If True, requires exactly 12 time steps and bypasses normal filtering.
2063
+ Defaults to False.
2064
+ allow_flex_time : bool, optional
2065
+ Whether to allow a +24h search window after `start_time` when `end_time`
2066
+ is None. If False (default), requires an exact match.
2067
+
2068
+ Returns
2069
+ -------
2070
+ xr.Dataset
2071
+ A filtered dataset containing only the selected time entries.
2072
+
2073
+ Raises
2074
+ ------
2075
+ ValueError
2076
+ - If `climatology=True` but the dataset does not contain exactly 12 time steps.
2077
+ - If `climatology=False` and the dataset contains integer time values.
2078
+ - If no valid records are found within the requested range or window.
2079
+
2080
+ Warns
2081
+ -----
2082
+ UserWarning
2083
+ - If no records exist at or before `start_time` or at or after `end_time`.
2084
+ - If the specified time dimension does not exist in the dataset.
2085
+
2086
+ Notes
2087
+ -----
2088
+ - For initial conditions (end_time=None), see `_select_initial_time` for details
2089
+ on strict vs. flexible selection behavior.
2090
+ - Logs warnings instead of failing hard when boundary records are missing, and
2091
+ defaults to using the earliest or latest available time in such cases.
2092
+ """
2093
+ if time_dim not in ds.variables:
2094
+ logging.warning(
2095
+ f"Dataset does not contain time dimension '{time_dim}'. "
2096
+ "Please check variable naming or dataset structure."
2097
+ )
2098
+ return ds
2099
+
2100
+ time_type = get_time_type(ds[time_dim])
2101
+
2102
+ if climatology:
2103
+ if len(ds[time_dim]) != 12:
2104
+ raise ValueError(
2105
+ f"The dataset contains {len(ds[time_dim])} time steps, but the climatology flag is set to True, which requires exactly 12 time steps."
2106
+ )
2107
+ else:
2108
+ if time_type == "int":
2109
+ raise ValueError(
2110
+ "The dataset contains integer time values, which are only supported when the climatology flag is set to True. However, your climatology flag is set to False."
2111
+ )
2112
+ if time_type == "cftime":
2113
+ ds = ds.assign_coords({time_dim: convert_cftime_to_datetime(ds[time_dim])})
2114
+
2115
+ if not end_time:
2116
+ # Assume we are looking for exactly one time record for initial conditions
2117
+ return _select_initial_time(
2118
+ ds, time_dim, start_time, climatology, allow_flex_time
2119
+ )
2120
+
2121
+ if climatology:
2122
+ return ds
2123
+
2124
+ # Identify records before or at start_time
2125
+ before_start = ds[time_dim] <= np.datetime64(start_time)
2126
+ if before_start.any():
2127
+ closest_before_start = ds[time_dim].where(before_start, drop=True)[-1]
2128
+ else:
2129
+ logging.warning(f"No records found at or before the start_time: {start_time}.")
2130
+ closest_before_start = ds[time_dim][0]
2131
+
2132
+ # Identify records after or at end_time
2133
+ after_end = ds[time_dim] >= np.datetime64(end_time)
2134
+ if after_end.any():
2135
+ closest_after_end = ds[time_dim].where(after_end, drop=True).min()
2136
+ else:
2137
+ logging.warning(f"No records found at or after the end_time: {end_time}.")
2138
+ closest_after_end = ds[time_dim].max()
2139
+
2140
+ # Select records within the time range and add the closest before/after
2141
+ within_range = (ds[time_dim] > np.datetime64(start_time)) & (
2142
+ ds[time_dim] < np.datetime64(end_time)
2143
+ )
2144
+ selected_times = ds[time_dim].where(
2145
+ within_range
2146
+ | (ds[time_dim] == closest_before_start)
2147
+ | (ds[time_dim] == closest_after_end),
2148
+ drop=True,
2149
+ )
2150
+ ds = ds.sel({time_dim: selected_times})
2151
+
2152
+ return ds
2153
+
2154
+
2155
+ def _select_initial_time(
2156
+ ds: xr.Dataset,
2157
+ time_dim: str,
2158
+ ini_time: datetime,
2159
+ climatology: bool,
2160
+ allow_flex_time: bool = False,
2161
+ ) -> xr.Dataset:
2162
+ """Select exactly one initial time from dataset.
2163
+
2164
+ Parameters
2165
+ ----------
2166
+ ds : xr.Dataset
2167
+ The input dataset with a time dimension.
2168
+ time_dim : str
2169
+ Name of the time dimension.
2170
+ ini_time : datetime
2171
+ The desired initial time.
2172
+ allow_flex_time : bool
2173
+ - If True: allow a +24h window and pick the closest available timestamp.
2174
+ - If False (default): require an exact match, otherwise raise ValueError.
2175
+
2176
+ Returns
2177
+ -------
2178
+ xr.Dataset
2179
+ Dataset reduced to exactly one timestamp.
2180
+
2181
+ Raises
2182
+ ------
2183
+ ValueError
2184
+ If no matching time is found (when `allow_flex_time=False`), or no entries are
2185
+ available within the +24h window (when `allow_flex_time=True`).
2186
+ """
2187
+ if climatology:
2188
+ # Convert from timedelta64[ns] to fractional days
2189
+ ds["time"] = ds["time"] / np.timedelta64(1, "D")
2190
+ # Interpolate from climatology for initial conditions
2191
+ return interpolate_from_climatology(ds, time_dim, ini_time)
2192
+
2193
+ if allow_flex_time:
2194
+ # Look in time range [ini_time, ini_time + 24h)
2195
+ end_time = ini_time + timedelta(days=1)
2196
+ times = (np.datetime64(ini_time) <= ds[time_dim]) & (
2197
+ ds[time_dim] < np.datetime64(end_time)
2198
+ )
2199
+
2200
+ if np.all(~times):
2201
+ raise ValueError(
2202
+ f"No time entries found between {ini_time} and {end_time}."
2203
+ )
2204
+
2205
+ ds = ds.where(times, drop=True)
2206
+ if ds.sizes[time_dim] > 1:
2207
+ # Pick the time closest to start_time
2208
+ ds = ds.isel({time_dim: 0})
2209
+
2210
+ logging.warning(
2211
+ f"Selected time entry closest to the specified start_time in +24 hour range: {ds[time_dim].values}"
2212
+ )
2213
+
2214
+ else:
2215
+ # Strict match required
2216
+ if not (ds[time_dim].values == np.datetime64(ini_time)).any():
2217
+ raise ValueError(
2218
+ f"No exact match found for initial time {ini_time}. Consider setting allow_flex_time to True."
2219
+ )
2220
+
2221
+ ds = ds.sel({time_dim: np.datetime64(ini_time)})
2222
+
2223
+ if time_dim not in ds.dims:
2224
+ ds = ds.expand_dims(time_dim)
2225
+
2226
+ return ds