scipy-doctest 1.6__tar.gz → 1.7__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.
Files changed (32) hide show
  1. {scipy_doctest-1.6 → scipy_doctest-1.7}/PKG-INFO +59 -45
  2. {scipy_doctest-1.6 → scipy_doctest-1.7}/README.md +50 -42
  3. {scipy_doctest-1.6 → scipy_doctest-1.7}/pyproject.toml +32 -1
  4. scipy_doctest-1.7/scipy_doctest/.ruff_cache/.gitignore +2 -0
  5. scipy_doctest-1.7/scipy_doctest/.ruff_cache/0.9.4/12495833369255784944 +0 -0
  6. scipy_doctest-1.7/scipy_doctest/.ruff_cache/CACHEDIR.TAG +1 -0
  7. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/__init__.py +1 -2
  8. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/conftest.py +0 -1
  9. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/frontend.py +6 -7
  10. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/impl.py +94 -35
  11. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/plugin.py +9 -9
  12. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/failure_cases_2.py +0 -1
  13. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/finder_cases.py +0 -2
  14. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/local_file_cases.py +0 -2
  15. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/module_cases.py +0 -2
  16. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/scipy_ndimage_tutorial_clone.rst +2 -2
  17. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_finder.py +6 -9
  18. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_parser.py +0 -3
  19. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_pytest_configuration.py +1 -2
  20. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_runner.py +0 -1
  21. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_skipmarkers.py +12 -7
  22. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_testmod.py +1 -1
  23. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/util.py +2 -3
  24. {scipy_doctest-1.6 → scipy_doctest-1.7}/LICENSE +0 -0
  25. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/__main__.py +0 -0
  26. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/__init__.py +0 -0
  27. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/failure_cases.py +0 -0
  28. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/finder_cases_2.py +0 -0
  29. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/local_file.txt +0 -0
  30. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/octave_a.mat +0 -0
  31. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/stopwords_cases.py +0 -0
  32. {scipy_doctest-1.6 → scipy_doctest-1.7}/scipy_doctest/tests/test_testfile.py +0 -0
@@ -1,6 +1,6 @@
1
- Metadata-Version: 2.3
1
+ Metadata-Version: 2.4
2
2
  Name: scipy_doctest
3
- Version: 1.6
3
+ Version: 1.7
4
4
  Summary: Configurable, whitespace-insensitive, floating-point-aware doctest helpers.
5
5
  Maintainer-email: SciPy developers <scipy-dev@python.org>
6
6
  Requires-Python: >=3.8
@@ -10,20 +10,36 @@ Classifier: License :: OSI Approved :: BSD License
10
10
  Classifier: Intended Audience :: Developers
11
11
  Classifier: Programming Language :: Python :: 3
12
12
  Classifier: Framework :: Pytest
13
+ License-File: LICENSE
13
14
  Requires-Dist: numpy>=1.19.5
14
15
  Requires-Dist: pytest
15
- Requires-Dist: scipy ; extra == "test"
16
+ Requires-Dist: furo==2024.8.6 ; extra == "doc"
17
+ Requires-Dist: myst-parser==4.0.0 ; extra == "doc"
18
+ Requires-Dist: sphinx==8.1.3 ; extra == "doc"
19
+ Requires-Dist: sphinx-copybutton==0.5.2 ; extra == "doc"
20
+ Requires-Dist: scipy <= 1.14.1 ; extra == "test"
16
21
  Requires-Dist: matplotlib ; extra == "test"
17
22
  Project-URL: Home, https://github.com/scipy/scipy_doctest
23
+ Provides-Extra: doc
18
24
  Provides-Extra: test
19
25
 
20
26
  # Floating-point aware, human readable, numpy-compatible doctesting.
21
27
 
28
+ [![PyPI version][pypi-version]][pypi-link]
29
+ [![Conda-Forge][conda-badge]][conda-link]
30
+
31
+ <!-- prettier-ignore-start -->
32
+ [conda-badge]: https://img.shields.io/conda/vn/conda-forge/scipy-doctest
33
+ [conda-link]: https://anaconda.org/conda-forge/scipy-doctest
34
+ [pypi-link]: https://pypi.org/project/scipy-doctest/
35
+ [pypi-version]: https://img.shields.io/pypi/v/scipy-doctest
36
+ <!-- prettier-ignore-end -->
37
+
22
38
  ## TL;DR
23
39
 
24
40
  This project extends the standard library `doctest` module to allow flexibility
25
41
  and easy customization of finding, parsing and checking code examples in
26
- documentation.
42
+ documentation.
27
43
 
28
44
  Can be used either as drop-in `doctest` replacement or through the `pytest`
