junifer 0.0.5.dev93__py3-none-any.whl → 0.0.5.dev110__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.
junifer/_version.py CHANGED
@@ -12,5 +12,5 @@ __version__: str
12
12
  __version_tuple__: VERSION_TUPLE
13
13
  version_tuple: VERSION_TUPLE
14
14
 
15
- __version__ = version = '0.0.5.dev93'
16
- __version_tuple__ = version_tuple = (0, 0, 5, 'dev93')
15
+ __version__ = version = '0.0.5.dev110'
16
+ __version_tuple__ = version_tuple = (0, 0, 5, 'dev110')
@@ -24,8 +24,8 @@ class DataladAOMICID1000(PatternDataladDataGrabber):
24
24
  The directory where the datalad dataset will be cloned. If None,
25
25
  the datalad dataset will be cloned into a temporary directory
26
26
  (default None).
27
- types: {"BOLD", "T1w", "VBM_CSF", "VBM_GM", "VBM_WM", "DWI"} or \
28
- list of the options, optional
27
+ types: {"BOLD", "T1w", "VBM_CSF", "VBM_GM", "VBM_WM", "DWI", \
28
+ "FreeSurfer"} or list of the options, optional
29
29
  AOMIC data types. If None, all available data types are selected.
30
30
  (default None).
31
31
  native_t1w : bool, optional
@@ -112,6 +112,39 @@ class DataladAOMICID1000(PatternDataladDataGrabber):
112
112
  "{subject}_desc-preproc_dwi.nii.gz"
113
113
  ),
114
114
  },
115
+ "FreeSurfer": {
116
+ "pattern": "derivatives/freesurfer/[!f]{subject}/mri/T1.mg[z]",
117
+ "aseg": {
118
+ "pattern": (
119
+ "derivatives/freesurfer/[!f]{subject}/mri/aseg.mg[z]"
120
+ )
121
+ },
122
+ "norm": {
123
+ "pattern": (
124
+ "derivatives/freesurfer/[!f]{subject}/mri/norm.mg[z]"
125
+ )
126
+ },
127
+ "lh_white": {
128
+ "pattern": (
129
+ "derivatives/freesurfer/[!f]{subject}/surf/lh.whit[e]"
130
+ )
131
+ },
132
+ "rh_white": {
133
+ "pattern": (
134
+ "derivatives/freesurfer/[!f]{subject}/surf/rh.whit[e]"
135
+ )
136
+ },
137
+ "lh_pial": {
138
+ "pattern": (
139
+ "derivatives/freesurfer/[!f]{subject}/surf/lh.pia[l]"
140
+ )
141
+ },
142
+ "rh_pial": {
143
+ "pattern": (
144
+ "derivatives/freesurfer/[!f]{subject}/surf/rh.pia[l]"
145
+ )
146
+ },
147
+ },
115
148
  }
116
149
  # Use native T1w assets
117
150
  self.native_t1w = False
@@ -26,8 +26,8 @@ class DataladAOMICPIOP1(PatternDataladDataGrabber):
26
26
  The directory where the datalad dataset will be cloned. If None,
27
27
  the datalad dataset will be cloned into a temporary directory
28
28
  (default None).
29
- types: {"BOLD", "T1w", "VBM_CSF", "VBM_GM", "VBM_WM", "DWI"} or \
30
- list of the options, optional
29
+ types: {"BOLD", "T1w", "VBM_CSF", "VBM_GM", "VBM_WM", "DWI", \
30
+ "FreeSurfer"} or list of the options, optional
31
31
  AOMIC data types. If None, all available data types are selected.
32
32
  (default None).
33
33
  tasks : {"restingstate", "anticipation", "emomatching", "faces", \
@@ -147,6 +147,39 @@ class DataladAOMICPIOP1(PatternDataladDataGrabber):
147
147
  "{subject}_desc-preproc_dwi.nii.gz"
148
148
  ),
149
149
  },
150
+ "FreeSurfer": {
151
+ "pattern": "derivatives/freesurfer/[!f]{subject}/mri/T1.mg[z]",
152
+ "aseg": {
153
+ "pattern": (
154
+ "derivatives/freesurfer/[!f]{subject}/mri/aseg.mg[z]"
155
+ )
156
+ },
157
+ "norm": {
158
+ "pattern": (
159
+ "derivatives/freesurfer/[!f]{subject}/mri/norm.mg[z]"
160
+ )
161
+ },
162
+ "lh_white": {
163
+ "pattern": (
164
+ "derivatives/freesurfer/[!f]{subject}/surf/lh.whit[e]"
165
+ )
166
+ },
167
+ "rh_white": {
168
+ "pattern": (
169
+ "derivatives/freesurfer/[!f]{subject}/surf/rh.whit[e]"
170
+ )
171
+ },
172
+ "lh_pial": {
173
+ "pattern": (
174
+ "derivatives/freesurfer/[!f]{subject}/surf/lh.pia[l]"
175
+ )
176
+ },
177
+ "rh_pial": {
178
+ "pattern": (
179
+ "derivatives/freesurfer/[!f]{subject}/surf/rh.pia[l]"
180
+ )
181
+ },
182
+ },
150
183
  }
151
184
  # Use native T1w assets
152
185
  self.native_t1w = False
@@ -26,8 +26,8 @@ class DataladAOMICPIOP2(PatternDataladDataGrabber):
26
26
  The directory where the datalad dataset will be cloned. If None,
27
27
  the datalad dataset will be cloned into a temporary directory
28
28
  (default None).
