roms-tools 3.2.0__py3-none-any.whl → 3.4.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 (318) hide show
  1. roms_tools/__init__.py +1 -1
  2. roms_tools/analysis/cdr_ensemble.py +10 -13
  3. roms_tools/analysis/roms_output.py +5 -304
  4. roms_tools/{download.py → datasets/download.py} +1 -0
  5. roms_tools/{setup/datasets.py → datasets/lat_lon_datasets.py} +85 -854
  6. roms_tools/datasets/river_datasets.py +532 -0
  7. roms_tools/datasets/roms_dataset.py +767 -0
  8. roms_tools/datasets/utils.py +475 -0
  9. roms_tools/{setup/fill.py → fill.py} +110 -13
  10. roms_tools/plot.py +42 -34
  11. roms_tools/setup/boundary_forcing.py +52 -44
  12. roms_tools/setup/cdr_release.py +2 -4
  13. roms_tools/setup/grid.py +42 -17
  14. roms_tools/setup/initial_conditions.py +23 -23
  15. roms_tools/setup/nesting.py +270 -94
  16. roms_tools/setup/river_forcing.py +5 -5
  17. roms_tools/setup/surface_forcing.py +17 -12
  18. roms_tools/setup/tides.py +1 -1
  19. roms_tools/setup/topography.py +13 -7
  20. roms_tools/setup/utils.py +103 -294
  21. roms_tools/tests/test_analysis/test_cdr_ensemble.py +4 -6
  22. roms_tools/tests/test_analysis/test_roms_output.py +1 -220
  23. roms_tools/tests/{test_setup/test_datasets.py → test_datasets/test_lat_lon_datasets.py} +25 -64
  24. roms_tools/tests/test_datasets/test_river_datasets.py +48 -0
  25. roms_tools/tests/test_datasets/test_roms_dataset.py +539 -0
  26. roms_tools/tests/test_datasets/test_utils.py +527 -0
  27. roms_tools/tests/{test_setup/test_fill.py → test_fill.py} +72 -9
  28. roms_tools/tests/test_setup/test_boundary_forcing.py +57 -138
  29. roms_tools/tests/test_setup/test_cdr_release.py +4 -5
  30. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_east/c/0/0/0 +0 -0
  31. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_north/c/0/0/0 +0 -0
  32. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_east/c/0/0/0 +0 -0
  33. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_north/c/0/0/0 +0 -0
  34. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_east/c/0/0/0 +0 -0
  35. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_north/c/0/0/0 +0 -0
  36. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_east/c/0/0/0 +0 -0
  37. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_north/c/0/0/0 +0 -0
  38. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_east/c/0/0/0 +0 -0
  39. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_north/c/0/0/0 +0 -0
  40. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_east/c/0/0/0 +0 -0
  41. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_north/c/0/0/0 +0 -0
  42. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_east/c/0/0/0 +0 -0
  43. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_north/c/0/0/0 +0 -0
  44. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_east/c/0/0/0 +0 -0
  45. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_north/c/0/0/0 +0 -0
  46. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_east/c/0/0/0 +0 -0
  47. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_north/c/0/0/0 +0 -0
  48. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_east/c/0/0/0 +0 -0
  49. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_north/c/0/0/0 +0 -0
  50. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_east/c/0/0/0 +0 -0
  51. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_north/c/0/0/0 +0 -0
  52. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_east/c/0/0/0 +0 -0
  53. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_north/c/0/0/0 +0 -0
  54. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_east/c/0/0/0 +0 -0
  55. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_north/c/0/0/0 +0 -0
  56. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_east/c/0/0/0 +0 -0
  57. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_north/c/0/0/0 +0 -0
  58. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_east/c/0/0/0 +0 -0
  59. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_north/c/0/0/0 +0 -0
  60. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_east/c/0/0/0 +0 -0
  61. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_north/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/diatC_east/c/0/0/0 +0 -0
  65. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatC_north/c/0/0/0 +0 -0
  66. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_east/c/0/0/0 +0 -0
  67. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_north/c/0/0/0 +0 -0
  68. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_east/c/0/0/0 +0 -0
  69. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_north/c/0/0/0 +0 -0
  70. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_east/c/0/0/0 +0 -0
  71. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_north/c/0/0/0 +0 -0
  72. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_east/c/0/0/0 +0 -0
  73. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_north/c/0/0/0 +0 -0
  74. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_east/c/0/0/0 +0 -0
  75. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_north/c/0/0/0 +0 -0
  76. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_east/c/0/0/0 +0 -0
  77. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_north/c/0/0/0 +0 -0
  78. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_east/c/0/0/0 +0 -0
  79. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_north/c/0/0/0 +0 -0
  80. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_east/c/0/0/0 +0 -0
  81. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_north/c/0/0/0 +0 -0
  82. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_east/c/0/0/0 +0 -0
  83. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_north/c/0/0/0 +0 -0
  84. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_east/c/0/0/0 +0 -0
  85. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_north/c/0/0/0 +0 -0
  86. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_east/c/0/0/0 +0 -0
  87. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_north/c/0/0/0 +0 -0
  88. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_east/c/0/0/0 +0 -0
  89. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_north/c/0/0/0 +0 -0
  90. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_east/c/0/0/0 +0 -0
  91. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_north/c/0/0/0 +0 -0
  92. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zarr.json +289 -2017
  93. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_east/c/0/0/0 +0 -0
  94. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_north/c/0/0/0 +0 -0
  95. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/zarr.json +294 -2022
  96. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_east/c/0/0/0 +0 -0
  97. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_north/c/0/0/0 +0 -0
  98. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_south/c/0/0/0 +0 -0
  99. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/salt_west/c/0/0/0 +0 -0
  100. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_east/c/0/0/0 +0 -0
  101. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_north/c/0/0/0 +0 -0
  102. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_south/c/0/0/0 +0 -0
  103. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/temp_west/c/0/0/0 +0 -0
  104. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_east/c/0/0/0 +0 -0
  105. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_north/c/0/0/0 +0 -0
  106. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_south/c/0/0/0 +0 -0
  107. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/u_west/c/0/0/0 +0 -0
  108. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_east/c/0/0 +0 -0
  109. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_north/c/0/0 +0 -0
  110. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_south/c/0/0 +0 -0
  111. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/ubar_west/c/0/0 +0 -0
  112. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_east/c/0/0/0 +0 -0
  113. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_north/c/0/0/0 +0 -0
  114. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_south/c/0/0/0 +0 -0
  115. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/v_west/c/0/0/0 +0 -0
  116. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_east/c/0/0 +0 -0
  117. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_north/c/0/0 +0 -0
  118. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_south/c/0/0 +0 -0
  119. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/vbar_west/c/0/0 +0 -0
  120. roms_tools/tests/test_setup/test_data/boundary_forcing.zarr/zarr.json +182 -182
  121. roms_tools/tests/test_setup/test_data/grid.zarr/h/c/0/0 +0 -0
  122. roms_tools/tests/test_setup/test_data/grid.zarr/zarr.json +191 -191
  123. roms_tools/tests/test_setup/test_data/grid_that_straddles_dateline.zarr/h/c/0/0 +0 -0
  124. roms_tools/tests/test_setup/test_data/grid_that_straddles_dateline.zarr/zarr.json +210 -210
  125. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/ALK/c/0/0/0/0 +0 -0
  126. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/ALK_ALT_CO2/c/0/0/0/0 +0 -0
  127. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DIC/c/0/0/0/0 +0 -0
  128. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DIC_ALT_CO2/c/0/0/0/0 +0 -0
  129. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOC/c/0/0/0/0 +0 -0
  130. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOCr/c/0/0/0/0 +0 -0
  131. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DON/c/0/0/0/0 +0 -0
  132. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DONr/c/0/0/0/0 +0 -0
  133. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOP/c/0/0/0/0 +0 -0
  134. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/DOPr/c/0/0/0/0 +0 -0
  135. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/Fe/c/0/0/0/0 +0 -0
  136. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/Lig/c/0/0/0/0 +0 -0
  137. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/NH4/c/0/0/0/0 +0 -0
  138. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/NO3/c/0/0/0/0 +0 -0
  139. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/O2/c/0/0/0/0 +0 -0
  140. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/PO4/c/0/0/0/0 +0 -0
  141. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/SiO3/c/0/0/0/0 +0 -0
  142. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatC/c/0/0/0/0 +0 -0
  143. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatChl/c/0/0/0/0 +0 -0
  144. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatFe/c/0/0/0/0 +0 -0
  145. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatP/c/0/0/0/0 +0 -0
  146. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diatSi/c/0/0/0/0 +0 -0
  147. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazC/c/0/0/0/0 +0 -0
  148. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazChl/c/0/0/0/0 +0 -0
  149. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazFe/c/0/0/0/0 +0 -0
  150. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/diazP/c/0/0/0/0 +0 -0
  151. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/salt/c/0/0/0/0 +0 -0
  152. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spC/c/0/0/0/0 +0 -0
  153. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spCaCO3/c/0/0/0/0 +0 -0
  154. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spChl/c/0/0/0/0 +0 -0
  155. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spFe/c/0/0/0/0 +0 -0
  156. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/spP/c/0/0/0/0 +0 -0
  157. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/temp/c/0/0/0/0 +0 -0
  158. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/u/c/0/0/0/0 +0 -0
  159. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/ubar/c/0/0/0 +0 -0
  160. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/v/c/0/0/0/0 +0 -0
  161. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/vbar/c/0/0/0 +0 -0
  162. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/zarr.json +182 -182
  163. roms_tools/tests/test_setup/test_data/initial_conditions_with_bgc_from_climatology.zarr/zooC/c/0/0/0/0 +0 -0
  164. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/salt/c/0/0/0/0 +0 -0
  165. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/temp/c/0/0/0/0 +0 -0
  166. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/u/c/0/0/0/0 +0 -0
  167. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/ubar/c/0/0/0 +0 -0
  168. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/v/c/0/0/0/0 +0 -0
  169. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/vbar/c/0/0/0 +0 -0
  170. roms_tools/tests/test_setup/test_data/initial_conditions_with_unified_bgc_from_climatology.zarr/zarr.json +187 -187
  171. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/u_Im/c/0/0/0 +0 -0
  172. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/u_Re/c/0/0/0 +0 -0
  173. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/v_Im/c/0/0/0 +0 -0
  174. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/v_Re/c/0/0/0 +0 -0
  175. roms_tools/tests/test_setup/test_data/tidal_forcing.zarr/zarr.json +66 -66
  176. roms_tools/tests/test_setup/test_grid.py +56 -1
  177. roms_tools/tests/test_setup/test_initial_conditions.py +3 -94
  178. roms_tools/tests/test_setup/test_nesting.py +119 -30
  179. roms_tools/tests/test_setup/test_surface_forcing.py +2 -2
  180. roms_tools/tests/test_setup/test_tides.py +1 -1
  181. roms_tools/tests/test_setup/test_utils.py +100 -15
  182. roms_tools/tests/test_tiling/test_partition.py +63 -15
  183. roms_tools/tests/test_utils.py +78 -0
  184. roms_tools/tiling/partition.py +81 -211
  185. roms_tools/utils.py +193 -0
  186. {roms_tools-3.2.0.dist-info → roms_tools-3.4.0.dist-info}/METADATA +1 -1
  187. {roms_tools-3.2.0.dist-info → roms_tools-3.4.0.dist-info}/RECORD +190 -312
  188. {roms_tools-3.2.0.dist-info → roms_tools-3.4.0.dist-info}/WHEEL +1 -1
  189. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_west/c/0/0/0 +0 -0
  190. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_ALT_CO2_west/zarr.json +0 -54
  191. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_west/c/0/0/0 +0 -0
  192. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/ALK_west/zarr.json +0 -54
  193. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_west/c/0/0/0 +0 -0
  194. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_ALT_CO2_west/zarr.json +0 -54
  195. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_west/c/0/0/0 +0 -0
  196. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DIC_west/zarr.json +0 -54
  197. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_west/c/0/0/0 +0 -0
  198. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOC_west/zarr.json +0 -54
  199. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_west/c/0/0/0 +0 -0
  200. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOCr_west/zarr.json +0 -54
  201. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_west/c/0/0/0 +0 -0
  202. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DON_west/zarr.json +0 -54
  203. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_west/c/0/0/0 +0 -0
  204. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DONr_west/zarr.json +0 -54
  205. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_west/c/0/0/0 +0 -0
  206. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOP_west/zarr.json +0 -54
  207. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_west/c/0/0/0 +0 -0
  208. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/DOPr_west/zarr.json +0 -54
  209. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_west/c/0/0/0 +0 -0
  210. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Fe_west/zarr.json +0 -54
  211. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_west/c/0/0/0 +0 -0
  212. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/Lig_west/zarr.json +0 -54
  213. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_west/c/0/0/0 +0 -0
  214. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NH4_west/zarr.json +0 -54
  215. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_west/c/0/0/0 +0 -0
  216. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/NO3_west/zarr.json +0 -54
  217. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_west/c/0/0/0 +0 -0
  218. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/O2_west/zarr.json +0 -54
  219. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_west/c/0/0/0 +0 -0
  220. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/PO4_west/zarr.json +0 -54
  221. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/SiO3_west/c/0/0/0 +0 -0
  222. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/SiO3_west/zarr.json +0 -54
  223. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatC_west/c/0/0/0 +0 -0
  224. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatC_west/zarr.json +0 -54
  225. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_west/c/0/0/0 +0 -0
  226. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatChl_west/zarr.json +0 -54
  227. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_west/c/0/0/0 +0 -0
  228. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatFe_west/zarr.json +0 -54
  229. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_west/c/0/0/0 +0 -0
  230. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatP_west/zarr.json +0 -54
  231. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_west/c/0/0/0 +0 -0
  232. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diatSi_west/zarr.json +0 -54
  233. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_west/c/0/0/0 +0 -0
  234. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazC_west/zarr.json +0 -54
  235. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_west/c/0/0/0 +0 -0
  236. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazChl_west/zarr.json +0 -54
  237. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_west/c/0/0/0 +0 -0
  238. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazFe_west/zarr.json +0 -54
  239. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_west/c/0/0/0 +0 -0
  240. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/diazP_west/zarr.json +0 -54
  241. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_west/c/0/0/0 +0 -0
  242. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spC_west/zarr.json +0 -54
  243. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_west/c/0/0/0 +0 -0
  244. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spCaCO3_west/zarr.json +0 -54
  245. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_west/c/0/0/0 +0 -0
  246. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spChl_west/zarr.json +0 -54
  247. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_west/c/0/0/0 +0 -0
  248. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spFe_west/zarr.json +0 -54
  249. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_west/c/0/0/0 +0 -0
  250. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/spP_west/zarr.json +0 -54
  251. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_west/c/0/0/0 +0 -0
  252. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_climatology.zarr/zooC_west/zarr.json +0 -54
  253. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/ALK_ALT_CO2_west/c/0/0/0 +0 -0
  254. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/ALK_ALT_CO2_west/zarr.json +0 -54
  255. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/ALK_west/c/0/0/0 +0 -0
  256. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/ALK_west/zarr.json +0 -54
  257. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DIC_ALT_CO2_west/c/0/0/0 +0 -0
  258. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DIC_ALT_CO2_west/zarr.json +0 -54
  259. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DIC_west/c/0/0/0 +0 -0
  260. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DIC_west/zarr.json +0 -54
  261. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOC_west/c/0/0/0 +0 -0
  262. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOC_west/zarr.json +0 -54
  263. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOCr_west/c/0/0/0 +0 -0
  264. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOCr_west/zarr.json +0 -54
  265. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DON_west/c/0/0/0 +0 -0
  266. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DON_west/zarr.json +0 -54
  267. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DONr_west/c/0/0/0 +0 -0
  268. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DONr_west/zarr.json +0 -54
  269. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOP_west/c/0/0/0 +0 -0
  270. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOP_west/zarr.json +0 -54
  271. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOPr_west/c/0/0/0 +0 -0
  272. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/DOPr_west/zarr.json +0 -54
  273. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/Fe_west/c/0/0/0 +0 -0
  274. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/Fe_west/zarr.json +0 -54
  275. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/Lig_west/c/0/0/0 +0 -0
  276. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/Lig_west/zarr.json +0 -54
  277. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/NH4_west/c/0/0/0 +0 -0
  278. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/NH4_west/zarr.json +0 -54
  279. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/NO3_west/c/0/0/0 +0 -0
  280. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/NO3_west/zarr.json +0 -54
  281. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/O2_west/c/0/0/0 +0 -0
  282. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/O2_west/zarr.json +0 -54
  283. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/PO4_west/c/0/0/0 +0 -0
  284. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/PO4_west/zarr.json +0 -54
  285. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/SiO3_west/c/0/0/0 +0 -0
  286. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/SiO3_west/zarr.json +0 -54
  287. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatC_west/c/0/0/0 +0 -0
  288. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatC_west/zarr.json +0 -54
  289. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatChl_west/c/0/0/0 +0 -0
  290. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatChl_west/zarr.json +0 -54
  291. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatFe_west/c/0/0/0 +0 -0
  292. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatFe_west/zarr.json +0 -54
  293. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatP_west/c/0/0/0 +0 -0
  294. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatP_west/zarr.json +0 -54
  295. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatSi_west/c/0/0/0 +0 -0
  296. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diatSi_west/zarr.json +0 -54
  297. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazC_west/c/0/0/0 +0 -0
  298. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazC_west/zarr.json +0 -54
  299. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazChl_west/c/0/0/0 +0 -0
  300. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazChl_west/zarr.json +0 -54
  301. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazFe_west/c/0/0/0 +0 -0
  302. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazFe_west/zarr.json +0 -54
  303. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazP_west/c/0/0/0 +0 -0
  304. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/diazP_west/zarr.json +0 -54
  305. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spC_west/c/0/0/0 +0 -0
  306. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spC_west/zarr.json +0 -54
  307. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spCaCO3_west/c/0/0/0 +0 -0
  308. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spCaCO3_west/zarr.json +0 -54
  309. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spChl_west/c/0/0/0 +0 -0
  310. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spChl_west/zarr.json +0 -54
  311. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spFe_west/c/0/0/0 +0 -0
  312. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spFe_west/zarr.json +0 -54
  313. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spP_west/c/0/0/0 +0 -0
  314. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/spP_west/zarr.json +0 -54
  315. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/zooC_west/c/0/0/0 +0 -0
  316. roms_tools/tests/test_setup/test_data/bgc_boundary_forcing_from_unified_climatology.zarr/zooC_west/zarr.json +0 -54
  317. {roms_tools-3.2.0.dist-info → roms_tools-3.4.0.dist-info}/licenses/LICENSE +0 -0
  318. {roms_tools-3.2.0.dist-info → roms_tools-3.4.0.dist-info}/top_level.txt +0 -0
