imas-python 2.2.0__tar.gz → 2.3.0__tar.gz

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 (227) hide show
  1. imas_python-2.3.0/.github/dependabot.yml +10 -0
  2. {imas_python-2.2.0 → imas_python-2.3.0}/.github/workflows/linting.yml +2 -2
  3. {imas_python-2.2.0 → imas_python-2.3.0}/.github/workflows/publish.yml +5 -5
  4. {imas_python-2.2.0 → imas_python-2.3.0}/.github/workflows/test_with_pytest.yml +4 -4
  5. {imas_python-2.2.0 → imas_python-2.3.0}/.readthedocs.yml +1 -1
  6. {imas_python-2.2.0/imas_python.egg-info → imas_python-2.3.0}/PKG-INFO +1 -1
  7. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/changelog.rst +49 -0
  8. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/conf.py +3 -0
  9. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/identifiers.rst +27 -6
  10. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/intro.rst +25 -15
  11. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/multi-dd.rst +5 -25
  12. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/netcdf.rst +38 -0
  13. {imas_python-2.2.0 → imas_python-2.3.0}/imas/_to_xarray.py +20 -13
  14. imas_python-2.3.0/imas/_version.py +24 -0
  15. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/ITER_134173_106_equilibrium.ids +0 -2
  16. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/equilibrium.ids +0 -2
  17. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/db_entry_impl.py +8 -0
  18. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/al_context.py +11 -0
  19. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/db_entry_al.py +13 -0
  20. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/imas_interface.py +5 -0
  21. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/db_entry_nc.py +23 -6
  22. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/ids2nc.py +12 -46
  23. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/ids_tensorizer.py +69 -10
  24. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/nc2ids.py +13 -14
  25. {imas_python-2.2.0 → imas_python-2.3.0}/imas/db_entry.py +67 -4
  26. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_convert.py +66 -32
  27. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_identifiers.py +28 -15
  28. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_primitive.py +3 -3
  29. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_convert_core_edge_plasma.py +1 -1
  30. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_identifiers.py +18 -9
  31. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_convert.py +72 -0
  32. imas_python-2.3.0/imas/test/test_list_filled_paths.py +101 -0
  33. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_to_xarray.py +25 -2
  34. {imas_python-2.2.0 → imas_python-2.3.0}/imas/training.py +11 -6
  35. {imas_python-2.2.0 → imas_python-2.3.0/imas_python.egg-info}/PKG-INFO +1 -1
  36. {imas_python-2.2.0 → imas_python-2.3.0}/imas_python.egg-info/SOURCES.txt +2 -1
  37. {imas_python-2.2.0 → imas_python-2.3.0}/pyproject.toml +0 -5
  38. imas_python-2.2.0/.github/workflows/verify_sphinx_doc.yml +0 -53
  39. imas_python-2.2.0/imas/_version.py +0 -34
  40. {imas_python-2.2.0 → imas_python-2.3.0}/.git-blame-ignore-revs +0 -0
  41. {imas_python-2.2.0 → imas_python-2.3.0}/.git_archival.txt +0 -0
  42. {imas_python-2.2.0 → imas_python-2.3.0}/.gitattributes +0 -0
  43. {imas_python-2.2.0 → imas_python-2.3.0}/.github/CODEOWNERS +0 -0
  44. {imas_python-2.2.0 → imas_python-2.3.0}/.gitignore +0 -0
  45. {imas_python-2.2.0 → imas_python-2.3.0}/.pylintrc +0 -0
  46. {imas_python-2.2.0 → imas_python-2.3.0}/CODE_OF_CONDUCT.md +0 -0
  47. {imas_python-2.2.0 → imas_python-2.3.0}/CONTRIBUTING.md +0 -0
  48. {imas_python-2.2.0 → imas_python-2.3.0}/LICENSE.txt +0 -0
  49. {imas_python-2.2.0 → imas_python-2.3.0}/MANIFEST.in +0 -0
  50. {imas_python-2.2.0 → imas_python-2.3.0}/README.md +0 -0
  51. {imas_python-2.2.0 → imas_python-2.3.0}/asv.conf.json +0 -0
  52. {imas_python-2.2.0 → imas_python-2.3.0}/benchmarks/__init__.py +0 -0
  53. {imas_python-2.2.0 → imas_python-2.3.0}/benchmarks/core_profiles.py +0 -0
  54. {imas_python-2.2.0 → imas_python-2.3.0}/benchmarks/edge_profiles.py +0 -0
  55. {imas_python-2.2.0 → imas_python-2.3.0}/benchmarks/technical.py +0 -0
  56. {imas_python-2.2.0 → imas_python-2.3.0}/benchmarks/utils.py +0 -0
  57. {imas_python-2.2.0 → imas_python-2.3.0}/conftest.py +0 -0
  58. {imas_python-2.2.0 → imas_python-2.3.0}/docs/.gitignore +0 -0
  59. {imas_python-2.2.0 → imas_python-2.3.0}/docs/Makefile +0 -0
  60. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/.gitignore +0 -0
  61. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_static/imas.css +0 -0
  62. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_static/imas_200x200.png +0 -0
  63. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/autosummary/accessor.rst +0 -0
  64. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/autosummary/accessor_attribute.rst +0 -0
  65. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/autosummary/accessor_callable.rst +0 -0
  66. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/autosummary/accessor_method.rst +0 -0
  67. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/autosummary/base.rst +0 -0
  68. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/custom-class-template.rst +0 -0
  69. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/custom-module-template.rst +0 -0
  70. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/_templates/layout.html +0 -0
  71. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/api-hidden.rst +0 -0
  72. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/api.rst +0 -0
  73. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/benchmarking.rst +0 -0
  74. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/ci_config.rst +0 -0
  75. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/cli.rst +0 -0
  76. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/code_style.rst +0 -0
  77. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/configuring.rst +0 -0
  78. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/dd_versions.rst +0 -0
  79. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/explore.rst +0 -0
  80. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/hashing.rst +0 -0
  81. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/alternative_coordinates.py +0 -0
  82. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/autoconvert_get.py +0 -0
  83. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/autoconvert_put.py +0 -0
  84. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/calc_with_units.py +0 -0
  85. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/coordinates.py +0 -0
  86. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/dd_versions.py +0 -0
  87. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/explore_data.py +0 -0
  88. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/explore_structures.py +0 -0
  89. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/hashing.py +0 -0
  90. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/ids_convert.py +0 -0
  91. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/ids_to_xarray.py +0 -0
  92. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/imas_snippets/tensorized_ids_to_xarray.py +0 -0
  93. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/metadata.rst +0 -0
  94. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced/xarray.rst +0 -0
  95. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/advanced_user_training.rst +0 -0
  96. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/analyze.rst +0 -0
  97. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/core_profiles_ne_timeslice.png +0 -0
  98. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/core_profiles_te.png +0 -0
  99. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/create.rst +0 -0
  100. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/explore.rst +0 -0
  101. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_inspect.png +0 -0
  102. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/create_core_profiles.py +0 -0
  103. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/explore_data_entry.py +0 -0
  104. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/explore_public_ec_launchers.py +0 -0
  105. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/explore_public_pf_active.py +0 -0
  106. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/explore_training_data.py +0 -0
  107. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/find_paths.py +0 -0
  108. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/iterate_core_profiles.py +0 -0
  109. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/plot_core_profiles_ne_timeslice.py +0 -0
  110. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/plot_core_profiles_te.py +0 -0
  111. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/print_idss.py +0 -0
  112. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/read_core_profiles_ne_timeslice.py +0 -0
  113. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/read_equilibrium_time_array.py +0 -0
  114. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/read_whole_equilibrium.py +0 -0
  115. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/imas_snippets/transform_grid.py +0 -0
  116. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/interactive_tab_core_profiles_toplevel.png +0 -0
  117. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/print_tree_ids_properties.png +0 -0
  118. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/setup.rst +0 -0
  119. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic/transform.rst +0 -0
  120. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/courses/basic_user_training.rst +0 -0
  121. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/examples/custom_conversion_em_coupling.py +0 -0
  122. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/examples/custom_conversion_em_coupling.rst +0 -0
  123. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/examples.rst +0 -0
  124. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/imas_architecture.rst +0 -0
  125. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/imas_structure.png +0 -0
  126. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/index.rst +0 -0
  127. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/installing.rst +0 -0
  128. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/lazy_loading.rst +0 -0
  129. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/mdsplus.rst +0 -0
  130. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/metadata.rst +0 -0
  131. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/netcdf/conventions.rst +0 -0
  132. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/release_imas.rst +0 -0
  133. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/resampling.rst +0 -0
  134. {imas_python-2.2.0 → imas_python-2.3.0}/docs/source/validation.rst +0 -0
  135. {imas_python-2.2.0 → imas_python-2.3.0}/imas/__init__.py +0 -0
  136. {imas_python-2.2.0 → imas_python-2.3.0}/imas/__main__.py +0 -0
  137. {imas_python-2.2.0 → imas_python-2.3.0}/imas/_util.py +0 -0
  138. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/IDSDef2MDSpreTree.xsl +0 -0
  139. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/IDS_fake_toplevel.xml +0 -0
  140. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/IDS_minimal.xml +0 -0
  141. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/IDS_minimal_2.xml +0 -0
  142. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/IDS_minimal_struct_array.xml +0 -0
  143. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/IDS_minimal_types.xml +0 -0
  144. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/ITER_134173_106_core_profiles.ids +0 -0
  145. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/README.md +0 -0
  146. {imas_python-2.2.0 → imas_python-2.3.0}/imas/assets/core_profiles.ids +0 -0
  147. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/__init__.py +0 -0
  148. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/__init__.py +0 -0
  149. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/db_entry_helpers.py +0 -0
  150. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/mdsplus_model.py +0 -0
  151. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/imas_core/uda_support.py +0 -0
  152. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/__init__.py +0 -0
  153. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/iterators.py +0 -0
  154. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/nc_metadata.py +0 -0
  155. {imas_python-2.2.0 → imas_python-2.3.0}/imas/backends/netcdf/nc_validate.py +0 -0
  156. {imas_python-2.2.0 → imas_python-2.3.0}/imas/command/cli.py +0 -0
  157. {imas_python-2.2.0 → imas_python-2.3.0}/imas/command/db_analysis.py +0 -0
  158. {imas_python-2.2.0 → imas_python-2.3.0}/imas/command/helpers.py +0 -0
  159. {imas_python-2.2.0 → imas_python-2.3.0}/imas/command/timer.py +0 -0
  160. {imas_python-2.2.0 → imas_python-2.3.0}/imas/convert_core_edge_plasma.py +0 -0
  161. {imas_python-2.2.0 → imas_python-2.3.0}/imas/dd_zip.py +0 -0
  162. {imas_python-2.2.0 → imas_python-2.3.0}/imas/exception.py +0 -0
  163. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_base.py +0 -0
  164. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_coordinates.py +0 -0
  165. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_data_type.py +0 -0
  166. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_defs.py +0 -0
  167. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_factory.py +0 -0
  168. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_metadata.py +0 -0
  169. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_path.py +0 -0
  170. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_struct_array.py +0 -0
  171. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_structure.py +0 -0
  172. {imas_python-2.2.0 → imas_python-2.3.0}/imas/ids_toplevel.py +0 -0
  173. {imas_python-2.2.0 → imas_python-2.3.0}/imas/setup_logging.py +0 -0
  174. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_all_dd_versions.py +0 -0
  175. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_cli.py +0 -0
  176. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_dbentry.py +0 -0
  177. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_dbentry_uda.py +0 -0
  178. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_dd_zip.py +0 -0
  179. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_deepcopy.py +0 -0
  180. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_exception.py +0 -0
  181. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_get_sample.py +0 -0
  182. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_hash.py +0 -0
  183. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_helpers.py +0 -0
  184. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids2nc.py +0 -0
  185. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_ascii_data.py +0 -0
  186. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_coordinates.py +0 -0
  187. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_data_type.py +0 -0
  188. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_factory.py +0 -0
  189. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_metadata.py +0 -0
  190. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_mixin.py +0 -0
  191. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_path.py +0 -0
  192. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_primitive.py +0 -0
  193. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_struct_array.py +0 -0
  194. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_structure.py +0 -0
  195. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_toplevel.py +0 -0
  196. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_ids_validate.py +0 -0
  197. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_latest_dd_autofill.py +0 -0
  198. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_latest_dd_manual.py +0 -0
  199. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_latest_dd_resample.py +0 -0
  200. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_lazy_loading.py +0 -0
  201. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_list_occurrences.py +0 -0
  202. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal.py +0 -0
  203. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal_conversion.py +0 -0
  204. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal_io.py +0 -0
  205. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal_struct_array_io.py +0 -0
  206. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal_types.py +0 -0
  207. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal_types_io.py +0 -0
  208. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_minimal_types_io_automatic.py +0 -0
  209. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_nbc_change.py +0 -0
  210. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_nc_autofill.py +0 -0
  211. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_nc_entry.py +0 -0
  212. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_nc_metadata.py +0 -0
  213. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_nc_validation.py +0 -0
  214. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_snippets.py +0 -0
  215. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_static_ids.py +0 -0
  216. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_str_1d.py +0 -0
  217. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_time_slicing.py +0 -0
  218. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_uda_support.py +0 -0
  219. {imas_python-2.2.0 → imas_python-2.3.0}/imas/test/test_util.py +0 -0
  220. {imas_python-2.2.0 → imas_python-2.3.0}/imas/util.py +0 -0
  221. {imas_python-2.2.0 → imas_python-2.3.0}/imas_python.egg-info/dependency_links.txt +0 -0
  222. {imas_python-2.2.0 → imas_python-2.3.0}/imas_python.egg-info/entry_points.txt +0 -0
  223. {imas_python-2.2.0 → imas_python-2.3.0}/imas_python.egg-info/requires.txt +0 -0
  224. {imas_python-2.2.0 → imas_python-2.3.0}/imas_python.egg-info/top_level.txt +0 -0
  225. {imas_python-2.2.0 → imas_python-2.3.0}/setup.cfg +0 -0
  226. {imas_python-2.2.0 → imas_python-2.3.0}/tools/compare_lowlevel_access_patterns.py +0 -0
  227. {imas_python-2.2.0 → imas_python-2.3.0}/tools/get_tagnames.py +0 -0
