bw-processing 0.9.6__tar.gz → 1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {bw_processing-0.9.6/bw_processing.egg-info → bw_processing-1.0}/PKG-INFO +1 -1
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/__init__.py +1 -1
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/constants.py +2 -1
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/datapackage.py +9 -0
- {bw_processing-0.9.6 → bw_processing-1.0/bw_processing.egg-info}/PKG-INFO +1 -1
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing.egg-info/SOURCES.txt +13 -20
- bw_processing-1.0/tests/test_array_creation.py +14 -0
- bw_processing-1.0/tests/test_datapackage.py +499 -0
- bw_processing-1.0/tests/test_filesystem.py +33 -0
- bw_processing-1.0/tests/test_filtered_datapackage.py +151 -0
- bw_processing-1.0/tests/test_indexing.py +384 -0
- bw_processing-1.0/tests/test_integration.py +472 -0
- bw_processing-1.0/tests/test_interfaces.py +113 -0
- bw_processing-1.0/tests/test_io_parquet_helpers.py +155 -0
- bw_processing-1.0/tests/test_io_pyarrow_helpers.py +66 -0
- bw_processing-1.0/tests/test_loading.py +64 -0
- bw_processing-1.0/tests/test_merging.py +369 -0
- bw_processing-1.0/tests/test_proxies.py +27 -0
- bw_processing-1.0/tests/test_unique_fields.py +139 -0
- bw_processing-0.9.6/dev/calculation_package.py +0 -179
- bw_processing-0.9.6/dev/loading.py +0 -85
- bw_processing-0.9.6/dev/processed_package.py +0 -261
- bw_processing-0.9.6/dev/resources.py +0 -32
- bw_processing-0.9.6/dev/speed_tests.py +0 -47
- bw_processing-0.9.6/docs/conf.py +0 -109
- {bw_processing-0.9.6 → bw_processing-1.0}/LICENSE +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/MANIFEST.in +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/README.md +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/array_creation.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/errors.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/__init__.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/another name.indices.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/sa-data-vector-from-dict.data.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/sa-data-vector-from-dict.distributions.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/sa-data-vector-from-dict.flip.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/sa-data-vector-from-dict.indices.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/some name.data.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/some name.flip.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_1/some name.indices.parquet +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/datapackage_2.zip +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/interfaces.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/parquet_files.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/examples/simple.zip +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/filesystem.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/indexing.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/io_helpers.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/io_parquet_helpers.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/io_pyarrow_helpers.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/merging.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/proxies.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/unique_fields.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing/utils.py +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing.egg-info/dependency_links.txt +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing.egg-info/requires.txt +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/bw_processing.egg-info/top_level.txt +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/pyproject.toml +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/setup.cfg +0 -0
- {bw_processing-0.9.6 → bw_processing-1.0}/tests/test_utils.py +0 -0
|
@@ -4,6 +4,7 @@ from enum import Enum
|
|
|
4
4
|
import numpy as np
|
|
5
5
|
|
|
6
6
|
MAX_SIGNED_32BIT_INT = 2147483647
|
|
7
|
+
MAX_SIGNED_64BIT_INT = 9223372036854775807
|
|
7
8
|
|
|
8
9
|
# We could try to save space by not storing the columns
|
|
9
10
|
# `row_index` and `col_index`, and add them after loading from
|
|
@@ -20,7 +21,7 @@ UNCERTAINTY_DTYPE = [
|
|
|
20
21
|
("maximum", np.float32),
|
|
21
22
|
("negative", bool),
|
|
22
23
|
]
|
|
23
|
-
INDICES_DTYPE = [("row", np.
|
|
24
|
+
INDICES_DTYPE = [("row", np.int64), ("col", np.int64)]
|
|
24
25
|
|
|
25
26
|
NAME_RE = re.compile(r"^[\w\-\.]*$")
|
|
26
27
|
|
|
@@ -14,6 +14,8 @@ from morefs.dict import DictFS
|
|
|
14
14
|
from .constants import (
|
|
15
15
|
DEFAULT_LICENSES,
|
|
16
16
|
INDICES_DTYPE,
|
|
17
|
+
MAX_SIGNED_32BIT_INT,
|
|
18
|
+
MAX_SIGNED_64BIT_INT,
|
|
17
19
|
NUMPY_SERIALIZE_FORMAT_EXTENSION,
|
|
18
20
|
NUMPY_SERIALIZE_FORMAT_NAME,
|
|
19
21
|
PARQUET_SERIALIZE_FORMAT_EXTENSION,
|
|
@@ -257,6 +259,12 @@ class DatapackageBase(ABC):
|
|
|
257
259
|
|
|
258
260
|
self.data[index] = resource
|
|
259
261
|
|
|
262
|
+
def get_max_index_value(self) -> int:
|
|
263
|
+
"""Get maximum index value (max signed 32 or 64 bit integer) for this datapackage"""
|
|
264
|
+
if self.metadata.get("64_bit_indices"):
|
|
265
|
+
return MAX_SIGNED_64BIT_INT
|
|
266
|
+
return MAX_SIGNED_32BIT_INT
|
|
267
|
+
|
|
260
268
|
|
|
261
269
|
class FilteredDatapackage(DatapackageBase):
|
|
262
270
|
"""A subset of a datapackage. Used in matrix construction or other data manipulation operations.
|
|
@@ -360,6 +368,7 @@ class Datapackage(DatapackageBase):
|
|
|
360
368
|
"combinatorial": combinatorial,
|
|
361
369
|
"sequential": sequential,
|
|
362
370
|
"seed": seed,
|
|
371
|
+
"64_bit_indices": True,
|
|
363
372
|
"sum_intra_duplicates": sum_intra_duplicates,
|
|
364
373
|
"sum_inter_duplicates": sum_inter_duplicates,
|
|
365
374
|
"matrix_serialize_format_type": matrix_serialize_format_type.value,
|
|
@@ -2,26 +2,6 @@ LICENSE
|
|
|
2
2
|
MANIFEST.in
|
|
3
3
|
README.md
|
|
4
4
|
pyproject.toml
|
|
5
|
-
./bw_processing/__init__.py
|
|
6
|
-
./bw_processing/array_creation.py
|
|
7
|
-
./bw_processing/constants.py
|
|
8
|
-
./bw_processing/datapackage.py
|
|
9
|
-
./bw_processing/errors.py
|
|
10
|
-
./bw_processing/filesystem.py
|
|
11
|
-
./bw_processing/indexing.py
|
|
12
|
-
./bw_processing/io_helpers.py
|
|
13
|
-
./bw_processing/merging.py
|
|
14
|
-
./bw_processing/proxies.py
|
|
15
|
-
./bw_processing/unique_fields.py
|
|
16
|
-
./bw_processing/utils.py
|
|
17
|
-
./bw_processing/examples/__init__.py
|
|
18
|
-
./bw_processing/examples/interfaces.py
|
|
19
|
-
./dev/calculation_package.py
|
|
20
|
-
./dev/loading.py
|
|
21
|
-
./dev/processed_package.py
|
|
22
|
-
./dev/resources.py
|
|
23
|
-
./dev/speed_tests.py
|
|
24
|
-
./docs/conf.py
|
|
25
5
|
bw_processing/__init__.py
|
|
26
6
|
bw_processing/array_creation.py
|
|
27
7
|
bw_processing/constants.py
|
|
@@ -54,4 +34,17 @@ bw_processing/examples/datapackage_1/sa-data-vector-from-dict.indices.parquet
|
|
|
54
34
|
bw_processing/examples/datapackage_1/some name.data.parquet
|
|
55
35
|
bw_processing/examples/datapackage_1/some name.flip.parquet
|
|
56
36
|
bw_processing/examples/datapackage_1/some name.indices.parquet
|
|
37
|
+
tests/test_array_creation.py
|
|
38
|
+
tests/test_datapackage.py
|
|
39
|
+
tests/test_filesystem.py
|
|
40
|
+
tests/test_filtered_datapackage.py
|
|
41
|
+
tests/test_indexing.py
|
|
42
|
+
tests/test_integration.py
|
|
43
|
+
tests/test_interfaces.py
|
|
44
|
+
tests/test_io_parquet_helpers.py
|
|
45
|
+
tests/test_io_pyarrow_helpers.py
|
|
46
|
+
tests/test_loading.py
|
|
47
|
+
tests/test_merging.py
|
|
48
|
+
tests/test_proxies.py
|
|
49
|
+
tests/test_unique_fields.py
|
|
57
50
|
tests/test_utils.py
|
|
@@ -0,0 +1,499 @@
|
|
|
1
|
+
import shutil
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
|
|
4
|
+
import numpy as np
|
|
5
|
+
import pandas as pd
|
|
6
|
+
import pytest
|
|
7
|
+
from fsspec.implementations.zip import ZipFileSystem
|
|
8
|
+
from morefs.dict import DictFS
|
|
9
|
+
|
|
10
|
+
from bw_processing import create_datapackage, load_datapackage, simple_graph
|
|
11
|
+
from bw_processing.constants import INDICES_DTYPE, UNCERTAINTY_DTYPE, MAX_SIGNED_64BIT_INT, MAX_SIGNED_32BIT_INT
|
|
12
|
+
from bw_processing.errors import NonUnique, PotentialInconsistency, ShapeMismatch, WrongDatatype
|
|
13
|
+
from bw_processing.io_helpers import generic_directory_filesystem
|
|
14
|
+
|
|
15
|
+
dirpath = Path(__file__).parent.resolve() / "fixtures"
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
class Dummy:
|
|
19
|
+
pass
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def add_data(dp):
|
|
23
|
+
data_array = np.array([2, 7, 12])
|
|
24
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
25
|
+
flip_array = np.array([1, 0, 0], dtype=bool)
|
|
26
|
+
dp.add_persistent_vector(
|
|
27
|
+
matrix="sa_matrix",
|
|
28
|
+
data_array=data_array,
|
|
29
|
+
name="sa-data-vector",
|
|
30
|
+
indices_array=indices_array,
|
|
31
|
+
nrows=2,
|
|
32
|
+
flip_array=flip_array,
|
|
33
|
+
)
|
|
34
|
+
|
|
35
|
+
json_data = [{"a": "b"}, 1, True]
|
|
36
|
+
df = pd.DataFrame(
|
|
37
|
+
[
|
|
38
|
+
{"id": 1, "a": 1, "c": 3, "d": 11},
|
|
39
|
+
{"id": 2, "a": 2, "c": 4, "d": 11},
|
|
40
|
+
{"id": 3, "a": 1, "c": 4, "d": 11},
|
|
41
|
+
]
|
|
42
|
+
).set_index(["id"])
|
|
43
|
+
|
|
44
|
+
dp.add_persistent_array(
|
|
45
|
+
matrix="sa_matrix",
|
|
46
|
+
data_array=np.arange(12).reshape((3, 4)),
|
|
47
|
+
indices_array=indices_array,
|
|
48
|
+
name="sa-data-array",
|
|
49
|
+
flip_array=flip_array,
|
|
50
|
+
)
|
|
51
|
+
|
|
52
|
+
dp.add_dynamic_vector(
|
|
53
|
+
interface=Dummy(),
|
|
54
|
+
indices_array=indices_array,
|
|
55
|
+
matrix="sa_matrix",
|
|
56
|
+
name="sa-vector-interface",
|
|
57
|
+
)
|
|
58
|
+
|
|
59
|
+
dp.add_dynamic_array(
|
|
60
|
+
interface=Dummy(),
|
|
61
|
+
matrix="sa_matrix",
|
|
62
|
+
name="sa-array-interface",
|
|
63
|
+
indices_array=indices_array,
|
|
64
|
+
)
|
|
65
|
+
dp.add_csv_metadata(
|
|
66
|
+
dataframe=df,
|
|
67
|
+
valid_for=[("sa-data-vector", "rows")],
|
|
68
|
+
name="sa-data-vector-csv-metadata",
|
|
69
|
+
)
|
|
70
|
+
dp.add_json_metadata(
|
|
71
|
+
data=json_data, valid_for="sa-data-array", name="sa-data-array-json-metadata"
|
|
72
|
+
)
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
def copy_fixture(fixture_name, dest):
|
|
76
|
+
source = Path(__file__).parent.resolve() / "fixtures" / fixture_name
|
|
77
|
+
for fp in source.iterdir():
|
|
78
|
+
shutil.copy(fp, dest / fp.name)
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
def test_group_ordering_consistent():
|
|
82
|
+
dp = load_datapackage(ZipFileSystem(dirpath / "test-fixture.zip"))
|
|
83
|
+
assert list(dp.groups) == [
|
|
84
|
+
"sa-data-vector-from-dict",
|
|
85
|
+
"sa-data-vector",
|
|
86
|
+
"sa-data-array",
|
|
87
|
+
"sa-vector-interface",
|
|
88
|
+
"sa-array-interface",
|
|
89
|
+
]
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
def test_get_max_index_value():
|
|
93
|
+
dp = load_datapackage(ZipFileSystem(dirpath / "test-fixture.zip"))
|
|
94
|
+
assert dp.metadata.get("64_bit_indices")
|
|
95
|
+
assert dp.get_max_index_value() == MAX_SIGNED_64BIT_INT
|
|
96
|
+
|
|
97
|
+
dp = load_datapackage(ZipFileSystem(dirpath / "test-fixture-32bit.zip"))
|
|
98
|
+
assert not dp.metadata.get("64_bit_indices")
|
|
99
|
+
assert dp.get_max_index_value() == MAX_SIGNED_32BIT_INT
|
|
100
|
+
|
|
101
|
+
|
|
102
|
+
def test_add_resource_with_same_name():
|
|
103
|
+
dp = create_datapackage()
|
|
104
|
+
add_data(dp)
|
|
105
|
+
|
|
106
|
+
data_array = np.array([2, 7, 12])
|
|
107
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
108
|
+
with pytest.raises(NonUnique):
|
|
109
|
+
dp.add_persistent_vector(
|
|
110
|
+
matrix="sa_matrix",
|
|
111
|
+
data_array=data_array,
|
|
112
|
+
name="sa-data-vector",
|
|
113
|
+
indices_array=indices_array,
|
|
114
|
+
)
|
|
115
|
+
|
|
116
|
+
|
|
117
|
+
def test_save_modifications(tmp_path):
|
|
118
|
+
copy_fixture("tfd", tmp_path)
|
|
119
|
+
dp = load_datapackage(generic_directory_filesystem(dirpath=tmp_path))
|
|
120
|
+
|
|
121
|
+
assert dp.resources[1]["name"] == "sa-data-vector-from-dict.data"
|
|
122
|
+
assert np.allclose(dp.data[1], [3.3, 8.3])
|
|
123
|
+
|
|
124
|
+
dp.data[1][:] = 42
|
|
125
|
+
dp._modified = [1]
|
|
126
|
+
dp.write_modified()
|
|
127
|
+
|
|
128
|
+
assert np.allclose(dp.data[1], 42)
|
|
129
|
+
assert not dp._modified
|
|
130
|
+
|
|
131
|
+
dp = load_datapackage(generic_directory_filesystem(dirpath=tmp_path))
|
|
132
|
+
assert np.allclose(dp.data[1], 42)
|
|
133
|
+
|
|
134
|
+
|
|
135
|
+
def test_del_resource_filesystem(tmp_path):
|
|
136
|
+
copy_fixture("tfd", tmp_path)
|
|
137
|
+
dp = load_datapackage(generic_directory_filesystem(dirpath=tmp_path))
|
|
138
|
+
reference_length = len(dp)
|
|
139
|
+
assert "sa-vector-interface.indices.npy" in [o.name for o in tmp_path.iterdir()]
|
|
140
|
+
dp.del_resource("sa-vector-interface.indices")
|
|
141
|
+
assert "sa-vector-interface.indices.npy" not in [o.name for o in tmp_path.iterdir()]
|
|
142
|
+
assert len(dp) == reference_length - 1
|
|
143
|
+
assert len(dp.data) == reference_length - 1
|
|
144
|
+
assert len(dp.metadata["resources"]) == reference_length - 1
|
|
145
|
+
assert len(dp.resources) == reference_length - 1
|
|
146
|
+
|
|
147
|
+
|
|
148
|
+
def test_del_resource_in_memory():
|
|
149
|
+
dp = create_datapackage()
|
|
150
|
+
add_data(dp)
|
|
151
|
+
assert isinstance(dp.fs, DictFS)
|
|
152
|
+
|
|
153
|
+
reference_length = len(dp)
|
|
154
|
+
assert "sa-vector-interface.indices" in [o["name"] for o in dp.resources]
|
|
155
|
+
dp.del_resource("sa-vector-interface.indices")
|
|
156
|
+
assert "sa-vector-interface.indices" not in [o["name"] for o in dp.resources]
|
|
157
|
+
assert len(dp) == reference_length - 1
|
|
158
|
+
assert len(dp.data) == reference_length - 1
|
|
159
|
+
assert len(dp.metadata["resources"]) == reference_length - 1
|
|
160
|
+
assert len(dp.resources) == reference_length - 1
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
def test_del_resource_error_modifications(tmp_path):
|
|
164
|
+
copy_fixture("tfd", tmp_path)
|
|
165
|
+
dp = load_datapackage(generic_directory_filesystem(dirpath=tmp_path))
|
|
166
|
+
dp._modified = [1]
|
|
167
|
+
with pytest.raises(PotentialInconsistency):
|
|
168
|
+
dp.del_resource(1)
|
|
169
|
+
|
|
170
|
+
|
|
171
|
+
def test_del_resource_group_filesystem(tmp_path):
|
|
172
|
+
copy_fixture("tfd", tmp_path)
|
|
173
|
+
dp = load_datapackage(generic_directory_filesystem(dirpath=tmp_path))
|
|
174
|
+
|
|
175
|
+
reference_length = len(dp)
|
|
176
|
+
assert "sa-data-vector.indices.npy" in [o.name for o in tmp_path.iterdir()]
|
|
177
|
+
dp.del_resource_group("sa-data-vector")
|
|
178
|
+
assert "sa-data-vector.indices.npy" not in [o.name for o in tmp_path.iterdir()]
|
|
179
|
+
assert len(dp) == reference_length - 3
|
|
180
|
+
assert len(dp.data) == reference_length - 3
|
|
181
|
+
assert len(dp.metadata["resources"]) == reference_length - 3
|
|
182
|
+
assert len(dp.resources) == reference_length - 3
|
|
183
|
+
|
|
184
|
+
|
|
185
|
+
def test_del_resource_group_in_memory():
|
|
186
|
+
dp = create_datapackage()
|
|
187
|
+
add_data(dp)
|
|
188
|
+
assert isinstance(dp.fs, DictFS)
|
|
189
|
+
|
|
190
|
+
reference_length = len(dp)
|
|
191
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
192
|
+
dp.del_resource_group("sa-data-vector")
|
|
193
|
+
assert "sa-data-vector.indices" not in [o["name"] for o in dp.resources]
|
|
194
|
+
assert len(dp) == reference_length - 3
|
|
195
|
+
assert len(dp.data) == reference_length - 3
|
|
196
|
+
assert len(dp.metadata["resources"]) == reference_length - 3
|
|
197
|
+
assert len(dp.resources) == reference_length - 3
|
|
198
|
+
|
|
199
|
+
|
|
200
|
+
def test_del_resource_group_error_modifications(tmp_path):
|
|
201
|
+
copy_fixture("tfd", tmp_path)
|
|
202
|
+
dp = load_datapackage(generic_directory_filesystem(dirpath=tmp_path))
|
|
203
|
+
dp._modified = [1]
|
|
204
|
+
with pytest.raises(PotentialInconsistency):
|
|
205
|
+
dp.del_resource_group("sa-vector-interface")
|
|
206
|
+
|
|
207
|
+
|
|
208
|
+
def test_exclude_basic():
|
|
209
|
+
dp = create_datapackage()
|
|
210
|
+
add_data(dp)
|
|
211
|
+
assert isinstance(dp.fs, DictFS)
|
|
212
|
+
|
|
213
|
+
reference_length = len(dp)
|
|
214
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
215
|
+
ndp = dp.exclude({"group": "sa-data-vector"})
|
|
216
|
+
assert ndp is not dp
|
|
217
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
218
|
+
assert "sa-data-vector.indices" not in [o["name"] for o in ndp.resources]
|
|
219
|
+
assert len(ndp) == reference_length - 3
|
|
220
|
+
assert len(ndp.data) == reference_length - 3
|
|
221
|
+
assert len(ndp.metadata["resources"]) == reference_length - 3
|
|
222
|
+
assert len(ndp.resources) == reference_length - 3
|
|
223
|
+
|
|
224
|
+
|
|
225
|
+
def test_exclude_no_match():
|
|
226
|
+
dp = create_datapackage()
|
|
227
|
+
add_data(dp)
|
|
228
|
+
assert isinstance(dp.fs, DictFS)
|
|
229
|
+
|
|
230
|
+
reference_length = len(dp)
|
|
231
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
232
|
+
ndp = dp.exclude({"foo": "bar"})
|
|
233
|
+
assert ndp is not dp
|
|
234
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
235
|
+
assert "sa-data-vector.indices" in [o["name"] for o in ndp.resources]
|
|
236
|
+
assert len(ndp) == reference_length
|
|
237
|
+
|
|
238
|
+
|
|
239
|
+
def test_exclude_multiple_filters():
|
|
240
|
+
dp = create_datapackage()
|
|
241
|
+
add_data(dp)
|
|
242
|
+
assert isinstance(dp.fs, DictFS)
|
|
243
|
+
|
|
244
|
+
reference_length = len(dp)
|
|
245
|
+
assert "sa-array-interface.indices" in [o["name"] for o in dp.resources]
|
|
246
|
+
ndp = dp.exclude({"group": "sa-array-interface", "matrix": "sa_matrix"})
|
|
247
|
+
assert ndp is not dp
|
|
248
|
+
assert "sa-array-interface.indices" in [o["name"] for o in dp.resources]
|
|
249
|
+
assert "sa-array-interface.indices" not in [o["name"] for o in ndp.resources]
|
|
250
|
+
assert len(ndp) == reference_length - 2
|
|
251
|
+
assert len(ndp.data) == reference_length - 2
|
|
252
|
+
assert len(ndp.metadata["resources"]) == reference_length - 2
|
|
253
|
+
assert len(ndp.resources) == reference_length - 2
|
|
254
|
+
|
|
255
|
+
|
|
256
|
+
def test_exclude_multiple_matrix():
|
|
257
|
+
dp = create_datapackage()
|
|
258
|
+
add_data(dp)
|
|
259
|
+
assert isinstance(dp.fs, DictFS)
|
|
260
|
+
|
|
261
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
262
|
+
ndp = dp.exclude({"matrix": "sa_matrix"})
|
|
263
|
+
assert ndp is not dp
|
|
264
|
+
assert "sa-data-vector.indices" in [o["name"] for o in dp.resources]
|
|
265
|
+
assert "sa-data-vector.indices" not in [o["name"] for o in ndp.resources]
|
|
266
|
+
assert len(ndp) == 2
|
|
267
|
+
assert len(ndp.data) == 2
|
|
268
|
+
assert len(ndp.metadata["resources"]) == 2
|
|
269
|
+
assert len(ndp.resources) == 2
|
|
270
|
+
|
|
271
|
+
|
|
272
|
+
def test_add_persistent_vector_data_shapemismatch_ndimensions():
|
|
273
|
+
dp = create_datapackage()
|
|
274
|
+
data_array = np.array([[2, 7, 12], [4, 5, 15]])
|
|
275
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
276
|
+
with pytest.raises(ShapeMismatch):
|
|
277
|
+
dp.add_persistent_vector(
|
|
278
|
+
matrix="sa_matrix",
|
|
279
|
+
data_array=data_array,
|
|
280
|
+
name="sa-data-vector",
|
|
281
|
+
indices_array=indices_array,
|
|
282
|
+
)
|
|
283
|
+
|
|
284
|
+
|
|
285
|
+
def test_add_persistent_vector_data_shapemismatch_nrows():
|
|
286
|
+
dp = create_datapackage()
|
|
287
|
+
data_array = np.array([2, 7, 12, 15])
|
|
288
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
289
|
+
with pytest.raises(ShapeMismatch):
|
|
290
|
+
dp.add_persistent_vector(
|
|
291
|
+
matrix="sa_matrix",
|
|
292
|
+
data_array=data_array,
|
|
293
|
+
name="sa-data-vector",
|
|
294
|
+
indices_array=indices_array,
|
|
295
|
+
)
|
|
296
|
+
|
|
297
|
+
|
|
298
|
+
def test_add_persistent_vector_distributions_shapemismatch():
|
|
299
|
+
dp = create_datapackage()
|
|
300
|
+
distributions_array = np.array(
|
|
301
|
+
[
|
|
302
|
+
(3, 1.3, 2.5, np.nan, np.nan, np.nan, False),
|
|
303
|
+
(0, 1.3, 2.5, np.nan, np.nan, np.nan, False),
|
|
304
|
+
],
|
|
305
|
+
dtype=UNCERTAINTY_DTYPE,
|
|
306
|
+
)
|
|
307
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
308
|
+
with pytest.raises(ShapeMismatch):
|
|
309
|
+
dp.add_persistent_vector(
|
|
310
|
+
matrix="sa_matrix",
|
|
311
|
+
distributions_array=distributions_array,
|
|
312
|
+
name="sa-data-vector",
|
|
313
|
+
indices_array=indices_array,
|
|
314
|
+
)
|
|
315
|
+
|
|
316
|
+
|
|
317
|
+
def test_add_persistent_vector_flip_dtype():
|
|
318
|
+
dp = create_datapackage()
|
|
319
|
+
data_array = np.array([2, 7, 12])
|
|
320
|
+
flip_array = np.array([0, 1, 0])
|
|
321
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
322
|
+
with pytest.raises(WrongDatatype):
|
|
323
|
+
dp.add_persistent_vector(
|
|
324
|
+
matrix="sa_matrix",
|
|
325
|
+
data_array=data_array,
|
|
326
|
+
name="sa-data-vector",
|
|
327
|
+
flip_array=flip_array,
|
|
328
|
+
indices_array=indices_array,
|
|
329
|
+
)
|
|
330
|
+
|
|
331
|
+
|
|
332
|
+
def test_add_persistent_vector_flip_shapemistmatch():
|
|
333
|
+
dp = create_datapackage()
|
|
334
|
+
data_array = np.array([2, 7, 12])
|
|
335
|
+
flip_array = np.array([0, 1, 0, 1], dtype=bool)
|
|
336
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=ShapeMismatch)
|
|
337
|
+
with pytest.raises(ShapeMismatch):
|
|
338
|
+
dp.add_persistent_vector(
|
|
339
|
+
matrix="sa_matrix",
|
|
340
|
+
data_array=data_array,
|
|
341
|
+
name="sa-data-vector",
|
|
342
|
+
flip_array=flip_array,
|
|
343
|
+
indices_array=indices_array,
|
|
344
|
+
)
|
|
345
|
+
|
|
346
|
+
|
|
347
|
+
def test_add_persistent_array_data_shapemismatch_ndimensions():
|
|
348
|
+
dp = create_datapackage()
|
|
349
|
+
data_array = np.array([2, 7, 12])
|
|
350
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
351
|
+
with pytest.raises(ShapeMismatch):
|
|
352
|
+
dp.add_persistent_array(
|
|
353
|
+
matrix="sa_matrix",
|
|
354
|
+
data_array=data_array,
|
|
355
|
+
name="sa-data-vector",
|
|
356
|
+
indices_array=indices_array,
|
|
357
|
+
)
|
|
358
|
+
|
|
359
|
+
|
|
360
|
+
def test_add_persistent_array_data_shapemismatch_nrows():
|
|
361
|
+
dp = create_datapackage()
|
|
362
|
+
data_array = np.arange(12).reshape(4, 3)
|
|
363
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
364
|
+
with pytest.raises(ShapeMismatch):
|
|
365
|
+
dp.add_persistent_array(
|
|
366
|
+
matrix="sa_matrix",
|
|
367
|
+
data_array=data_array,
|
|
368
|
+
name="sa-data-vector",
|
|
369
|
+
indices_array=indices_array,
|
|
370
|
+
)
|
|
371
|
+
|
|
372
|
+
|
|
373
|
+
def test_add_persistent_array_flip_dtype():
|
|
374
|
+
dp = create_datapackage()
|
|
375
|
+
data_array = np.arange(12).reshape(3, 4)
|
|
376
|
+
flip_array = np.array([0, 1, 0])
|
|
377
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
378
|
+
with pytest.raises(WrongDatatype):
|
|
379
|
+
dp.add_persistent_array(
|
|
380
|
+
matrix="sa_matrix",
|
|
381
|
+
data_array=data_array,
|
|
382
|
+
name="sa-data-vector",
|
|
383
|
+
flip_array=flip_array,
|
|
384
|
+
indices_array=indices_array,
|
|
385
|
+
)
|
|
386
|
+
|
|
387
|
+
|
|
388
|
+
def test_add_persistent_array_flip_shapemistmatch():
|
|
389
|
+
dp = create_datapackage()
|
|
390
|
+
data_array = np.arange(12).reshape(3, 4)
|
|
391
|
+
flip_array = np.array([0, 1, 0, 1], dtype=bool)
|
|
392
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=ShapeMismatch)
|
|
393
|
+
with pytest.raises(ShapeMismatch):
|
|
394
|
+
dp.add_persistent_array(
|
|
395
|
+
matrix="sa_matrix",
|
|
396
|
+
data_array=data_array,
|
|
397
|
+
name="sa-data-vector",
|
|
398
|
+
flip_array=flip_array,
|
|
399
|
+
indices_array=indices_array,
|
|
400
|
+
)
|
|
401
|
+
|
|
402
|
+
|
|
403
|
+
def test_add_dynamic_array_flip_dtype():
|
|
404
|
+
dp = create_datapackage()
|
|
405
|
+
flip_array = np.array([0, 1, 0])
|
|
406
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
407
|
+
with pytest.raises(WrongDatatype):
|
|
408
|
+
dp.add_dynamic_array(
|
|
409
|
+
matrix="sa_matrix",
|
|
410
|
+
interface=Dummy(),
|
|
411
|
+
name="sa-data-vector",
|
|
412
|
+
flip_array=flip_array,
|
|
413
|
+
indices_array=indices_array,
|
|
414
|
+
)
|
|
415
|
+
|
|
416
|
+
|
|
417
|
+
def test_add_dynamic_array_flip_shapemistmatch():
|
|
418
|
+
dp = create_datapackage()
|
|
419
|
+
flip_array = np.array([0, 1, 0, 1], dtype=bool)
|
|
420
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=ShapeMismatch)
|
|
421
|
+
with pytest.raises(ShapeMismatch):
|
|
422
|
+
dp.add_dynamic_array(
|
|
423
|
+
matrix="sa_matrix",
|
|
424
|
+
interface=Dummy(),
|
|
425
|
+
name="sa-data-vector",
|
|
426
|
+
flip_array=flip_array,
|
|
427
|
+
indices_array=indices_array,
|
|
428
|
+
)
|
|
429
|
+
|
|
430
|
+
|
|
431
|
+
def test_add_dynamic_vector_flip_dtype():
|
|
432
|
+
dp = create_datapackage()
|
|
433
|
+
flip_array = np.array([0, 1, 0])
|
|
434
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=INDICES_DTYPE)
|
|
435
|
+
with pytest.raises(WrongDatatype):
|
|
436
|
+
dp.add_dynamic_vector(
|
|
437
|
+
matrix="sa_matrix",
|
|
438
|
+
interface=Dummy(),
|
|
439
|
+
name="sa-data-vector",
|
|
440
|
+
flip_array=flip_array,
|
|
441
|
+
indices_array=indices_array,
|
|
442
|
+
)
|
|
443
|
+
|
|
444
|
+
|
|
445
|
+
def test_add_dynamic_vector_flip_shapemistmatch():
|
|
446
|
+
dp = create_datapackage()
|
|
447
|
+
flip_array = np.array([0, 1, 0, 1], dtype=bool)
|
|
448
|
+
indices_array = np.array([(1, 4), (2, 5), (3, 6)], dtype=ShapeMismatch)
|
|
449
|
+
with pytest.raises(ShapeMismatch):
|
|
450
|
+
dp.add_dynamic_vector(
|
|
451
|
+
matrix="sa_matrix",
|
|
452
|
+
interface=Dummy(),
|
|
453
|
+
name="sa-data-vector",
|
|
454
|
+
flip_array=flip_array,
|
|
455
|
+
indices_array=indices_array,
|
|
456
|
+
)
|
|
457
|
+
|
|
458
|
+
|
|
459
|
+
def test_simple_graph():
|
|
460
|
+
data = {
|
|
461
|
+
"some_matrix": [(1, 2, 3.14), (4, 5, 17, True), (8, 9, 11.11, False)],
|
|
462
|
+
"a different life": [
|
|
463
|
+
(99, 100, 101.234, False, "ignored"),
|
|
464
|
+
(1001, 1002, 777, 1),
|
|
465
|
+
],
|
|
466
|
+
}
|
|
467
|
+
expected_resource = {
|
|
468
|
+
"category": "vector",
|
|
469
|
+
"profile": "data-resource",
|
|
470
|
+
"format": "npy",
|
|
471
|
+
"mediatype": "application/octet-stream",
|
|
472
|
+
"name": "some_matrix-data.flip",
|
|
473
|
+
"matrix": "some_matrix",
|
|
474
|
+
"kind": "flip",
|
|
475
|
+
"nrows": 3,
|
|
476
|
+
"path": "some_matrix-data.flip.npy",
|
|
477
|
+
"group": "some_matrix-data",
|
|
478
|
+
}
|
|
479
|
+
dp = simple_graph(data, name="foo", sequential=True)
|
|
480
|
+
assert dp.metadata["name"] == "foo"
|
|
481
|
+
assert dp.metadata["sequential"]
|
|
482
|
+
assert len(dp.metadata["resources"]) == 6
|
|
483
|
+
assert expected_resource in dp.metadata["resources"]
|
|
484
|
+
|
|
485
|
+
d, _ = dp.get_resource("some_matrix-data.flip")
|
|
486
|
+
assert np.allclose(d, np.array([False, True, False]))
|
|
487
|
+
d, _ = dp.get_resource("some_matrix-data.indices")
|
|
488
|
+
assert d["row"].sum() == 13
|
|
489
|
+
assert d["col"].sum() == 16
|
|
490
|
+
d, _ = dp.get_resource("some_matrix-data.data")
|
|
491
|
+
assert np.allclose(d, np.array([3.14, 17, 11.11]))
|
|
492
|
+
|
|
493
|
+
d, _ = dp.get_resource("a different life-data.flip")
|
|
494
|
+
assert np.allclose(d, np.array([False, True]))
|
|
495
|
+
d, _ = dp.get_resource("a different life-data.indices")
|
|
496
|
+
assert d["row"].sum() == 1100
|
|
497
|
+
assert d["col"].sum() == 1102
|
|
498
|
+
d, _ = dp.get_resource("a different life-data.data")
|
|
499
|
+
assert np.allclose(d, np.array([101.234, 777]))
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import platform
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
|
|
4
|
+
import pytest
|
|
5
|
+
|
|
6
|
+
from bw_processing.filesystem import clean_datapackage_name, md5, safe_filename
|
|
7
|
+
|
|
8
|
+
fixtures_dir = Path(__file__, "..").resolve() / "fixtures"
|
|
9
|
+
_windows = platform.system() == "Windows"
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
@pytest.mark.skipif(_windows, reason="Different line encodings on Windows")
|
|
13
|
+
def test_md5_text():
|
|
14
|
+
assert md5(fixtures_dir / "lorem.txt") == "edc715389af2498a623134608ba0a55b"
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
def test_md5_binary():
|
|
18
|
+
assert md5(fixtures_dir / "array.npy") == "bbadddf09cf6b1e36d8333f474e36cee"
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
def test_safe_filename():
|
|
22
|
+
assert safe_filename("Wave your hand yeah 🙋!") == "Wave-your-hand-yeah.f7952a3d"
|
|
23
|
+
assert (
|
|
24
|
+
safe_filename("Wave your hand yeah 🙋!", full=True)
|
|
25
|
+
== "Wave-your-hand-yeah.f7952a3d4b0534cdac0e0cbbf66aac73"
|
|
26
|
+
)
|
|
27
|
+
assert safe_filename("Wave your hand yeah 🙋!", add_hash=False) == "Wave-your-hand-yeah"
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
def test_clean_datapackage_name():
|
|
31
|
+
a = "('IPCC', 'simple') processed arrays"
|
|
32
|
+
b = "IPCC_simple_processed_arrays"
|
|
33
|
+
assert clean_datapackage_name(a) == b
|