junifer 0.0.7.dev332__py3-none-any.whl → 0.0.8__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 (293) hide show
  1. junifer/_version.py +9 -19
  2. junifer/api/__init__.pyi +17 -2
  3. junifer/api/functions.py +222 -39
  4. junifer/api/queue_context/__init__.pyi +11 -3
  5. junifer/api/queue_context/gnu_parallel_local_adapter.py +81 -120
  6. junifer/api/queue_context/htcondor_adapter.py +118 -181
  7. junifer/api/queue_context/queue_context_adapter.py +51 -7
  8. junifer/api/queue_context/tests/test_gnu_parallel_local_adapter.py +10 -35
  9. junifer/api/queue_context/tests/test_htcondor_adapter.py +13 -50
  10. junifer/api/res/fsl/run_fsl_docker.sh +4 -0
  11. junifer/api/tests/test_functions.py +863 -36
  12. junifer/cli/__init__.py +1 -7
  13. junifer/cli/cli.py +41 -22
  14. junifer/cli/parser.py +23 -147
  15. junifer/cli/tests/data/gmd_mean.yaml +6 -6
  16. junifer/cli/tests/data/gmd_mean_htcondor.yaml +6 -5
  17. junifer/cli/tests/data/partly_cloudy_agg_mean_tian.yml +1 -0
  18. junifer/cli/tests/test_cli.py +120 -4
  19. junifer/cli/tests/test_cli_utils.py +23 -6
  20. junifer/cli/utils.py +14 -9
  21. junifer/configs/__init__.py +5 -0
  22. junifer/configs/__init__.pyi +0 -0
  23. junifer/configs/juseless/datagrabbers/__init__.pyi +4 -2
  24. junifer/configs/juseless/datagrabbers/aomic_id1000_vbm.py +18 -24
  25. junifer/configs/juseless/datagrabbers/camcan_vbm.py +20 -27
  26. junifer/configs/juseless/datagrabbers/ixi_vbm.py +44 -52
  27. junifer/configs/juseless/datagrabbers/tests/test_ixi_vbm.py +0 -7
  28. junifer/configs/juseless/datagrabbers/tests/test_ucla.py +2 -19
  29. junifer/configs/juseless/datagrabbers/ucla.py +111 -104
  30. junifer/configs/juseless/datagrabbers/ukb_vbm.py +19 -25
  31. junifer/configs/py.typed +0 -0
  32. junifer/conftest.py +63 -24
  33. junifer/data/_dispatch.py +9 -19
  34. junifer/data/coordinates/_ants_coordinates_warper.py +4 -1
  35. junifer/data/coordinates/_coordinates.py +51 -6
  36. junifer/data/coordinates/_fsl_coordinates_warper.py +4 -1
  37. junifer/data/coordinates/tests/test_coordinates.py +15 -3
  38. junifer/data/coordinates/tests/test_coordinates_names.py +37 -0
  39. junifer/data/maps/_ants_maps_warper.py +18 -12
  40. junifer/data/maps/_fsl_maps_warper.py +7 -3
  41. junifer/data/maps/_maps.py +12 -8
  42. junifer/data/maps/tests/test_maps.py +13 -21
  43. junifer/data/masks/_ants_mask_warper.py +18 -12
  44. junifer/data/masks/_fsl_mask_warper.py +7 -3
  45. junifer/data/masks/_masks.py +15 -12
  46. junifer/data/masks/tests/test_masks.py +20 -17
  47. junifer/data/parcellations/_ants_parcellation_warper.py +18 -12
  48. junifer/data/parcellations/_fsl_parcellation_warper.py +7 -5
  49. junifer/data/parcellations/_parcellations.py +125 -91
  50. junifer/data/parcellations/tests/test_parcellations.py +122 -1
  51. junifer/data/template_spaces.py +117 -50
  52. junifer/data/tests/test_template_spaces.py +10 -7
  53. junifer/data/utils.py +10 -8
  54. junifer/datagrabber/__init__.pyi +38 -5
  55. junifer/datagrabber/aomic/__init__.pyi +8 -1
  56. junifer/datagrabber/aomic/_types.py +22 -0
  57. junifer/datagrabber/aomic/id1000.py +193 -183
  58. junifer/datagrabber/aomic/piop1.py +215 -259
  59. junifer/datagrabber/aomic/piop2.py +211 -244
  60. junifer/datagrabber/aomic/tests/test_id1000.py +70 -53
  61. junifer/datagrabber/aomic/tests/test_piop1.py +98 -102
  62. junifer/datagrabber/aomic/tests/test_piop2.py +88 -85
  63. junifer/datagrabber/base.py +253 -79
  64. junifer/datagrabber/datalad_base.py +127 -76
  65. junifer/datagrabber/dmcc13_benchmark.py +204 -289
  66. junifer/datagrabber/hcp1200/__init__.pyi +7 -2
  67. junifer/datagrabber/hcp1200/datalad_hcp1200.py +61 -40
  68. junifer/datagrabber/hcp1200/hcp1200.py +151 -164
  69. junifer/datagrabber/hcp1200/tests/test_hcp1200.py +116 -128
  70. junifer/datagrabber/multiple.py +183 -63
  71. junifer/datagrabber/pattern.py +358 -227
  72. junifer/datagrabber/pattern_datalad.py +84 -124
  73. junifer/datagrabber/pattern_validation_mixin.py +22 -50
  74. junifer/datagrabber/tests/test_base.py +17 -4
  75. junifer/datagrabber/tests/test_datalad_base.py +20 -27
  76. junifer/datagrabber/tests/test_dmcc13_benchmark.py +110 -122
  77. junifer/datagrabber/tests/test_multiple.py +293 -31
  78. junifer/datagrabber/tests/test_pattern.py +577 -18
  79. junifer/datagrabber/tests/test_pattern_datalad.py +177 -107
  80. junifer/datagrabber/tests/test_pattern_validation_mixin.py +9 -51
  81. junifer/datareader/default.py +8 -5
  82. junifer/datareader/tests/test_default_reader.py +1 -1
  83. junifer/external/BrainPrint/.codecov.yml +2 -0
  84. junifer/external/BrainPrint/.codespellignore +2 -0
  85. junifer/external/BrainPrint/.github/ISSUE_TEMPLATE/bug-report.md +45 -0
  86. junifer/external/BrainPrint/.github/ISSUE_TEMPLATE/documentation.md +12 -0
  87. junifer/external/BrainPrint/.github/ISSUE_TEMPLATE/feature-request.md +24 -0
  88. junifer/external/BrainPrint/.github/ISSUE_TEMPLATE/questions-help-support.md +28 -0
  89. junifer/external/BrainPrint/.github/dependabot.yml +6 -0
  90. junifer/external/BrainPrint/.github/workflows/build.yml +53 -0
  91. junifer/external/BrainPrint/.github/workflows/code-style.yml +44 -0
  92. junifer/external/BrainPrint/.github/workflows/doc.yml +65 -0
  93. junifer/external/BrainPrint/.github/workflows/publish.yml +31 -0
  94. junifer/external/BrainPrint/.github/workflows/pytest.yml +54 -0
  95. junifer/external/BrainPrint/.gitignore +123 -0
  96. junifer/external/BrainPrint/LICENSE +21 -0
  97. junifer/external/BrainPrint/README.md +108 -0
  98. junifer/external/BrainPrint/brainprint/cli/__init__.py +11 -0
  99. junifer/external/BrainPrint/brainprint/cli/help_text.py +169 -0
  100. junifer/external/BrainPrint/brainprint/cli/parser.py +150 -0
  101. junifer/external/BrainPrint/brainprint/cli/utils.py +14 -0
  102. junifer/external/BrainPrint/brainprint/commands/__init__.py +0 -0
  103. junifer/external/BrainPrint/brainprint/commands/sys_info.py +18 -0
  104. junifer/external/BrainPrint/brainprint/utils/tests/__init__.py +0 -0
  105. junifer/external/BrainPrint/brainprint/utils/tests/test_config.py +33 -0
  106. junifer/external/BrainPrint/doc/Makefile +20 -0
  107. junifer/external/BrainPrint/doc/_static/.gitkeep +0 -0
  108. junifer/external/BrainPrint/doc/_templates/autosummary/class.rst +10 -0
  109. junifer/external/BrainPrint/doc/_templates/autosummary/function.rst +8 -0
  110. junifer/external/BrainPrint/doc/_templates/autosummary/module.rst +6 -0
  111. junifer/external/BrainPrint/doc/api/index.rst +11 -0
  112. junifer/external/BrainPrint/doc/conf.py +272 -0
  113. junifer/external/BrainPrint/doc/index.rst +140 -0
  114. junifer/external/BrainPrint/doc/links.inc +36 -0
  115. junifer/external/BrainPrint/doc/make.bat +35 -0
  116. junifer/external/BrainPrint/doc/references.bib +23 -0
  117. junifer/external/BrainPrint/pyproject.toml +170 -0
  118. junifer/external/BrainPrint/setup.py +3 -0
  119. junifer/external/__init__.py +5 -0
  120. junifer/external/__init__.pyi +0 -0
  121. junifer/external/nilearn/junifer_connectivity_measure.py +95 -39
  122. junifer/external/nilearn/junifer_nifti_spheres_masker.py +226 -67
  123. junifer/external/nilearn/tests/test_junifer_connectivity_measure.py +39 -27
  124. junifer/external/nilearn/tests/test_junifer_nifti_spheres_masker.py +231 -21
  125. junifer/external/py.typed +0 -0
  126. junifer/markers/__init__.pyi +6 -3
  127. junifer/markers/base.py +126 -76
  128. junifer/markers/brainprint.py +30 -39
  129. junifer/markers/complexity/__init__.py +20 -3
  130. junifer/markers/complexity/complexity_base.py +40 -41
  131. junifer/markers/complexity/hurst_exponent.py +22 -35
  132. junifer/markers/complexity/multiscale_entropy_auc.py +53 -41
  133. junifer/markers/complexity/perm_entropy.py +22 -36
  134. junifer/markers/complexity/range_entropy.py +22 -35
  135. junifer/markers/complexity/range_entropy_auc.py +27 -36
  136. junifer/markers/complexity/sample_entropy.py +22 -36
  137. junifer/markers/complexity/tests/test_complexity_registry.py +48 -0
  138. junifer/markers/complexity/tests/test_hurst_exponent.py +47 -36
  139. junifer/markers/complexity/tests/test_multiscale_entropy_auc.py +50 -36
  140. junifer/markers/complexity/tests/test_perm_entropy.py +48 -36
  141. junifer/markers/complexity/tests/test_range_entropy.py +47 -36
  142. junifer/markers/complexity/tests/test_range_entropy_auc.py +47 -36
  143. junifer/markers/complexity/tests/test_sample_entropy.py +48 -36
  144. junifer/markers/complexity/tests/test_weighted_perm_entropy.py +50 -36
  145. junifer/markers/complexity/weighted_perm_entropy.py +22 -36
  146. junifer/markers/ets_rss.py +35 -31
  147. junifer/markers/falff/__init__.pyi +7 -1
  148. junifer/markers/falff/_afni_falff.py +22 -9
  149. junifer/markers/falff/_junifer_falff.py +47 -31
  150. junifer/markers/falff/falff_base.py +80 -60
  151. junifer/markers/falff/falff_maps.py +17 -41
  152. junifer/markers/falff/falff_parcels.py +26 -51
  153. junifer/markers/falff/falff_spheres.py +34 -61
  154. junifer/markers/falff/tests/test_falff_maps.py +20 -23
  155. junifer/markers/falff/tests/test_falff_mask.py +99 -0
  156. junifer/markers/falff/tests/test_falff_parcels.py +14 -10
  157. junifer/markers/falff/tests/test_falff_spheres.py +14 -10
  158. junifer/markers/functional_connectivity/crossparcellation_functional_connectivity.py +32 -34
  159. junifer/markers/functional_connectivity/edge_functional_connectivity_maps.py +12 -25
  160. junifer/markers/functional_connectivity/edge_functional_connectivity_parcels.py +19 -34
  161. junifer/markers/functional_connectivity/edge_functional_connectivity_spheres.py +24 -44
  162. junifer/markers/functional_connectivity/functional_connectivity_base.py +50 -40
  163. junifer/markers/functional_connectivity/functional_connectivity_maps.py +12 -25
  164. junifer/markers/functional_connectivity/functional_connectivity_parcels.py +19 -34
  165. junifer/markers/functional_connectivity/functional_connectivity_spheres.py +24 -45
  166. junifer/markers/functional_connectivity/tests/test_crossparcellation_functional_connectivity.py +21 -22
  167. junifer/markers/functional_connectivity/tests/test_edge_functional_connectivity_maps.py +8 -7
  168. junifer/markers/functional_connectivity/tests/test_edge_functional_connectivity_parcels.py +8 -4
  169. junifer/markers/functional_connectivity/tests/test_edge_functional_connectivity_spheres.py +8 -4
  170. junifer/markers/functional_connectivity/tests/test_functional_connectivity_maps.py +8 -7
  171. junifer/markers/functional_connectivity/tests/test_functional_connectivity_parcels.py +9 -5
  172. junifer/markers/functional_connectivity/tests/test_functional_connectivity_spheres.py +8 -12
  173. junifer/markers/maps_aggregation.py +77 -55
  174. junifer/markers/parcel_aggregation.py +91 -70
  175. junifer/markers/reho/__init__.pyi +7 -1
  176. junifer/markers/reho/_afni_reho.py +23 -14
  177. junifer/markers/reho/_junifer_reho.py +112 -123
  178. junifer/markers/reho/reho_base.py +115 -37
  179. junifer/markers/reho/reho_maps.py +18 -32
  180. junifer/markers/reho/reho_parcels.py +26 -41
  181. junifer/markers/reho/reho_spheres.py +33 -54
  182. junifer/markers/reho/tests/test_junifer_reho.py +178 -0
  183. junifer/markers/reho/tests/test_reho_maps.py +27 -25
  184. junifer/markers/reho/tests/test_reho_parcels.py +28 -22
  185. junifer/markers/reho/tests/test_reho_spheres.py +16 -12
  186. junifer/markers/sphere_aggregation.py +88 -72
  187. junifer/markers/temporal_snr/temporal_snr_base.py +32 -30
  188. junifer/markers/temporal_snr/temporal_snr_maps.py +9 -18
  189. junifer/markers/temporal_snr/temporal_snr_parcels.py +19 -27
  190. junifer/markers/temporal_snr/temporal_snr_spheres.py +27 -41
  191. junifer/markers/temporal_snr/tests/test_temporal_snr_base.py +2 -2
  192. junifer/markers/temporal_snr/tests/test_temporal_snr_maps.py +17 -22
  193. junifer/markers/temporal_snr/tests/test_temporal_snr_parcels.py +11 -3
  194. junifer/markers/temporal_snr/tests/test_temporal_snr_spheres.py +9 -9
  195. junifer/markers/tests/test_brainprint.py +10 -9
  196. junifer/markers/tests/test_ets_rss.py +7 -3
  197. junifer/markers/tests/test_lost_regions.py +279 -0
  198. junifer/markers/tests/test_maps_aggregation.py +67 -114
  199. junifer/markers/tests/test_marker_utils.py +40 -1
  200. junifer/markers/tests/test_markers_base.py +275 -6
  201. junifer/markers/tests/test_parcel_aggregation.py +91 -53
  202. junifer/markers/tests/test_sphere_aggregation.py +53 -47
  203. junifer/markers/utils.py +267 -5
  204. junifer/onthefly/__init__.py +2 -3
  205. junifer/onthefly/__init__.pyi +4 -0
  206. junifer/onthefly/_brainprint.py +3 -5
  207. junifer/onthefly/py.typed +0 -0
  208. junifer/onthefly/read_transform.py +11 -9
  209. junifer/onthefly/tests/test_read_transform.py +7 -7
  210. junifer/pipeline/__init__.pyi +4 -2
  211. junifer/pipeline/marker_collection.py +14 -10
  212. junifer/pipeline/pipeline_component_registry.py +25 -6
  213. junifer/pipeline/pipeline_step_mixin.py +5 -12
  214. junifer/pipeline/tests/test_data_object_dumper.py +10 -10
  215. junifer/pipeline/tests/test_marker_collection.py +145 -168
  216. junifer/pipeline/tests/test_pipeline_component_registry.py +52 -8
  217. junifer/pipeline/tests/test_pipeline_step_mixin.py +12 -26
  218. junifer/pipeline/tests/test_update_meta_mixin.py +4 -5
  219. junifer/pipeline/tests/test_workdir_manager.py +39 -0
  220. junifer/pipeline/update_meta_mixin.py +13 -10
  221. junifer/pipeline/utils.py +22 -17
  222. junifer/pipeline/workdir_manager.py +41 -32
  223. junifer/preprocess/__init__.pyi +9 -4
  224. junifer/preprocess/_temporal_filter.py +34 -33
  225. junifer/preprocess/_temporal_slicer.py +17 -30
  226. junifer/preprocess/base.py +99 -55
  227. junifer/preprocess/confounds/__init__.pyi +10 -2
  228. junifer/preprocess/confounds/fmriprep_confound_remover.py +87 -109
  229. junifer/preprocess/confounds/tests/test_fmriprep_confound_remover.py +64 -45
  230. junifer/preprocess/smoothing/__init__.pyi +2 -2
  231. junifer/preprocess/smoothing/_afni_smoothing.py +8 -7
  232. junifer/preprocess/smoothing/_fsl_smoothing.py +6 -4
  233. junifer/preprocess/smoothing/_nilearn_smoothing.py +7 -5
  234. junifer/preprocess/smoothing/smoothing.py +59 -40
  235. junifer/preprocess/smoothing/tests/test_smoothing.py +28 -8
  236. junifer/preprocess/tests/test_preprocess_base.py +17 -9
  237. junifer/preprocess/tests/test_temporal_filter.py +37 -16
  238. junifer/preprocess/tests/test_temporal_slicer.py +12 -12
  239. junifer/preprocess/warping/__init__.pyi +2 -2
  240. junifer/preprocess/warping/_ants_warper.py +56 -40
  241. junifer/preprocess/warping/_fsl_warper.py +49 -36
  242. junifer/preprocess/warping/_utils.py +106 -0
  243. junifer/preprocess/warping/space_warper.py +99 -98
  244. junifer/preprocess/warping/tests/test_space_warper.py +46 -41
  245. junifer/preprocess/warping/tests/test_warping_utils.py +163 -0
  246. junifer/stats.py +46 -34
  247. junifer/storage/__init__.pyi +8 -4
  248. junifer/storage/base.py +129 -64
  249. junifer/storage/hdf5.py +307 -199
  250. junifer/storage/pandas_base.py +46 -24
  251. junifer/storage/sqlite.py +99 -62
  252. junifer/storage/tests/data/collected_h5io_fork.hdf5 +0 -0
  253. junifer/storage/tests/test_hdf5.py +147 -12
  254. junifer/storage/tests/test_repeated_storage.py +293 -0
  255. junifer/storage/tests/test_sqlite.py +9 -20
  256. junifer/storage/tests/test_storage_base.py +18 -21
  257. junifer/storage/tests/test_utils.py +83 -22
  258. junifer/storage/utils.py +58 -38
  259. junifer/testing/__init__.pyi +2 -2
  260. junifer/testing/datagrabbers.py +480 -44
  261. junifer/testing/registry.py +12 -0
  262. junifer/testing/tests/test_adhdtesting_datagrabber.py +24 -0
  263. junifer/testing/tests/test_oasisvmbtesting_datagrabber.py +5 -0
  264. junifer/testing/tests/test_partlycloudytesting_datagrabber.py +52 -0
  265. junifer/testing/tests/test_spmauditory_datagrabber.py +16 -0
  266. junifer/testing/tests/test_testing_registry.py +31 -0
  267. junifer/testing/tests/test_testing_utils.py +35 -0
  268. junifer/testing/tests/test_uclacnpvbmtesting_datagrabber.py +81 -0
  269. junifer/testing/utils.py +33 -1
  270. junifer/tests/test_stats.py +1 -5
  271. junifer/typing/__init__.pyi +2 -0
  272. junifer/typing/_typing.py +34 -19
  273. junifer/typing/py.typed +0 -0
  274. junifer/utils/__init__.pyi +10 -1
  275. junifer/utils/_config.py +1 -2
  276. junifer/utils/helpers.py +68 -2
  277. junifer/utils/logging.py +31 -7
  278. junifer/utils/tests/test_helpers.py +36 -1
  279. {junifer-0.0.7.dev332.dist-info → junifer-0.0.8.dist-info}/METADATA +43 -35
  280. junifer-0.0.8.dist-info/RECORD +402 -0
  281. {junifer-0.0.7.dev332.dist-info → junifer-0.0.8.dist-info}/WHEEL +1 -1
  282. junifer/cli/tests/test_parser.py +0 -280
  283. junifer/external/h5io/h5io/__init__.py +0 -15
  284. junifer/external/h5io/h5io/_h5io.py +0 -767
  285. junifer/external/h5io/h5io/_version.py +0 -1
  286. junifer/external/h5io/h5io/chunked_array.py +0 -94
  287. junifer/external/h5io/h5io/chunked_list.py +0 -65
  288. junifer/markers/complexity/__init__.pyi +0 -17
  289. junifer-0.0.7.dev332.dist-info/RECORD +0 -353
  290. {junifer-0.0.7.dev332.dist-info → junifer-0.0.8.dist-info}/entry_points.txt +0 -0
  291. {junifer-0.0.7.dev332.dist-info → junifer-0.0.8.dist-info}/licenses/AUTHORS.rst +0 -0
  292. {junifer-0.0.7.dev332.dist-info → junifer-0.0.8.dist-info}/licenses/LICENSE.md +0 -0
  293. {junifer-0.0.7.dev332.dist-info → junifer-0.0.8.dist-info}/top_level.txt +0 -0
