requireit 0.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.
- requireit-0.1.0/AUTHORS.md +5 -0
- requireit-0.1.0/CHANGES.md +11 -0
- requireit-0.1.0/LICENSE.md +24 -0
- requireit-0.1.0/PKG-INFO +205 -0
- requireit-0.1.0/README.md +155 -0
- requireit-0.1.0/pyproject.toml +80 -0
- requireit-0.1.0/setup.cfg +10 -0
- requireit-0.1.0/src/requireit.egg-info/PKG-INFO +205 -0
- requireit-0.1.0/src/requireit.egg-info/SOURCES.txt +12 -0
- requireit-0.1.0/src/requireit.egg-info/dependency_links.txt +1 -0
- requireit-0.1.0/src/requireit.egg-info/requires.txt +4 -0
- requireit-0.1.0/src/requireit.egg-info/top_level.txt +1 -0
- requireit-0.1.0/src/requireit.py +306 -0
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
# Release Notes
|
|
2
|
+
|
|
3
|
+
## 0.1.0 (not yet released)
|
|
4
|
+
|
|
5
|
+
- Added documentation to the README [#1](https://github.com/mcflugen/requireit/issues/1)
|
|
6
|
+
- Added project metadata files [#2](https://github.com/mcflugen/requireit/issues/2)
|
|
7
|
+
- Added the `requireit` module [#3](https://github.com/mcflugen/requireit/issues/3)
|
|
8
|
+
- Added `pyproject.toml` file [#4](https://github.com/mcflugen/requireit/issues/4)
|
|
9
|
+
- Added `noxfile.py` file and linters [#5](https://github.com/mcflugen/requireit/issues/5)
|
|
10
|
+
- Added unit tests for `requireit` [#6](https://github.com/mcflugen/requireit/issues/6)
|
|
11
|
+
- Added GitHub Actions for CI [#7](https://github.com/mcflugen/requireit/issues/7)
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# The MIT License (MIT)
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Eric Hutton
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person
|
|
6
|
+
obtaining a copy of this software and associated documentation
|
|
7
|
+
files (the "Software"), to deal in the Software without
|
|
8
|
+
restriction, including without limitation the rights to use,
|
|
9
|
+
copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
10
|
+
copies of the Software, and to permit persons to whom the
|
|
11
|
+
Software is furnished to do so, subject to the following
|
|
12
|
+
conditions:
|
|
13
|
+
|
|
14
|
+
The above copyright notice and this permission notice shall be
|
|
15
|
+
included in all copies or substantial portions of the Software.
|
|
16
|
+
|
|
17
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
18
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
|
19
|
+
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
20
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
|
21
|
+
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
|
22
|
+
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
|
23
|
+
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
|
24
|
+
OTHER DEALINGS IN THE SOFTWARE.
|
requireit-0.1.0/PKG-INFO
ADDED
|
@@ -0,0 +1,205 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: requireit
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Tiny runtime validators for explicit precondition checks
|
|
5
|
+
Author-email: Eric Hutton <mcflugen@gmail.com>
|
|
6
|
+
Maintainer-email: Eric Hutton <mcflugen@gmail.com>
|
|
7
|
+
License-Expression: MIT
|
|
8
|
+
Project-URL: homepage, https://github.com/mcflugen/requireit
|
|
9
|
+
Project-URL: documentation, https://github.com/mcflugen/requireit/blob/main/README.md
|
|
10
|
+
Project-URL: repository, https://github.com/mcflugen/requireit
|
|
11
|
+
Project-URL: changelog, https://github.com/mcflugen/requireit/blob/main/CHANGES.md
|
|
12
|
+
Keywords: preconditions,runtime-checks,utilities,validation
|
|
13
|
+
Classifier: Development Status :: 4 - Beta
|
|
14
|
+
Classifier: Intended Audience :: Developers
|
|
15
|
+
Classifier: Operating System :: OS Independent
|
|
16
|
+
Classifier: Programming Language :: Python :: 3
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
22
|
+
Classifier: Programming Language :: Python :: 3 :: Only
|
|
23
|
+
Classifier: Programming Language :: Python :: Implementation :: CPython
|
|
24
|
+
Classifier: Programming Language :: Python :: Implementation :: PyPy
|
|
25
|
+
Requires-Python: >=3.10
|
|
26
|
+
Description-Content-Type: text/markdown
|
|
27
|
+
License-File: LICENSE.md
|
|
28
|
+
Requires-Dist: numpy
|
|
29
|
+
Provides-Extra: dev
|
|
30
|
+
Requires-Dist: nox; extra == "dev"
|
|
31
|
+
Dynamic: license-file
|
|
32
|
+
|
|
33
|
+
# requireit
|
|
34
|
+
|
|
35
|
+
**Tiny, numpy-aware runtime validators for explicit precondition checks.**
|
|
36
|
+
|
|
37
|
+
`requireit` provides a small collection of lightweight helper functions such as
|
|
38
|
+
`require_positive`, `require_between`, and `validate_array` for validating values
|
|
39
|
+
and arrays at runtime.
|
|
40
|
+
|
|
41
|
+
It is intentionally minimal and dependency-light (*numpy* only).
|
|
42
|
+
|
|
43
|
+
## Why `requireit`?
|
|
44
|
+
|
|
45
|
+
* **Explicit** – reads clearly
|
|
46
|
+
* **numpy-aware** – works correctly with scalars *and* arrays
|
|
47
|
+
* **Fail-fast** – raises immediately with clear error messages
|
|
48
|
+
* **Lightweight** – just a bunch of small functions
|
|
49
|
+
* **Reusable** – avoids copy-pasted validation code across projects
|
|
50
|
+
|
|
51
|
+
```python
|
|
52
|
+
from requireit import require_one_of
|
|
53
|
+
from requireit import require_positive
|
|
54
|
+
|
|
55
|
+
require_positive(dt)
|
|
56
|
+
require_one_of(method, allowed={"foo", "bar"})
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
## Design principles
|
|
60
|
+
|
|
61
|
+
* Prefer small, single-purpose functions
|
|
62
|
+
* Raise standard exceptions (`ValidationError`)
|
|
63
|
+
* Never coerce or "fix" invalid inputs
|
|
64
|
+
* Validate *all* elements for array-like inputs
|
|
65
|
+
* Keep the public API small
|
|
66
|
+
|
|
67
|
+
## Non-goals
|
|
68
|
+
|
|
69
|
+
`requireit` is **not**:
|
|
70
|
+
|
|
71
|
+
* a schema or data-modeling system
|
|
72
|
+
* a replacement for static typing
|
|
73
|
+
* a validation framework
|
|
74
|
+
* a substitute for unit tests
|
|
75
|
+
* a coercion or parsing library
|
|
76
|
+
|
|
77
|
+
If you need structured validation, transformations, or user-facing error
|
|
78
|
+
aggregation, you probably want something heavier.
|
|
79
|
+
|
|
80
|
+
## Installation
|
|
81
|
+
|
|
82
|
+
```bash
|
|
83
|
+
pip install requireit
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
## API overview
|
|
87
|
+
|
|
88
|
+
All validators:
|
|
89
|
+
|
|
90
|
+
* return the original value/array on success
|
|
91
|
+
* raise `ValidationError` on failure
|
|
92
|
+
|
|
93
|
+
### Membership validation
|
|
94
|
+
|
|
95
|
+
```python
|
|
96
|
+
require_one_of(value, *, allowed)
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
Validate that a value is one of a set of allowed values.
|
|
100
|
+
|
|
101
|
+
```python
|
|
102
|
+
require_one_of("foo", allowed=("foo", "bar")) # ok, returns "foo"
|
|
103
|
+
require_one_of("baz", allowed=("foo", "bar")) # raises ValidationError
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
### Range validation
|
|
107
|
+
|
|
108
|
+
```python
|
|
109
|
+
require_between(
|
|
110
|
+
value,
|
|
111
|
+
a_min=None,
|
|
112
|
+
a_max=None,
|
|
113
|
+
*,
|
|
114
|
+
inclusive_min=True,
|
|
115
|
+
inclusive_max=True,
|
|
116
|
+
)
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
Validate that a scalar or array lies within specified bounds.
|
|
120
|
+
|
|
121
|
+
* Bounds may be inclusive or strict
|
|
122
|
+
* Validation fails if **any element** violates the constraint
|
|
123
|
+
|
|
124
|
+
```python
|
|
125
|
+
require_between([0, 1], a_min=0.0) # ok, returns [0, 1]
|
|
126
|
+
require_between([0, 1], a_min=0.0, inclusive_min=False) # raises
|
|
127
|
+
```
|
|
128
|
+
|
|
129
|
+
### Sign-based helpers
|
|
130
|
+
|
|
131
|
+
Convenience wrappers around `require_between`:
|
|
132
|
+
|
|
133
|
+
```python
|
|
134
|
+
require_positive(value) # > 0
|
|
135
|
+
require_nonnegative(value) # >= 0
|
|
136
|
+
require_negative(value) # < 0
|
|
137
|
+
require_nonpositive(value) # <= 0
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
All accept scalars or array-like inputs.
|
|
141
|
+
|
|
142
|
+
|
|
143
|
+
### Array validation
|
|
144
|
+
|
|
145
|
+
```python
|
|
146
|
+
validate_array(
|
|
147
|
+
array,
|
|
148
|
+
*,
|
|
149
|
+
dtype=None,
|
|
150
|
+
shape=None,
|
|
151
|
+
writable=None,
|
|
152
|
+
contiguous=None,
|
|
153
|
+
)
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
Validate NumPy array properties without copying or modifying the array.
|
|
157
|
+
|
|
158
|
+
```python
|
|
159
|
+
validate_array(x, dtype=np.float64, shape=(100,))
|
|
160
|
+
validate_array(x, writable=True, contiguous=True)
|
|
161
|
+
```
|
|
162
|
+
|
|
163
|
+
Checks are applied only if the corresponding keyword is provided.
|
|
164
|
+
|
|
165
|
+
|
|
166
|
+
## Errors
|
|
167
|
+
|
|
168
|
+
All validation failures raise:
|
|
169
|
+
|
|
170
|
+
```python
|
|
171
|
+
requireit.ValidationError
|
|
172
|
+
```
|
|
173
|
+
|
|
174
|
+
This allows callers to catch validation failures distinctly from other errors.
|
|
175
|
+
|
|
176
|
+
|
|
177
|
+
## Contributing
|
|
178
|
+
|
|
179
|
+
This project is intentionally small.
|
|
180
|
+
|
|
181
|
+
Contributions should preserve:
|
|
182
|
+
|
|
183
|
+
* minimal surface area
|
|
184
|
+
* explicit semantics
|
|
185
|
+
* no additional dependencies
|
|
186
|
+
|
|
187
|
+
If a proposed change needs much explanation, it probably doesn’t belong here.
|
|
188
|
+
|
|
189
|
+
# Credits
|
|
190
|
+
|
|
191
|
+
## Development Leads
|
|
192
|
+
|
|
193
|
+
- [Eric Hutton](https://github.com/mcflugen)
|
|
194
|
+
|
|
195
|
+
# Release Notes
|
|
196
|
+
|
|
197
|
+
## 0.1.0 (not yet released)
|
|
198
|
+
|
|
199
|
+
- Added documentation to the README [#1](https://github.com/mcflugen/requireit/issues/1)
|
|
200
|
+
- Added project metadata files [#2](https://github.com/mcflugen/requireit/issues/2)
|
|
201
|
+
- Added the `requireit` module [#3](https://github.com/mcflugen/requireit/issues/3)
|
|
202
|
+
- Added `pyproject.toml` file [#4](https://github.com/mcflugen/requireit/issues/4)
|
|
203
|
+
- Added `noxfile.py` file and linters [#5](https://github.com/mcflugen/requireit/issues/5)
|
|
204
|
+
- Added unit tests for `requireit` [#6](https://github.com/mcflugen/requireit/issues/6)
|
|
205
|
+
- Added GitHub Actions for CI [#7](https://github.com/mcflugen/requireit/issues/7)
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
# requireit
|
|
2
|
+
|
|
3
|
+
**Tiny, numpy-aware runtime validators for explicit precondition checks.**
|
|
4
|
+
|
|
5
|
+
`requireit` provides a small collection of lightweight helper functions such as
|
|
6
|
+
`require_positive`, `require_between`, and `validate_array` for validating values
|
|
7
|
+
and arrays at runtime.
|
|
8
|
+
|
|
9
|
+
It is intentionally minimal and dependency-light (*numpy* only).
|
|
10
|
+
|
|
11
|
+
## Why `requireit`?
|
|
12
|
+
|
|
13
|
+
* **Explicit** – reads clearly
|
|
14
|
+
* **numpy-aware** – works correctly with scalars *and* arrays
|
|
15
|
+
* **Fail-fast** – raises immediately with clear error messages
|
|
16
|
+
* **Lightweight** – just a bunch of small functions
|
|
17
|
+
* **Reusable** – avoids copy-pasted validation code across projects
|
|
18
|
+
|
|
19
|
+
```python
|
|
20
|
+
from requireit import require_one_of
|
|
21
|
+
from requireit import require_positive
|
|
22
|
+
|
|
23
|
+
require_positive(dt)
|
|
24
|
+
require_one_of(method, allowed={"foo", "bar"})
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
## Design principles
|
|
28
|
+
|
|
29
|
+
* Prefer small, single-purpose functions
|
|
30
|
+
* Raise standard exceptions (`ValidationError`)
|
|
31
|
+
* Never coerce or "fix" invalid inputs
|
|
32
|
+
* Validate *all* elements for array-like inputs
|
|
33
|
+
* Keep the public API small
|
|
34
|
+
|
|
35
|
+
## Non-goals
|
|
36
|
+
|
|
37
|
+
`requireit` is **not**:
|
|
38
|
+
|
|
39
|
+
* a schema or data-modeling system
|
|
40
|
+
* a replacement for static typing
|
|
41
|
+
* a validation framework
|
|
42
|
+
* a substitute for unit tests
|
|
43
|
+
* a coercion or parsing library
|
|
44
|
+
|
|
45
|
+
If you need structured validation, transformations, or user-facing error
|
|
46
|
+
aggregation, you probably want something heavier.
|
|
47
|
+
|
|
48
|
+
## Installation
|
|
49
|
+
|
|
50
|
+
```bash
|
|
51
|
+
pip install requireit
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
## API overview
|
|
55
|
+
|
|
56
|
+
All validators:
|
|
57
|
+
|
|
58
|
+
* return the original value/array on success
|
|
59
|
+
* raise `ValidationError` on failure
|
|
60
|
+
|
|
61
|
+
### Membership validation
|
|
62
|
+
|
|
63
|
+
```python
|
|
64
|
+
require_one_of(value, *, allowed)
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
Validate that a value is one of a set of allowed values.
|
|
68
|
+
|
|
69
|
+
```python
|
|
70
|
+
require_one_of("foo", allowed=("foo", "bar")) # ok, returns "foo"
|
|
71
|
+
require_one_of("baz", allowed=("foo", "bar")) # raises ValidationError
|
|
72
|
+
```
|
|
73
|
+
|
|
74
|
+
### Range validation
|
|
75
|
+
|
|
76
|
+
```python
|
|
77
|
+
require_between(
|
|
78
|
+
value,
|
|
79
|
+
a_min=None,
|
|
80
|
+
a_max=None,
|
|
81
|
+
*,
|
|
82
|
+
inclusive_min=True,
|
|
83
|
+
inclusive_max=True,
|
|
84
|
+
)
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
Validate that a scalar or array lies within specified bounds.
|
|
88
|
+
|
|
89
|
+
* Bounds may be inclusive or strict
|
|
90
|
+
* Validation fails if **any element** violates the constraint
|
|
91
|
+
|
|
92
|
+
```python
|
|
93
|
+
require_between([0, 1], a_min=0.0) # ok, returns [0, 1]
|
|
94
|
+
require_between([0, 1], a_min=0.0, inclusive_min=False) # raises
|
|
95
|
+
```
|
|
96
|
+
|
|
97
|
+
### Sign-based helpers
|
|
98
|
+
|
|
99
|
+
Convenience wrappers around `require_between`:
|
|
100
|
+
|
|
101
|
+
```python
|
|
102
|
+
require_positive(value) # > 0
|
|
103
|
+
require_nonnegative(value) # >= 0
|
|
104
|
+
require_negative(value) # < 0
|
|
105
|
+
require_nonpositive(value) # <= 0
|
|
106
|
+
```
|
|
107
|
+
|
|
108
|
+
All accept scalars or array-like inputs.
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
### Array validation
|
|
112
|
+
|
|
113
|
+
```python
|
|
114
|
+
validate_array(
|
|
115
|
+
array,
|
|
116
|
+
*,
|
|
117
|
+
dtype=None,
|
|
118
|
+
shape=None,
|
|
119
|
+
writable=None,
|
|
120
|
+
contiguous=None,
|
|
121
|
+
)
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
Validate NumPy array properties without copying or modifying the array.
|
|
125
|
+
|
|
126
|
+
```python
|
|
127
|
+
validate_array(x, dtype=np.float64, shape=(100,))
|
|
128
|
+
validate_array(x, writable=True, contiguous=True)
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
Checks are applied only if the corresponding keyword is provided.
|
|
132
|
+
|
|
133
|
+
|
|
134
|
+
## Errors
|
|
135
|
+
|
|
136
|
+
All validation failures raise:
|
|
137
|
+
|
|
138
|
+
```python
|
|
139
|
+
requireit.ValidationError
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
This allows callers to catch validation failures distinctly from other errors.
|
|
143
|
+
|
|
144
|
+
|
|
145
|
+
## Contributing
|
|
146
|
+
|
|
147
|
+
This project is intentionally small.
|
|
148
|
+
|
|
149
|
+
Contributions should preserve:
|
|
150
|
+
|
|
151
|
+
* minimal surface area
|
|
152
|
+
* explicit semantics
|
|
153
|
+
* no additional dependencies
|
|
154
|
+
|
|
155
|
+
If a proposed change needs much explanation, it probably doesn’t belong here.
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["setuptools", "wheel"]
|
|
3
|
+
build-backend = "setuptools.build_meta"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "requireit"
|
|
7
|
+
description = "Tiny runtime validators for explicit precondition checks"
|
|
8
|
+
authors = [
|
|
9
|
+
{name = "Eric Hutton", email = "mcflugen@gmail.com"},
|
|
10
|
+
]
|
|
11
|
+
maintainers = [
|
|
12
|
+
{name = "Eric Hutton", email = "mcflugen@gmail.com"},
|
|
13
|
+
]
|
|
14
|
+
keywords = [
|
|
15
|
+
"preconditions",
|
|
16
|
+
"runtime-checks",
|
|
17
|
+
"utilities",
|
|
18
|
+
"validation",
|
|
19
|
+
]
|
|
20
|
+
license = "MIT"
|
|
21
|
+
license-files = ["LICENSE.md"]
|
|
22
|
+
classifiers = [
|
|
23
|
+
"Development Status :: 4 - Beta",
|
|
24
|
+
"Intended Audience :: Developers",
|
|
25
|
+
"Operating System :: OS Independent",
|
|
26
|
+
"Programming Language :: Python :: 3",
|
|
27
|
+
"Programming Language :: Python :: 3.10",
|
|
28
|
+
"Programming Language :: Python :: 3.11",
|
|
29
|
+
"Programming Language :: Python :: 3.12",
|
|
30
|
+
"Programming Language :: Python :: 3.13",
|
|
31
|
+
"Programming Language :: Python :: 3.14",
|
|
32
|
+
"Programming Language :: Python :: 3 :: Only",
|
|
33
|
+
"Programming Language :: Python :: Implementation :: CPython",
|
|
34
|
+
"Programming Language :: Python :: Implementation :: PyPy",
|
|
35
|
+
]
|
|
36
|
+
requires-python = ">=3.10"
|
|
37
|
+
dependencies = [
|
|
38
|
+
"numpy",
|
|
39
|
+
]
|
|
40
|
+
dynamic = ["readme", "version"]
|
|
41
|
+
|
|
42
|
+
[project.urls]
|
|
43
|
+
homepage = "https://github.com/mcflugen/requireit"
|
|
44
|
+
documentation = "https://github.com/mcflugen/requireit/blob/main/README.md"
|
|
45
|
+
repository = "https://github.com/mcflugen/requireit"
|
|
46
|
+
changelog = "https://github.com/mcflugen/requireit/blob/main/CHANGES.md"
|
|
47
|
+
|
|
48
|
+
[project.optional-dependencies]
|
|
49
|
+
dev = ["nox"]
|
|
50
|
+
|
|
51
|
+
[tool.setuptools]
|
|
52
|
+
package-dir = {"" = "src"}
|
|
53
|
+
py-modules = ["requireit"]
|
|
54
|
+
|
|
55
|
+
[tool.setuptools.dynamic]
|
|
56
|
+
readme = {file = ["README.md", "AUTHORS.md", "CHANGES.md"], content-type="text/markdown"}
|
|
57
|
+
version = {attr = "requireit.__version__"}
|
|
58
|
+
|
|
59
|
+
[tool.pytest.ini_options]
|
|
60
|
+
minversion = "6.0"
|
|
61
|
+
testpaths = ["tests", "src/requireit.py"]
|
|
62
|
+
norecursedirs = [".*", "*.egg*", "build", "dist", "utilities"]
|
|
63
|
+
addopts = [
|
|
64
|
+
"--ignore=setup.py",
|
|
65
|
+
"--tb=native",
|
|
66
|
+
"--strict-config",
|
|
67
|
+
"--strict-markers",
|
|
68
|
+
"--durations=16",
|
|
69
|
+
"--doctest-modules",
|
|
70
|
+
"-vvv",
|
|
71
|
+
]
|
|
72
|
+
doctest_optionflags = [
|
|
73
|
+
"NORMALIZE_WHITESPACE",
|
|
74
|
+
"IGNORE_EXCEPTION_DETAIL",
|
|
75
|
+
"ALLOW_UNICODE"
|
|
76
|
+
]
|
|
77
|
+
|
|
78
|
+
[tool.isort]
|
|
79
|
+
combine_as_imports = true
|
|
80
|
+
profile = "black"
|
|
@@ -0,0 +1,205 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: requireit
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Tiny runtime validators for explicit precondition checks
|
|
5
|
+
Author-email: Eric Hutton <mcflugen@gmail.com>
|
|
6
|
+
Maintainer-email: Eric Hutton <mcflugen@gmail.com>
|
|
7
|
+
License-Expression: MIT
|
|
8
|
+
Project-URL: homepage, https://github.com/mcflugen/requireit
|
|
9
|
+
Project-URL: documentation, https://github.com/mcflugen/requireit/blob/main/README.md
|
|
10
|
+
Project-URL: repository, https://github.com/mcflugen/requireit
|
|
11
|
+
Project-URL: changelog, https://github.com/mcflugen/requireit/blob/main/CHANGES.md
|
|
12
|
+
Keywords: preconditions,runtime-checks,utilities,validation
|
|
13
|
+
Classifier: Development Status :: 4 - Beta
|
|
14
|
+
Classifier: Intended Audience :: Developers
|
|
15
|
+
Classifier: Operating System :: OS Independent
|
|
16
|
+
Classifier: Programming Language :: Python :: 3
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
21
|
+
Classifier: Programming Language :: Python :: 3.14
|
|
22
|
+
Classifier: Programming Language :: Python :: 3 :: Only
|
|
23
|
+
Classifier: Programming Language :: Python :: Implementation :: CPython
|
|
24
|
+
Classifier: Programming Language :: Python :: Implementation :: PyPy
|
|
25
|
+
Requires-Python: >=3.10
|
|
26
|
+
Description-Content-Type: text/markdown
|
|
27
|
+
License-File: LICENSE.md
|
|
28
|
+
Requires-Dist: numpy
|
|
29
|
+
Provides-Extra: dev
|
|
30
|
+
Requires-Dist: nox; extra == "dev"
|
|
31
|
+
Dynamic: license-file
|
|
32
|
+
|
|
33
|
+
# requireit
|
|
34
|
+
|
|
35
|
+
**Tiny, numpy-aware runtime validators for explicit precondition checks.**
|
|
36
|
+
|
|
37
|
+
`requireit` provides a small collection of lightweight helper functions such as
|
|
38
|
+
`require_positive`, `require_between`, and `validate_array` for validating values
|
|
39
|
+
and arrays at runtime.
|
|
40
|
+
|
|
41
|
+
It is intentionally minimal and dependency-light (*numpy* only).
|
|
42
|
+
|
|
43
|
+
## Why `requireit`?
|
|
44
|
+
|
|
45
|
+
* **Explicit** – reads clearly
|
|
46
|
+
* **numpy-aware** – works correctly with scalars *and* arrays
|
|
47
|
+
* **Fail-fast** – raises immediately with clear error messages
|
|
48
|
+
* **Lightweight** – just a bunch of small functions
|
|
49
|
+
* **Reusable** – avoids copy-pasted validation code across projects
|
|
50
|
+
|
|
51
|
+
```python
|
|
52
|
+
from requireit import require_one_of
|
|
53
|
+
from requireit import require_positive
|
|
54
|
+
|
|
55
|
+
require_positive(dt)
|
|
56
|
+
require_one_of(method, allowed={"foo", "bar"})
|
|
57
|
+
```
|
|
58
|
+
|
|
59
|
+
## Design principles
|
|
60
|
+
|
|
61
|
+
* Prefer small, single-purpose functions
|
|
62
|
+
* Raise standard exceptions (`ValidationError`)
|
|
63
|
+
* Never coerce or "fix" invalid inputs
|
|
64
|
+
* Validate *all* elements for array-like inputs
|
|
65
|
+
* Keep the public API small
|
|
66
|
+
|
|
67
|
+
## Non-goals
|
|
68
|
+
|
|
69
|
+
`requireit` is **not**:
|
|
70
|
+
|
|
71
|
+
* a schema or data-modeling system
|
|
72
|
+
* a replacement for static typing
|
|
73
|
+
* a validation framework
|
|
74
|
+
* a substitute for unit tests
|
|
75
|
+
* a coercion or parsing library
|
|
76
|
+
|
|
77
|
+
If you need structured validation, transformations, or user-facing error
|
|
78
|
+
aggregation, you probably want something heavier.
|
|
79
|
+
|
|
80
|
+
## Installation
|
|
81
|
+
|
|
82
|
+
```bash
|
|
83
|
+
pip install requireit
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
## API overview
|
|
87
|
+
|
|
88
|
+
All validators:
|
|
89
|
+
|
|
90
|
+
* return the original value/array on success
|
|
91
|
+
* raise `ValidationError` on failure
|
|
92
|
+
|
|
93
|
+
### Membership validation
|
|
94
|
+
|
|
95
|
+
```python
|
|
96
|
+
require_one_of(value, *, allowed)
|
|
97
|
+
```
|
|
98
|
+
|
|
99
|
+
Validate that a value is one of a set of allowed values.
|
|
100
|
+
|
|
101
|
+
```python
|
|
102
|
+
require_one_of("foo", allowed=("foo", "bar")) # ok, returns "foo"
|
|
103
|
+
require_one_of("baz", allowed=("foo", "bar")) # raises ValidationError
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
### Range validation
|
|
107
|
+
|
|
108
|
+
```python
|
|
109
|
+
require_between(
|
|
110
|
+
value,
|
|
111
|
+
a_min=None,
|
|
112
|
+
a_max=None,
|
|
113
|
+
*,
|
|
114
|
+
inclusive_min=True,
|
|
115
|
+
inclusive_max=True,
|
|
116
|
+
)
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
Validate that a scalar or array lies within specified bounds.
|
|
120
|
+
|
|
121
|
+
* Bounds may be inclusive or strict
|
|
122
|
+
* Validation fails if **any element** violates the constraint
|
|
123
|
+
|
|
124
|
+
```python
|
|
125
|
+
require_between([0, 1], a_min=0.0) # ok, returns [0, 1]
|
|
126
|
+
require_between([0, 1], a_min=0.0, inclusive_min=False) # raises
|
|
127
|
+
```
|
|
128
|
+
|
|
129
|
+
### Sign-based helpers
|
|
130
|
+
|
|
131
|
+
Convenience wrappers around `require_between`:
|
|
132
|
+
|
|
133
|
+
```python
|
|
134
|
+
require_positive(value) # > 0
|
|
135
|
+
require_nonnegative(value) # >= 0
|
|
136
|
+
require_negative(value) # < 0
|
|
137
|
+
require_nonpositive(value) # <= 0
|
|
138
|
+
```
|
|
139
|
+
|
|
140
|
+
All accept scalars or array-like inputs.
|
|
141
|
+
|
|
142
|
+
|
|
143
|
+
### Array validation
|
|
144
|
+
|
|
145
|
+
```python
|
|
146
|
+
validate_array(
|
|
147
|
+
array,
|
|
148
|
+
*,
|
|
149
|
+
dtype=None,
|
|
150
|
+
shape=None,
|
|
151
|
+
writable=None,
|
|
152
|
+
contiguous=None,
|
|
153
|
+
)
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
Validate NumPy array properties without copying or modifying the array.
|
|
157
|
+
|
|
158
|
+
```python
|
|
159
|
+
validate_array(x, dtype=np.float64, shape=(100,))
|
|
160
|
+
validate_array(x, writable=True, contiguous=True)
|
|
161
|
+
```
|
|
162
|
+
|
|
163
|
+
Checks are applied only if the corresponding keyword is provided.
|
|
164
|
+
|
|
165
|
+
|
|
166
|
+
## Errors
|
|
167
|
+
|
|
168
|
+
All validation failures raise:
|
|
169
|
+
|
|
170
|
+
```python
|
|
171
|
+
requireit.ValidationError
|
|
172
|
+
```
|
|
173
|
+
|
|
174
|
+
This allows callers to catch validation failures distinctly from other errors.
|
|
175
|
+
|
|
176
|
+
|
|
177
|
+
## Contributing
|
|
178
|
+
|
|
179
|
+
This project is intentionally small.
|
|
180
|
+
|
|
181
|
+
Contributions should preserve:
|
|
182
|
+
|
|
183
|
+
* minimal surface area
|
|
184
|
+
* explicit semantics
|
|
185
|
+
* no additional dependencies
|
|
186
|
+
|
|
187
|
+
If a proposed change needs much explanation, it probably doesn’t belong here.
|
|
188
|
+
|
|
189
|
+
# Credits
|
|
190
|
+
|
|
191
|
+
## Development Leads
|
|
192
|
+
|
|
193
|
+
- [Eric Hutton](https://github.com/mcflugen)
|
|
194
|
+
|
|
195
|
+
# Release Notes
|
|
196
|
+
|
|
197
|
+
## 0.1.0 (not yet released)
|
|
198
|
+
|
|
199
|
+
- Added documentation to the README [#1](https://github.com/mcflugen/requireit/issues/1)
|
|
200
|
+
- Added project metadata files [#2](https://github.com/mcflugen/requireit/issues/2)
|
|
201
|
+
- Added the `requireit` module [#3](https://github.com/mcflugen/requireit/issues/3)
|
|
202
|
+
- Added `pyproject.toml` file [#4](https://github.com/mcflugen/requireit/issues/4)
|
|
203
|
+
- Added `noxfile.py` file and linters [#5](https://github.com/mcflugen/requireit/issues/5)
|
|
204
|
+
- Added unit tests for `requireit` [#6](https://github.com/mcflugen/requireit/issues/6)
|
|
205
|
+
- Added GitHub Actions for CI [#7](https://github.com/mcflugen/requireit/issues/7)
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
AUTHORS.md
|
|
2
|
+
CHANGES.md
|
|
3
|
+
LICENSE.md
|
|
4
|
+
README.md
|
|
5
|
+
pyproject.toml
|
|
6
|
+
setup.cfg
|
|
7
|
+
src/requireit.py
|
|
8
|
+
src/requireit.egg-info/PKG-INFO
|
|
9
|
+
src/requireit.egg-info/SOURCES.txt
|
|
10
|
+
src/requireit.egg-info/dependency_links.txt
|
|
11
|
+
src/requireit.egg-info/requires.txt
|
|
12
|
+
src/requireit.egg-info/top_level.txt
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
requireit
|
|
@@ -0,0 +1,306 @@
|
|
|
1
|
+
from collections.abc import Callable
|
|
2
|
+
from collections.abc import Collection
|
|
3
|
+
from collections.abc import Iterable
|
|
4
|
+
from typing import Any
|
|
5
|
+
|
|
6
|
+
import numpy as np
|
|
7
|
+
from numpy.typing import ArrayLike
|
|
8
|
+
from numpy.typing import DTypeLike
|
|
9
|
+
from numpy.typing import NDArray
|
|
10
|
+
|
|
11
|
+
__version__ = "0.1.0"
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
class RequireItError(Exception):
|
|
15
|
+
"""Base class for exceptions raised from this module."""
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
class ValidationError(RequireItError):
|
|
19
|
+
"""Error to indicate that a validation has failed."""
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def require_one_of(value: Any, *, allowed: Iterable[Any]) -> Any:
|
|
23
|
+
"""Validate that ``value`` is one of ``allowed``.
|
|
24
|
+
|
|
25
|
+
Parameters
|
|
26
|
+
----------
|
|
27
|
+
value : any
|
|
28
|
+
A scalar value to validate.
|
|
29
|
+
allowed : iterable of any
|
|
30
|
+
Allowed values.
|
|
31
|
+
|
|
32
|
+
Returns
|
|
33
|
+
-------
|
|
34
|
+
any
|
|
35
|
+
The original value.
|
|
36
|
+
|
|
37
|
+
Raises
|
|
38
|
+
------
|
|
39
|
+
ValidationError
|
|
40
|
+
If the value is not in ``allowed``.
|
|
41
|
+
|
|
42
|
+
Examples
|
|
43
|
+
--------
|
|
44
|
+
>>> require_one_of("foo", allowed=("foo", "bar"))
|
|
45
|
+
'foo'
|
|
46
|
+
>>> require_one_of("baz", allowed=("foo", "bar"))
|
|
47
|
+
Traceback (most recent call last):
|
|
48
|
+
...
|
|
49
|
+
requireit.ValidationError: invalid value: 'baz' is not one of 'bar', 'foo'
|
|
50
|
+
>>> require_one_of("Foo", allowed=("foo", "bar"))
|
|
51
|
+
Traceback (most recent call last):
|
|
52
|
+
...
|
|
53
|
+
requireit.ValidationError: invalid value: 'Foo' is not one of 'bar', 'foo'
|
|
54
|
+
"""
|
|
55
|
+
try:
|
|
56
|
+
collection_of_allowed: Collection = set(allowed)
|
|
57
|
+
in_collection = value in collection_of_allowed
|
|
58
|
+
except TypeError:
|
|
59
|
+
collection_of_allowed = list(allowed)
|
|
60
|
+
in_collection = value in collection_of_allowed
|
|
61
|
+
|
|
62
|
+
if not in_collection:
|
|
63
|
+
allowed_str = ", ".join(sorted(repr(x) for x in collection_of_allowed))
|
|
64
|
+
raise ValidationError(f"invalid value: {value!r} is not one of {allowed_str}")
|
|
65
|
+
return value
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
def require_between(
|
|
69
|
+
value: ArrayLike,
|
|
70
|
+
a_min: float | None = None,
|
|
71
|
+
a_max: float | None = None,
|
|
72
|
+
*,
|
|
73
|
+
inclusive_min: bool = True,
|
|
74
|
+
inclusive_max: bool = True,
|
|
75
|
+
) -> ArrayLike:
|
|
76
|
+
"""Validate that a value lies within a specified interval.
|
|
77
|
+
|
|
78
|
+
Parameters
|
|
79
|
+
----------
|
|
80
|
+
value : scalar or array-like
|
|
81
|
+
The input value(s) to be validated.
|
|
82
|
+
a_min : float or None, optional
|
|
83
|
+
Minimum allowable value. If ``None``, no lower bound is applied.
|
|
84
|
+
a_max : float or None, optional
|
|
85
|
+
Maximum allowable value. If ``None``, no upper bound is applied.
|
|
86
|
+
inclusive_min : bool, optional
|
|
87
|
+
If ``True`` (default), the lower bound is inclusive (``>=``).
|
|
88
|
+
If ``False``, the lower bound is strict (``>``).
|
|
89
|
+
inclusive_max : bool, optional
|
|
90
|
+
If ``True`` (default), the upper bound is inclusive (``<=``).
|
|
91
|
+
If ``False``, the upper bound is strict (``<``).
|
|
92
|
+
|
|
93
|
+
Returns
|
|
94
|
+
-------
|
|
95
|
+
value : scalar or array-like
|
|
96
|
+
The validated value.
|
|
97
|
+
|
|
98
|
+
Raises
|
|
99
|
+
------
|
|
100
|
+
ValidationError
|
|
101
|
+
If any element of ``value`` violates the specified bounds.
|
|
102
|
+
|
|
103
|
+
Examples
|
|
104
|
+
--------
|
|
105
|
+
>>> require_between([0, 1], a_min=0.0, inclusive_min=True)
|
|
106
|
+
[0, 1]
|
|
107
|
+
>>> require_between([0, 1], a_min=0.0, inclusive_min=False)
|
|
108
|
+
Traceback (most recent call last):
|
|
109
|
+
...
|
|
110
|
+
requireit.ValidationError: value must be > 0.0
|
|
111
|
+
"""
|
|
112
|
+
arr = np.asarray(value)
|
|
113
|
+
|
|
114
|
+
if a_min is not None:
|
|
115
|
+
cmp: Callable = np.less if inclusive_min else np.less_equal
|
|
116
|
+
op = ">=" if inclusive_min else ">"
|
|
117
|
+
if np.any(cmp(arr, a_min)):
|
|
118
|
+
raise ValidationError(f"value must be {op} {a_min}")
|
|
119
|
+
|
|
120
|
+
if a_max is not None:
|
|
121
|
+
cmp = np.greater if inclusive_max else np.greater_equal
|
|
122
|
+
op = "<=" if inclusive_max else "<"
|
|
123
|
+
if np.any(cmp(arr, a_max)):
|
|
124
|
+
raise ValidationError(f"value must be {op} {a_max}")
|
|
125
|
+
|
|
126
|
+
return value
|
|
127
|
+
|
|
128
|
+
|
|
129
|
+
def require_positive(value: ArrayLike) -> ArrayLike:
|
|
130
|
+
"""Validate that a value is strictly greater than zero.
|
|
131
|
+
|
|
132
|
+
Parameters
|
|
133
|
+
----------
|
|
134
|
+
value : scalar or array-like
|
|
135
|
+
The input value(s) to be validated.
|
|
136
|
+
|
|
137
|
+
Returns
|
|
138
|
+
-------
|
|
139
|
+
value : scalar or array-like
|
|
140
|
+
The validated value.
|
|
141
|
+
|
|
142
|
+
Raises
|
|
143
|
+
------
|
|
144
|
+
ValidationError
|
|
145
|
+
If any element of ``value`` is less than or equal to zero.
|
|
146
|
+
|
|
147
|
+
Examples
|
|
148
|
+
--------
|
|
149
|
+
>>> require_positive(1.0)
|
|
150
|
+
1.0
|
|
151
|
+
>>> require_positive(0.0)
|
|
152
|
+
Traceback (most recent call last):
|
|
153
|
+
...
|
|
154
|
+
requireit.ValidationError: value must be > 0.0
|
|
155
|
+
"""
|
|
156
|
+
return require_between(value, a_min=0.0, a_max=None, inclusive_min=False)
|
|
157
|
+
|
|
158
|
+
|
|
159
|
+
def require_nonnegative(value: ArrayLike) -> ArrayLike:
|
|
160
|
+
"""Validate that a value is greater than or equal to zero.
|
|
161
|
+
|
|
162
|
+
Parameters
|
|
163
|
+
----------
|
|
164
|
+
value : scalar or array-like
|
|
165
|
+
The input value(s) to be validated.
|
|
166
|
+
|
|
167
|
+
Returns
|
|
168
|
+
-------
|
|
169
|
+
value : scalar or array-like
|
|
170
|
+
The validated value.
|
|
171
|
+
|
|
172
|
+
Raises
|
|
173
|
+
------
|
|
174
|
+
ValidationError
|
|
175
|
+
If any element of ``value`` is less than zero.
|
|
176
|
+
|
|
177
|
+
Examples
|
|
178
|
+
--------
|
|
179
|
+
>>> require_nonnegative(-1.0)
|
|
180
|
+
Traceback (most recent call last):
|
|
181
|
+
...
|
|
182
|
+
requireit.ValidationError: value must be >= 0.0
|
|
183
|
+
>>> require_nonnegative(0.0)
|
|
184
|
+
0.0
|
|
185
|
+
>>> require_nonnegative(1.0)
|
|
186
|
+
1.0
|
|
187
|
+
"""
|
|
188
|
+
return require_between(value, a_min=0.0, a_max=None, inclusive_min=True)
|
|
189
|
+
|
|
190
|
+
|
|
191
|
+
def require_negative(value: ArrayLike) -> ArrayLike:
|
|
192
|
+
"""Validate that a value is strictly less than zero.
|
|
193
|
+
|
|
194
|
+
Parameters
|
|
195
|
+
----------
|
|
196
|
+
value : scalar or array-like
|
|
197
|
+
The input value(s) to be validated.
|
|
198
|
+
|
|
199
|
+
Returns
|
|
200
|
+
-------
|
|
201
|
+
value : scalar or array-like
|
|
202
|
+
The validated value.
|
|
203
|
+
|
|
204
|
+
Raises
|
|
205
|
+
------
|
|
206
|
+
ValidationError
|
|
207
|
+
If any element of ``value`` is greater than or equal to zero.
|
|
208
|
+
|
|
209
|
+
Examples
|
|
210
|
+
--------
|
|
211
|
+
>>> require_negative(-1.0)
|
|
212
|
+
-1.0
|
|
213
|
+
>>> require_negative(0.0)
|
|
214
|
+
Traceback (most recent call last):
|
|
215
|
+
...
|
|
216
|
+
requireit.ValidationError: value must be < 0.0
|
|
217
|
+
"""
|
|
218
|
+
return require_between(value, a_min=None, a_max=0.0, inclusive_max=False)
|
|
219
|
+
|
|
220
|
+
|
|
221
|
+
def require_nonpositive(value: ArrayLike) -> ArrayLike:
|
|
222
|
+
"""Validate that a value is less than or equal to zero.
|
|
223
|
+
|
|
224
|
+
Parameters
|
|
225
|
+
----------
|
|
226
|
+
value : scalar or array-like
|
|
227
|
+
The input value(s) to be validated.
|
|
228
|
+
|
|
229
|
+
Returns
|
|
230
|
+
-------
|
|
231
|
+
value : scalar or array-like
|
|
232
|
+
The validated value.
|
|
233
|
+
|
|
234
|
+
Raises
|
|
235
|
+
------
|
|
236
|
+
ValidationError
|
|
237
|
+
If any element of ``value`` is greater than zero.
|
|
238
|
+
|
|
239
|
+
Examples
|
|
240
|
+
--------
|
|
241
|
+
>>> require_nonpositive(-1.0)
|
|
242
|
+
-1.0
|
|
243
|
+
>>> require_nonpositive(0.0)
|
|
244
|
+
0.0
|
|
245
|
+
>>> require_nonpositive(1.0)
|
|
246
|
+
Traceback (most recent call last):
|
|
247
|
+
...
|
|
248
|
+
requireit.ValidationError: value must be <= 0.0
|
|
249
|
+
"""
|
|
250
|
+
return require_between(value, a_min=None, a_max=0.0, inclusive_max=True)
|
|
251
|
+
|
|
252
|
+
|
|
253
|
+
def validate_array(
|
|
254
|
+
array: NDArray,
|
|
255
|
+
*,
|
|
256
|
+
dtype: DTypeLike | None = None,
|
|
257
|
+
shape: tuple[int, ...] | None = None,
|
|
258
|
+
writable: bool | None = None,
|
|
259
|
+
contiguous: bool | None = None,
|
|
260
|
+
):
|
|
261
|
+
"""Validate an array to satisfy requirements.
|
|
262
|
+
|
|
263
|
+
Parameters
|
|
264
|
+
----------
|
|
265
|
+
array : ndarray
|
|
266
|
+
The array to be validated.
|
|
267
|
+
dtype : data-type, optional
|
|
268
|
+
The required data type.
|
|
269
|
+
shape : tuple of int, optional
|
|
270
|
+
The required shape.
|
|
271
|
+
writable : bool, optional
|
|
272
|
+
Require the array to be writable.
|
|
273
|
+
contiguous : bool, optional
|
|
274
|
+
Require the array to be c-contiguous.
|
|
275
|
+
|
|
276
|
+
Returns
|
|
277
|
+
-------
|
|
278
|
+
array : ndarray
|
|
279
|
+
The validated array.
|
|
280
|
+
|
|
281
|
+
Raises
|
|
282
|
+
------
|
|
283
|
+
ValidationError
|
|
284
|
+
If the array is invalid.
|
|
285
|
+
|
|
286
|
+
Examples
|
|
287
|
+
--------
|
|
288
|
+
>>> import numpy as np
|
|
289
|
+
>>> validate_array(np.array([1, 2, 3, 4]), shape=(2, 2))
|
|
290
|
+
Traceback (most recent call last):
|
|
291
|
+
...
|
|
292
|
+
requireit.ValidationError: incorrect shape: expected (2, 2), got (4,)
|
|
293
|
+
"""
|
|
294
|
+
if shape is not None and array.shape != shape:
|
|
295
|
+
raise ValidationError(f"incorrect shape: expected {shape}, got {array.shape}")
|
|
296
|
+
|
|
297
|
+
if dtype is not None and array.dtype != np.dtype(dtype):
|
|
298
|
+
raise ValidationError(f"incorrect type: expected {dtype}, got {array.dtype}")
|
|
299
|
+
|
|
300
|
+
if writable and not array.flags.writeable:
|
|
301
|
+
raise ValidationError("array is not writable")
|
|
302
|
+
|
|
303
|
+
if contiguous and not array.flags.c_contiguous:
|
|
304
|
+
raise ValidationError("array is not contiguous")
|
|
305
|
+
|
|
306
|
+
return array
|