@@ -0,0 +1,10 @@
1
+ version: 2
2
+ updates:
3
+ # Enable version updates for Github Actions
4
+ - package-ecosystem: "github-actions"
5
+ # Look for `/.github/workflows` and `/action.yml` or `.yaml`
6
+ directory: "/"
7
+ # Check for updates once a week
8
+ schedule:
9
+ interval: "weekly"
10
+
@@ -12,10 +12,10 @@ jobs:
12
12
 
13
13
  steps:
14
14
  - name: Checkout IMAS-Python sources
15
- uses: actions/checkout@v4
15
+ uses: actions/checkout@v6
16
16
 
17
17
  - name: Set up Python
18
- uses: actions/setup-python@v5
18
+ uses: actions/setup-python@v6
19
19
  with:
20
20
  # until saxonche is available in 3.13
21
21
  # https://saxonica.plan.io/issues/6561
@@ -10,11 +10,11 @@ jobs:
10
10
  name: Build distribution
11
11
  runs-on: ubuntu-22.04
12
12
  steps:
13
- - uses: actions/checkout@v4
13
+ - uses: actions/checkout@v6
14
14
  with:
15
15
  fetch-depth: 0
16
16
  - name: Set up Python
17
- uses: actions/setup-python@v5
17
+ uses: actions/setup-python@v6
18
18
  with:
19
19
  # until saxonche is available in 3.13
20
20
  # https://saxonica.plan.io/issues/6561
@@ -25,7 +25,7 @@ jobs:
25
25
  - name: Build a binary wheel and a source tarball
26
26
  run: python3 -m build .
27
27
  - name: Store the distribution packages
28
- uses: actions/upload-artifact@v4
28
+ uses: actions/upload-artifact@v7
29
29
  with:
30
30
  name: python-package-distributions
31
31
  path: dist/
@@ -43,7 +43,7 @@ jobs:
43
43
  id-token: write # IMPORTANT: mandatory for trusted publishing
44
44
  steps:
45
45
  - name: Download all the dists
46
- uses: actions/download-artifact@v4
46
+ uses: actions/download-artifact@v8
47
47
  with:
48
48
  name: python-package-distributions
49
49
  path: dist/
@@ -63,7 +63,7 @@ jobs:
63
63
  id-token: write # IMPORTANT: mandatory for trusted publishing
64
64
  steps:
65
65
  - name: Download all the dists
66
- uses: actions/download-artifact@v4
66
+ uses: actions/download-artifact@v8
67
67
  with:
68
68
  name: python-package-distributions
69
69
  path: dist/
@@ -14,11 +14,11 @@ jobs:
14
14
 