29
- types: {"BOLD", "T1w", "VBM_CSF", "VBM_GM", "VBM_WM", "DWI"} or \
30
- list of the options, optional
29
+ types: {"BOLD", "T1w", "VBM_CSF", "VBM_GM", "VBM_WM", "DWI", \
30
+ "FreeSurfer"} or list of the options, optional
31
31
  AOMIC data types. If None, all available data types are selected.
32
32
  (default None).
33
33
  tasks : {"restingstate", "stopsignal", "workingmemory"} or \
@@ -144,6 +144,39 @@ class DataladAOMICPIOP2(PatternDataladDataGrabber):
144
144
  "{subject}_desc-preproc_dwi.nii.gz"
145
145
  ),
146
146
  },
147
+ "FreeSurfer": {
148
+ "pattern": "derivatives/freesurfer/[!f]{subject}/mri/T1.mg[z]",
149
+ "aseg": {
150
+ "pattern": (
151
+ "derivatives/freesurfer/[!f]{subject}/mri/aseg.mg[z]"
152
+ )
153
+ },
154
+ "norm": {
155
+ "pattern": (
156
+ "derivatives/freesurfer/[!f]{subject}/mri/norm.mg[z]"
157
+ )
158
+ },
159
+ "lh_white": {
160
+ "pattern": (
161
+ "derivatives/freesurfer/[!f]{subject}/surf/lh.whit[e]"
162
+ )
163
+ },
164
+ "rh_white": {
165
+ "pattern": (
166
+ "derivatives/freesurfer/[!f]{subject}/surf/rh.whit[e]"
167
+ )
168
+ },
169
+ "lh_pial": {
170
+ "pattern": (
171
+ "derivatives/freesurfer/[!f]{subject}/surf/lh.pia[l]"
172
+ )
173
+ },
174
+ "rh_pial": {
175
+ "pattern": (
176
+ "derivatives/freesurfer/[!f]{subject}/surf/rh.pia[l]"
177
+ )
178
+ },
179
+ },
147
180
  }
148
181
  # Use native T1w assets
149
182
  self.native_t1w = False
@@ -7,7 +7,7 @@
7
7
  # Synchon Mandal <s.mandal@fz-juelich.de>
8
8
  # License: AGPL
9
9
 
10
- from typing import List, Union
10
+ from typing import List, Optional, Union
11
11
 
12
12
  import pytest
13
13
 
@@ -17,112 +17,58 @@ from junifer.datagrabber.aomic.id1000 import DataladAOMICID1000
17
17
  URI = "https://gin.g-node.org/juaml/datalad-example-aomic1000"
18
18
 
19
19
 
20
- def test_DataladAOMICID1000() -> None:
21
- """Test DataladAOMICID1000 DataGrabber."""
22
- dg = DataladAOMICID1000()
20
+ @pytest.mark.parametrize(
21
+ "type_, nested_types",
22
+ [
23
+ ("BOLD", ["confounds", "mask"]),
24
+ ("T1w", ["mask"]),
25
+ ("VBM_CSF", None),
26
+ ("VBM_GM", None),
27
+ ("VBM_WM", None),
28
+ ("DWI", None),
29
+ ("FreeSurfer", None),
30
+ ],
31
+ )
32
+ def test_DataladAOMICID1000(
33
+ type_: str,
34
+ nested_types: Optional[List[str]],
35
+ ) -> None:
36
+ """Test DataladAOMICID1000 DataGrabber.
37
+
38
+ Parameters
39
+ ----------
40
+ type_ : str
41
+ The parametrized type.
42
+ nested_types : list of str or None
43
+ The parametrized nested types.
44
+
45
+ """
46
+ dg = DataladAOMICID1000(types=type_)
23
47
  # Set URI to Gin
24
48
  dg.uri = URI
25
49
 
26
50
  with dg:
51
+ # Get all elements
27
52
  all_elements = dg.get_elements()
53
+ # Get test element
28
54
  test_element = all_elements[0]
29
-
55
+ # Get test element data
30
56
  out = dg[test_element]