@@ -0,0 +1,37 @@
1
+ """Provide tests for coordinates VOI names sanitizing."""
2
+
3
+ # Authors: Federico Raimondo <f.raimondo@fz-juelich.de>
4
+ # License: AGPL
5
+
6
+ import pytest
7
+
8
+ from junifer.data.coordinates._coordinates import _sanitize_names
9
+
10
+
11
+ @pytest.mark.parametrize(
12
+ "names, expected",
13
+ [
14
+ (["a", "b", "c"], ["a", "b", "c"]),
15
+ (["inf cerebellum", "vmPFC"], ["inf_cerebellum", "vmPFC"]),
16
+ (["a", "b", "a", "c", "a"], ["a-1", "b", "a-2", "c", "a-3"]),
17
+ (
18
+ ["mid insula", "mid insula", "x"],
19
+ ["mid_insula-1", "mid_insula-2", "x"],
20
+ ),
21
+ ([1, 2, 3], [1, 2, 3]),
22
+ (["a", "a", "a-1"], ["a-2", "a-3", "a-1"]),
23
+ (["a-1", "a", "a"], ["a-1", "a-2", "a-3"]),
24
+ ],
25
+ )
26
+ def test_sanitize_names(names: list, expected: list) -> None:
27
+ """Test _sanitize_names.
28
+
29
+ Parameters
30
+ ----------
31
+ names : list
32
+ The parametrized VOI names.
33
+ expected : list
34
+ The parametrized expected sanitized names.
35
+
36
+ """
37
+ assert _sanitize_names(names) == expected
@@ -4,12 +4,13 @@
4
4
  # License: AGPL