15
15
  steps:
16
16
  - name: Checkout repository
17
- uses: actions/checkout@v4
17
+ uses: actions/checkout@v6
18
18
 
19
19
  - name: Set up Python ${{ matrix.python-version }}
20
20
 
21
- uses: actions/setup-python@v4
21
+ uses: actions/setup-python@v6
22
22
  with:
23
23
  python-version: ${{ matrix.python-version }}
24
24
  - name: Display Python version
@@ -37,13 +37,13 @@ jobs:
37
37
  python -m pytest -n=auto --cov=imas --cov-report=term-missing --cov-report=xml:coverage.xml --cov-report=html:htmlcov --junit-xml=junit.xml
38
38
 
39
39
  - name: Upload coverage report ${{ matrix.python-version }}
40
- uses: actions/upload-artifact@v4
40
+ uses: actions/upload-artifact@v7
41
41
  with:
42
42
  name: coverage-report-${{ matrix.python-version }}
43
43
  path: htmlcov
44
44
 
45
45
  - name: Upload test report ${{ matrix.python-version }}
46
- uses: actions/upload-artifact@v4
46
+ uses: actions/upload-artifact@v7
47
47
  with:
48
48
  name: test-report-${{ matrix.python-version }}
49
49
  path: junit.xml
@@ -20,4 +20,4 @@ python:
20
20
  sphinx:
21
21
  builder: html
22
22
  configuration: docs/source/conf.py
23
- fail_on_warning: false
23
+ fail_on_warning: true
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: imas-python
3
- Version: 2.2.0
3
+ Version: 2.3.0
4
4
  Summary: Pythonic wrappers for the IMAS Access Layer
5
5
  Author: ITER Organization
6
6
  Author-email: Karel Lucas van de Plassche <karelvandeplassche@gmail.com>, Daan van Vugt <dvanvugt@ignitioncomputing.com>, Maarten Sebregts <msebregts@ignitioncomputing.com>, imas-support@iter.org
@@ -3,6 +3,55 @@
3
3
  Changelog
4
4
  =========
5
5
 
6
+ What's new in IMAS-Python 2.3.0
7
+ -------------------------------
8
+
9
+ Features
10
+ ''''''''
11
+
12
+ - :merge:`131`: introduce alias and units metadata in the :ref:`Identifiers` API
13
+ - :merge:`104`: add a :py:func:`imas.db_entry.DBEntry.list_filled_paths` function (requires imas_core >= 5.7 for HDF5 backend)
14
+
15
+ Improvements
16
+ ''''''''''''
17
+
18
+ - :issue:`116`: migrate `magnetics` obsolescent fields (`method -> ip`, `bpol_probe -> b_field_pol_probe`) with a value during a 3to4 conversion
19
+ - :merge:`112`: include metadata variables when writing an IDS to a netCDF files with the function `to_xarray`, allowing to read back the IDS with a `get` (see :ref:`Store Xarray Datasets in IMAS-compatible netCDF file`)
20
+ - improve documentation w.r.t netcdf URI and UDA backend usage limitations and associated workarounds
21
+
22
+ Bug fixes
23
+ '''''''''
24
+
25
+ - :issue:`118`: fix deprecation warning with copy keyword for __array__ implementation (Numpy > 2)
26
+ - :issue:`117`: fix 3to4 conversion of name/identifier when identifier is empty
27
+ - :merge:`105`: fix training data assets that failed loading
28
+
29
+
30
+
31
+ What's new in IMAS-Python 2.2.0
32
+ -------------------------------
33
+
34
+ Features
35
+ ''''''''
36
+ - :issue:`44`: add `--convert-to-plasma-ids` option to `imas convert`
37
+
38
+ Improvements
39
+ ''''''''''''
40
+
41
+ - :merge:`100`: remove legacy tool `extract_test_data`
42
+ - :merge:`98`: support MDSplus models configuration change introduced in imas_core >= 5.6
43
+ - :issue:`97`: better documentation, exception message and control of DD compatibility when using UDA backend
44
+ - :merge:`95`: defer loading the default DD definitions
45
+ - :issue:`91`: remove hidden `has_imas` attribute (may break compatibility of applications that used it!)
46
+
47
+ Bug fixes
48
+ '''''''''
49
+
50
+ - :merge:`100`: fix incorrect type hints
51
+ - :issue:`89`: properly unpack 0D data when reading an IDS from a netCDF file
52
+
53
+
54
+
6
55
  What's new in IMAS-Python 2.1.0
7
56
  -------------------------------
8
57
 
@@ -34,6 +34,9 @@ copyright = f"2020-{datetime.datetime.now().year}, ITER Organization"
34
34
  author = "ITER Organization"
35
35
  src_host = "https://github.com/iterorganization/"
36
36
 
37
+ # Warn about missing references
38
+ nitpicky = True
39
+
37
40
  # Parse urls here for convenience, to be re-used
38
41
  # ITER docs
39
42
  iter_projects = "https://github.com/iterorganization/"
