blissdata 2.4.2__tar.gz → 2.4.4__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.
- {blissdata-2.4.2/src/blissdata.egg-info → blissdata-2.4.4}/PKG-INFO +2 -3
- {blissdata-2.4.2 → blissdata-2.4.4}/pyproject.toml +2 -3
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/redis_hdf5.py +18 -8
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5map/data_items.py +5 -6
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/lima/image_utils.py +6 -4
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/scan.py +6 -1
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/store.py +17 -2
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/__init__.py +1 -1
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/plugins/test_plugin_base.py +37 -32
- {blissdata-2.4.2 → blissdata-2.4.4/src/blissdata.egg-info}/PKG-INFO +2 -3
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata.egg-info/requires.txt +1 -2
- {blissdata-2.4.2 → blissdata-2.4.4}/LICENSE +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/README.md +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/setup.cfg +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/beacon/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/beacon/_base.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/beacon/_utils.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/beacon/config.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/beacon/data.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/beacon/files.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/deprecation.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/exceptions.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/abstract.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/dynamic_hdf5.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/file_arguments.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/h5_scan_map.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/static_hdf5.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/utils/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/utils/bliss.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/utils/hdf5.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/utils/hdf5_retry.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/utils/lima.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5api/utils/types.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5map/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/h5map/hdf5_items.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/lima/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/lima/client.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/py.typed +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/encoding/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/encoding/json.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/encoding/numeric.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/event_stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/exceptions.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/identities.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/redis_engine/memory_tracker.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/scan.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/schemas/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/schemas/scan_info.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/schemas/scan_info_display.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/base.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/default.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/encoding/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/encoding/json.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/encoding/numeric.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/event_stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/hdf5_fallback/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/hdf5_fallback/stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/lima/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/lima/stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/scan_sequence/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/scan_sequence/stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/streams/sink.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/beacon/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/beacon/test_config.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/beacon/test_data.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/beacon/test_files.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/conftest.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/scanner.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/test_dynamic_files.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/test_h5api_lima_utils.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/test_hdf5_handlers.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/test_redis_files.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5api/test_static_files.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5map/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5map/test_data_items.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/h5map/test_hdf5_items.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/lima/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/lima/test_image_utils.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/conftest.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/test_cursor.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/test_memory_tracker.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/test_scan.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/test_search.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/redis_engine/utils.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/encoding/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/encoding/test_json.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/encoding/test_numeric.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/plugins/__init__.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/plugins/test_file_backed_stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/plugins/test_lima_stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/test_event_stream.py +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata.egg-info/SOURCES.txt +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata.egg-info/dependency_links.txt +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata.egg-info/entry_points.txt +0 -0
- {blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: blissdata
|
|
3
|
-
Version: 2.4.
|
|
3
|
+
Version: 2.4.4
|
|
4
4
|
Summary: Bliss data streaming client
|
|
5
5
|
Maintainer: BCU (ESRF)
|
|
6
6
|
License-Expression: LGPL-3.0-or-later
|
|
@@ -39,9 +39,8 @@ Requires-Dist: blissdata[test]; extra == "dev"
|
|
|
39
39
|
Requires-Dist: black; extra == "dev"
|
|
40
40
|
Requires-Dist: flake8>=4; extra == "dev"
|
|
41
41
|
Requires-Dist: flake8-pep585; extra == "dev"
|
|
42
|
-
Requires-Dist: mkdocs; extra == "dev"
|
|
42
|
+
Requires-Dist: mkdocs<2; extra == "dev"
|
|
43
43
|
Requires-Dist: mkdocs-material; extra == "dev"
|
|
44
|
-
Requires-Dist: mkdocstrings[python]>=0.18; extra == "dev"
|
|
45
44
|
Provides-Extra: beacon
|
|
46
45
|
Requires-Dist: ruamel.yaml; extra == "beacon"
|
|
47
46
|
Dynamic: license-file
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "blissdata"
|
|
3
|
-
version = "2.4.
|
|
3
|
+
version = "2.4.4"
|
|
4
4
|
description = "Bliss data streaming client"
|
|
5
5
|
readme = "README.md"
|
|
6
6
|
license = "LGPL-3.0-or-later"
|
|
@@ -46,9 +46,8 @@ dev = [
|
|
|
46
46
|
"black",
|
|
47
47
|
"flake8>=4",
|
|
48
48
|
"flake8-pep585",
|
|
49
|
-
"mkdocs",
|
|
49
|
+
"mkdocs<2",
|
|
50
50
|
"mkdocs-material",
|
|
51
|
-
"mkdocstrings[python]>=0.18",
|
|
52
51
|
]
|
|
53
52
|
beacon = ["ruamel.yaml"]
|
|
54
53
|
|
|
@@ -15,21 +15,31 @@ from blissdata.h5api.h5_scan_map import H5ScanMap
|
|
|
15
15
|
|
|
16
16
|
|
|
17
17
|
class Attributes(abstract.Attributes):
|
|
18
|
-
def __init__(self,
|
|
19
|
-
self.
|
|
18
|
+
def __init__(self, attrs: dict[str : h5m.DataItemType]):
|
|
19
|
+
self._attrs: dict[str : h5m.DataItemType] = attrs
|
|
20
20
|
super().__init__()
|
|
21
21
|
|
|
22
22
|
def __repr__(self):
|
|
23
|
-
return f"<Attributes of
|
|
23
|
+
return f"<Attributes of Live-HDF5 object at {hex(id(self))}>"
|
|
24
24
|
|
|
25
25
|
def __getitem__(self, key: str):
|
|
26
|
-
|
|
26
|
+
value = self._attrs[key].decode()
|
|
27
|
+
# h5map decoded values are always numpy arrays, "O" type is used for
|
|
28
|
+
# strings. In h5py the same value will be returned as 'bytes' when in a
|
|
29
|
+
# dataset, but as 'str' when in an attribute.
|
|
30
|
+
if value.dtype == np.dtype("O"):
|
|
31
|
+
# Decode 'bytes' into 'str' to reproduce h5py attribute's behavior
|
|
32
|
+
value = np.vectorize(lambda x: x.decode(), otypes=[np.dtype("O")])(value)
|
|
33
|
+
if value.shape == ():
|
|
34
|
+
# extract value when array is a scalar
|
|
35
|
+
value = value[()]
|
|
36
|
+
return value
|
|
27
37
|
|
|
28
38
|
def __iter__(self):
|
|
29
|
-
yield from self.
|
|
39
|
+
yield from self._attrs
|
|
30
40
|
|
|
31
41
|
def __len__(self):
|
|
32
|
-
return len(self.
|
|
42
|
+
return len(self._attrs)
|
|
33
43
|
|
|
34
44
|
|
|
35
45
|
class File(abstract.File):
|
|
@@ -68,7 +78,7 @@ class File(abstract.File):
|
|
|
68
78
|
|
|
69
79
|
@property
|
|
70
80
|
def attrs(self) -> abstract.Attributes:
|
|
71
|
-
return Attributes({"NX_class": "NXroot"})
|
|
81
|
+
return Attributes({"NX_class": h5m.InlineRaw("NXroot")})
|
|
72
82
|
|
|
73
83
|
@property
|
|
74
84
|
def file(self) -> "File":
|
|
@@ -541,4 +551,4 @@ def dataset_factory(parent: File, path: str, item: h5m.HDF5ItemType, scan) -> Da
|
|
|
541
551
|
# TODO
|
|
542
552
|
raise NotImplementedError
|
|
543
553
|
|
|
544
|
-
return Dataset(parent, path, item, array, virtual, external)
|
|
554
|
+
return Dataset(parent, path, item.attributes, array, virtual, external)
|
|
@@ -211,20 +211,19 @@ class Compound(BaseModel):
|
|
|
211
211
|
return rec.view(np.ndarray)
|
|
212
212
|
|
|
213
213
|
@model_validator(mode="after")
|
|
214
|
-
|
|
215
|
-
def verify_names_and_shapes(cls, value):
|
|
214
|
+
def verify_names_and_shapes(self):
|
|
216
215
|
"""Ensure uniqueness of names and shape equality between columns"""
|
|
217
|
-
if len(
|
|
216
|
+
if len(self.columns) != len({name for name, _ in self.columns}):
|
|
218
217
|
raise ValueError("found columns with same name")
|
|
219
218
|
|
|
220
|
-
shape_iterator = iter((col.decode().shape for _, col in
|
|
219
|
+
shape_iterator = iter((col.decode().shape for _, col in self.columns))
|
|
221
220
|
try:
|
|
222
221
|
first_shape = next(shape_iterator)
|
|
223
222
|
except StopIteration:
|
|
224
|
-
return
|
|
223
|
+
return self
|
|
225
224
|
if not all(first_shape == shape for shape in shape_iterator):
|
|
226
225
|
raise ValueError("columns have different shapes")
|
|
227
|
-
return
|
|
226
|
+
return self
|
|
228
227
|
|
|
229
228
|
|
|
230
229
|
class Stream(BaseModel):
|
|
@@ -273,8 +273,9 @@ def decode_devencoded_video(raw_data: bytes | tuple[str, bytes]) -> ImageData |
|
|
|
273
273
|
|
|
274
274
|
if mode in MODE_TO_NUMPY:
|
|
275
275
|
dtype = MODE_TO_NUMPY[mode]
|
|
276
|
-
data = numpy.frombuffer(raw_data, offset=header_size, dtype=dtype).
|
|
277
|
-
|
|
276
|
+
data = numpy.frombuffer(raw_data, offset=header_size, dtype=dtype).reshape(
|
|
277
|
+
(image_height, image_width), copy=True
|
|
278
|
+
)
|
|
278
279
|
elif mode in _RGB_CODECS:
|
|
279
280
|
data = decode_rgb_data(
|
|
280
281
|
raw_data, image_width, image_height, mode, offset=header_size
|
|
@@ -411,8 +412,9 @@ def decode_devencoded_image(raw_data: bytes | tuple[str, bytes]) -> ImageData:
|
|
|
411
412
|
except Exception:
|
|
412
413
|
raise ImageFormatNotSupported("Data format %s is not supported" % mode)
|
|
413
414
|
|
|
414
|
-
data = numpy.frombuffer(raw_data, offset=header_size, dtype=dtype)
|
|
415
|
-
|
|
415
|
+
data = numpy.frombuffer(raw_data, offset=header_size, dtype=dtype).reshape(
|
|
416
|
+
(dim2, dim1)
|
|
417
|
+
)
|
|
416
418
|
|
|
417
419
|
# Create a memory copy only if it is needed
|
|
418
420
|
if not data.flags.writeable:
|
|
@@ -357,6 +357,7 @@ class Scan:
|
|
|
357
357
|
|
|
358
358
|
stream = self._wrap_event_stream(event_stream)
|
|
359
359
|
if isinstance(stream, BrokenStream):
|
|
360
|
+
event_stream._sink.stop()
|
|
360
361
|
raise stream._exception
|
|
361
362
|
self._model.data_streams[name] = model
|
|
362
363
|
self._writer_streams[name] = stream
|
|
@@ -374,7 +375,11 @@ class Scan:
|
|
|
374
375
|
multiple places."""
|
|
375
376
|
model = self._model.data_streams[name]
|
|
376
377
|
rw_event_stream = EventStream.create(self._data_store, name, model)
|
|
377
|
-
|
|
378
|
+
stream = self._wrap_event_stream(rw_event_stream)
|
|
379
|
+
if isinstance(stream, BrokenStream):
|
|
380
|
+
rw_event_stream._sink.stop()
|
|
381
|
+
raise stream._exception
|
|
382
|
+
return stream
|
|
378
383
|
|
|
379
384
|
@needs_write_permission
|
|
380
385
|
def _close_writer_streams(self):
|
|
@@ -109,6 +109,16 @@ class DataStore:
|
|
|
109
109
|
f"Cannot re-index a non-empty Redis database, {nb_keys} keys are already present"
|
|
110
110
|
)
|
|
111
111
|
|
|
112
|
+
# Ensure ReJSON and RediSearch modules are installed on server side
|
|
113
|
+
installed_modules = {
|
|
114
|
+
module[b"name"].decode() for module in self._redis.module_list()
|
|
115
|
+
}
|
|
116
|
+
for module in ["ReJSON", "search"]:
|
|
117
|
+
if module not in installed_modules:
|
|
118
|
+
raise RuntimeError(
|
|
119
|
+
f"Redis server is missing '{module}' module for blissdata to function"
|
|
120
|
+
)
|
|
121
|
+
|
|
112
122
|
# Configure RediSearch indexing with redis-om, but block redis-om mechanism which auto-discover any
|
|
113
123
|
# model class for indexing. Instead we set model_registry by hand to only enable self._scan_model indexing
|
|
114
124
|
# and not to interfer with existing DataStores.
|
|
@@ -122,7 +132,12 @@ class DataStore:
|
|
|
122
132
|
|
|
123
133
|
# TODO how to ensure this is always greater than the number of scan in redis ?
|
|
124
134
|
# otherwise search results may be truncated without warning
|
|
125
|
-
|
|
135
|
+
try:
|
|
136
|
+
# redis-server 8+ API
|
|
137
|
+
self._redis.config_set("search-max-prefix-expansions", 2000)
|
|
138
|
+
except redis.exceptions.ResponseError:
|
|
139
|
+
# fallback to legacy API
|
|
140
|
+
self._redis.ft().config_set("MAXPREFIXEXPANSIONS", 2000)
|
|
126
141
|
|
|
127
142
|
# Server side sealing function:
|
|
128
143
|
# For the seal to contain the complete length of the stream, we
|
|
@@ -350,7 +365,7 @@ redis.register_function('seal_stream', seal_stream)"""
|
|
|
350
365
|
for stream_key in stream_keys:
|
|
351
366
|
pipe.xrevrange(stream_key, count=1)
|
|
352
367
|
raw = pipe.execute()
|
|
353
|
-
scan_states = [ScanState(val[0][1][b"state"].decode()) for val in raw]
|
|
368
|
+
scan_states = [ScanState(int(val[0][1][b"state"].decode())) for val in raw]
|
|
354
369
|
|
|
355
370
|
return {key: state for key, state in zip(scan_keys, scan_states)}
|
|
356
371
|
|
|
@@ -12,11 +12,11 @@ from blissdata.streams.default import (
|
|
|
12
12
|
)
|
|
13
13
|
|
|
14
14
|
|
|
15
|
-
class
|
|
15
|
+
class MockPluginView(View):
|
|
16
16
|
pass
|
|
17
17
|
|
|
18
18
|
|
|
19
|
-
class
|
|
19
|
+
class MockPluginStream(Stream):
|
|
20
20
|
def __init__(self, event_stream):
|
|
21
21
|
if event_stream.info.get("fail", False):
|
|
22
22
|
raise Exception("Oops, broken plugin...")
|
|
@@ -25,56 +25,61 @@ class FakePluginStream(Stream):
|
|
|
25
25
|
@staticmethod
|
|
26
26
|
def make_definition(name, info={}) -> StreamDefinition:
|
|
27
27
|
return Stream.make_definition(
|
|
28
|
-
name, dtype=np.int64, info=info | {"plugin": "
|
|
28
|
+
name, dtype=np.int64, info=info | {"plugin": "mock"}
|
|
29
29
|
)
|
|
30
30
|
|
|
31
31
|
@property
|
|
32
32
|
def kind(self):
|
|
33
|
-
return "
|
|
33
|
+
return "mock"
|
|
34
34
|
|
|
35
35
|
@property
|
|
36
36
|
def plugin(self):
|
|
37
|
-
return "
|
|
37
|
+
return "mock"
|
|
38
38
|
|
|
39
39
|
def _build_view_from_events(self, index, events: EventRange, last_only):
|
|
40
|
-
return
|
|
40
|
+
return MockPluginView(events)
|
|
41
41
|
|
|
42
42
|
|
|
43
|
-
@
|
|
44
|
-
def
|
|
45
|
-
|
|
43
|
+
@pytest.fixture
|
|
44
|
+
def mock_plugin(monkeypatch):
|
|
45
|
+
@contextmanager
|
|
46
|
+
def mock_plugin_ctx():
|
|
47
|
+
"""Emulate installation of 'mock' plugin module"""
|
|
46
48
|
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
49
|
+
class MockPluginModule:
|
|
50
|
+
stream_cls = MockPluginStream
|
|
51
|
+
view_cls = MockPluginView
|
|
50
52
|
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
53
|
+
try:
|
|
54
|
+
monkeypatch.setitem(
|
|
55
|
+
blissdata.redis_engine.scan.loaded_plugins, "mock", MockPluginModule
|
|
56
|
+
)
|
|
57
|
+
yield
|
|
58
|
+
finally:
|
|
59
|
+
monkeypatch.delitem(blissdata.redis_engine.scan.loaded_plugins, "mock")
|
|
57
60
|
|
|
61
|
+
return mock_plugin_ctx
|
|
58
62
|
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
63
|
+
|
|
64
|
+
def test_plugin_load(dummy_scan, mock_plugin):
|
|
65
|
+
with mock_plugin():
|
|
66
|
+
stream_definition = MockPluginStream.make_definition("mystream")
|
|
62
67
|
_ = dummy_scan.create_stream(stream_definition)
|
|
63
68
|
dummy_scan.prepare()
|
|
64
69
|
|
|
65
70
|
stream = dummy_scan.streams["mystream"]
|
|
66
|
-
assert isinstance(stream,
|
|
71
|
+
assert isinstance(stream, MockPluginStream)
|
|
67
72
|
|
|
68
73
|
|
|
69
74
|
def test_missing_plugin_create(dummy_scan):
|
|
70
|
-
stream_definition =
|
|
75
|
+
stream_definition = MockPluginStream.make_definition("mystream")
|
|
71
76
|
with pytest.raises(MissingPluginException):
|
|
72
77
|
_ = dummy_scan.create_stream(stream_definition)
|
|
73
78
|
|
|
74
79
|
|
|
75
|
-
def test_missing_plugin_load(dummy_scan):
|
|
76
|
-
with
|
|
77
|
-
stream_definition =
|
|
80
|
+
def test_missing_plugin_load(dummy_scan, mock_plugin):
|
|
81
|
+
with mock_plugin():
|
|
82
|
+
stream_definition = MockPluginStream.make_definition("mystream")
|
|
78
83
|
_ = dummy_scan.create_stream(stream_definition)
|
|
79
84
|
dummy_scan.prepare()
|
|
80
85
|
stream = dummy_scan.streams["mystream"]
|
|
@@ -83,9 +88,9 @@ def test_missing_plugin_load(dummy_scan):
|
|
|
83
88
|
len(stream)
|
|
84
89
|
|
|
85
90
|
|
|
86
|
-
def test_broken_plugin_create(data_store, dummy_scan):
|
|
87
|
-
with
|
|
88
|
-
stream_definition =
|
|
91
|
+
def test_broken_plugin_create(data_store, dummy_scan, mock_plugin):
|
|
92
|
+
with mock_plugin():
|
|
93
|
+
stream_definition = MockPluginStream.make_definition(
|
|
89
94
|
"mystream", info={"fail": True}
|
|
90
95
|
)
|
|
91
96
|
with pytest.raises(Exception) as exc_info:
|
|
@@ -93,9 +98,9 @@ def test_broken_plugin_create(data_store, dummy_scan):
|
|
|
93
98
|
assert "Oops, broken plugin..." in str(exc_info)
|
|
94
99
|
|
|
95
100
|
|
|
96
|
-
def test_broken_plugin_load(data_store, dummy_scan):
|
|
97
|
-
with
|
|
98
|
-
stream_definition =
|
|
101
|
+
def test_broken_plugin_load(data_store, dummy_scan, mock_plugin):
|
|
102
|
+
with mock_plugin():
|
|
103
|
+
stream_definition = MockPluginStream.make_definition(
|
|
99
104
|
"mystream", info={"fail": False}
|
|
100
105
|
)
|
|
101
106
|
rw_stream = dummy_scan.create_stream(stream_definition)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: blissdata
|
|
3
|
-
Version: 2.4.
|
|
3
|
+
Version: 2.4.4
|
|
4
4
|
Summary: Bliss data streaming client
|
|
5
5
|
Maintainer: BCU (ESRF)
|
|
6
6
|
License-Expression: LGPL-3.0-or-later
|
|
@@ -39,9 +39,8 @@ Requires-Dist: blissdata[test]; extra == "dev"
|
|
|
39
39
|
Requires-Dist: black; extra == "dev"
|
|
40
40
|
Requires-Dist: flake8>=4; extra == "dev"
|
|
41
41
|
Requires-Dist: flake8-pep585; extra == "dev"
|
|
42
|
-
Requires-Dist: mkdocs; extra == "dev"
|
|
42
|
+
Requires-Dist: mkdocs<2; extra == "dev"
|
|
43
43
|
Requires-Dist: mkdocs-material; extra == "dev"
|
|
44
|
-
Requires-Dist: mkdocstrings[python]>=0.18; extra == "dev"
|
|
45
44
|
Provides-Extra: beacon
|
|
46
45
|
Requires-Dist: ruamel.yaml; extra == "beacon"
|
|
47
46
|
Dynamic: license-file
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{blissdata-2.4.2 → blissdata-2.4.4}/src/blissdata/tests/streams/plugins/test_file_backed_stream.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|