5
5
 
6
6
  import uuid
7
- from typing import TYPE_CHECKING, Any, Optional
7
+ from typing import TYPE_CHECKING, Any
8
8
 
9
9
  import nibabel as nib
10
10
 
11
11
  from ...pipeline import WorkDirManager
12
- from ...utils import logger, raise_error, run_ext_cmd
12
+ from ...typing import SpaceLike
13
+ from ...utils import raise_error, run_ext_cmd
13
14
  from ..template_spaces import get_template, get_xfm
14
15
 
15
16
 
@@ -31,10 +32,10 @@ class ANTsMapsWarper:
31
32
  self,
32
33
  maps_name: str,
33
34
  maps_img: "Nifti1Image",
34
- src: str,
35
- dst: str,
35
+ src: SpaceLike,
36
+ dst: SpaceLike,
36
37
  target_data: dict[str, Any],
37
- warp_data: Optional[dict[str, Any]],
38
+ warp_data: dict[str, Any] | None,
38
39
  ) -> "Nifti1Image":
39
40
  """Warp ``maps_img`` to correct space.
40
41
 
@@ -44,10 +45,10 @@ class ANTsMapsWarper:
44
45
  The name of the maps.
45
46
  maps_img : nibabel.nifti1.Nifti1Image
46
47
  The maps image to transform.
47
- src : str
48
+ src : str or Enum
48
49
  The data type or template space to warp from.
49
50
  It should be empty string if ``dst="T1w"``.
50
- dst : str
51
+ dst : str or Enum
51
52
  The data type or template space to warp to.
52
53
  `"T1w"` is the only allowed data type and it uses the resampled T1w
53
54
  found in ``target_data.reference``. The ``"reference"``
@@ -71,6 +72,9 @@ class ANTsMapsWarper:
71
72
  If ``warp_data`` is None when ``dst="T1w"``.
72
73
 
73
74
  """
