Skip to content

Commit 7d83f6b

Browse files
authored
Merge pull request #544 from FZJ-INM1-BDA/feat_ngInfoLocalCache
fix: info uses siibra.retrieval module for local file cache
2 parents 7236737 + ad2d639 commit 7d83f6b

File tree

2 files changed

+33
-11
lines changed

2 files changed

+33
-11
lines changed

siibra/volumes/providers/neuroglancer.py

+19-11
Original file line numberDiff line numberDiff line change
@@ -20,13 +20,14 @@
2020
from ...locations import boundingbox as _boundingbox
2121

2222
from neuroglancer_scripts.precomputed_io import get_IO_for_existing_dataset
23-
from neuroglancer_scripts.accessor import get_accessor_for_url
23+
from neuroglancer_scripts.http_accessor import HttpAccessor
2424
from neuroglancer_scripts.mesh import read_precomputed_mesh, affine_transform_mesh
2525
from io import BytesIO
2626
import nibabel as nib
2727
import os
2828
import numpy as np
2929
from typing import Union, Dict, Tuple
30+
import json
3031

3132

3233
class NeuroglancerProvider(_provider.VolumeProvider, srctype="neuroglancer/precomputed"):
@@ -210,8 +211,9 @@ def __init__(self, url: str):
210211
assert isinstance(url, str)
211212
self.url = url
212213
self._scales_cached = None
213-
self._io = None
214+
self._info = None
214215
self._transform_nm = None
216+
self._io = None
215217

216218
@property
217219
def transform_nm(self):
@@ -234,34 +236,40 @@ def transform_nm(self, val):
234236
self._transform_nm = val
235237

236238
@property
237-
def map_type(self):
239+
def io(self):
238240
if self._io is None:
241+
accessor = HttpAccessor(self.url)
242+
self._io = get_IO_for_existing_dataset(accessor)
243+
return self._io
244+
245+
@property
246+
def map_type(self):
247+
if self._info is None:
239248
self._bootstrap()
240249
return (
241250
MapType.LABELLED
242-
if self._io.info.get("type") == "segmentation"
251+
if self._info.get("type") == "segmentation"
243252
else MapType.STATISTICAL
244253
)
245254

246255
@map_type.setter
247256
def map_type(self, val):
248257
if val is not None:
249258
logger.debug(
250-
"NeuroglancerVolume can determine its own maptype from self._io.info.get('type')"
259+
"NeuroglancerVolume can determine its own maptype from self._info.get('type')"
251260
)
252261

253262
def _bootstrap(self):
254-
accessor = get_accessor_for_url(self.url)
255-
self._io = get_IO_for_existing_dataset(accessor)
263+
self._info = requests.HttpRequest(f"{self.url}/info", func=lambda b: json.loads(b.decode())).get()
256264
self._scales_cached = sorted(
257-
[NeuroglancerScale(self, i) for i in self._io.info["scales"]]
265+
[NeuroglancerScale(self, i) for i in self._info["scales"]]
258266
)
259267

260268
@property
261269
def dtype(self):
262-
if self._io is None:
270+
if self._info is None:
263271
self._bootstrap()
264-
return np.dtype(self._io.info["data_type"])
272+
return np.dtype(self._info["data_type"])
265273

266274
@property
267275
def scales(self):
@@ -422,7 +430,7 @@ def _read_chunk(self, gx, gy, gz):
422430
y0 = gy * self.chunk_sizes[1]
423431
z0 = gz * self.chunk_sizes[2]
424432
x1, y1, z1 = np.minimum(self.chunk_sizes + [x0, y0, z0], self.size)
425-
chunk_czyx = self.volume._io.read_chunk(self.key, (x0, x1, y0, y1, z0, z1))
433+
chunk_czyx = self.volume.io.read_chunk(self.key, (x0, x1, y0, y1, z0, z1))
426434
if not chunk_czyx.shape[0] == 1 and not self.color_warning_issued:
427435
logger.warning(
428436
"Color channel data is not yet supported. Returning first channel only."
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
from unittest.mock import patch, MagicMock
2+
3+
from siibra.volumes.providers.neuroglancer import NeuroglancerVolume
4+
from siibra.retrieval import requests
5+
6+
7+
@patch.object(requests, 'HttpRequest')
8+
def test_ngvol_info_uses_cached(MockedHttpReq):
9+
MockedHttpReq.return_value = MagicMock()
10+
MockedHttpReq.return_value.get.return_value = {"scales": []}
11+
vol = NeuroglancerVolume("foo/bar")
12+
vol._bootstrap()
13+
assert MockedHttpReq.called
14+
MockedHttpReq.return_value.get.assert_called_once()

0 commit comments

Comments
 (0)