29
45
  integration. Uses a floating-point aware doctest checker by default.
@@ -31,7 +47,7 @@ integration. Uses a floating-point aware doctest checker by default.
31
47
  ## Motivation and scope
32
48
 
33
49
  Having examples in the documentation is great. Having wrong examples in the
34
- documentation is not that great however.
50
+ documentation is not that great however.
35
51
 
36
52
  The standard library `doctest` module is great for making sure that docstring
37
53
  examples are correct. However, the `doctest` module is limited in several
@@ -46,7 +62,7 @@ This looks reasonably clear but does not work, in three different ways.
46
62
  _First_, `1/3` is not equal to 0.333 because floating-point arithmetic.
47
63
  _Second_, `numpy` adds whitespace to its output, this whitespace confuses the
48
64
  `doctest`, which is whitespace-sensitive. Therefore, we added a magic directive,
49
- `+SKIP` to avoid a doctest error. _Third_, the example is actually
65
+ `+SKIP` to avoid a doctest error. _Third_, the example is actually
50
66
  wrong---notice `0.669` which is not equal to `2/3` to three sig figs. The error
51
67
  went unnoticed by the doctester also because of the `+SKIP` directive.
52
68
 
@@ -56,44 +72,44 @@ a human reader, and should not be present in the documentation.
56
72
  This package defines modified doctesting routines which fix these deficiencies.
57
73
  Its main features are
58
74
 
59
- - *Doctesting is floating-point aware.* In a nutshell, the core check is
75
+ - _Doctesting is floating-point aware._ In a nutshell, the core check is
60
76
  `np.allclose(want, got, atol=..., rtol=...)`, with user-controllable abs
61
77
  and relative tolerances. In the example above (_sans_ `# doctest: +SKIP`),
62
78
  `want` is the desired output, `array([0.333, 0.669, 1])` and `got` is the
63
79
  actual output from numpy: `array([0.33333333, 0.66666667, 1. ])`.
64
80
 
65
- - *Human-readable skip markers.* Consider
81
+ - _Human-readable skip markers._ Consider
66
82
  ```
67
83
  >>> np.random.randint(100)
68
84
  42 # may vary
69
85
  ```
70
- Note that the markers (by default, `"# may vary"` and `"# random"`) can be applied
71
- to either an example's output, or its source.
86
+ Note that the markers (by default, `"# may vary"` and `"# random"`) can be applied
87
+ to either an example's output, or its source.
72
88
 
73
89
  Also note a difference with respect to the standard `# doctest: +SKIP`: the latter
74
90
  skips the example entirely, while these additional markers only skip checking
75
91
  the output. Thus the example source needs to be valid python code still.
76
92
 
77
- - A user-configurable list of *stopwords*. If an example contains a stopword,
93
+ - A user-configurable list of _stopwords_. If an example contains a stopword,
78
94
  it is checked to be valid python, but the output is not checked. This can
79
95
  be useful e.g. for not littering the documentation with the output of
80
96
  `import matplotlib.pyplot as plt; plt.xlim([2.3, 4.5])`.
81
97
 
82
- - A user-configurable list of *pseudocode* markers. If an example contains one
98
+ - A user-configurable list of _pseudocode_ markers. If an example contains one
83
99
  of these markers, it is considered pseudocode and is not checked.
84
100
  This is useful for `from example import some_functions` and similar stanzas.
85
101
 
86
102
  - A `# doctest: +SKIPBLOCK` option flag to skip whole blocks of pseudocode. Here
87
103
  a 'block' is a sequence of doctest examples without any intervening text.
88
104
 
89
- - *Doctest discovery* is somewhat more flexible then the standard library
105
+ - _Doctest discovery_ is somewhat more flexible then the standard library
90
106
  `doctest` module. Specifically, one can use `testmod(module, strategy='api')`
91
107
  to only examine public objects of a module. This is helpful for complex
92
108
  packages, with non-trivial internal file structure. Alternatively, the default
93
109
  value of `strategy=None` is equivalent to the standard `doctest` module
94
110
  behavior.
95
111
 
96
- - *User configuration*. Essentially all aspects of the behavior are user
112
+ - _User configuration_. Essentially all aspects of the behavior are user
97
113
  configurable via a `DTConfig` instance attributes. See the `DTConfig`
98
114
  docstring for details.
99
115
 
@@ -124,7 +140,7 @@ pip install scipy-doctest
124
140
 
125
141
  2. **Register or load the plugin**
126
142
 
127
- Next, you need to register or load the pytest plugin within your test module or `conftest.py` file.
143
+ Next, you need to register or load the pytest plugin within your test module or `conftest.py` file.
128
144
 