@@ -0,0 +1,527 @@
1
+ import logging
2
+ from copy import deepcopy
3
+ from datetime import datetime, timedelta
4
+
5
+ import cftime
6
+ import numpy as np
7
+ import pytest
8
+ import xarray as xr
9
+
10
+ from roms_tools.datasets.utils import (
11
+ _select_initial_time,
12
+ check_dataset,
13
+ convert_cftime_to_datetime,
14
+ convert_to_float64,
15
+ extrapolate_deepest_to_bottom,
16
+ get_time_type,
17
+ select_relevant_fields,
18
+ select_relevant_times,
19
+ validate_start_end_time,
20
+ )
21
+
22
+
23
+ def test_convert_to_float64():
24
+ # Create dataset with mixed dtypes
25
+ ds = xr.Dataset(
26
+ {
27
+ "temp": (("x",), np.array([1, 2, 3], dtype=np.float32)),
28
+ "mask_rho": (("x",), np.array([0, 1, 0], dtype=np.int16)),
29
+ }
30
+ )
31
+
32
+ out = convert_to_float64(ds)
33
+
34
+ # Non-mask variables should be converted to float64
35
+ assert out["temp"].dtype == np.float64
36
+
37
+ # Mask variables should keep their original dtype
38
+ assert out["mask_rho"].dtype == np.int16
39
+
40
+ # Values should be preserved
41
+ xr.testing.assert_equal(out["temp"], ds["temp"].astype("float64"))
42
+ xr.testing.assert_equal(out["mask_rho"], ds["mask_rho"])
43
+
44
+
45
+ def test_extrapolate_deepest_to_bottom():
46
+ data = np.array(
47
+ [
48
+ [1, 2],
49
+ [3, 4],
50
+ [5, np.nan],
51
+ [np.nan, np.nan],
52
+ [np.nan, np.nan],
53
+ ]
54
+ )
55
+ ds = xr.Dataset({"var": (("s_rho", "x"), data)})
56
+
57
+ ds_filled = extrapolate_deepest_to_bottom(ds, "s_rho")
58
+
59
+ expected = np.array(
60
+ [
61
+ [1, 2],
62
+ [3, 4],
63
+ [5, 4],
64
+ [5, 4],
65
+ [5, 4],
66
+ ]
67
+ )
68
+ np.testing.assert_array_equal(ds_filled["var"].values, expected)
69
+
70
+
71
+ # tests for validate_start_end_time
72
+
73
+
74
+ def test_valid_times():
75
+ start = datetime(2024, 1, 1, 12, 0)
76
+ end = start + timedelta(hours=3)
77
+
78
+ # Should not raise
79
+ validate_start_end_time(start, end)
80
+
81
+
82
+ def test_none_times():
83
+ # None for both is allowed
84
+ validate_start_end_time(None, None)
85
+
86
+ # Only start_time provided
87
+ validate_start_end_time(datetime(2024, 1, 1), None)
88
+
89
+ # Only end_time provided
90
+ validate_start_end_time(None, datetime(2024, 1, 2))
91
+
92
+
93
+ def test_equal_times():
94
+ t = datetime(2024, 1, 1, 12, 0)
95
+
96
+ # end_time == start_time is allowed
97
+ validate_start_end_time(t, t)
98
+
99
+
100
+ def test_invalid_start_type():
101
+ with pytest.raises(TypeError):
102
+ validate_start_end_time("2024-01-01", None)
103
+
104
+
105
+ def test_invalid_end_type():
106
+ with pytest.raises(TypeError):
107
+ validate_start_end_time(None, 123)
108
+
109
+
110
+ def test_end_time_before_start_time():
111
+ start = datetime(2024, 1, 2)
112
+ end = datetime(2024, 1, 1)
113
+
114
+ with pytest.raises(ValueError):
115
+ validate_start_end_time(start, end)
116
+
117
+
118
+ # tests for check_dataset
119
+
120
+
121
+ def test_valid_dataset():
122
+ ds = xr.Dataset(
123
+ data_vars={
124
+ "temp": (("x", "y"), [[1, 2], [3, 4]]),
125
+ "salt": (("x", "y"), [[5, 6], [7, 8]]),
126
+ },
127
+ coords={
128
+ "x": [0, 1],
129
+ "y": [0, 1],
130
+ },
131
+ )
132
+
133
+ dim_names = {"xdim": "x", "ydim": "y"}
134
+ var_names = {"temperature": "temp", "salinity": "salt"}
135
+
136
+ # Should NOT raise
137
+ check_dataset(ds, dim_names, var_names)
138
+
139
+
140
+ def test_missing_required_dimension():
141
+ ds = xr.Dataset(data_vars={"temp": (("x",), [1])}, coords={"x": [0]})
142
+
143
+ dim_names = {"xdim": "x", "ydim": "y"}
144
+
145
+ with pytest.raises(ValueError, match="missing"):
146
+ check_dataset(ds, dim_names=dim_names)
147
+
148
+
149
+ def test_missing_required_variable():
150
+ ds = xr.Dataset(data_vars={"temp": (("x",), [1])}, coords={"x": [0]})
151
+
152
+ var_names = {"temperature": "temp", "salinity": "salt"}
153
+
154
+ with pytest.raises(ValueError, match="missing"):
155
+ check_dataset(ds, var_names=var_names)
156
+
157
+
158
+ def test_optional_variables_warning(caplog):
159
+ ds = xr.Dataset(data_vars={"temp": (("x",), [1])}, coords={"x": [0]})
160
+
161
+ opt_var_names = {"some_opt": "opt_var"}
162
+
163
+ with caplog.at_level(logging.WARNING):
164
+ # Should not raise, only warn
165
+ check_dataset(ds, opt_var_names=opt_var_names)
166
+
167
+ assert "Optional variables missing" in caplog.text
168
+ assert "opt_var" in caplog.text
169
+
170
+
171
+ def test_no_checks_pass():
172
+ ds = xr.Dataset(data_vars={"temp": (("x",), [1])}, coords={"x": [0]})
173
+
174
+ # Should not fail because no dim_names/var_names provided
175
+ check_dataset(ds)
176
+
177
+
178
+ # tests for select_relevant_fields
179
+
180
+
181
+ def test_select_relevant_fields_basic():
182
+ """Keep only required + optional variables and drop others."""
183
+ ds = xr.Dataset(
184
+ {
185
+ "temp": (("x",), np.arange(5)),
186
+ "salt": (("x",), np.arange(5) * 2),
187
+ "u": (("x",), np.arange(5) * 3),
188
+ "mask": (("x",), np.ones(5)),
189
+ "extra": (("x",), np.zeros(5)),
190
+ }
191
+ )
192
+
193
+ keep_vars = ["temp", "u"] # required + optional
194
+
195
+ out = select_relevant_fields(ds, keep_vars)
196
+
197
+ assert set(out.data_vars) == {"temp", "u", "mask"}
198
+ assert "salt" not in out
199
+ assert "extra" not in out
200
+
201
+
202
+ def test_select_relevant_fields_does_not_modify_input():
203
+ """Function must not mutate the original dataset."""
204
+ ds = xr.Dataset(
205
+ {
206
+ "temp": (("x",), np.arange(5)),
207
+ "salt": (("x",), np.arange(5)),
208
+ "mask": (("x",), np.ones(5)),
209
+ }
210
+ )
211
+
212
+ ds_copy = deepcopy(ds)
213
+
214
+ _ = select_relevant_fields(ds, ["temp"])
215
+
216
+ # ensure original dataset is unchanged
217
+ assert set(ds.data_vars) == set(ds_copy.data_vars)
218
+ assert "salt" in ds
219
+ assert "mask" in ds
220
+
221
+
222
+ def test_select_relevant_fields_duplicate_keep_names():
223
+ """Duplicate keep names should not cause issues."""
224
+ ds = xr.Dataset(
225
+ {
226
+ "temp": (("x",), np.arange(5)),
227
+ "mask": (("x",), np.ones(5)),
228
+ }
229
+ )
230
+
231
+ keep_vars = ["temp", "temp"] # duplicates
232
+
233
+ out = select_relevant_fields(ds, keep_vars)
234
+
235
+ assert set(out.data_vars) == {"temp", "mask"}
236
+
237
+
238
+ # tests for select_relevant_times
239
+
240
+
241
+ def make_time_dataset(times):
242
+ return xr.Dataset(
243
+ data_vars={"var": ("time", np.arange(len(times)))},
244
+ coords={"time": times},
245
+ )
246
+
247
+
248
+ def test_missing_time_dimension(caplog):
249
+ ds = xr.Dataset({"x": ("x", [1, 2])})
250
+
251
+ with caplog.at_level(logging.WARNING):
252
+ out = select_relevant_times(
253
+ ds, "time", datetime(2024, 1, 1), datetime(2024, 1, 2)
254
+ )
255
+
256
+ assert "does not contain time dimension" in caplog.text
257
+ assert out is ds # unchanged
258
+
259
+
260
+ def test_climatology_must_have_12_steps():
261
+ times = np.arange(10).astype("datetime64[D]")
262
+ ds = make_time_dataset(times)
263
+
264
+ with pytest.raises(ValueError):
265
+ select_relevant_times(
266
+ ds,
267
+ "time",
268
+ "time",
269
+ datetime(2024, 1, 1),
270
+ climatology=True,
271
+ end_time=datetime(2024, 1, 2),
272
+ )
273
+
274
+
275
+ def test_climatology_pass_through():
276
+ times = np.arange(12)
277
+ ds = make_time_dataset(times)
278
+
279
+ out = select_relevant_times(
280
+ ds,
281
+ "time",
282
+ "time",
283
+ datetime(2024, 1, 1),
284
+ end_time=datetime(2024, 1, 10),
285
+ climatology=True,
286
+ )
287
+ assert out.equals(ds)
288
+
289
+
290
+ def test_int_time_rejected():
291
+ ds = xr.Dataset(
292
+ data_vars={"var": ("time", [1, 2, 3])},
293
+ coords={"time": [1, 2, 3]},
294
+ )
295
+
296
+ with pytest.raises(ValueError):
297
+ select_relevant_times(
298
+ ds, "time", "time", datetime(2024, 1, 1), datetime(2024, 1, 2)
299
+ )
300
+
301
+
302
+ def test_cftime_conversion(monkeypatch):
303
+ times = xr.DataArray(
304
+ [cftime.DatetimeGregorian(2024, 1, i + 1) for i in range(3)], dims="time"
305
+ )
306
+ ds = xr.Dataset({"var": ("time", [1, 2, 3])}, coords={"time": times})
307
+
308
+ # Mock conversion function to ensure it is called
309
+ def mock_convert(t):
310
+ return np.array(
311
+ ["2024-01-01", "2024-01-02", "2024-01-03"], dtype="datetime64[ns]"
312
+ )
313
+
314
+ monkeypatch.setattr(
315
+ "roms_tools.datasets.utils.convert_cftime_to_datetime", mock_convert
316
+ )
317
+
318
+ out = select_relevant_times(
319
+ ds, "time", "time", datetime(2024, 1, 1), datetime(2024, 1, 3)
320
+ )
321
+
322
+ assert np.issubdtype(out["time"].dtype, np.datetime64)
323
+
324
+
325
+ def test_time_range_selection():
326
+ times = np.array(
327
+ ["2024-01-01", "2024-01-02", "2024-01-05", "2024-01-10"], dtype="datetime64[ns]"
328
+ )
329
+ ds = make_time_dataset(times)
330
+
331
+ out = select_relevant_times(
332
+ ds,
333
+ "time",
334
+ "time",
335
+ datetime(2024, 1, 2),
336
+ datetime(2024, 1, 7),
337
+ )
338
+
339
+ # Should include:
340
+ # - closest before start: 2024-01-02
341
+ # - records inside strict range: 2024-01-05
342
+ # - closest after end: 2024-01-10
343
+ expected_times = np.array(
344
+ ["2024-01-02", "2024-01-05", "2024-01-10"],
345
+ dtype="datetime64[ns]",
346
+ )
347
+
348
+ assert np.array_equal(out["time"].values, expected_times)
349
+
350
+
351
+ def test_range_selection_missing_before(caplog):
352
+ times = np.array(["2024-01-05", "2024-01-10"], dtype="datetime64[ns]")
353
+ ds = make_time_dataset(times)
354
+
355
+ with caplog.at_level(logging.WARNING):
356
+ out = select_relevant_times(
357
+ ds,
358
+ "time",
359
+ "time",
360
+ datetime(2024, 1, 1),
361
+ datetime(2024, 1, 12),
362
+ )
363
+
364
+ assert "No records found at or before the start_time" in caplog.text
365
+ # Should fallback to first record
366
+ assert out["time"].values[0] == np.datetime64("2024-01-05")
367
+
368
+
369
+ def test_range_selection_missing_after(caplog):
370
+ times = np.array(["2024-01-01", "2024-01-02"], dtype="datetime64[ns]")
371
+ ds = make_time_dataset(times)
372
+
373
+ with caplog.at_level(logging.WARNING):
374
+ out = select_relevant_times(
375
+ ds,
376
+ "time",
377
+ "time",
378
+ datetime(2024, 1, 1),
379
+ datetime(2024, 1, 10),
380
+ )
381
+
382
+ assert "No records found at or after the end_time" in caplog.text
383
+ assert out["time"].values[-1] == np.datetime64("2024-01-02")
384
+
385
+
386
+ # Tests for _select_initial_time
387
+
388
+
389
+ def test_initial_time_exact_match():
390
+ times = np.array(["2024-01-01", "2024-01-02"], dtype="datetime64[ns]")
391
+ ds = make_time_dataset(times)
392
+
393
+ out = _select_initial_time(
394
+ ds,
395
+ "time",
396
+ "time",
397
+ datetime(2024, 1, 2),
398
+ climatology=False,
399
+ allow_flex_time=False,
400
+ )
401
+
402
+ assert out["time"].values == np.datetime64("2024-01-02")
403
+
404
+
405
+ def test_initial_time_no_exact_match():
406
+ times = np.array(["2024-01-01", "2024-01-03"], dtype="datetime64[ns]")
407
+ ds = make_time_dataset(times)
408
+
409
+ with pytest.raises(ValueError):
410
+ _select_initial_time(
411
+ ds,
412
+ "time",
413
+ "time",
414
+ datetime(2024, 1, 2),
415
+ climatology=False,
416
+ allow_flex_time=False,
417
+ )
418
+
419
+
420
+ def test_initial_flexible_time():
421
+ times = np.array(["2024-01-01", "2024-01-02", "2024-01-15"], dtype="datetime64[ns]")
422
+ ds = make_time_dataset(times)
423
+
424
+ out = _select_initial_time(
425
+ ds,
426
+ "time",
427
+ "time",
428
+ datetime(2024, 1, 1),
429
+ climatology=False,
430
+ allow_flex_time=True,
431
+ )
432
+
433
+ assert out["time"].values == np.datetime64("2024-01-01")
434
+
435
+
436
+ def test_initial_flexible_time_out_of_range():
437
+ times = np.array(["2024-01-10", "2024-01-11"], dtype="datetime64[ns]")
438
+ ds = make_time_dataset(times)
439
+
440
+ with pytest.raises(ValueError):
441
+ _select_initial_time(
442
+ ds,
443
+ "time",
444
+ "time",
445
+ datetime(2024, 1, 1),
446
+ climatology=False,
447
+ allow_flex_time=True,
448
+ )
449
+
450
+
451
+ # tests for get_time_type
452
+
453
+
454
+ def test_get_time_type_datetime():
455
+ times = np.array(["2020-01-01", "2020-01-02"], dtype="datetime64[ns]")
456
+ da = xr.DataArray(times)
457
+ assert get_time_type(da) == "datetime"
458
+
459
+
460
+ def test_get_time_type_cftime():
461
+ times = np.array(
462
+ [
463
+ cftime.DatetimeNoLeap(2000, 1, 1),
464
+ cftime.DatetimeNoLeap(2000, 1, 2),
465
+ ],
466
+ dtype=object,
467
+ )
468
+ da = xr.DataArray(times)
469
+ assert get_time_type(da) == "cftime"
470
+
471
+
472
+ def test_get_time_type_integer():
473
+ da = xr.DataArray(np.array([1, 2, 3], dtype=int))
474
+ assert get_time_type(da) == "int"
475
+
476
+
477
+ def test_get_time_type_unsupported_type():
478
+ da = xr.DataArray(np.array(["a", "b"], dtype=object))
479
+ with pytest.raises(ValueError, match="Unsupported data type"):
480
+ get_time_type(da)
481
+
482
+
483
+ def test_get_time_type_invalid_input_type():
484
+ da = xr.DataArray("not-an-array")
485
+ with pytest.raises(ValueError):
486
+ get_time_type(da)
487
+
488
+
489
+ # Tests for convert_cftime_to_datetime
490
+
491
+
492
+ def test_convert_cftime_to_datetime_basic():
493
+ arr = np.array(
494
+ [
495
+ cftime.DatetimeNoLeap(2000, 1, 1),
496
+ cftime.DatetimeNoLeap(2000, 1, 2),
497
+ ]
498
+ )
499
+
500
+ converted = convert_cftime_to_datetime(arr)
501
+
502
+ assert converted.dtype == "datetime64[ns]"
503
+ assert converted[0] == np.datetime64("2000-01-01")
504
+ assert converted[1] == np.datetime64("2000-01-02")
505
+
506
+
507
+ def test_convert_cftime_to_datetime_mixed_inputs():
508
+ arr = np.array(
509
+ [
510
+ cftime.DatetimeNoLeap(2000, 1, 1),
511
+ "2001-01-01",
512
+ np.datetime64("2002-01-01"),
513
+ ],
514
+ dtype=object,
515
+ )
516
+
517
+ converted = convert_cftime_to_datetime(arr)
518
+
519
+ assert converted[0] == np.datetime64("2000-01-01")
520
+ assert converted[1] == np.datetime64("2001-01-01")
521
+ assert converted[2] == np.datetime64("2002-01-01")
522
+
523
+
524
+ def test_convert_cftime_to_datetime_returns_numpy_array():
525
+ arr = np.array([cftime.DatetimeNoLeap(1999, 12, 31)])
526
+ converted = convert_cftime_to_datetime(arr)
527
+ assert isinstance(converted, np.ndarray)
@@ -2,7 +2,7 @@ import numpy as np
2
2
  import pytest