@@ -14,13 +14,16 @@ enumerated list of options for defining, for example:
14
14
  - These may have alternative naming conventions supported through aliases
15
15
  (e.g., "235U" and "U_235" for Uranium 235).
16
16
 
17
- Identifiers are a list of possible valid labels. Each label has up to four
18
- representations:
17
+ Identifiers are a list of possible valid options. Each option has three representations
18
+ that are stored in an IDS:
19
19
 
20
20
  1. An index (integer)
21
21
  2. A name (short string)
22
22
  3. A description (long string)
23
- 4. List of aliases (list of short strings)
23
+
24
+ .. seealso::
25
+ `Data Dictionary documentation for identifiers
26
+ <https://imas-data-dictionary.readthedocs.io/en/latest/identifiers.html>`__
24
27
 
25
28
 
26
29
  Identifiers in IMAS-Python
@@ -32,6 +35,20 @@ constructed on-demand from the loaded Data Dictionary definitions.
32
35
  All identifier enums can be accessed through ``imas.identifiers``. A list of
33
36
  the available identifiers is stored as ``imas.identifiers.identifiers``.
34
37
 
38
+ Each identifier option provides the following attributes:
39
+
40
+ - ``name``: the name of the option.
41
+ - ``index``: the integer index value of the option.
42
+ - ``description``: a longer string describing the option.
43
+ - ``aliases``: a list of aliases that can be used instead of the name.
44
+ - ``units``: optional information about the units of the quantities that are affected by
45
+ the identifier option. Take, for example, the `poloidal plan coordinate identifier
46
+ <https://imas-data-dictionary.readthedocs.io/en/stable/generated/identifier/poloidal_plane_coordinates_identifier.html>`__
47
+ which affects the units of ``grid/dim1`` and ``grid/dim2``.
48
+
49
+ .. versionadded:: 2.1.0 ``aliases`` for identifiers.
50
+ .. versionadded:: 2.3.0 ``units`` metadata.
51
+
35
52
  .. code-block:: python
36
53
  :caption: Accessing identifiers
37
54
 
@@ -47,6 +64,9 @@ the available identifiers is stored as ``imas.identifiers.identifiers``.
47
64
  print(csid.total.index)
48
65
  print(csid.total.description)
49
66
 
67
+ # Search identifier options by their index value
68
+ print(csid(1))
69
+
50
70
  # Access identifiers with aliases (when available)
51
71
  mid = imas.identifiers.materials_identifier
52
72
  print(mid["235U"].name) # Access by canonical name
@@ -57,12 +77,12 @@ the available identifiers is stored as ``imas.identifiers.identifiers``.
57
77
  assert mid["235U"].name is mid.U_235.name
58
78
 
59
79
  # Item access is also possible
60
- print(identifiers["edge_source_identifier"])
80
+ print(imas.identifiers["edge_source_identifier"])
61
81
 
62
82
  # You can use imas.util.inspect to list all options
63
- imas.util.inspect(identifiers.ggd_identifier)
83
+ imas.util.inspect(imas.identifiers.ggd_identifier)
64
84
  # And also to get more details of a specific option
65
- imas.util.inspect(identifiers.ggd_identifier.SN)
85
+ imas.util.inspect(imas.identifiers.ggd_identifier.SN)
66
86
 
67
87
  # When an IDS node is an identifier, you can use
68
88
  # metadata.identifier_enum to get the identifier
@@ -186,6 +206,7 @@ material_identifier["235U"].
186
206
  mat.names[0] = mid.U_235.name # enum value via alias
187
207
  mat.names[0] = mid["U_235"].name # enum value via alias
188
208
 
209
+
189
210
  Compare identifiers
190
211
  -------------------
191
212
 
@@ -86,17 +86,6 @@ get an error message if this is not possible:
86
86
  Load and store an IDS to disk with IMAS-Core
87
87
  ''''''''''''''''''''''''''''''''''''''''''''
88
88
 
89
- .. note::
90
-
91
- - This functionality requires the IMAS-Core, until this library is openly available
92
- on GitHub you may need to fetch it from `git.iter.org <https://git.iter.org/>`_
93
- (requires to have an ITER account). Using IMAS-Core also enable slicing methods
94
- :py:meth:`~imas.db_entry.DBEntry.get_slice`,
95
- :py:meth:`~imas.db_entry.DBEntry.put_slice` and
96
- :py:meth:`~imas.db_entry.DBEntry.get_sample` (with IMAS-Core>=5.4).
97
- - If you can't have access to it, you can save IDS to disk with the built-in
98
- netCDF backend :ref:`Load and store an IDS to disk with netCDF`
99
-
100
89
  To store an IDS to disk, we need to indicate the following URI to the
101
90
  IMAS-Core: ``imas:<backend>?path=<path_to_folder>`` or using the legacy query keys
102
91
  ``imas:<backend>?user=<user>;database=<database>;version=<version>;pulse=<pulse>;run=<run>``
@@ -115,11 +104,9 @@ In IMAS-Python you do this as follows:
115
104
  >>> # now store the core_profiles IDS we just populated
116
105
  >>> dbentry.put(core_profiles)
117
106
 
118
- .. image:: imas_structure.png
119
-
120
107
  To load an IDS from disk, you need to specify the same information as
121
108
  when storing the IDS (see above). Once the data entry is opened, you
122
- can use ``<IDS>.get()`` to load IDS data from disk:
109
+ can use ``dbentry.get()`` to load IDS data from disk:
123
110
 
124
111
  .. code-block:: python
125
112
 