31
-
32
- # asserts type "BOLD"
33
- assert "BOLD" in out
34
-
35
- assert (
36
- out["BOLD"]["path"].name == f"{test_element}_task-moviewatching_"
37
- "space-MNI152NLin2009cAsym_desc-preproc_bold.nii.gz"
38
- )
39
-
40
- assert out["BOLD"]["path"].exists()
41
- assert out["BOLD"]["path"].is_file()
42
-
43
- # asserts type BOLD.confounds
44
- assert "confounds" in out["BOLD"]
45
-
46
- assert (
47
- out["BOLD"]["confounds"]["path"].name
48
- == f"{test_element}_task-moviewatching_"
49
- "desc-confounds_regressors.tsv"
50
- )
51
-
52
- assert out["BOLD"]["confounds"]["path"].exists()
53
- assert out["BOLD"]["confounds"]["path"].is_file()
54
-
55
- # assert BOLD.mask
56
- assert out["BOLD"]["mask"]["path"].exists()
57
-
58
- # asserts type "T1w"
59
- assert "T1w" in out
60
-
61
- assert (
62
- out["T1w"]["path"].name
63
- == f"{test_element}_space-MNI152NLin2009cAsym_"
64
- "desc-preproc_T1w.nii.gz"
65
- )
66
-
67
- assert out["T1w"]["path"].exists()
68
- assert out["T1w"]["path"].is_file()
69
-
70
- # asserts T1w.mask
71
- assert out["T1w"]["mask"]["path"].exists()
72
-
73
- # asserts type "VBM_CSF"
74
- assert "VBM_CSF" in out
75
-
76
- assert (
77
- out["VBM_CSF"]["path"].name
78
- == f"{test_element}_space-MNI152NLin2009cAsym_label-"
79
- "CSF_probseg.nii.gz"
80
- )
81
-
82
- assert out["VBM_CSF"]["path"].exists()
83
- assert out["VBM_CSF"]["path"].is_file()
84
-
85
- # asserts type "VBM_GM"
86
- assert "VBM_GM" in out
87
-
88
- assert (
89
- out["VBM_GM"]["path"].name
90
- == f"{test_element}_space-MNI152NLin2009cAsym_label-"
91
- "GM_probseg.nii.gz"
92
- )
93
-
94
- assert out["VBM_GM"]["path"].exists()
95
- assert out["VBM_GM"]["path"].is_file()
96
-
97
- # asserts type "VBM_WM"
98
- assert "VBM_WM" in out
99
-
100
- assert (
101
- out["VBM_WM"]["path"].name
102
- == f"{test_element}_space-MNI152NLin2009cAsym_label-"
103
- "WM_probseg.nii.gz"
104
- )
105
-
106
- assert out["VBM_WM"]["path"].exists()
107
- assert out["VBM_WM"]["path"].is_file()
108
-
109
- # asserts type "DWI"
110
- assert "DWI" in out
111
-
112
- assert (
113
- out["DWI"]["path"].name
114
- == f"{test_element}_desc-preproc_dwi.nii.gz"
115
- )
116
-
117
- assert out["DWI"]["path"].exists()
118
- assert out["DWI"]["path"].is_file()
119
-
120
- # asserts meta
121
- assert "meta" in out["BOLD"]
122
- meta = out["BOLD"]["meta"]
57
+ # Assert data type
58
+ assert type_ in out
59
+ assert out[type_]["path"].exists()
60
+ assert out[type_]["path"].is_file()
61
+ # Asserts data type metadata
62
+ assert "meta" in out[type_]
63
+ meta = out[type_]["meta"]
123
64
  assert "element" in meta
124
65
  assert "subject" in meta["element"]
125
66
  assert test_element == meta["element"]["subject"]
67
+ # Assert nested data type if not None
68
+ if nested_types is not None:
69
+ for nested_type in nested_types:
70
+ assert out[type_][nested_type]["path"].exists()
71
+ assert out[type_][nested_type]["path"].is_file()
126
72
 
127
73
 