3
3
  import xarray as xr
4
4
 
5
- from roms_tools.setup.fill import LateralFill
5
+ from roms_tools.fill import LateralFill
6
6
 
7
7
 
8
8
  @pytest.mark.parametrize(
@@ -19,12 +19,12 @@ def test_lateral_fill_no_nans(data_fixture, request):
19
19
  data = request.getfixturevalue(data_fixture)
20
20
  lateral_fill = LateralFill(
21
21
  data.ds["mask"],
22
- [data.dim_names["latitude"], data.dim_names["longitude"]],
22
+ (data.dim_names["latitude"], data.dim_names["longitude"]),
23
23
  )
24
24
  if "mask_vel" in data.ds.data_vars:
25
25
  lateral_fill_vel = LateralFill(
26
26
  data.ds["mask_vel"],
27
- [data.dim_names["latitude"], data.dim_names["longitude"]],
27
+ (data.dim_names["latitude"], data.dim_names["longitude"]),
28
28
  )
29
29
 
30
30
  for var in data.var_names:
@@ -40,10 +40,10 @@ def test_lateral_fill_no_nans(data_fixture, request):
40
40
  def test_lateral_fill_correct_order_of_magnitude(coarsened_cesm_bgc_data):
41
41
  lateral_fill = LateralFill(
42
42
  coarsened_cesm_bgc_data.ds["mask"],
43
- [
43
+ (
44
44
  coarsened_cesm_bgc_data.dim_names["latitude"],
45
45
  coarsened_cesm_bgc_data.dim_names["longitude"],
46
- ],
46
+ ),
47
47
  )
48
48
 
49
49
  ALK = coarsened_cesm_bgc_data.ds["ALK"]
@@ -78,21 +78,21 @@ def test_lateral_fill_reproducibility(data_fixture, request):
78
78
  data = request.getfixturevalue(data_fixture)
79
79
  lateral_fill0 = LateralFill(
80
80
  data.ds["mask"],
81
- [data.dim_names["latitude"], data.dim_names["longitude"]],
81
+ (data.dim_names["latitude"], data.dim_names["longitude"]),
82
82
  )
83
83
  if "mask_vel" in data.ds.data_vars:
84
84
  lateral_fill_vel0 = LateralFill(
85
85
  data.ds["mask_vel"],
86
- [data.dim_names["latitude"], data.dim_names["longitude"]],
86
+ (data.dim_names["latitude"], data.dim_names["longitude"]),
87
87
  )
88
88
  lateral_fill1 = LateralFill(
89
89
  data.ds["mask"],
90
- [data.dim_names["latitude"], data.dim_names["longitude"]],
90
+ (data.dim_names["latitude"], data.dim_names["longitude"]),
91
91
  )
92
92
  if "mask_vel" in data.ds.data_vars:
93
93
  lateral_fill_vel1 = LateralFill(
94
94
  data.ds["mask_vel"],
95
- [data.dim_names["latitude"], data.dim_names["longitude"]],
95
+ (data.dim_names["latitude"], data.dim_names["longitude"]),
96
96
  )
97
97
 
98
98
  ds0 = data.ds.copy()
@@ -116,3 +116,66 @@ def test_lateral_fill_reproducibility(data_fixture, request):
116
116
  )