129
145
  To do this, add the following line of code:
130
146
 
@@ -136,14 +152,16 @@ pytest_plugins = "scipy_doctest"
136
152
 
137
153
  Check out the [pytest documentation](https://docs.pytest.org/en/stable/how-to/writing_plugins.html#requiring-loading-plugins-in-a-test-module-or-conftest-file) for more information on requiring/loading plugins in a test module or `conftest.py` file.
138
154
 
139
- 3. **Run doctests**
155
+ 3. **Run doctests**
140
156
 
141
157
  Once the plugin is registered, run the doctests by executing the following command:
142
158
 
143
159
  ```bash
144
160
  $ python -m pytest --doctest-modules
145
161
  ```
162
+
146
163
  or
164
+
147
165
  ```bash
148
166
  $ pytest --pyargs <your-package> --doctest-modules
149
167
  ```
@@ -155,10 +173,9 @@ use the command flag
155
173
  $ pytest --pyargs <your-package> --doctest-modules --doctest-collect=api
156
174
  ```
157
175
 
158
- See [More fine-grained control](https://github.com/scipy/scipy_doctest#More-fine-grained-control) section
176
+ See [More fine-grained control](#more-fine-grained-control) section
159
177
  for details on how to customize the behavior.
160
178
 
161
-
162
179
  ### Basic usage
163
180
 
164
181
  The use of `pytest` is optional, and you can use the `doctest` layer API.
@@ -171,6 +188,7 @@ For example,
171
188
  >>> res
172
189
  TestResults(failed=0, attempted=764)
173
190
  ```
191
+
174
192
  The second return value, `hist` is a dict which maps the names of the objects
175
193
  to the numbers of failures and attempts for individual examples.
176
194
 
@@ -178,10 +196,10 @@ For more details, see the `testmod` docstring. Other useful functions are
178
196
  `find_doctests`, `run_docstring_examples` and `testfile` (the latter two mimic
179
197
  the behavior of the eponymous functions of the `doctest` module).
180
198
 
181
-
182
199
  ### Command-line interface
183
200
 
184
201
  There is a basic CLI, which also mimics that of the `doctest` module:
202
+
185
203
  ```
186
204
  $ python -m scipy_doctest foo.py
187
205
  ```
@@ -190,28 +208,30 @@ Note that, just like `$ python -m doctest foo.py`, this may
190
208
  fail if `foo.py` is a part of a package due to package imports.
191
209
 
192
210
  Text files can also be CLI-checked:
211
+
193
212
  ```
194
213
  $ python -m scipy_doctest bar.rst
195
214
  ```
196
215
 
197
216
  Notice that the command-line usage only uses the default `DTConfig` settings.
198
217
 
218
+ (more-fine-grained-control)=
199
219
 
200
220
  ## More fine-grained control
201
221
 
202
222
  More fine-grained control of the functionality is available via the following
203
223
  classes
204
224
 
205
- | Class | `doctest` analog |
206
- |-------------|--------------------|
207
- | `DTChecker` | `DocTestChecker` |
208
- | `DTParser` | `DocTestParser` |
209
- | `DTRunner` | `DocTestRunner` |
210
- | `DTFinder` | `DocTestFinder` |
211
- | `DTContext` | -- |
225
+ | Class | `doctest` analog |
226
+ | ----------- | ---------------- |
227
+ | `DTChecker` | `DocTestChecker` |
228
+ | `DTParser` | `DocTestParser` |
229
+ | `DTRunner` | `DocTestRunner` |
230
+ | `DTFinder` | `DocTestFinder` |
231
+ | `DTContext` | -- |
212
232
 
213
233
  The `DTContext` class is just a bag class which holds various configuration
214
- settings as attributes. An instance of this class is passed around, so user
234
+ settings as attributes. An instance of this class is passed around, so user
215
235
  configuration is simply creating an instance, overriding an attribute and
216
236
  passing the instance to `testmod` or constructors of `DT*` objects. Defaults
217
237
  are provided, based on a long-term usage in SciPy.
@@ -220,7 +240,7 @@ See the [DTConfig docstring](https://github.com/scipy/scipy_doctest/blob/main/sc
220
240
  for the full set of attributes that allow you to fine-tune your doctesting experience.
221
241
 
222
242
  To set any of these attributes, create an instance of `DTConfig` and assign the attributes
223
- in a usual way.
243
+ in a usual way.
224
244
 
225
245
  If using the pytest plugin, it is convenient to use the default instance, which
226
246
  is predefined in `scipy_doctest/conftest.py`. This instance will be automatically
@@ -260,14 +280,12 @@ dt_config.skiplist = {
260
280
 
261
281
  If you don't set these attributes, the [default settings](https://github.com/scipy/scipy_doctest/blob/58ff06a837b7bff1dbac6560013fc6fd07952ae2/scipy_doctest/impl.py#L94) of the attributes are used.
262
282
 
263
-
264
283
  #### Alternative Checkers
265
284
 
266
285
  By default, we use the floating-point aware `DTChecker`. If you want to use an
267
286
  alternative checker, all you need to do is to define the corresponding class,
268
287
  and add an attribute to the `DTConfig` instance. For example,
269
288
 
270
-
271
289
  ```
272
290
  class VanillaOutputChecker(doctest.OutputChecker):
273
291
  """doctest.OutputChecker to drop in for DTChecker.
@@ -290,10 +308,8 @@ See [a pytest example](https://github.com/scipy/scipy_doctest/blob/main/scipy_do
290
308
  and [a doctest example](https://github.com/scipy/scipy_doctest/blob/main/scipy_doctest/tests/test_runner.py#L94)
291
309
  for more details.
292
310
 
293
-
294
311
  ### NumPy and SciPy wrappers
295
312
 
296
-
297
313
  NumPy wraps `scipy-doctest` with the `spin` command
298
314
 
299
315
  ```
@@ -307,13 +323,11 @@ $ python dev.py smoke-docs # check docstrings
307
323
  $ python dev.py smoke-tutorials # ReST user guide tutorials
308
324
  ```
309
325
 
310
-
311
-
312
326
  ## Rough edges and sharp bits
313
327
 
314
328
  Here is a (non-exhaustive) list of possible gotchas:
315
329
 
316
- - *In-place development builds*.
330
+ - _In-place development builds_.
317
331
 
318
332
  Some tools (looking at you `meson-python`) simulate in-place builds with a
319
333
  `build-install` directory. If this directory is located under the project root,
@@ -329,12 +343,15 @@ $ pytest build-install/lib/python3.10/site-packages/scipy/ --doctest-modules
329
343
 
330
344
  instead of `$ pytest --pyargs scipy`.
331
345
 
332
- If push comes to shove, you may try using the magic env variable:
346
+ If you use actual editable installs, of the `pip install --no-build-isolation -e .` variety, you may
347
+ need to add `--import-mode=importlib` to the `pytest` invocation.
348
+
349
+ If push really comes to shove, you may try using the magic env variable:
333
350
  ` PY_IGNORE_IMPORTMISMATCH=1 pytest ...`,
334
351
  however the need usually indicates an issue with the package itself.
335
352
  (see [gh-107](https://github.com/scipy/scipy_doctest/pull/107) for an example).
336
353
 
337
- - *Optional dependencies are not that optional*
354
+ - _Optional dependencies are not that optional_
338
355
 
339
356
  If your package contains optional dependencies, doctests do not know about them
340
357
  being optional. So you either guard the imports in doctests (yikes!), or
@@ -353,11 +370,11 @@ Note that installed packages are no different:
353
370
  $ pytest --pyargs scipy --doctest-modules --ignore=/path/to/installed/scipy/_lib
354
371
  ```
355
372
 
356
- - *Doctest collection strategies*
373
+ - _Doctest collection strategies_
357
374
 
358
375
  The default collection strategy follows `doctest` module and `pytest`. This leads
359
376
  to duplicates if your package has the split between public and \_private modules,
360
- where public modules re-export things from private ones. The solution is to
377
+ where public modules re-export things from private ones. The solution is to
361
378
  use `$ pytest --doctest-collect=api` CLI switch: with this, only public
362
379
  objects will be collected.
363
380
 
@@ -375,8 +392,7 @@ leads to
375
392
  - `scipy.linalg._basic.det`, collected from `scipy/linalg/_basic.py`, is private.
376
393
  - `scipy.linalg.det`, collected from `scipy/linalg/__init__.py`, is public.
377
394
 
378
-
379
- - *`pytest`'s assertion rewriting*
395
+ - _`pytest`'s assertion rewriting_
380
396
 
381
397
  In some rare cases you may need to either explicitly register the `scipy_doctest`
382
398
  package with the `pytest` assertion rewriting machinery, or ask it to avoid rewriting
@@ -388,7 +404,6 @@ In general, rewriting assertions is not very useful for doctests, as the
388
404
  output on error is fixed by the doctest machinery anyway. Therefore, we believe
389
405
  adding `--assert=plain` is reasonable.
390
406
 
391
-
392
407
  ## Prior art and related work
393
408
 
394
409
  - `pytest` provides some limited floating-point aware `NumericLiteralChecker`.
@@ -409,15 +424,14 @@ adding `--assert=plain` is reasonable.
409
424
  to be not easy to reason about, work with, and extend to other projects.
410
425
 
411
426
  This project is mainly the core functionality of the modified
412
- `refguide-check` doctesting, extracted to a separate package.
427
+ `refguide-check` doctesting, extracted to a separate package.
413
428
  We believe having it separate simplifies both addressing the needs of these
414
429
  two packages, and potential adoption by other projects.
415
430
 
416
-
417
431
  ### Bug reports, feature requests and contributions
418
432
 
419
433
  This package is work in progress. Contributions are most welcome!
420
434
  Please don't hesitate to open an issue in the tracker or send a pull request.
421
435
 
422
- The current location of the issue tracker is https://github.com/scipy/scipy_doctest.
436
+ The current location of the issue tracker is <https://github.com/scipy/scipy_doctest>.
423
437
 
@@ -1,10 +1,20 @@
1
1
  # Floating-point aware, human readable, numpy-compatible doctesting.
2
2
 
3
+ [![PyPI version][pypi-version]][pypi-link]
4
+ [![Conda-Forge][conda-badge]][conda-link]
5
+
6
+ <!-- prettier-ignore-start -->
7
+ [conda-badge]: https://img.shields.io/conda/vn/conda-forge/scipy-doctest
8
+ [conda-link]: https://anaconda.org/conda-forge/scipy-doctest
9
+ [pypi-link]: https://pypi.org/project/scipy-doctest/
10
+ [pypi-version]: https://img.shields.io/pypi/v/scipy-doctest
11
+ <!-- prettier-ignore-end -->
12
+
3
13
  ## TL;DR
4
14
 
5
15
  This project extends the standard library `doctest` module to allow flexibility
6
16
  and easy customization of finding, parsing and checking code examples in
7
- documentation.
17
+ documentation.
8
18
 
9
19
  Can be used either as drop-in `doctest` replacement or through the `pytest`
10
20
  integration. Uses a floating-point aware doctest checker by default.
@@ -12,7 +22,7 @@ integration. Uses a floating-point aware doctest checker by default.
12
22
  ## Motivation and scope
13
23
 
14
24
  Having examples in the documentation is great. Having wrong examples in the
15
- documentation is not that great however.
25
+ documentation is not that great however.
16
26
 
17
27
  The standard library `doctest` module is great for making sure that docstring
18
28
  examples are correct. However, the `doctest` module is limited in several
@@ -27,7 +37,7 @@ This looks reasonably clear but does not work, in three different ways.
27
37
  _First_, `1/3` is not equal to 0.333 because floating-point arithmetic.
28
38
  _Second_, `numpy` adds whitespace to its output, this whitespace confuses the
29
39
  `doctest`, which is whitespace-sensitive. Therefore, we added a magic directive,
30
- `+SKIP` to avoid a doctest error. _Third_, the example is actually
40
+ `+SKIP` to avoid a doctest error. _Third_, the example is actually
31
41
  wrong---notice `0.669` which is not equal to `2/3` to three sig figs. The error
32
42
  went unnoticed by the doctester also because of the `+SKIP` directive.
33
43
 
@@ -37,44 +47,44 @@ a human reader, and should not be present in the documentation.
37
47
  This package defines modified doctesting routines which fix these deficiencies.
38
48
  Its main features are
39
49
 
40
- - *Doctesting is floating-point aware.* In a nutshell, the core check is
50
+ - _Doctesting is floating-point aware._ In a nutshell, the core check is
41
51
  `np.allclose(want, got, atol=..., rtol=...)`, with user-controllable abs
42
52
  and relative tolerances. In the example above (_sans_ `# doctest: +SKIP`),
43
53
  `want` is the desired output, `array([0.333, 0.669, 1])` and `got` is the
44
54
  actual output from numpy: `array([0.33333333, 0.66666667, 1. ])`.
45
55
 
46
- - *Human-readable skip markers.* Consider
56
+ - _Human-readable skip markers._ Consider
47
57
  ```
48
58
  >>> np.random.randint(100)
49
59
  42 # may vary
50
60
  ```
51
- Note that the markers (by default, `"# may vary"` and `"# random"`) can be applied
52
- to either an example's output, or its source.
61
+ Note that the markers (by default, `"# may vary"` and `"# random"`) can be applied
62
+ to either an example's output, or its source.
53
63
 
54
64
  Also note a difference with respect to the standard `# doctest: +SKIP`: the latter
55
65
  skips the example entirely, while these additional markers only skip checking
56
66
  the output. Thus the example source needs to be valid python code still.
57
67
 
58
- - A user-configurable list of *stopwords*. If an example contains a stopword,
68
+ - A user-configurable list of _stopwords_. If an example contains a stopword,
59
69
  it is checked to be valid python, but the output is not checked. This can
60
70
  be useful e.g. for not littering the documentation with the output of
61
71
  `import matplotlib.pyplot as plt; plt.xlim([2.3, 4.5])`.
62
72
 
63
- - A user-configurable list of *pseudocode* markers. If an example contains one
73
+ - A user-configurable list of _pseudocode_ markers. If an example contains one
64
74
  of these markers, it is considered pseudocode and is not checked.
65
75
  This is useful for `from example import some_functions` and similar stanzas.
66
76
 
67
77
  - A `# doctest: +SKIPBLOCK` option flag to skip whole blocks of pseudocode. Here
68
78
  a 'block' is a sequence of doctest examples without any intervening text.
69
79
 
70
- - *Doctest discovery* is somewhat more flexible then the standard library
80
+ - _Doctest discovery_ is somewhat more flexible then the standard library
71
81
  `doctest` module. Specifically, one can use `testmod(module, strategy='api')`
72
82
  to only examine public objects of a module. This is helpful for complex
73
83
  packages, with non-trivial internal file structure. Alternatively, the default
74
84
  value of `strategy=None` is equivalent to the standard `doctest` module
75
85
  behavior.
76
86
 
77
- - *User configuration*. Essentially all aspects of the behavior are user
87
+ - _User configuration_. Essentially all aspects of the behavior are user
78
88
  configurable via a `DTConfig` instance attributes. See the `DTConfig`
79
89
  docstring for details.
80
90
 
@@ -105,7 +115,7 @@ pip install scipy-doctest
105
115
 
106
116
  2. **Register or load the plugin**
107
117
 
108
- Next, you need to register or load the pytest plugin within your test module or `conftest.py` file.
118
+ Next, you need to register or load the pytest plugin within your test module or `conftest.py` file.
109
119
 
110
120
  To do this, add the following line of code:
111
121
 
@@ -117,14 +127,16 @@ pytest_plugins = "scipy_doctest"
117
127
 
118
128
  Check out the [pytest documentation](https://docs.pytest.org/en/stable/how-to/writing_plugins.html#requiring-loading-plugins-in-a-test-module-or-conftest-file) for more information on requiring/loading plugins in a test module or `conftest.py` file.
119
129
 
120
- 3. **Run doctests**
130
+ 3. **Run doctests**
121
131
 
122
132
  Once the plugin is registered, run the doctests by executing the following command:
123
133
 
124
134
  ```bash
125
135
  $ python -m pytest --doctest-modules
126
136
  ```
137
+
127
138
  or
139
+
128
140
  ```bash
129
141
  $ pytest --pyargs <your-package> --doctest-modules
130
142
  ```
@@ -136,10 +148,9 @@ use the command flag
136
148
  $ pytest --pyargs <your-package> --doctest-modules --doctest-collect=api
137
149
  ```
138
150
 
139
- See [More fine-grained control](https://github.com/scipy/scipy_doctest#More-fine-grained-control) section
151
+ See [More fine-grained control](#more-fine-grained-control) section
140
152
  for details on how to customize the behavior.
141
153
 
142
-
143
154
  ### Basic usage
144
155
 
145
156
  The use of `pytest` is optional, and you can use the `doctest` layer API.
@@ -152,6 +163,7 @@ For example,
152
163
  >>> res
153
164
  TestResults(failed=0, attempted=764)
154
165
  ```
166
+
155
167
  The second return value, `hist` is a dict which maps the names of the objects
156
168
  to the numbers of failures and attempts for individual examples.
157
169
 
@@ -159,10 +171,10 @@ For more details, see the `testmod` docstring. Other useful functions are
159
171
  `find_doctests`, `run_docstring_examples` and `testfile` (the latter two mimic
160
172
  the behavior of the eponymous functions of the `doctest` module).
161
173
 
162
-
163
174
  ### Command-line interface
164
175
 
165
176
  There is a basic CLI, which also mimics that of the `doctest` module:
177
+
166
178
  ```
167
179
  $ python -m scipy_doctest foo.py
168
180
  ```
@@ -171,28 +183,30 @@ Note that, just like `$ python -m doctest foo.py`, this may
171
183
  fail if `foo.py` is a part of a package due to package imports.
172
184
 
173
185
  Text files can also be CLI-checked:
186
+
174
187
  ```
175
188
  $ python -m scipy_doctest bar.rst
176
189
  ```
177
190
 
178
191
  Notice that the command-line usage only uses the default `DTConfig` settings.
179
192
 
193
+ (more-fine-grained-control)=
180
194
 
181
195
  ## More fine-grained control
182
196
 
183
197
  More fine-grained control of the functionality is available via the following
184
198
  classes
185
199
 
186
- | Class | `doctest` analog |
187
- |-------------|--------------------|
188
- | `DTChecker` | `DocTestChecker` |
189
- | `DTParser` | `DocTestParser` |
190
- | `DTRunner` | `DocTestRunner` |
191
- | `DTFinder` | `DocTestFinder` |
192
- | `DTContext` | -- |
200
+ | Class | `doctest` analog |
201
+ | ----------- | ---------------- |
202
+ | `DTChecker` | `DocTestChecker` |
203
+ | `DTParser` | `DocTestParser` |
204
+ | `DTRunner` | `DocTestRunner` |
205
+ | `DTFinder` | `DocTestFinder` |
206
+ | `DTContext` | -- |
193
207
 
194
208
  The `DTContext` class is just a bag class which holds various configuration
195
- settings as attributes. An instance of this class is passed around, so user
209
+ settings as attributes. An instance of this class is passed around, so user
196
210
  configuration is simply creating an instance, overriding an attribute and
197
211
  passing the instance to `testmod` or constructors of `DT*` objects. Defaults
198
212
  are provided, based on a long-term usage in SciPy.
@@ -201,7 +215,7 @@ See the [DTConfig docstring](https://github.com/scipy/scipy_doctest/blob/main/sc
201
215
  for the full set of attributes that allow you to fine-tune your doctesting experience.
202
216
 
203
217
  To set any of these attributes, create an instance of `DTConfig` and assign the attributes
204
- in a usual way.
218
+ in a usual way.
205
219
 
206
220
  If using the pytest plugin, it is convenient to use the default instance, which
207
221
  is predefined in `scipy_doctest/conftest.py`. This instance will be automatically
@@ -241,14 +255,12 @@ dt_config.skiplist = {
241
255
 
242
256
  If you don't set these attributes, the [default settings](https://github.com/scipy/scipy_doctest/blob/58ff06a837b7bff1dbac6560013fc6fd07952ae2/scipy_doctest/impl.py#L94) of the attributes are used.
243
257
 
244
-
245
258
  #### Alternative Checkers
246
259
 
247
260
  By default, we use the floating-point aware `DTChecker`. If you want to use an
248
261
  alternative checker, all you need to do is to define the corresponding class,
249
262
  and add an attribute to the `DTConfig` instance. For example,
250
263
 
251
-
252
264
  ```
253
265
  class VanillaOutputChecker(doctest.OutputChecker):
254
266
  """doctest.OutputChecker to drop in for DTChecker.
@@ -271,10 +283,8 @@ See [a pytest example](https://github.com/scipy/scipy_doctest/blob/main/scipy_do
271
283
  and [a doctest example](https://github.com/scipy/scipy_doctest/blob/main/scipy_doctest/tests/test_runner.py#L94)
272
284
  for more details.
273
285
 
274
-
275
286
  ### NumPy and SciPy wrappers
276
287
 
277
-
278
288
  NumPy wraps `scipy-doctest` with the `spin` command
279
289
 
280
290
  ```
@@ -288,13 +298,11 @@ $ python dev.py smoke-docs # check docstrings
288
298
  $ python dev.py smoke-tutorials # ReST user guide tutorials
289
299
  ```
290
300
 
291
-
292
-
293
301
  ## Rough edges and sharp bits
294
302
 
295
303
  Here is a (non-exhaustive) list of possible gotchas:
296
304
 
297
- - *In-place development builds*.
305
+ - _In-place development builds_.
298
306
 
299
307
  Some tools (looking at you `meson-python`) simulate in-place builds with a
300
308
  `build-install` directory. If this directory is located under the project root,
@@ -310,12 +318,15 @@ $ pytest build-install/lib/python3.10/site-packages/scipy/ --doctest-modules
310
318
 
311
319
  instead of `$ pytest --pyargs scipy`.
312
320
 
313
- If push comes to shove, you may try using the magic env variable:
321
+ If you use actual editable installs, of the `pip install --no-build-isolation -e .` variety, you may
322
+ need to add `--import-mode=importlib` to the `pytest` invocation.
323
+
324
+ If push really comes to shove, you may try using the magic env variable:
314
325
  ` PY_IGNORE_IMPORTMISMATCH=1 pytest ...`,
315
326
  however the need usually indicates an issue with the package itself.
316
327
  (see [gh-107](https://github.com/scipy/scipy_doctest/pull/107) for an example).
317
328
 
318
- - *Optional dependencies are not that optional*
329
+ - _Optional dependencies are not that optional_
319
330
 
320
331
  If your package contains optional dependencies, doctests do not know about them
321
332
  being optional. So you either guard the imports in doctests (yikes!), or
@@ -334,11 +345,11 @@ Note that installed packages are no different:
334
345
  $ pytest --pyargs scipy --doctest-modules --ignore=/path/to/installed/scipy/_lib
335
346
  ```
336
347
 
337
- - *Doctest collection strategies*
348
+ - _Doctest collection strategies_
338
349
 
339
350
  The default collection strategy follows `doctest` module and `pytest`. This leads
340
351
  to duplicates if your package has the split between public and \_private modules,
341
- where public modules re-export things from private ones. The solution is to
352
+ where public modules re-export things from private ones. The solution is to
342
353
  use `$ pytest --doctest-collect=api` CLI switch: with this, only public
343
354
  objects will be collected.
344
355
 
@@ -356,8 +367,7 @@ leads to
356
367
  - `scipy.linalg._basic.det`, collected from `scipy/linalg/_basic.py`, is private.
357
368
  - `scipy.linalg.det`, collected from `scipy/linalg/__init__.py`, is public.
358
369
 
359
-
360
- - *`pytest`'s assertion rewriting*
370
+ - _`pytest`'s assertion rewriting_
361
371
 
362
372
  In some rare cases you may need to either explicitly register the `scipy_doctest`
363
373
  package with the `pytest` assertion rewriting machinery, or ask it to avoid rewriting
@@ -369,7 +379,6 @@ In general, rewriting assertions is not very useful for doctests, as the
369
379
  output on error is fixed by the doctest machinery anyway. Therefore, we believe
370
380
  adding `--assert=plain` is reasonable.
371
381
 
372
-
373
382
  ## Prior art and related work
374
383
 
375
384
  - `pytest` provides some limited floating-point aware `NumericLiteralChecker`.
@@ -390,14 +399,13 @@ adding `--assert=plain` is reasonable.
390
399
  to be not easy to reason about, work with, and extend to other projects.
391
400
 
392
401
  This project is mainly the core functionality of the modified
393
- `refguide-check` doctesting, extracted to a separate package.
402
+ `refguide-check` doctesting, extracted to a separate package.
394
403
  We believe having it separate simplifies both addressing the needs of these
395
404
  two packages, and potential adoption by other projects.
396
405
 
397
-
398
406
  ### Bug reports, feature requests and contributions
399
407
 
400
408
  This package is work in progress. Contributions are most welcome!
401
409
  Please don't hesitate to open an issue in the tracker or send a pull request.
402
410
 
403
- The current location of the issue tracker is https://github.com/scipy/scipy_doctest.
411
+ The current location of the issue tracker is <https://github.com/scipy/scipy_doctest>.
@@ -25,13 +25,44 @@ dependencies = [
25
25
 
26
26
  [project.optional-dependencies]
27
27
  test = [
28
- "scipy",
28
+ "scipy <= 1.14.1", # black-list 1.5.1 ?
29
29
  "matplotlib"
30
30
  ]
31
+ doc = [
32
+ "furo==2024.8.6",
33
+ "myst-parser==4.0.0",
34
+ "sphinx==8.1.3",
35
+ "sphinx-copybutton==0.5.2"
36
+ ]
31
37
 
32
38
  [project.urls]
33
39
  Home = "https://github.com/scipy/scipy_doctest"
34
40
 
41
+ [tool.ruff.lint]
42
+ select = [
43
+ # pycodestyle
44
+ "E",
45
+ # Pyflakes
46
+ "F",
47
+ # pyupgrade
48
+ "UP",
49
+ # flake8-bugbear
50
+ "B",
51
+ # isort
52
+ "I",
53
+ ]
54
+
55
+ [tool.ruff.lint.per-file-ignores]
56
+ "scipy_doctest/tests/module_cases.py" = ["E501"]
57
+ "scipy_doctest/tests/local_file_cases.py" = ["E501"]
58
+
59
+ [tool.ruff.format]
60
+ # Enable reformatting of code snippets in docstrings.
61
+ docstring-code-format = true
62
+
63
+ [tool.ruff.lint.pydocstyle]
64
+ convention = "numpy"
65
+
35
66
  [tool.pytest.ini_options]
36
67
  addopts = "--verbose --color=yes"
37
68
 
@@ -0,0 +1,2 @@
1
+ # Automatically created by ruff.
2
+ *