128
74
  @pytest.mark.parametrize(
@@ -18,129 +18,87 @@ URI = "https://gin.g-node.org/juaml/datalad-example-aomicpiop1"
18
18
 
19
19
 
20
20
  @pytest.mark.parametrize(
21
- "tasks",
22
- [None, "restingstate"],
21
+ "type_, nested_types, tasks",
22
+ [
23
+ ("BOLD", ["confounds", "mask"], None),
24
+ ("BOLD", ["confounds", "mask"], ["anticipation"]),
25
+ ("BOLD", ["confounds", "mask"], ["emomatching", "faces"]),
26
+ ("BOLD", ["confounds", "mask"], ["restingstate"]),
27
+ ("BOLD", ["confounds", "mask"], ["workingmemory", "gstroop"]),
28
+ (
29
+ "BOLD",
30
+ ["confounds", "mask"],
31
+ ["anticipation", "faces", "restingstate"],
32
+ ),
33
+ ("T1w", ["mask"], None),
34
+ ("VBM_CSF", None, None),
35
+ ("VBM_GM", None, None),
36
+ ("VBM_WM", None, None),
37
+ ("DWI", None, None),
38
+ ("FreeSurfer", None, None),
39
+ ],
23
40
  )
24
- def test_DataladAOMICPIOP1(tasks: Optional[str]) -> None:
41
+ def test_DataladAOMICPIOP1(
42
+ type_: str,
43
+ nested_types: Optional[List[str]],
44
+ tasks: Optional[List[str]],
45
+ ) -> None:
25
46
  """Test DataladAOMICPIOP1 DataGrabber.
26
47
 
27
48
  Parameters
28
49
  ----------
29
- tasks : str or None
50
+ type_ : str
51
+ The parametrized type.
52
+ nested_types : list of str or None
53
+ The parametrized nested types.
54
+ tasks : list of str or None
30
55
  The parametrized task values.
31
56
 
32
57
  """
33
- dg = DataladAOMICPIOP1(tasks=tasks)
58
+ dg = DataladAOMICPIOP1(types=type_, tasks=tasks)
34
59
  # Set URI to Gin
35
60
  dg.uri = URI
36
61
 
37
62
  with dg:
63
+ # Get all elements
38
64
  all_elements = dg.get_elements()
65
+ # Get test element
39
66
  test_element = all_elements[0]
40
- sub, task = test_element
41
-
67
+ # Get test element data
42
68
  out = dg[test_element]
43
-
44
- # asserts type "BOLD"
45
- assert "BOLD" in out
46
-
47
- # depending on task 'acquisition is different'
48
- task_acqs = {
49
- "anticipation": "seq",
50
- "emomatching": "seq",
51
- "faces": "mb3",
52
- "gstroop": "seq",
53
- "restingstate": "mb3",
54
- "workingmemory": "seq",
55
- }
56
- acq = task_acqs[task]
57
- new_task = f"{task}_acq-{acq}"
58
- assert (
59
- out["BOLD"]["path"].name == f"{sub}_task-{new_task}_"
60
- "space-MNI152NLin2009cAsym_desc-preproc_bold.nii.gz"
61
- )
62
-
63
- assert out["BOLD"]["path"].exists()
64
- assert out["BOLD"]["path"].is_file()
65
-
66
- # asserts type BOLD.confounds
67
- assert "confounds" in out["BOLD"]
68
-
69
- assert (
70
- out["BOLD"]["confounds"]["path"].name == f"{sub}_task-{new_task}_"
71
- "desc-confounds_regressors.tsv"
72
- )
73
-
74
- assert out["BOLD"]["confounds"]["path"].exists()
75
- assert out["BOLD"]["confounds"]["path"].is_file()
76
-
77
- # assert BOLD.mask
78
- assert out["BOLD"]["mask"]["path"].exists()
79
-
80
- # asserts type "T1w"
81
- assert "T1w" in out
82
-
83
- assert (
84
- out["T1w"]["path"].name == f"{sub}_space-MNI152NLin2009cAsym_"
85
- "desc-preproc_T1w.nii.gz"
86
- )
87
-
88
- assert out["T1w"]["path"].exists()
89
- assert out["T1w"]["path"].is_file()
90
-
91
- # asserts T1w.mask
92
- assert out["T1w"]["mask"]["path"].exists()
93
-
94
- # asserts type "VBM_CSF"
95
- assert "VBM_CSF" in out
96
-
97
- assert (
98
- out["VBM_CSF"]["path"].name
99
- == f"{sub}_space-MNI152NLin2009cAsym_label-"
100
- "CSF_probseg.nii.gz"
101
- )
102
-
103
- assert out["VBM_CSF"]["path"].exists()
104
- assert out["VBM_CSF"]["path"].is_file()
105
-
106
- # asserts type "VBM_GM"
107
- assert "VBM_GM" in out
108
-
109
- assert (
110
- out["VBM_GM"]["path"].name
111
- == f"{sub}_space-MNI152NLin2009cAsym_label-"
112
- "GM_probseg.nii.gz"
113
- )
114
-
115
- assert out["VBM_GM"]["path"].exists()
116
- assert out["VBM_GM"]["path"].is_file()
117
-
118
- # asserts type "VBM_WM"
119
- assert "VBM_WM" in out
120
-
121
- assert (
122
- out["VBM_WM"]["path"].name
123
- == f"{sub}_space-MNI152NLin2009cAsym_label-"
124
- "WM_probseg.nii.gz"
125
- )
126
-
127
- assert out["VBM_WM"]["path"].exists()
128
- assert out["VBM_WM"]["path"].is_file()
129
-
130
- # asserts type "DWI"
131
- assert "DWI" in out
132
-
133
- assert out["DWI"]["path"].name == f"{sub}_desc-preproc_dwi.nii.gz"
134
-
135
- assert out["DWI"]["path"].exists()
136
- assert out["DWI"]["path"].is_file()
137
-
138
- # asserts meta
139
- assert "meta" in out["BOLD"]
140
- meta = out["BOLD"]["meta"]
69
+ # Get all elements
70
+ all_elements = dg.get_elements()
71
+ # Get test element
72
+ test_element = all_elements[0]
73
+ # Get test element data
74
+ out = dg[test_element]
75
+ # Assert data type
76
+ assert type_ in out
77
+ # Check task name if BOLD
78
+ if type_ == "BOLD" and tasks is not None:
79
+ # Depending on task 'acquisition is different'
80
+ task_acqs = {
81
+ "anticipation": "seq",
82
+ "emomatching": "seq",
83
+ "faces": "mb3",
84
+ "gstroop": "seq",
85
+ "restingstate": "mb3",
86
+ "workingmemory": "seq",
87
+ }
88
+ assert task_acqs[test_element[1]] in out[type_]["path"].name
89
+ assert out[type_]["path"].exists()
90
+ assert out[type_]["path"].is_file()
91
+ # Asserts data type metadata
92
+ assert "meta" in out[type_]
93
+ meta = out[type_]["meta"]
141
94
  assert "element" in meta
142
95
  assert "subject" in meta["element"]
143
- assert sub == meta["element"]["subject"]
96
+ assert test_element[0] == meta["element"]["subject"]
97
+ # Assert nested data type if not None
98
+ if nested_types is not None:
99
+ for nested_type in nested_types:
100
+ assert out[type_][nested_type]["path"].exists()
101
+ assert out[type_][nested_type]["path"].is_file()
144
102
 
145
103
 
146
104
  @pytest.mark.parametrize(
@@ -18,123 +18,67 @@ URI = "https://gin.g-node.org/juaml/datalad-example-aomicpiop2"
18
18
 
19
19
 
20
20
  @pytest.mark.parametrize(
21
- "tasks",
22
- [None, "restingstate"],
21
+ "type_, nested_types, tasks",
22
+ [
23
+ ("BOLD", ["confounds", "mask"], None),
24
+ ("BOLD", ["confounds", "mask"], ["restingstate"]),
25
+ ("BOLD", ["confounds", "mask"], ["restingstate", "stopsignal"]),
26
+ ("BOLD", ["confounds", "mask"], ["workingmemory", "stopsignal"]),
27
+ ("BOLD", ["confounds", "mask"], ["workingmemory"]),
28
+ ("T1w", ["mask"], None),
29
+ ("VBM_CSF", None, None),
30
+ ("VBM_GM", None, None),
31
+ ("VBM_WM", None, None),
32
+ ("DWI", None, None),
33
+ ("FreeSurfer", None, None),
34
+ ],
23
35
  )
24
- def test_DataladAOMICPIOP2(tasks: Optional[str]) -> None:
36
+ def test_DataladAOMICPIOP2(
37
+ type_: str,
38
+ nested_types: Optional[List[str]],
39
+ tasks: Optional[List[str]],
40
+ ) -> None:
25
41
  """Test DataladAOMICPIOP2 DataGrabber.
26
42
 
27
43
  Parameters
28
44
  ----------
29
- tasks : str or None
45
+ type_ : str
46
+ The parametrized type.
47
+ nested_types : list of str or None
48
+ The parametrized nested types.
49
+ tasks : list of str or None
30
50
  The parametrized task values.
31
51
 
32
52
  """
33
- dg = DataladAOMICPIOP2(tasks=tasks)
53
+ dg = DataladAOMICPIOP2(types=type_, tasks=tasks)
34
54
  # Set URI to Gin
35
55
  dg.uri = URI
36
56
 
37
57
  with dg:
58
+ # Get all elements
38
59
  all_elements = dg.get_elements()
39
-
40
- if tasks == "restingstate":
41
- for el in all_elements:
42
- assert el[1] == "restingstate"
43
-
60
+ # Get test element
44
61
  test_element = all_elements[0]
45
- sub, task = test_element
62
+ # Get test element data
46
63
  out = dg[test_element]
47
-
48
- # asserts type "BOLD"
49
- assert "BOLD" in out
50
-
51
- new_task = f"{task}_acq-seq"
52
- assert (
53
- out["BOLD"]["path"].name == f"{sub}_task-{new_task}_"
54
- "space-MNI152NLin2009cAsym_desc-preproc_bold.nii.gz"
55
- )
56
-
57
- assert out["BOLD"]["path"].exists()
58
- assert out["BOLD"]["path"].is_file()
59
-
60
- # asserts type BOLD.confounds
61
- assert "confounds" in out["BOLD"]
62
-
63
- assert (
64
- out["BOLD"]["confounds"]["path"].name == f"{sub}_task-{new_task}_"
65
- "desc-confounds_regressors.tsv"
66
- )
67
-
68
- assert out["BOLD"]["confounds"]["path"].exists()
69
- assert out["BOLD"]["confounds"]["path"].is_file()
70
-
71
- # assert BOLD.mask
72
- assert out["BOLD"]["mask"]["path"].exists()
73
-
74
- # asserts type "T1w"
75
- assert "T1w" in out
76
-
77
- assert (
78
- out["T1w"]["path"].name == f"{sub}_space-MNI152NLin2009cAsym_"
79
- "desc-preproc_T1w.nii.gz"
80
- )
81
-
82
- assert out["T1w"]["path"].exists()
83
- assert out["T1w"]["path"].is_file()
84
-
85
- # asserts T1w.mask
86
- assert out["T1w"]["mask"]["path"].exists()
87
-
88
- # asserts type "VBM_CSF"
89
- assert "VBM_CSF" in out
90
-
91
- assert (
92
- out["VBM_CSF"]["path"].name
93
- == f"{sub}_space-MNI152NLin2009cAsym_label-"
94
- "CSF_probseg.nii.gz"
95
- )
96
-
97
- assert out["VBM_CSF"]["path"].exists()
98
- assert out["VBM_CSF"]["path"].is_file()
99
-
100
- # asserts type "VBM_GM"
101
- assert "VBM_GM" in out
102
-
103
- assert (
104
- out["VBM_GM"]["path"].name
105
- == f"{sub}_space-MNI152NLin2009cAsym_label-"
106
- "GM_probseg.nii.gz"
107
- )
108
-
109
- assert out["VBM_GM"]["path"].exists()
110
- assert out["VBM_GM"]["path"].is_file()
111
-
112
- # asserts type "VBM_WM"
113
- assert "VBM_WM" in out
114
-
115
- assert (
116
- out["VBM_WM"]["path"].name
117
- == f"{sub}_space-MNI152NLin2009cAsym_label-"
118
- "WM_probseg.nii.gz"
119
- )
120
-
121
- assert out["VBM_WM"]["path"].exists()
122
- assert out["VBM_WM"]["path"].is_file()
123
-
124
- # asserts type "DWI"
125
- assert "DWI" in out
126
-
127
- assert out["DWI"]["path"].name == f"{sub}_desc-preproc_dwi.nii.gz"
128
-
129
- assert out["DWI"]["path"].exists()
130
- assert out["DWI"]["path"].is_file()
131
-
132
- # asserts meta
133
- assert "meta" in out["BOLD"]
134
- meta = out["BOLD"]["meta"]
64
+ # Assert data type
65
+ assert type_ in out
66
+ # Check task name if BOLD
67
+ if type_ == "BOLD" and tasks is not None:
68
+ assert test_element[1] in out[type_]["path"].name
69
+ assert out[type_]["path"].exists()
70
+ assert out[type_]["path"].is_file()
71
+ # Asserts data type metadata
72
+ assert "meta" in out[type_]
73
+ meta = out[type_]["meta"]
135
74
  assert "element" in meta
136
75
  assert "subject" in meta["element"]
137
- assert sub == meta["element"]["subject"]
76
+ assert test_element[0] == meta["element"]["subject"]
77
+ # Assert nested data type if not None
78
+ if nested_types is not None:
79
+ for nested_type in nested_types:
80
+ assert out[type_][nested_type]["path"].exists()
81
+ assert out[type_][nested_type]["path"].is_file()
138
82
 
139
83
 
140
84
  @pytest.mark.parametrize(
@@ -214,18 +214,25 @@ class PatternDataGrabber(BaseDataGrabber):
214
214
  t_replacements = [
215
215
  x for x in self.replacements if f"{{{x}}}" in pattern
216
216
  ]
217
-
217
+ # Ops on re_pattern
218
+ # Remove negated unix glob pattern i.e., [!...] for re_pattern
219
+ re_pattern = re.sub(r"\[!.?\]", "", re_pattern)
220
+ # Remove enclosing square brackets from unix glob pattern i.e., [...]
221
+ # for re_pattern
222
+ re_pattern = re.sub(r"\[|\]", "", re_pattern)
223
+ # Iteratively replace the first of each with a named group definition
218
224
  for t_r in t_replacements:
219
- # Replace the first of each with a named group definition
220
225
  re_pattern = re_pattern.replace(f"{{{t_r}}}", f"(?P<{t_r}>.*)", 1)
221
-
226
+ # Iteratively replace the second appearance of each with the named
227
+ # group back reference
222
228
  for t_r in t_replacements:
223
- # Replace the second appearance of each with the named group
224
- # back reference
225
229
  re_pattern = re_pattern.replace(f"{{{t_r}}}", f"(?P={t_r})")
226
-
230
+ # Ops on glob_pattern
231
+ # Iteratively replace replacements with wildcard i.e., *
232
+ # for glob_pattern
227
233
  for t_r in t_replacements:
228
234
  glob_pattern = glob_pattern.replace(f"{{{t_r}}}", "*")
235
+
229
236
  return re_pattern, glob_pattern, t_replacements
230
237
 
231
238
  def _replace_patterns_glob(self, element: Dict, pattern: str) -> str:
@@ -254,6 +261,10 @@ class PatternDataGrabber(BaseDataGrabber):
254
261
  f"The element keys must be {self.replacements}, "
255
262
  f"element has {list(element.keys())}."
256
263
  )
264
+ # Remove negated unix glob pattern i.e., [!...]
265
+ pattern = re.sub(r"\[!.?\]", "", pattern)
266
+ # Remove enclosing square brackets from unix glob pattern i.e., [...]
267
+ pattern = re.sub(r"\[|\]", "", pattern)
257
268
  return pattern.format(**element)
258
269
 
259
270
  def _get_path_from_patterns(
@@ -236,6 +236,51 @@ def test_PatternDataGrabber(tmp_path: Path) -> None:
236
236
  assert out1["VBM_GM"]["path"] != out2["VBM_GM"]["path"]
237
237
 
238
238
 
239
+ def test_PatternDataGrabber_unix_path_expansion(tmp_path: Path) -> None:
240
+ """Test PatterDataGrabber for patterns with unix path expansion.
241
+
242
+ Parameters
243
+ ----------
244
+ tmp_path : pathlib.Path
245
+ The path to the test directory.
246
+
247
+ """
248
+ # Create test data root dir
249
+ freesurfer_dir = tmp_path / "derivatives" / "freesurfer"
250
+ freesurfer_dir.mkdir(parents=True, exist_ok=True)
251
+ # Create test data sub dirs and files
252
+ for dir_name in ["fsaverage", "sub-0001"]:
253
+ mri_dir = freesurfer_dir / dir_name / "mri"
254
+ mri_dir.mkdir(parents=True, exist_ok=True)
255
+ # Create files
256
+ (mri_dir / "T1.mgz").touch(exist_ok=True)
257
+ (mri_dir / "aseg.mgz").touch(exist_ok=True)
258
+ # Create datagrabber
259
+ dg = PatternDataGrabber(
260
+ datadir=tmp_path,
261
+ types=["FreeSurfer"],
262
+ patterns={
263
+ "FreeSurfer": {
264
+ "pattern": "derivatives/freesurfer/[!f]{subject}/mri/T1.mg[z]",
265
+ "aseg": {
266
+ "pattern": (
267
+ "derivatives/freesurfer/[!f]{subject}/mri/aseg.mg[z]"
268
+ )
269
+ },
270
+ },
271
+ },
272
+ replacements=["subject"],
273
+ )
274
+ # Check that "fsaverage" is filtered
275
+ elements = dg.get_elements()
276
+ assert elements == ["sub-0001"]
277
+ # Fetch data
278
+ out = dg["sub-0001"]
279
+ # Check paths are found
280
+ assert set(out["FreeSurfer"].keys()) == {"path", "aseg", "meta"}
281
+ assert list(out["FreeSurfer"]["aseg"].keys()) == ["path"]
282
+
283
+
239
284
  def test_PatternDataGrabber_confounds_format_error_on_init() -> None:
240
285
  """Test PatterDataGrabber confounds format error on initialisation."""
241
286
  with pytest.raises(
@@ -53,6 +53,17 @@ PATTERNS_SCHEMA = {
53
53
  "mandatory": ["pattern"],
54
54
  "optional": {},
55
55
  },
56
+ "FreeSurfer": {
57
+ "mandatory": ["pattern"],
58
+ "optional": {
59
+ "aseg": {"mandatory": ["pattern"], "optional": []},
60
+ "norm": {"mandatory": ["pattern"], "optional": []},
61
+ "lh_white": {"mandatory": ["pattern"], "optional": []},
62
+ "rh_white": {"mandatory": ["pattern"], "optional": []},
63
+ "lh_pial": {"mandatory": ["pattern"], "optional": []},
64
+ "rh_pial": {"mandatory": ["pattern"], "optional": []},
65
+ },
66
+ },
56
67
  }
57
68
 
58
69
 
@@ -103,8 +103,8 @@ class DefaultDataReader(PipelineStepMixin, UpdateMetaMixin):
103
103
  params = {}
104
104
  # For each type of data, try to read it
105
105
  for type_key, type_val in input.items():
106
- # Skip Warp data type
107
- if type_key == "Warp":
106
+ # Skip Warp and FreeSurfer data type
107
+ if type_key in ["Warp", "FreeSurfer"]:
108
108
  continue
109
109
 
110
110
  # Check for malformed datagrabber specification
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: junifer
3
- Version: 0.0.5.dev93
3
+ Version: 0.0.5.dev110
4
4
  Summary: JUelich NeuroImaging FEature extractoR
5
5
  Author-email: Fede Raimondo <f.raimondo@fz-juelich.de>, Synchon Mandal <s.mandal@fz-juelich.de>
6
6
  Maintainer-email: Fede Raimondo <f.raimondo@fz-juelich.de>, Synchon Mandal <s.mandal@fz-juelich.de>
@@ -1,5 +1,5 @@
1
1
  junifer/__init__.py,sha256=x1UR2jUcrUdm2HNl-3Qvyi4UUrU6ms5qm2qcmNY7zZk,391
2
- junifer/_version.py,sha256=OuEXOAHKhbHnm8jc8By5AoScd2qmQjT4HRDoRe1JlYM,426
2
+ junifer/_version.py,sha256=0CYyZtK7X8YB7AsyaklZtJl2q0LTvCx3UPEiwmdAmQU,428
3
3
  junifer/stats.py,sha256=jN22_qFvWYBU9ZIMnCSzN4iOscWnWrcrUPIdLeDkV64,6163
4
4
  junifer/api/__init__.py,sha256=pSj8V8tmwOAQ3sshWJfRfB-n3z5bcJj3pHOBX4-8ONc,251
5
5
  junifer/api/cli.py,sha256=53pews3mXkJ7DUDSkV51PbitYnuVAdQRkWG-gjO08Uw,16142
@@ -94,16 +94,16 @@ junifer/datagrabber/base.py,sha256=KgMSKfkwd4yLW4PhoJDoWMgcDkGmDoIs6jkgKyOJd9A,6
94
94
  junifer/datagrabber/datalad_base.py,sha256=gP-DsyCd2F8W-aF2PXOg99Ntp2bj8QEtb535y06q39o,11009
95
95
  junifer/datagrabber/dmcc13_benchmark.py,sha256=se9F6QVw9WX22MNld33OQv_BtdW-yPvXXu6kYykxLNw,12225
96
96
  junifer/datagrabber/multiple.py,sha256=eXQIsvSNvD8GuEITjMaMoi1GwoeyWXXbQMRi-f2qgc4,4923
97
- junifer/datagrabber/pattern.py,sha256=w1aTL5xZRH9vq3-RofdmW-d_1t2OrAKRL0McCQErHGE,15273
97
+ junifer/datagrabber/pattern.py,sha256=4OcGSCwBpeQOj6_YZohJjRFC_L69y7MAKsoE4-XO2So,15949
98
98
  junifer/datagrabber/pattern_datalad.py,sha256=R3LMeknT7tAXs2AN0XVPRf6tGkCMPgDfkNT2bfi7UNc,4526
99
- junifer/datagrabber/utils.py,sha256=s0Ife1qKEwXP47GfoxQ0qGqSP8L8ZNAms3HAvrSFoGI,9406
99
+ junifer/datagrabber/utils.py,sha256=2ujwltVc__qPJ2RwnEhSSoC_RkDchGEBNw7bC0a3bvk,9898
100
100
  junifer/datagrabber/aomic/__init__.py,sha256=R7yrRVBWsBW25CH0fw-KHpFwb_EC-MlPKDzssGfj5A0,281
101
- junifer/datagrabber/aomic/id1000.py,sha256=DGQVMgSv8HoUH6qj_WnBQTMunaJNSlVihjfiCmICN2c,5963
102
- junifer/datagrabber/aomic/piop1.py,sha256=CR4L9VJk-lJnoYTJDOAzs39Z_fgFQAYt2pvAmKfGl-g,8382
103
- junifer/datagrabber/aomic/piop2.py,sha256=_vrUnFyfhwFjWR3O23-ksVXlj49rc-q-eK1lVytIquo,8001
104
- junifer/datagrabber/aomic/tests/test_id1000.py,sha256=jKkhvglMsvEK06sSJXj4vuFvH2YR9CfEbcnElX_HU-o,4683
105
- junifer/datagrabber/aomic/tests/test_piop1.py,sha256=GuNllX8VbEbpGsPcEWf3ssRzcSrIj4RlLCFfTsbF-tU,5449
106
- junifer/datagrabber/aomic/tests/test_piop2.py,sha256=ydQhrF4fQsp6j6M79p68r8SKmDcwHwQccLKDW4lbztI,5248
101
+ junifer/datagrabber/aomic/id1000.py,sha256=2Lhu3Wf-U3RRLgoWbrSQCGxfri3--OQTsk9nrowK5G4,7184
102
+ junifer/datagrabber/aomic/piop1.py,sha256=r_OsORrVAU6mbOxuergIxo0ZR0Msx_I8MyrfiT_gD3E,9603
103
+ junifer/datagrabber/aomic/piop2.py,sha256=Twu2yN4-h-aR3-ZCg0ERxI54HGxr6C64cmBo6Nq3TAI,9222
104
+ junifer/datagrabber/aomic/tests/test_id1000.py,sha256=AWacDroSxvRjzozFjyRlDpiJpPflYRfhDm_RANrYAKM,3283
105
+ junifer/datagrabber/aomic/tests/test_piop1.py,sha256=J9ei2HLzdJPciysWjRo33cbZsqPF1OEDySmQWWNvYuM,4820
106
+ junifer/datagrabber/aomic/tests/test_piop2.py,sha256=Bk23KvRse4clMTuC88YntSfJnJyTunafC79Y1OJwJI0,4166
107
107
  junifer/datagrabber/hcp1200/__init__.py,sha256=zy4Qq1_m3vECEhioG-UDteco2b5cni_8xuElICaRtt4,189
108
108
  junifer/datagrabber/hcp1200/datalad_hcp1200.py,sha256=p5Bbg09qoM46km9eFSlspwLwOe6LMJFSIZ9NC9E2lmc,2432
109
109
  junifer/datagrabber/hcp1200/hcp1200.py,sha256=ohXHmrQHWjqRZSEXI6E5zla1d_t6LZTbv-cAj79w3PU,6091
@@ -113,10 +113,10 @@ junifer/datagrabber/tests/test_datagrabber_utils.py,sha256=x1nqFiHI9xHBQFwXji0DP
113
113
  junifer/datagrabber/tests/test_datalad_base.py,sha256=SYxUB9_4YPMfrb7iJM-aJCWbGa3EJfYz31wAUCNa03s,16285
114
114
  junifer/datagrabber/tests/test_dmcc13_benchmark.py,sha256=DcqkDXXBoabHFVbxekGR2NZyGeugGlxpOwXIwy38Ofg,9109
115
115
  junifer/datagrabber/tests/test_multiple.py,sha256=Mx3xfDrQiWG2W5MW24P5L2XiSeALpJ2-jFlzWkKtu9w,5659
116
- junifer/datagrabber/tests/test_pattern.py,sha256=Zmwg79f-qs6AEPVoFpooOquK7rm1hsmgkzuo11BG5PE,8019
116
+ junifer/datagrabber/tests/test_pattern.py,sha256=H55jYRPfT3rMsoIQOAnWJgw3nGrkU7m2xFa3-ed6NQE,9527
117
117
  junifer/datagrabber/tests/test_pattern_datalad.py,sha256=hxw_aXBwHjUo-aUrHescBA2dn1bSJxh-0oV8495iIEA,6483
118
118
  junifer/datareader/__init__.py,sha256=_vtrLX_vxlHFD90gPa3gWnhTuvfWM7Uzyj6y8ZPaWm8,259
119
- junifer/datareader/default.py,sha256=_ntvkcF0H089bHwj0VOLTKWp8RvP7qy2HyieWHuRp2c,6680
119
+ junifer/datareader/default.py,sha256=Md2q0hjoh454F-fmFFlyzwZMcu9vmFFT-akR42SSwUs,6711
120
120
  junifer/datareader/tests/test_default_reader.py,sha256=9dPZSkba1YQjFsA0XwdUbx5sq8DVIEZoy_WfMAcvRus,5220
121
121
  junifer/external/__init__.py,sha256=CBB7eQul2hf-WWwT_PYFV1MS9KkXlZBO7oQWWVLgB_I,110
122
122
  junifer/external/h5io/h5io/__init__.py,sha256=LG7ru_Rt3EOE2H4PGYfBhC12Iax3yeTquZkd8TICiKk,469
@@ -253,10 +253,10 @@ junifer/utils/logging.py,sha256=furcU3XIUpUvnpe4PEwzWWIWgmH4j2ZA4MQdvSGWjj0,9216
253
253
  junifer/utils/tests/test_fs.py,sha256=WQS7cKlKEZ742CIuiOYYpueeAhY9PqlastfDVpVVtvE,923
254
254
  junifer/utils/tests/test_helpers.py,sha256=k5qqfxK8dFyuewTJyR1Qn6-nFaYNuVr0ysc18bfPjyU,929
255
255
  junifer/utils/tests/test_logging.py,sha256=l8oo-AiBV7H6_IzlsNcj__cLeZBUvgIGoaMszD9VaJg,7754
256
- junifer-0.0.5.dev93.dist-info/AUTHORS.rst,sha256=rmULKpchpSol4ExWFdm-qu4fkpSZPYqIESVJBZtGb6E,163
257
- junifer-0.0.5.dev93.dist-info/LICENSE.md,sha256=MqCnOBu8uXsEOzRZWh9EBVfVz-kE9NkXcLCrtGXo2yU,34354
258
- junifer-0.0.5.dev93.dist-info/METADATA,sha256=GPQBJL5Fvtivl1q6VYeAV6eoIDVCjubyMZCizh3mn9k,8234
259
- junifer-0.0.5.dev93.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
260
- junifer-0.0.5.dev93.dist-info/entry_points.txt,sha256=DxFvKq0pOqRunAK0FxwJcoDfV1-dZvsFDpD5HRqSDhw,48
261
- junifer-0.0.5.dev93.dist-info/top_level.txt,sha256=4bAq1R2QFQ4b3hohjys2JBvxrl0GKk5LNFzYvz9VGcA,8
262
- junifer-0.0.5.dev93.dist-info/RECORD,,
256
+ junifer-0.0.5.dev110.dist-info/AUTHORS.rst,sha256=rmULKpchpSol4ExWFdm-qu4fkpSZPYqIESVJBZtGb6E,163
257
+ junifer-0.0.5.dev110.dist-info/LICENSE.md,sha256=MqCnOBu8uXsEOzRZWh9EBVfVz-kE9NkXcLCrtGXo2yU,34354
258
+ junifer-0.0.5.dev110.dist-info/METADATA,sha256=SgyLdexnard9sSn0O75ZjN0DxjMCQ8tElN68xB8KNtw,8235
259
+ junifer-0.0.5.dev110.dist-info/WHEEL,sha256=GJ7t_kWBFywbagK5eo9IoUwLW6oyOeTKmQ-9iHFVNxQ,92
260
+ junifer-0.0.5.dev110.dist-info/entry_points.txt,sha256=DxFvKq0pOqRunAK0FxwJcoDfV1-dZvsFDpD5HRqSDhw,48
261
+ junifer-0.0.5.dev110.dist-info/top_level.txt,sha256=4bAq1R2QFQ4b3hohjys2JBvxrl0GKk5LNFzYvz9VGcA,8
262
+ junifer-0.0.5.dev110.dist-info/RECORD,,