75
+ # Imported here to avoid circular import
76
+ from ._maps import logger
77
+
74
78
  # Create element-scoped tempdir so that warped maps is
75
79
  # available later as nibabel stores file path reference for
76
80
  # loading on computation
@@ -96,16 +100,17 @@ class ANTsMapsWarper:
96
100
  logger.debug("Using ANTs for maps transformation")
97
101
 
98
102
  # Save existing maps image to a tempfile
99
- prewarp_maps_path = element_tempdir / "prewarp_maps.nii.gz"
103
+ prewarp_maps_path = element_tempdir / "prewarp_maps.nii"
100
104
  nib.save(maps_img, prewarp_maps_path)
101
105
 
102
106
  # Create a tempfile for warped output
103
- warped_maps_path = element_tempdir / "maps_warped.nii.gz"
107
+ warped_maps_path = element_tempdir / "maps_warped.nii"
104
108
  # Set antsApplyTransforms command
105
109
  apply_transforms_cmd = [
106
110
  "antsApplyTransforms",
107
111
  "-d 3",
108
112
  "-e 3",
113
+ "--float 1",
109
114
  "-n LanczosWindowedSinc",
110
115
  f"-i {prewarp_maps_path.resolve()}",
111
116
  # use resampled reference
@@ -129,20 +134,21 @@ class ANTsMapsWarper:
129
134
  extra_input=None,
130
135
  )