@@ -146,7 +133,7 @@ In IMAS-Python you do this as follows:
146
133
 
147
134
  To load an IDS from disk, you need to specify the same file information as
148
135
  when storing the IDS. Once the data entry is opened, you
149
- can use ``<IDS>.get()`` to load IDS data from disk:
136
+ can use ``dbentry.get()`` to load IDS data from disk:
150
137
 
151
138
  .. code-block:: python
152
139
 
@@ -154,3 +141,26 @@ can use ``<IDS>.get()`` to load IDS data from disk:
154
141
  >>> dbentry2 = imas.DBEntry("mypulsefile.nc","r")
155
142
  >>> core_profiles2 = dbentry2.get("core_profiles")
156
143
  >>> print(core_profiles2.ids_properties.comment.value)
144
+
145
+
146
+ Data Entry API overview
147
+ '''''''''''''''''''''''
148
+
149
+ See the documentation of :py:class:`imas.DBEntry <imas.db_entry.DBEntry>` for more
150
+ details on reading and writing IDSs to disk. Useful functions include:
151
+
152
+ - :py:meth:`~imas.db_entry.DBEntry.put` and :py:meth:`~imas.db_entry.DBEntry.put_slice`
153
+ to write a full IDS or write append a time slice to existing data.
154
+ - :py:meth:`~imas.db_entry.DBEntry.get`, :py:meth:`~imas.db_entry.DBEntry.get_slice` and
155
+ :py:meth:`~imas.db_entry.DBEntry.get_sample` to read all time slices, a single time
156
+ slice, or a sample of time slices from disk. ``get_slice()`` and ``get_sample()`` can
157
+ also interpolate data to a requested point in time.
158
+
159
+ All three ``get()`` methods have a ``lazy`` mode, which will only load data from disk
160
+ when you need it. This can greatly speed up data access in some scenarios. See
161
+ :ref:`Lazy loading` for more details.
162
+ - :py:meth:`~imas.db_entry.DBEntry.list_all_occurrences` to query whether there are any
163
+ occurrences of a certain IDS stored on disk.
164
+ - :py:meth:`~imas.db_entry.DBEntry.list_filled_paths` to query which Data Dictionary
165
+ paths have data filled inside a specific IDS.
166
+
@@ -290,24 +290,17 @@ you may see the following error:
290
290
  Dictionary version of the DBEntry (3.42.0). This is not supported when using the
291
291
  UDA backend.
292
292
 
293
- There are three possible workarounds. The first two require passing an additional option
293
+ There are two possible workarounds. The first one requires passing an additional option
294
294
  in the IMAS UDA URI: please see the `imas-core documentation
295
295
  <https://imas-core.readthedocs.io/en/stable/user_guide/backends_guide.html#query-keys-specific-for-the-uda-backend>`__
296
- for more details on these URI options.
296
+ for more details on URI options.
297
297
 
298
298
  1. Use UDA fetch to bypass the cache problem. You can do this by appending ``&fetch=1``
299
299
  to the URI when you create the :py:class:`~imas.db_entry.DBEntry`.
300
300
 
301
301
  Note that this will download the entire IDS files from the remote server, this may
302
302
  not be desired if you only want to read a single time slice.
303
- 2. Disable the UDA cache. You can do this by appending ``&cache_mode=none`` to the URI
304
- when you create the :py:class:`~imas.db_entry.DBEntry`.
305
-
306
- Note that this may make the ``get()`` (a lot) slower, since a separate request needs
307
- to be sent to the remote UDA server for every data variable. However, this may still
308
- be the best performing option if you are only interested in a subset of all the data
309
- in an IDS (and use :ref:`lazy loading`).
310
- 3. Explicitly provide the data dictionary version when you create the
303
+ 2. Explicitly provide the data dictionary version when you create the
311
304
  :py:class:`~imas.db_entry.DBEntry`, setting it to match the Data Dictionary version
312
305
  of the data you want to load. To obtain the version of the data on the remote server
313
306
  from the field `ids_properties.put_version.data_dictionary` via a _lazy_ ``get()``
@@ -316,7 +309,7 @@ for more details on these URI options.
316
309
  Note that you may need to call ``imas.convert_ids`` to convert the IDS to your
317
310
  desired Data Dictionary version.
318
311
 
319
- All three possible workarounds are shown in the examples below:
312
+ The two possible workarounds are shown in the examples below:
320
313
 
321
314
  .. md-tab-set::
322
315
 
@@ -346,20 +339,7 @@ All three possible workarounds are shown in the examples below:
346
339
  with imas.DBEntry(URI, "r") as entry:
347
340
  cp = entry.get("core_profiles")
348
341
 
349
- .. md-tab-item:: 2. Disable the UDA cache
350
-
351
- .. code-block:: python
352
-
353
- import imas
354
-
355
- URI = (
356
- "imas://uda.iter.org:56565/uda?backend=hdf5"
357
- "&path=/work/imas/shared/imasdb/ITER/3/121013/50&cache_mode=none"
358
- )
359
- with imas.DBEntry(URI, "r") as entry:
360
- cp = entry.get("core_profiles")
361
-
362
- .. md-tab-item:: 3. Explicitly provide the DD version
342
+ .. md-tab-item:: 2. Explicitly provide the DD version
363
343
 
364
344
  .. code-block:: python
365
345
 
@@ -183,3 +183,41 @@ specific paths inside the IDS. The latter variant can also be combined with
183
183
  # profiles_1d.grid.rho_tor
184
184
  # profiles_1d.grid.rho_tor_norm
185
185
  # profiles_1d.grid.psi
186
+
187
+
188
+ .. _`Store Xarray Datasets in IMAS-compatible netCDF file`:
189
+
190
+ Store Xarray Datasets in IMAS-compatible netCDF file
191
+ ''''''''''''''''''''''''''''''''''''''''''''''''''''
192
+
193
+ .. versionadded:: 2.3.0 :py:meth:`~imas.util.to_xarray` now includes the required
194
+ metadata to load the IDS from a netCDF file.
195
+
196
+ The following snippet shows how to store an IMAS Xarray dataset in an IMAS-compatible
197
+ netCDF file. The group name in the netCDF file must correspond to ``<IDS
198
+ Name>/<occurrence>`` (``core_profiles/0`` in the snippet).
199
+
200
+ .. code-block:: python
201
+ :caption: Store IMAS Xarray dataset in an IMAS-compatible netCDF file
202
+
203
+ import imas.training
204
+ import netCDF4
205
+
206
+ with imas.training.get_training_db_entry() as training_entry:
207
+ core_profiles = training_entry.get("core_profiles")
208
+ xrds = imas.util.to_xarray(core_profiles)
209
+
210
+ # Store the xarray dataset in an IMAS-compatible netCDF dataset
211
+ filename = "data.nc"
212
+ xrds.to_netcdf(
213
+ filename,
214
+ group="core_profiles/0", # Update to the correct IDS name and occurrence
215
+ # auto_complex=True, # Uncomment if the dataset contains complex data
216
+ )
217
+ # Set global DD version metadata
218
+ with netCDF4.Dataset(filename, "a") as ds:
219
+ ds.data_dictionary_version = imas.util.get_data_dictionary_version(ids)
220
+
221
+ # Test that we can get the IDS from the netCDF file
222
+ with imas.DBEntry(filename, "r") as entry:
223
+ ids2 = entry.get("core_profiles")
@@ -8,7 +8,7 @@ from imas.backends.netcdf.ids_tensorizer import IDSTensorizer
8
8
  from imas.ids_data_type import IDSDataType
