FlaskTester 1.3__tar.gz → 1.4__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {FlaskTester-1.3 → FlaskTester-1.4}/FlaskTester.egg-info/PKG-INFO +14 -4
- {FlaskTester-1.3 → FlaskTester-1.4}/FlaskTester.py +47 -6
- {FlaskTester-1.3 → FlaskTester-1.4}/PKG-INFO +14 -4
- {FlaskTester-1.3 → FlaskTester-1.4}/README.md +13 -3
- {FlaskTester-1.3 → FlaskTester-1.4}/pyproject.toml +1 -1
- {FlaskTester-1.3 → FlaskTester-1.4}/tests/test.py +18 -8
- {FlaskTester-1.3 → FlaskTester-1.4}/FlaskTester.egg-info/SOURCES.txt +0 -0
- {FlaskTester-1.3 → FlaskTester-1.4}/FlaskTester.egg-info/dependency_links.txt +0 -0
- {FlaskTester-1.3 → FlaskTester-1.4}/FlaskTester.egg-info/requires.txt +0 -0
- {FlaskTester-1.3 → FlaskTester-1.4}/FlaskTester.egg-info/top_level.txt +0 -0
- {FlaskTester-1.3 → FlaskTester-1.4}/LICENSE +0 -0
- {FlaskTester-1.3 → FlaskTester-1.4}/MANIFEST.in +0 -0
- {FlaskTester-1.3 → FlaskTester-1.4}/setup.cfg +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: FlaskTester
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.4
|
|
4
4
|
Summary: Pytest fixtures for Flask internal and external authenticated tests
|
|
5
5
|
Author-email: Fabien Coelho <flask.tester@coelho.net>
|
|
6
6
|
License: CC0
|
|
@@ -65,7 +65,7 @@ achieved through environment variables.
|
|
|
65
65
|
Install package with `pip install FlaskTester` or equivalent.
|
|
66
66
|
|
|
67
67
|
The following test creates a local fixture with 2 users identified by a
|
|
68
|
-
password, and retrieves
|
|
68
|
+
password, and retrieves tokens for both users using a `/login` route
|
|
69
69
|
provided by the application.
|
|
70
70
|
It then proceeds to run authenticated requests against the `/admin` route.
|
|
71
71
|
|
|
@@ -225,14 +225,24 @@ The implementation of these fixtures is based on five classes plus exceptions:
|
|
|
225
225
|
|
|
226
226
|
## License
|
|
227
227
|
|
|
228
|
-
This code is
|
|
228
|
+
This code is [Public Domain](https://creativecommons.org/publicdomain/zero/1.0/).
|
|
229
|
+
|
|
230
|
+
All software has bug, this is software, hence… Beware that you may lose your
|
|
231
|
+
hairs or your friends because of it. If you like it, feel free to send a
|
|
232
|
+
postcard to the author.
|
|
233
|
+
|
|
234
|
+
## Versions
|
|
229
235
|
|
|
230
236
|
Packages are distributed from [PyPI](https://pypi.org/project/FlaskTester/),
|
|
231
237
|
[sources](https://github.com/zx80/flask-tester) are available on GitHub,
|
|
232
238
|
see also the [documentation](https://zx80.github.io/flask-tester/),
|
|
233
239
|
please report any [issues](https://github.com/zx80/flask-tester/issues).
|
|
234
240
|
|
|
235
|
-
|
|
241
|
+
### 1.4 on 2024-03-19
|
|
242
|
+
|
|
243
|
+
Test expected assert failures.
|
|
244
|
+
Improved API documentation.
|
|
245
|
+
Keep first found app.
|
|
236
246
|
|
|
237
247
|
### 1.3 on 2024-03-16
|
|
238
248
|
|
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
"""FlaskTester - Pytest fixtures for Flask authenticated internal and external tests.
|
|
2
|
+
|
|
3
|
+
Pytest: PYTEST_DONT_REWRITE
|
|
4
|
+
"""
|
|
5
|
+
|
|
1
6
|
import os
|
|
2
7
|
import io
|
|
3
8
|
import re
|
|
@@ -283,9 +288,9 @@ class Client:
|
|
|
283
288
|
res = self._request(method, path, **kwargs) # type: ignore
|
|
284
289
|
|
|
285
290
|
if status is not None:
|
|
286
|
-
if res.status_code != status: #
|
|
291
|
+
if res.status_code != status: # show error before aborting
|
|
287
292
|
log.error(f"bad {status} result: {res.status_code} {res.text[:512]}")
|
|
288
|
-
assert res.status_code == status
|
|
293
|
+
assert res.status_code == status, f"unexpected status {res.status_code}, expecting {status}"
|
|
289
294
|
|
|
290
295
|
return res
|
|
291
296
|
|
|
@@ -330,9 +335,9 @@ class Client:
|
|
|
330
335
|
|
|
331
336
|
# check contents
|
|
332
337
|
if content is not None:
|
|
333
|
-
if not re.search(content, res.text, re.DOTALL):
|
|
338
|
+
if not re.search(content, res.text, re.DOTALL):
|
|
334
339
|
log.error(f"cannot find {content} in {res.text}")
|
|
335
|
-
assert False, "content not found"
|
|
340
|
+
assert False, f"expected content {content} not found in {res.text}"
|
|
336
341
|
|
|
337
342
|
return res
|
|
338
343
|
|
|
@@ -404,7 +409,31 @@ class FlaskClient(Client):
|
|
|
404
409
|
|
|
405
410
|
@pytest.fixture
|
|
406
411
|
def ft_authenticator():
|
|
407
|
-
"""Pytest Fixture: ft_authenticator.
|
|
412
|
+
"""Pytest Fixture: ft_authenticator.
|
|
413
|
+
|
|
414
|
+
Environment variables:
|
|
415
|
+
|
|
416
|
+
- ``FLASK_TESTER_LOG_LEVEL``: package log level in
|
|
417
|
+
``DEBUG INFO WARNING ERROR CRITICAL NOSET``.
|
|
418
|
+
- ``FLASK_TESTER_ALLOW``: allowed space-separated authentication schemes, in
|
|
419
|
+
``basic param bearer header cookie tparam fake``.
|
|
420
|
+
Default is ``bearer basic param``.
|
|
421
|
+
- ``FLASK_TESTER_USER``: user login parameter for ``param`` authentication.
|
|
422
|
+
Default is ``USER``.
|
|
423
|
+
- ``FLASK_TESTER_PASS``: user password parameter for ``param`` authentication.
|
|
424
|
+
Default is ``PASS``.
|
|
425
|
+
- ``FLASK_TESTER_LOGIN``: user login parameter for ``fake`` authentication.
|
|
426
|
+
Default is ``LOGIN``.
|
|
427
|
+
- ``FLASK_TESTER_BEARER``: bearer name for *token* authentication.
|
|
428
|
+
Default is ``Bearer``.
|
|
429
|
+
- ``FLASK_TESTER_HEADER``: header name for *token* authentication.
|
|
430
|
+
Default is ``Auth``.
|
|
431
|
+
- ``FLASK_TESTER_COOKIE``: cookie name for *token* authentication.
|
|
432
|
+
Default is ``auth``.
|
|
433
|
+
- ``FLASK_TESTER_TPARAM``: parameter for *token* authentication.
|
|
434
|
+
Default is ``AUTH``.
|
|
435
|
+
- ``FLASK_TESTER_AUTH``: initial comma-separated list of *login:password*.
|
|
436
|
+
"""
|
|
408
437
|
|
|
409
438
|
level = os.environ.get("FLASK_TESTER_LOG_LEVEL", "NOTSET")
|
|
410
439
|
log.setLevel(logging.DEBUG if level == "DEBUG" else
|
|
@@ -436,7 +465,18 @@ def ft_authenticator():
|
|
|
436
465
|
|
|
437
466
|
@pytest.fixture
|
|
438
467
|
def ft_client(ft_authenticator):
|
|
439
|
-
"""Pytest Fixture: ft_client.
|
|
468
|
+
"""Pytest Fixture: ft_client.
|
|
469
|
+
|
|
470
|
+
Target environment variable, one **must** be defined:
|
|
471
|
+
|
|
472
|
+
- ``FLASK_TESTER_URL``: application HTTP base URL.
|
|
473
|
+
- ``FLASK_TESTER_APP``: Flask application, eg ``app:create_app``.
|
|
474
|
+
|
|
475
|
+
Other environment variable:
|
|
476
|
+
|
|
477
|
+
- ``FLASK_TESTER_DEFAULT``: Default client login, default is *None* for no
|
|
478
|
+
default.
|
|
479
|
+
"""
|
|
440
480
|
|
|
441
481
|
default_login = os.environ.get("FLASK_TESTER_DEFAULT", None)
|
|
442
482
|
client: Client
|
|
@@ -461,6 +501,7 @@ def ft_client(ft_authenticator):
|
|
|
461
501
|
app = getattr(pkg, name)
|
|
462
502
|
if callable(app) and not hasattr(app, "test_client"):
|
|
463
503
|
app = app()
|
|
504
|
+
break
|
|
464
505
|
if not app: # pragma: no cover
|
|
465
506
|
raise FlaskTesterError(f"cannot find Flask app in {pkg_name}")
|
|
466
507
|
client = FlaskClient(ft_authenticator, app.test_client(), default_login)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: FlaskTester
|
|
3
|
-
Version: 1.
|
|
3
|
+
Version: 1.4
|
|
4
4
|
Summary: Pytest fixtures for Flask internal and external authenticated tests
|
|
5
5
|
Author-email: Fabien Coelho <flask.tester@coelho.net>
|
|
6
6
|
License: CC0
|
|
@@ -65,7 +65,7 @@ achieved through environment variables.
|
|
|
65
65
|
Install package with `pip install FlaskTester` or equivalent.
|
|
66
66
|
|
|
67
67
|
The following test creates a local fixture with 2 users identified by a
|
|
68
|
-
password, and retrieves
|
|
68
|
+
password, and retrieves tokens for both users using a `/login` route
|
|
69
69
|
provided by the application.
|
|
70
70
|
It then proceeds to run authenticated requests against the `/admin` route.
|
|
71
71
|
|
|
@@ -225,14 +225,24 @@ The implementation of these fixtures is based on five classes plus exceptions:
|
|
|
225
225
|
|
|
226
226
|
## License
|
|
227
227
|
|
|
228
|
-
This code is
|
|
228
|
+
This code is [Public Domain](https://creativecommons.org/publicdomain/zero/1.0/).
|
|
229
|
+
|
|
230
|
+
All software has bug, this is software, hence… Beware that you may lose your
|
|
231
|
+
hairs or your friends because of it. If you like it, feel free to send a
|
|
232
|
+
postcard to the author.
|
|
233
|
+
|
|
234
|
+
## Versions
|
|
229
235
|
|
|
230
236
|
Packages are distributed from [PyPI](https://pypi.org/project/FlaskTester/),
|
|
231
237
|
[sources](https://github.com/zx80/flask-tester) are available on GitHub,
|
|
232
238
|
see also the [documentation](https://zx80.github.io/flask-tester/),
|
|
233
239
|
please report any [issues](https://github.com/zx80/flask-tester/issues).
|
|
234
240
|
|
|
235
|
-
|
|
241
|
+
### 1.4 on 2024-03-19
|
|
242
|
+
|
|
243
|
+
Test expected assert failures.
|
|
244
|
+
Improved API documentation.
|
|
245
|
+
Keep first found app.
|
|
236
246
|
|
|
237
247
|
### 1.3 on 2024-03-16
|
|
238
248
|
|
|
@@ -22,7 +22,7 @@ achieved through environment variables.
|
|
|
22
22
|
Install package with `pip install FlaskTester` or equivalent.
|
|
23
23
|
|
|
24
24
|
The following test creates a local fixture with 2 users identified by a
|
|
25
|
-
password, and retrieves
|
|
25
|
+
password, and retrieves tokens for both users using a `/login` route
|
|
26
26
|
provided by the application.
|
|
27
27
|
It then proceeds to run authenticated requests against the `/admin` route.
|
|
28
28
|
|
|
@@ -182,14 +182,24 @@ The implementation of these fixtures is based on five classes plus exceptions:
|
|
|
182
182
|
|
|
183
183
|
## License
|
|
184
184
|
|
|
185
|
-
This code is
|
|
185
|
+
This code is [Public Domain](https://creativecommons.org/publicdomain/zero/1.0/).
|
|
186
|
+
|
|
187
|
+
All software has bug, this is software, hence… Beware that you may lose your
|
|
188
|
+
hairs or your friends because of it. If you like it, feel free to send a
|
|
189
|
+
postcard to the author.
|
|
190
|
+
|
|
191
|
+
## Versions
|
|
186
192
|
|
|
187
193
|
Packages are distributed from [PyPI](https://pypi.org/project/FlaskTester/),
|
|
188
194
|
[sources](https://github.com/zx80/flask-tester) are available on GitHub,
|
|
189
195
|
see also the [documentation](https://zx80.github.io/flask-tester/),
|
|
190
196
|
please report any [issues](https://github.com/zx80/flask-tester/issues).
|
|
191
197
|
|
|
192
|
-
|
|
198
|
+
### 1.4 on 2024-03-19
|
|
199
|
+
|
|
200
|
+
Test expected assert failures.
|
|
201
|
+
Improved API documentation.
|
|
202
|
+
Keep first found app.
|
|
193
203
|
|
|
194
204
|
### 1.3 on 2024-03-16
|
|
195
205
|
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "FlaskTester"
|
|
7
|
-
version = "1.
|
|
7
|
+
version = "1.4"
|
|
8
8
|
authors = [ { name = "Fabien Coelho", email = "flask.tester@coelho.net" } ]
|
|
9
9
|
description = "Pytest fixtures for Flask internal and external authenticated tests"
|
|
10
10
|
readme = "README.md"
|
|
@@ -96,12 +96,22 @@ def test_admin(api):
|
|
|
96
96
|
api.check("GET", "/admin", 403, login="hobbes", auth=auth)
|
|
97
97
|
api.check("GET", "/admin", 401, login="moe", auth=auth)
|
|
98
98
|
api.check("GET", "/admin", 401, login=None, auth=auth)
|
|
99
|
+
try:
|
|
100
|
+
api.check("GET", "/admin", status=599, login="calvin", auth=auth)
|
|
101
|
+
pytest.fail("assert on status must fail") # pragma: no cover
|
|
102
|
+
except AssertionError as e:
|
|
103
|
+
assert "200" in str(e)
|
|
104
|
+
try:
|
|
105
|
+
api.check("GET", "/admin", status=200, login="calvin", auth=auth, content="NOT THERE")
|
|
106
|
+
pytest.fail("assert on content must fail") # pragma: no cover
|
|
107
|
+
except AssertionError as e:
|
|
108
|
+
assert "NOT THERE" in str(e)
|
|
99
109
|
|
|
100
110
|
def test_errors(api):
|
|
101
111
|
for scheme in ("header", "cookie", "fake", "tparam", "unexpected"):
|
|
102
112
|
try:
|
|
103
113
|
api.get("/login", login="calvin", auth=scheme)
|
|
104
|
-
|
|
114
|
+
pytest.fail("must raise an exception") # pragma: no cover
|
|
105
115
|
except ft.AuthError as e:
|
|
106
116
|
assert True, "expected error"
|
|
107
117
|
|
|
@@ -138,13 +148,13 @@ def test_authenticator_token():
|
|
|
138
148
|
try:
|
|
139
149
|
kwargs = {}
|
|
140
150
|
auth.setAuth("dad", kwargs)
|
|
141
|
-
|
|
151
|
+
pytest.fail("must raise an error") # pragma: no cover
|
|
142
152
|
except ft.FlaskTesterError:
|
|
143
153
|
assert True, "error raised"
|
|
144
154
|
# rosalyn as a password, but no password carrier is allowed
|
|
145
155
|
try:
|
|
146
156
|
auth.setPass("rosalyn", "rsln-pass")
|
|
147
|
-
|
|
157
|
+
pytest.fail("must raise an error") # pragma: no cover
|
|
148
158
|
except ft.AuthError:
|
|
149
159
|
assert True, "error raised"
|
|
150
160
|
# force to trigger later errors
|
|
@@ -153,7 +163,7 @@ def test_authenticator_token():
|
|
|
153
163
|
try:
|
|
154
164
|
kwargs={}
|
|
155
165
|
auth.setAuth("rosalyn", kwargs)
|
|
156
|
-
|
|
166
|
+
pytest.fail("must raise an error") # pragma: no cover
|
|
157
167
|
except ft.FlaskTesterError:
|
|
158
168
|
assert True, "error raised"
|
|
159
169
|
|
|
@@ -182,7 +192,7 @@ def test_authenticator_password():
|
|
|
182
192
|
# susie as a token, but no token carrier is allowed
|
|
183
193
|
try:
|
|
184
194
|
auth.setToken("susie", "ss-token")
|
|
185
|
-
|
|
195
|
+
pytest.fail("must raise an error") # pragma: no cover
|
|
186
196
|
except ft.FlaskTesterError:
|
|
187
197
|
assert True, "error raised"
|
|
188
198
|
# force to trigger later error
|
|
@@ -191,7 +201,7 @@ def test_authenticator_password():
|
|
|
191
201
|
try:
|
|
192
202
|
kwargs={}
|
|
193
203
|
auth.setAuth("susie", kwargs)
|
|
194
|
-
|
|
204
|
+
pytest.fail("must raise an error") # pragma: no cover
|
|
195
205
|
except ft.FlaskTesterError:
|
|
196
206
|
assert True, "error raised"
|
|
197
207
|
|
|
@@ -224,9 +234,9 @@ def test_client():
|
|
|
224
234
|
client = ft.Client(ft.Authenticator())
|
|
225
235
|
try:
|
|
226
236
|
client._request("GET", "/")
|
|
227
|
-
|
|
237
|
+
pytest.fail("must raise an error") # pragma: no cover
|
|
228
238
|
except NotImplementedError:
|
|
229
|
-
assert True, "error raised"
|
|
239
|
+
assert True, "expected error raised"
|
|
230
240
|
|
|
231
241
|
def test_request_client():
|
|
232
242
|
httpd = htsv.HTTPServer(("", 8888), htsv.SimpleHTTPRequestHandler)
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|