131
136
  # Save template to a tempfile
132
- template_space_img_path = element_tempdir / f"{dst}_T1w.nii.gz"
137
+ template_space_img_path = element_tempdir / f"{dst}_T1w.nii"
133
138
  nib.save(template_space_img, template_space_img_path)
134
139
 
135
140
  # Save existing maps image to a tempfile
136
- prewarp_maps_path = element_tempdir / "prewarp_maps.nii.gz"
141
+ prewarp_maps_path = element_tempdir / "prewarp_maps.nii"
137
142
  nib.save(maps_img, prewarp_maps_path)
138
143
 
139
144
  # Create a tempfile for warped output
140
- warped_maps_path = element_tempdir / "maps_warped.nii.gz"
145
+ warped_maps_path = element_tempdir / "maps_warped.nii"
141
146
  # Set antsApplyTransforms command
142
147
  apply_transforms_cmd = [
143
148
  "antsApplyTransforms",
144
149
  "-d 3",
145
150
  "-e 3",
151
+ "--float 1",
146
152
  "-n LanczosWindowedSinc",
147
153
  f"-i {prewarp_maps_path.resolve()}",
148
154
  f"-r {template_space_img_path.resolve()}",
@@ -9,7 +9,7 @@ from typing import TYPE_CHECKING, Any
9
9
  import nibabel as nib
10
10
 
11
11
  from ...pipeline import WorkDirManager
12
- from ...utils import logger, run_ext_cmd
12
+ from ...utils import run_ext_cmd
13
13
 
14
14
 
15
15
  if TYPE_CHECKING:
@@ -53,6 +53,9 @@ class FSLMapsWarper:
53
53
  The transformed maps image.
54
54
 
55
55
  """
56
+ # Imported here to avoid circular import
57
+ from ._maps import logger
58
+
56
59
  logger.debug("Using FSL for maps transformation")
57
60
 
58
61
  # Create element-scoped tempdir so that warped maps is
@@ -63,13 +66,14 @@ class FSLMapsWarper:
63
66
  )
64
67
 
65
68
  # Save existing maps image to a tempfile
66
- prewarp_maps_path = element_tempdir / "prewarp_maps.nii.gz"
69
+ prewarp_maps_path = element_tempdir / "prewarp_maps.nii"
67
70
  nib.save(maps_img, prewarp_maps_path)
68
71
 
69
72
  # Create a tempfile for warped output
70
- warped_maps_path = element_tempdir / "maps_warped.nii.gz"
73
+ warped_maps_path = element_tempdir / "maps_warped.nii"
71
74
  # Set applywarp command
72
75
  applywarp_cmd = [
76
+ "FSLOUTPUTTYPE=NIFTI",
73
77
  "applywarp",
74
78
  "--interp=spline",
75
79
  f"-i {prewarp_maps_path.resolve()}",
@@ -4,14 +4,15 @@
4
4
  # License: AGPL
5
5
 
6
6
  from pathlib import Path
7
- from typing import TYPE_CHECKING, Any, Optional, Union
7
+ from typing import TYPE_CHECKING, Any, Optional
8
8
 
9
9
  import nibabel as nib
10
10
  import nilearn.image as nimg
11
11
  import numpy as np
12
+ import structlog
12
13
  from junifer_data import get
13
14
 
14
- from ...utils import logger, raise_error
15
+ from ...utils import raise_error
15
16
  from ..pipeline_data_registry_base import BasePipelineDataRegistry
16
17
  from ..utils import (
17
18
  JUNIFER_DATA_PARAMS,
@@ -29,6 +30,9 @@ if TYPE_CHECKING:
29
30
 
30
31
  __all__ = ["MapsRegistry"]
31
32
 
33
+ _log = structlog.get_logger("junifer")
34
+ logger = _log.bind(pkg="data")
35
+
32
36
 
33
37
  class MapsRegistry(BasePipelineDataRegistry):
34
38
  """Class for maps data registry.
@@ -74,7 +78,7 @@ class MapsRegistry(BasePipelineDataRegistry):
74
78
  def register(
75
79
  self,
76
80
  name: str,
77
- maps_path: Union[str, Path],
81
+ maps_path: str | Path,
78
82
  maps_labels: list[str],
79
83
  space: str,
80
84
  overwrite: bool = False,
@@ -156,7 +160,7 @@ class MapsRegistry(BasePipelineDataRegistry):
156
160
  self,
157
161
  name: str,
158
162
  target_space: str,
159
- resolution: Optional[float] = None,
163
+ resolution: float | None = None,
160
164
  path_only: bool = False,
161
165
  ) -> tuple[Optional["Nifti1Image"], list[str], Path, str]:
162
166
  """Load map(s) and labels.
@@ -251,7 +255,7 @@ class MapsRegistry(BasePipelineDataRegistry):
251
255
  self,
252
256
  maps: str,
253
257
  target_data: dict[str, Any],
254
- extra_input: Optional[dict[str, Any]] = None,
258
+ extra_input: dict[str, Any] | None = None,
255
259
  ) -> tuple["Nifti1Image", list[str]]:
256
260
  """Get map(s), tailored for the target image.
257
261
 
@@ -376,9 +380,9 @@ class MapsRegistry(BasePipelineDataRegistry):
376
380
 
377
381
 
378
382
  def _retrieve_smith(
379
- resolution: Optional[float] = None,
380
- components: Optional[str] = None,
381
- dimension: Optional[int] = None,
383
+ resolution: float | None = None,
384
+ components: str | None = None,
385
+ dimension: int | None = None,
382
386
  ) -> tuple[Path, list[str]]:
383
387
  """Retrieve Smith maps.
384
388
 
@@ -4,7 +4,7 @@
4
4
  # License: AGPL
5
5
 
6
6
  import pytest
7
- from numpy.testing import assert_array_equal
7
+ from numpy.testing import assert_array_almost_equal, assert_array_equal
8
8
 
9
9
  from junifer.data import (
10
10
  deregister_data,
@@ -14,10 +14,15 @@ from junifer.data import (
14
14
  register_data,
15
15
  )
16
16
  from junifer.data.maps._maps import _retrieve_smith
17
- from junifer.datagrabber import PatternDataladDataGrabber
18
17
  from junifer.datareader import DefaultDataReader
19
18
  from junifer.pipeline.utils import _check_ants
20
- from junifer.testing.datagrabbers import PartlyCloudyTestingDataGrabber
19
+ from junifer.testing.datagrabbers import (
20
+ ADHDTestingDataGrabber,
21
+ PartlyCloudyTestingDataGrabber,
22
+ )
23
+
24
+
25
+ pytestmark = pytest.mark.external
21
26
 
22
27
 
23
28
  def test_register_built_in_check() -> None:
@@ -116,22 +121,8 @@ def test_load_nonexisting() -> None:
116
121
 
117
122
  def test_get() -> None:
118
123
  """Test tailored maps fetch."""
119
- with PatternDataladDataGrabber(
120
- uri="https://github.com/OpenNeuroDatasets/ds005226.git",
121
- types=["BOLD"],
122
- patterns={
123
- "BOLD": {
124
- "pattern": (
125
- "derivatives/pre-processed_data/space-MNI/{subject}/"
126
- "{subject-padded}_task-{task}_run-{run}_space-MNI152NLin6Asym"
127
- "_res-2_desc-preproc_bold.nii.gz"
128
- ),
129
- "space": "MNI152NLin6Asym",
130
- },
131
- },
132
- replacements=["subject", "subject-padded", "task", "run"],
133
- ) as dg:
134
- element = dg[("sub-01", "sub-001", "rest", "1")]
124
+ with ADHDTestingDataGrabber() as dg:
125
+ element = dg["sub-01"]
135
126
  element_data = DefaultDataReader().fit_transform(element)
136
127
  bold = element_data["BOLD"]
137
128
  bold_img = bold["data"]
@@ -147,8 +138,9 @@ def test_get() -> None:
147
138
  raw_maps, raw_labels, _, _ = load_data(
148
139
  kind="maps", name="Smith_rsn_10", target_space="MNI152NLin6Asym"
149
140
  )
150
- # Tailored and raw shape should be same
151
- assert tailored_maps.shape[:3] == raw_maps.shape[:3]
141
+ # Tailored maps are on the BOLD grid and keep all the raw maps
142
+ assert_array_almost_equal(tailored_maps.affine, bold_img.affine)
143
+ assert tailored_maps.shape[3] == raw_maps.shape[3]
152
144
  assert tailored_labels == raw_labels
153
145
 
154
146
 
@@ -4,13 +4,14 @@
4
4
  # License: AGPL
5
5
 
6
6
  import uuid
7
- from typing import TYPE_CHECKING, Any, Optional
7
+ from typing import TYPE_CHECKING, Any
8
8
 
9
9
  import nibabel as nib
10
10
  import numpy as np
11
11
 
12
12
  from ...pipeline import WorkDirManager
13
- from ...utils import logger, raise_error, run_ext_cmd
13
+ from ...typing import SpaceLike
14
+ from ...utils import raise_error, run_ext_cmd
14
15
  from ..template_spaces import get_template, get_xfm
15
16
 
16
17
 
@@ -52,10 +53,10 @@ class ANTsMaskWarper:
52
53
  self,
53
54
  mask_name: str,
54
55
  mask_img: "Nifti1Image",
55
- src: str,
56
- dst: str,
56
+ src: SpaceLike,
57
+ dst: SpaceLike,
57
58
  target_data: dict[str, Any],
58
- warp_data: Optional[dict[str, Any]],
59
+ warp_data: dict[str, Any] | None,
59
60
  ) -> "Nifti1Image": # pragma: no cover
60
61
  """Warp ``mask_img`` to correct space.
61
62
 
@@ -65,10 +66,10 @@ class ANTsMaskWarper:
65
66
  The name of the mask.
66
67
  mask_img : nibabel.nifti1.Nifti1Image
67
68
  The mask image to transform.
68
- src : str
69
+ src : str or Enum
69
70
  The data type or template space to warp from.
70
71
  It should be empty string if ``dst="native"``.
71
- dst : str
72
+ dst : str or Enum
72
73
  The data type or template space to warp to.
73
74
  `"native"` is the only allowed data type and it uses the resampled
74
75
  T1w found in ``target_data.reference``. The
@@ -92,6 +93,9 @@ class ANTsMaskWarper:
92
93
  If ``warp_data`` is None when ``dst="T1w"``.
93
94
 
94
95
  """
96
+ # Imported here to avoid circular import
97
+ from ._masks import logger
98
+
95
99
  # Create element-scoped tempdir so that warped mask is
96
100
  # available later as nibabel stores file path reference for
97
101
  # loading on computation
@@ -117,16 +121,17 @@ class ANTsMaskWarper:
117
121
  logger.debug("Using ANTs for mask transformation")
118
122
 
119
123
  # Save existing mask image to a tempfile
120
- prewarp_mask_path = element_tempdir / "prewarp_mask.nii.gz"
124
+ prewarp_mask_path = element_tempdir / "prewarp_mask.nii"
121
125
  nib.save(mask_img, prewarp_mask_path)
122
126
 
123
127
  # Create a tempfile for warped output
124
- warped_mask_path = element_tempdir / "mask_warped.nii.gz"
128
+ warped_mask_path = element_tempdir / "mask_warped.nii"
125
129
  # Set antsApplyTransforms command
126
130
  apply_transforms_cmd = [
127
131
  "antsApplyTransforms",
128
132
  "-d 3",
129
133
  "-e 3",
134
+ "--float 1",
130
135
  "-n 'GenericLabel[NearestNeighbor]'",
131
136
  f"-i {prewarp_mask_path.resolve()}",
132
137
  # use resampled reference
@@ -150,20 +155,21 @@ class ANTsMaskWarper:
150
155
  extra_input=None,
151
156
  )
152
157
  # Save template to a tempfile
153
- template_space_img_path = element_tempdir / f"{dst}_T1w.nii.gz"
158
+ template_space_img_path = element_tempdir / f"{dst}_T1w.nii"
154
159
  nib.save(template_space_img, template_space_img_path)
155
160
 
156
161
  # Save existing mask image to a tempfile
157
- prewarp_mask_path = element_tempdir / "prewarp_mask.nii.gz"
162
+ prewarp_mask_path = element_tempdir / "prewarp_mask.nii"
158
163
  nib.save(mask_img, prewarp_mask_path)
159
164
 
160
165
  # Create a tempfile for warped output
161
- warped_mask_path = element_tempdir / "mask_warped.nii.gz"
166
+ warped_mask_path = element_tempdir / "mask_warped.nii"
162
167
  # Set antsApplyTransforms command
163
168
  apply_transforms_cmd = [
164
169
  "antsApplyTransforms",
165
170
  "-d 3",
166
171
  "-e 3",
172
+ "--float 1",
167
173
  f"-n {_get_interpolation_method(mask_img)}",
168
174
  f"-i {prewarp_mask_path.resolve()}",
169
175
  f"-r {template_space_img_path.resolve()}",
@@ -10,7 +10,7 @@ import nibabel as nib
10
10
  import numpy as np
11
11
 
12
12
  from ...pipeline import WorkDirManager
13
- from ...utils import logger, run_ext_cmd
13
+ from ...utils import run_ext_cmd
14
14
 
15
15
 
16
16
  if TYPE_CHECKING:
@@ -74,6 +74,9 @@ class FSLMaskWarper:
74
74
  The transformed mask image.
75
75
 
76
76
  """
77
+ # Imported here to avoid circular import
78
+ from ._masks import logger
79
+
77
80
  logger.debug("Using FSL for mask transformation")
78
81
 
79
82
  # Create element-scoped tempdir so that warped mask is
@@ -84,13 +87,14 @@ class FSLMaskWarper:
84
87
  )