9
9
 
10
10
  fillvals = {
11
- IDSDataType.INT: -(2**31) + 1,
11
+ IDSDataType.INT: numpy.int32(-(2**31) + 1),
12
12
  IDSDataType.STR: "",
13
13
  IDSDataType.FLT: numpy.nan,
14
14
  IDSDataType.CPX: numpy.nan * (1 + 1j),
@@ -50,21 +50,28 @@ def to_xarray(ids: IDSToplevel, *paths: str) -> xarray.Dataset:
50
50
  var_name = path.replace("/", ".")
51
51
  metadata = ids.metadata[path]
52
52
  if metadata.data_type in (IDSDataType.STRUCTURE, IDSDataType.STRUCT_ARRAY):
53
- continue # We don't store these in xarray
54
-
55
- dimensions = tensorizer.ncmeta.get_dimensions(path, tensorizer.homogeneous_time)
56
- data = tensorizer.tensorize(path, fillvals[metadata.data_type])
57
-
58
- attrs = dict(documentation=metadata.documentation)
59
- if metadata.units:
60
- attrs["units"] = metadata.units
61
- coordinates = tensorizer.filter_coordinates(path)
62
- if coordinates:
63
- coordinate_names.update(coordinates.split(" "))
64
- attrs["coordinates"] = coordinates
53
+ # Metadata variables for (arrays of) structures
54
+ if paths and path not in paths:
55
+ continue
56
+ dimensions = ()
57
+ data = b""
58
+ else:
59
+ dimensions = tensorizer.get_dimensions(path)
60
+ data = tensorizer.tensorize(path, fillvals[metadata.data_type])
65
61
 
62
+ attrs = tensorizer.get_attributes(path, fillvals)
63
+ if "coordinates" in attrs:
64
+ coordinate_names.update(attrs["coordinates"].split(" "))
66
65
  data_vars[var_name] = (dimensions, data, attrs)
67
66
 
67
+ # :shape array for sparse data
68
+ if path in tensorizer.shapes and metadata.ndim:
69
+ shape_name = f"{var_name}:shape"
70
+ dimensions = tensorizer.get_shape_dimensions(path)
71
+ data = tensorizer.shapes[path]
72
+ attrs = tensorizer.get_shape_attributes(var_name)
73
+ data_vars[shape_name] = (dimensions, data, attrs)
74
+
68
75
  # Remove coordinates from data_vars and put in coordinates mapping:
69
76
  coordinates = {}
70
77
  for coordinate_name in coordinate_names:
@@ -0,0 +1,24 @@
1
+ # file generated by vcs-versioning
2
+ # don't change, don't track in version control
3
+ from __future__ import annotations
4
+
5
+ __all__ = [
6
+ "__version__",
7
+ "__version_tuple__",
8
+ "version",
9
+ "version_tuple",
10
+ "__commit_id__",
11
+ "commit_id",
12
+ ]
13
+
14
+ version: str
15
+ __version__: str
16
+ __version_tuple__: tuple[int | str, ...]
17
+ version_tuple: tuple[int | str, ...]
18
+ commit_id: str | None
19
+ __commit_id__: str | None
20
+
21
+ __version__ = version = '2.3.0'
22
+ __version_tuple__ = version_tuple = (2, 3, 0)
23
+
24
+ __commit_id__ = commit_id = 'g474bc8bbe'
@@ -26,8 +26,6 @@ equilibrium/vacuum_toroidal_field/b0
26
26
  dim: 1
27
27
  size: 3
28
28
  -5.2999999999999998e+00 -5.2999999999999998e+00 -5.2999999999999998e+00
29
- equilibrium/grids_ggd
30
- size: 1
31
29
  equilibrium/time_slice
32
30
  size: 3
33
31
  equilibrium/time_slice[0]/boundary/outline/r
@@ -26,8 +26,6 @@ equilibrium/vacuum_toroidal_field/b0
26
26
  dim: 1
27
27
  size: 3
28
28
  -5.2999999999999998e+00 -5.2999999999999998e+00 -5.2999999999999998e+00
29
- equilibrium/grids_ggd
30
- size: 1
31
29
  equilibrium/time_slice
32
30
  size: 3
33
31
  equilibrium/time_slice[0]/boundary/outline/r
@@ -120,3 +120,11 @@ class DBEntryImpl(ABC):
120
120
  @abstractmethod
121
121
  def list_all_occurrences(self, ids_name: str) -> List[int]:
122
122
  """Implement DBEntry.list_all_occurrences()"""
123
+
124
+ @abstractmethod
125
+ def list_filled_paths(self, ids_name: str, occurrence: int) -> List[str]:
126
+ """Implement DBEntry.list_filled_paths().
127
+
128
+ N.B. DD conversion is handled in DBEntry.list_filled_paths(), this method
129
+ returns the data paths as stored on-disk.
130
+ """
@@ -174,6 +174,17 @@ class ALContext:
174
174
  return list(occurrences)
175
175
  return []
176
176
 
177
+ def list_filled_paths(self, path: str) -> List[str]:
178
+ """List all filled paths in an IDS.
179
+
180
+ Args:
181
+ path: IDS and occurrence as a string: <IDS>[/<occurrence>]
182
+ """
183
+ status, result = ll_interface.list_filled_paths(self.ctx, path)
184
+ if status != 0:
185
+ raise LowlevelError(f"list filled paths for {path!r}", status)
186
+ return result
187
+
177
188
  def close(self):
178
189
  """Close this ALContext."""
179
190
  ll_interface.end_action(self.ctx)
@@ -364,6 +364,19 @@ class ALDBEntryImpl(DBEntryImpl):
364
364
  ) from None