117
117
 
118
118
  assert ds0.equals(ds1)
119
+
120
+
121
+ def test_lateralfill_raises_notimplemented_for_non2d_mask():
122
+ mask_3d = xr.DataArray(np.ones((3, 3, 3)), dims=("eta_rho", "xi_rho", "s_rho"))
123
+ with pytest.raises(
124
+ NotImplementedError, match="LateralFill currently supports only 2D masks"
125
+ ):
126
+ LateralFill(mask_3d, dims=("eta_rho", "xi_rho"))
127
+
128
+
129
+ def test_lateralfill_raises_valueerror_for_list_of_dims():
130
+ mask = xr.DataArray(np.ones((3, 3)), dims=("eta_rho", "xi_rho"))
131
+ with pytest.raises(TypeError, match="must be a tuple"):
132
+ LateralFill(mask, dims=["eta_rho", "xi_rho"])
133
+
134
+
135
+ def test_lateralfill_raises_valueerror_for_wrong_number_of_dims():
136
+ mask = xr.DataArray(np.ones((3, 3)), dims=("eta_rho", "xi_rho"))
137
+
138
+ with pytest.raises(ValueError, match="must contain exactly two"):
139
+ LateralFill(mask, dims=("eta_rho", "xi_rho", "extra_dim")) # 3 dims
140
+
141
+
142
+ def test_lateralfill_raises_valueerror_for_mask_dim_order_mismatch():
143
+ mask = xr.DataArray(np.ones((3, 3)), dims=("xi_rho", "eta_rho")) # dims reversed
144
+ with pytest.raises(ValueError, match="dimension order is incorrect"):
145
+ LateralFill(mask, dims=("eta_rho", "xi_rho"))
146
+
147
+
148
+ def test_apply_raises_if_var_missing_dims():
149
+ mask = xr.DataArray(np.ones((3, 3)), dims=("eta_rho", "xi_rho"))
150
+ lf = LateralFill(mask, dims=("eta_rho", "xi_rho"))
151
+ var = xr.DataArray(np.ones((3, 3)), dims=("eta_rho", "eta_u")) # missing xi_rho
152
+ with pytest.raises(
153
+ ValueError, match="does not contain the required horizontal dimensions"
154
+ ):
155
+ lf.apply(var)
156
+
157
+
158
+ def test_apply_raises_if_var_dim_order_mismatch():
159
+ mask = xr.DataArray(np.ones((3, 3)), dims=("eta_rho", "xi_rho"))
160
+ lf = LateralFill(mask, dims=("eta_rho", "xi_rho"))
161
+ var = xr.DataArray(np.ones((3, 3)), dims=("xi_rho", "eta_rho")) # wrong order
162
+ with pytest.raises(ValueError, match="dimension order is incorrect"):
163
+ lf.apply(var)
164
+
165
+
166
+ def test_apply_raises_if_var_has_nans_on_valid_mask():
167
+ # 2D mask
168
+ mask = xr.DataArray(np.ones((3, 3), dtype=bool), dims=("eta_rho", "xi_rho"))
169
+
170
+ lf = LateralFill(mask, dims=("eta_rho", "xi_rho"))
171
+
172
+ # Variable with a NaN at a location where mask is True
173
+ data = np.ones((3, 3))
174
+ data[1, 1] = np.nan
175
+ var = xr.DataArray(data, dims=("eta_rho", "xi_rho"))
176
+
177
+ # Expect ValueError
178
+ with pytest.raises(
179
+ ValueError, match="contains NaNs at grid points marked as valid"
180
+ ):
181
+ lf.apply(var)