85
88
 
86
89
  # Save existing mask image to a tempfile
87
- prewarp_mask_path = element_tempdir / "prewarp_mask.nii.gz"
90
+ prewarp_mask_path = element_tempdir / "prewarp_mask.nii"
88
91
  nib.save(mask_img, prewarp_mask_path)
89
92
 
90
93
  # Create a tempfile for warped output
91
- warped_mask_path = element_tempdir / "mask_warped.nii.gz"
94
+ warped_mask_path = element_tempdir / "mask_warped.nii"
92
95
  # Set applywarp command
93
96
  applywarp_cmd = [
97
+ "FSLOUTPUTTYPE=NIFTI",
94
98
  "applywarp",
95
99
  f"--interp={_get_interpolation_method(mask_img)}",
96
100
  f"-i {prewarp_mask_path.resolve()}",
@@ -4,18 +4,18 @@
4
4
  # Synchon Mandal <s.mandal@fz-juelich.de>
5
5
  # License: AGPL
6
6
 
7
+ from collections.abc import Callable
7
8
  from pathlib import Path
8
9
  from typing import (
9
10
  TYPE_CHECKING,
10
11
  Any,
11
- Callable,
12
- Optional,
13
12
  Union,
14
13
  )
15
14
 
16
15
  import nibabel as nib
17
16
  import nilearn.image as nimg
18
17
  import numpy as np
18
+ import structlog
19
19
  from junifer_data import get
20
20
  from nilearn.masking import (
21
21
  compute_background_mask,
@@ -23,7 +23,7 @@ from nilearn.masking import (
23
23
  intersect_masks,
24
24
  )
25
25
 
26
- from ...utils import logger, raise_error
26
+ from ...utils import raise_error
27
27
  from ..pipeline_data_registry_base import BasePipelineDataRegistry
28
28
  from ..template_spaces import get_template
29
29
  from ..utils import (
@@ -42,15 +42,18 @@ if TYPE_CHECKING:
42
42
 
43
43
  __all__ = ["MaskRegistry", "compute_brain_mask"]
44
44
 
45
+ _log = structlog.get_logger("junifer")
46
+ logger = _log.bind(pkg="data")
47
+
45
48
 
46
49
  def compute_brain_mask(
47
50
  target_data: dict[str, Any],
48
- warp_data: Optional[dict[str, Any]] = None,
51
+ warp_data: dict[str, Any] | None = None,
49
52
  mask_type: str = "brain",
50
53
  threshold: float = 0.5,
51
54
  source: str = "template",
52
- template_space: Optional[str] = None,
53
- extra_input: Optional[dict[str, Any]] = None,
55
+ template_space: str | None = None,
56
+ extra_input: dict[str, Any] | None = None,
54
57
  ) -> "Nifti1Image":
55
58
  """Compute the whole-brain, grey-matter or white-matter mask.
56
59
 
@@ -281,7 +284,7 @@ class MaskRegistry(BasePipelineDataRegistry):
281
284
  def register(
282
285
  self,
283
286
  name: str,
284
- mask_path: Union[str, Path],
287
+ mask_path: str | Path,
285
288
  space: str,
286
289
  overwrite: bool = False,
287
290
  ) -> None:
@@ -355,9 +358,9 @@ class MaskRegistry(BasePipelineDataRegistry):
355
358
  def load(
356
359
  self,
357
360
  name: str,
358
- resolution: Optional[float] = None,
361
+ resolution: float | None = None,
359
362
  path_only: bool = False,
360
- ) -> tuple[Optional[Union["Nifti1Image", Callable]], Optional[Path], str]:
363
+ ) -> tuple[Union["Nifti1Image", Callable] | None, Path | None, str]:
361
364
  """Load mask.
362
365
 
363
366
  Parameters
@@ -428,9 +431,9 @@ class MaskRegistry(BasePipelineDataRegistry):
428
431
 
429
432
  def get( # noqa: C901
430
433
  self,
431
- masks: Union[str, dict, list[Union[dict, str]]],
434
+ masks: str | dict | list[dict | str],
432
435
  target_data: dict[str, Any],
433
- extra_input: Optional[dict[str, Any]] = None,
436
+ extra_input: dict[str, Any] | None = None,
434
437
  ) -> "Nifti1Image":
435
438
  """Get mask, tailored for the target image.
436
439
 
@@ -718,7 +721,7 @@ class MaskRegistry(BasePipelineDataRegistry):
718
721
 
719
722
  def _load_vickery_patil_mask(
720
723
  name: str,
721
- resolution: Optional[float] = None,
724
+ resolution: float | None = None,
722
725
  ) -> Path:
723
726
  """Load Vickery-Patil mask.
724
727
 
@@ -6,8 +6,8 @@
6
6
  # License: AGPL
7
7
 
8
8
  import socket
9
+ from collections.abc import Callable
9
10
  from pathlib import Path
10
- from typing import Callable, Optional, Union
11
11
 
12
12
  import nibabel as nib
13
13
  import numpy as np
@@ -36,12 +36,15 @@ from junifer.data.masks._masks import (
36
36
  from junifer.datagrabber import DMCC13Benchmark
37
37
  from junifer.datareader import DefaultDataReader
38
38
  from junifer.testing.datagrabbers import (
39
- OasisVBMTestingDataGrabber,
40
39
  PartlyCloudyTestingDataGrabber,
41
40
  SPMAuditoryTestingDataGrabber,
41
+ UCLACNPVBMTestingDataGrabber,
42
42
  )
43
43
 
44
44
 
45
+ pytestmark = pytest.mark.external
46
+
47
+
45
48
  @pytest.mark.parametrize(
46
49
  "mask_type, threshold",
47
50
  [
@@ -98,11 +101,11 @@ def test_compute_brain_mask_for_native(mask_type: str) -> None:
98
101
 
99
102
  """
100
103
  with DMCC13Benchmark(
101
- types=["BOLD"],
102
- sessions=["ses-wave1bas"],
103
- tasks=["Rest"],
104
- phase_encodings=["AP"],
105
- runs=["1"],
104
+ types="BOLD",
105
+ sessions="ses-wave1bas",
106
+ tasks="Rest",
107
+ phase_encodings="AP",
108
+ runs="1",
106
109
  native_t1w=True,
107
110
  ) as dg:
108
111
  element_data = DefaultDataReader().fit_transform(
@@ -177,7 +180,7 @@ def test_register_already_registered() -> None:
177
180
  )
178
181
  def test_register(
179
182
  name: str,
180
- mask_path: str,
183
+ mask_path: str | Path,
181
184
  space: str,
182
185
  overwrite: bool,
183
186
  ) -> None:
@@ -264,7 +267,7 @@ def test_load_incorrect() -> None:
264
267
  )
265
268
  def test_vickery_patil(
266
269
  name: str,
267
- resolution: Optional[float],
270
+ resolution: float | None,
268
271
  pixdim: list[float],
269
272
  fname: str,
270
273
  ) -> None:
@@ -319,8 +322,8 @@ def test_ukb_error() -> None:
319
322
 
320
323
  def test_get() -> None:
321
324
  """Test tailored mask fetch."""
322
- with OasisVBMTestingDataGrabber() as dg:
323
- element_data = DefaultDataReader().fit_transform(dg["sub-01"])
325
+ with UCLACNPVBMTestingDataGrabber() as dg:
326
+ element_data = DefaultDataReader().fit_transform(dg["sub-10206"])
324
327
  vbm_gm = element_data["VBM_GM"]
325
328
  vbm_gm_img = vbm_gm["data"]
326
329
  mask = get_data(
@@ -354,8 +357,8 @@ def test_mask_callable() -> None:
354
357
  "func": ident,
355
358
  "space": "MNI152Lin",
356
359
  }
357
- with OasisVBMTestingDataGrabber() as dg:
358
- element_data = DefaultDataReader().fit_transform(dg["sub-01"])
360
+ with UCLACNPVBMTestingDataGrabber() as dg:
361
+ element_data = DefaultDataReader().fit_transform(dg["sub-10206"])
359
362
  vbm_gm = element_data["VBM_GM"]
360
363
  vbm_gm_img = vbm_gm["data"]
361
364
  mask = MaskRegistry().get(masks="identity", target_data=vbm_gm)
@@ -367,8 +370,8 @@ def test_mask_callable() -> None:
367
370
 
368
371
  def test_get_errors() -> None:
369
372
  """Test passing wrong parameters to fetch mask."""
370
- with OasisVBMTestingDataGrabber() as dg:
371
- element_data = DefaultDataReader().fit_transform(dg["sub-01"])
373
+ with UCLACNPVBMTestingDataGrabber() as dg:
374
+ element_data = DefaultDataReader().fit_transform(dg["sub-10206"])
372
375
  vbm_gm = element_data["VBM_GM"]
373
376
  # Test wrong masks definitions (more than one key per dict)
374
377
  with pytest.raises(ValueError, match=r"only one key"):
@@ -417,7 +420,7 @@ def test_get_errors() -> None:
417
420
  def test_nilearn_compute_masks(
418
421
  mask_name: str,
419
422
  function: Callable,
420
- params: Union[dict, None],
423
+ params: dict | None,
421
424
  resample: bool,
422
425
  ) -> None:
423
426
  """Test using nilearn compute mask functions.
@@ -502,7 +505,7 @@ def test_get_inherit() -> None:
502
505
  ],
503
506
  )
504
507
  def test_get_multiple(
505
- masks: Union[str, dict, list[Union[dict, str]]], params: dict
508
+ masks: str | dict | list[dict | str], params: dict
506
509
  ) -> None:
507
510
  """Test getting multiple masks.
508
511