365
365
  return occurrence_list
366
366
 
367
+ def list_filled_paths(self, ids_name: str, occurrence: int) -> List[str]:
368
+ if self._db_ctx is None:
369
+ raise RuntimeError("Database entry is not open.")
370
+ ll_path = ids_name
371
+ if occurrence != 0:
372
+ ll_path += f"/{occurrence}"
373
+ paths = self._db_ctx.list_filled_paths(ll_path)
374
+ if not paths:
375
+ raise DataEntryException(
376
+ f"IDS {ids_name!r}, occurrence {occurrence} is empty."
377
+ )
378
+ return paths
379
+
367
380
  def _check_uda_warnings(self, lazy: bool) -> None:
368
381
  """Various checks / warnings for the UDA backend."""
369
382
  cache_mode = self._querydict.get("cache_mode")
@@ -166,6 +166,11 @@ class LowlevelInterface:
166
166
  ):
167
167
  raise self._minimal_version("5.4")
168
168
 
169
+ # New method in AL 5.7
170
+
171
+ def list_filled_paths(self, ctx, path):
172
+ raise self._minimal_version("5.7")
173
+
169
174
 
170
175
  # Dummy documentation for interface:
171
176
  for funcname in dir(LowlevelInterface):
@@ -92,6 +92,14 @@ class NCDBEntryImpl(DBEntryImpl):
92
92
  )
93
93
  self._dataset.close()
94
94
 
95
+ def _get_group(self, ids_name: str, occurrence: int) -> "netCDF4.Group":
96
+ try:
97
+ return self._dataset[f"{ids_name}/{occurrence}"]
98
+ except LookupError as exc:
99
+ raise DataEntryException(
100
+ f"IDS {ids_name!r}, occurrence {occurrence} is not found."
101
+ ) from exc
102
+
95
103
  def get(
96
104
  self,
97
105
  ids_name: str,
@@ -110,12 +118,7 @@ class NCDBEntryImpl(DBEntryImpl):
110
118
  raise NotImplementedError(f"`{func}` is not available for netCDF files.")
111
119
 
112
120
  # Check if the IDS/occurrence exists, and obtain the group it is stored in
113
- try:
114
- group = self._dataset[f"{ids_name}/{occurrence}"]
115
- except KeyError:
116
- raise DataEntryException(
117
- f"IDS {ids_name!r}, occurrence {occurrence} is not found."
118
- )
121
+ group = self._get_group(ids_name, occurrence)
119
122
 
120
123
  # Load data into the destination IDS
121
124
  if self._ds_factory.dd_version == destination._dd_version:
@@ -183,3 +186,17 @@ class NCDBEntryImpl(DBEntryImpl):
183
186
 
184
187
  occurrence_list.sort()
185
188
  return occurrence_list
189
+
190
+ def list_filled_paths(self, ids_name: str, occurrence: int) -> List[str]:
191
+ # Check if the IDS/occurrence exists, and obtain the group it is stored in
192
+ group = self._get_group(ids_name, occurrence)
193
+
194
+ result = []
195
+ for name, variable in group.variables.items():
196
+ if variable.ndim == 0 and variable.dtype == "S1":
197
+ continue # (Array of) Structure metadata node, no data
198
+ if name.endswith(":shape"):
199
+ continue # Shape data, not a DD path
200
+ result.append(name.replace(".", "/"))
201
+
202
+ return result