schemathesis 4.0.18__py3-none-any.whl → 4.0.20__py3-none-any.whl
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.
- schemathesis/core/errors.py +1 -1
- schemathesis/specs/openapi/checks.py +2 -0
- schemathesis/specs/openapi/converter.py +1 -1
- schemathesis/specs/openapi/patterns.py +60 -5
- schemathesis/specs/openapi/schemas.py +4 -0
- {schemathesis-4.0.18.dist-info → schemathesis-4.0.20.dist-info}/METADATA +1 -1
- {schemathesis-4.0.18.dist-info → schemathesis-4.0.20.dist-info}/RECORD +10 -10
- {schemathesis-4.0.18.dist-info → schemathesis-4.0.20.dist-info}/WHEEL +0 -0
- {schemathesis-4.0.18.dist-info → schemathesis-4.0.20.dist-info}/entry_points.txt +0 -0
- {schemathesis-4.0.18.dist-info → schemathesis-4.0.20.dist-info}/licenses/LICENSE +0 -0
schemathesis/core/errors.py
CHANGED
@@ -52,7 +52,7 @@ class InvalidSchema(SchemathesisError):
|
|
52
52
|
|
53
53
|
@classmethod
|
54
54
|
def from_jsonschema_error(
|
55
|
-
cls, error: ValidationError, path: str | None, method: str | None, config: OutputConfig
|
55
|
+
cls, error: ValidationError | JsonSchemaError, path: str | None, method: str | None, config: OutputConfig
|
56
56
|
) -> InvalidSchema:
|
57
57
|
if error.absolute_path:
|
58
58
|
part = error.absolute_path[-1]
|
@@ -513,6 +513,8 @@ def ignored_auth(ctx: CheckContext, response: Response, case: Case) -> bool | No
|
|
513
513
|
_remove_auth_from_container(container, security_parameters, location=location)
|
514
514
|
kwargs[container_name] = container
|
515
515
|
kwargs.pop("session", None)
|
516
|
+
if case.operation.app is not None:
|
517
|
+
kwargs.setdefault("app", case.operation.app)
|
516
518
|
ctx._record_case(parent_id=case.id, case=no_auth_case)
|
517
519
|
no_auth_response = case.operation.schema.transport.send(no_auth_case, **kwargs)
|
518
520
|
ctx._record_response(case_id=no_auth_case.id, response=no_auth_response)
|
@@ -34,7 +34,7 @@ def to_json_schema(
|
|
34
34
|
update_pattern_in_schema(schema)
|
35
35
|
# Sometimes `required` is incorrectly has a boolean value
|
36
36
|
properties = schema.get("properties")
|
37
|
-
if properties:
|
37
|
+
if isinstance(properties, dict):
|
38
38
|
for name, subschema in properties.items():
|
39
39
|
if not isinstance(subschema, dict):
|
40
40
|
continue
|
@@ -174,8 +174,18 @@ def _handle_anchored_pattern(parsed: list, pattern: str, min_length: int | None,
|
|
174
174
|
continue
|
175
175
|
if pattern[current_position] == "\\":
|
176
176
|
# Escaped value
|
177
|
-
current_position += 2
|
178
177
|
result += "\\"
|
178
|
+
# Could be an octal value
|
179
|
+
if (
|
180
|
+
current_position + 2 < len(pattern)
|
181
|
+
and pattern[current_position + 1] == "0"
|
182
|
+
and pattern[current_position + 2] in ("0", "1", "2", "3", "4", "5", "6", "7")
|
183
|
+
):
|
184
|
+
result += pattern[current_position + 1]
|
185
|
+
result += pattern[current_position + 2]
|
186
|
+
current_position += 3
|
187
|
+
continue
|
188
|
+
current_position += 2
|
179
189
|
else:
|
180
190
|
current_position += 1
|
181
191
|
result += chr(value)
|
@@ -349,13 +359,58 @@ def _handle_repeat_quantifier(
|
|
349
359
|
) -> str:
|
350
360
|
"""Handle repeat quantifiers (e.g., '+', '*', '?')."""
|
351
361
|
min_repeat, max_repeat, _ = value
|
352
|
-
|
353
|
-
|
354
|
-
return pattern
|
362
|
+
|
363
|
+
# First, analyze the inner pattern
|
355
364
|
inner = _strip_quantifier(pattern)
|
356
365
|
if inner.startswith("(") and inner.endswith(")"):
|
357
366
|
inner = inner[1:-1]
|
358
|
-
|
367
|
+
|
368
|
+
# Determine the length of the inner pattern
|
369
|
+
inner_length = 1 # default assumption for non-literal patterns
|
370
|
+
try:
|
371
|
+
parsed = sre_parse.parse(inner)
|
372
|
+
if all(item[0] == LITERAL for item in parsed):
|
373
|
+
inner_length = len(parsed)
|
374
|
+
if max_length and max_length > 0 and inner_length > max_length:
|
375
|
+
return pattern
|
376
|
+
except re.error:
|
377
|
+
pass
|
378
|
+
|
379
|
+
if inner_length == 0:
|
380
|
+
# Empty pattern contributes 0 chars regardless of repetitions
|
381
|
+
# For length constraints, only 0 repetitions make sense
|
382
|
+
if min_length is not None and min_length > 0:
|
383
|
+
return pattern # Can't satisfy positive length with empty pattern
|
384
|
+
return f"({inner})" + _build_quantifier(0, 0)
|
385
|
+
|
386
|
+
# Convert external length constraints to repetition constraints
|
387
|
+
external_min_repeat = None
|
388
|
+
external_max_repeat = None
|
389
|
+
|
390
|
+
if min_length is not None:
|
391
|
+
# Need at least ceil(min_length / inner_length) repetitions
|
392
|
+
external_min_repeat = (min_length + inner_length - 1) // inner_length
|
393
|
+
|
394
|
+
if max_length is not None:
|
395
|
+
# Can have at most floor(max_length / inner_length) repetitions
|
396
|
+
external_max_repeat = max_length // inner_length
|
397
|
+
|
398
|
+
# Merge original repetition constraints with external constraints
|
399
|
+
final_min_repeat = min_repeat
|
400
|
+
if external_min_repeat is not None:
|
401
|
+
final_min_repeat = max(min_repeat, external_min_repeat)
|
402
|
+
|
403
|
+
final_max_repeat = max_repeat
|
404
|
+
if external_max_repeat is not None:
|
405
|
+
if max_repeat == MAXREPEAT:
|
406
|
+
final_max_repeat = external_max_repeat
|
407
|
+
else:
|
408
|
+
final_max_repeat = min(max_repeat, external_max_repeat)
|
409
|
+
|
410
|
+
if final_min_repeat > final_max_repeat:
|
411
|
+
return pattern
|
412
|
+
|
413
|
+
return f"({inner})" + _build_quantifier(final_min_repeat, final_max_repeat)
|
359
414
|
|
360
415
|
|
361
416
|
def _handle_literal_or_in_quantifier(pattern: str, min_length: int | None, max_length: int | None) -> str:
|
@@ -646,6 +646,10 @@ class BaseOpenAPISchema(BaseSchema):
|
|
646
646
|
# Use a recent JSON Schema format checker to get most of formats checked for older drafts as well
|
647
647
|
format_checker=jsonschema.Draft202012Validator.FORMAT_CHECKER,
|
648
648
|
)
|
649
|
+
except jsonschema.SchemaError as exc:
|
650
|
+
raise InvalidSchema.from_jsonschema_error(
|
651
|
+
exc, path=operation.path, method=operation.method, config=self.config.output
|
652
|
+
) from exc
|
649
653
|
except jsonschema.ValidationError as exc:
|
650
654
|
failures.append(
|
651
655
|
JsonSchemaError.from_exception(
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.4
|
2
2
|
Name: schemathesis
|
3
|
-
Version: 4.0.
|
3
|
+
Version: 4.0.20
|
4
4
|
Summary: Property-based testing framework for Open API and GraphQL based apps
|
5
5
|
Project-URL: Documentation, https://schemathesis.readthedocs.io/en/stable/
|
6
6
|
Project-URL: Changelog, https://github.com/schemathesis/schemathesis/blob/master/CHANGELOG.md
|
@@ -51,7 +51,7 @@ schemathesis/core/compat.py,sha256=9BWCrFoqN2sJIaiht_anxe8kLjYMR7t0iiOkXqLRUZ8,1
|
|
51
51
|
schemathesis/core/control.py,sha256=IzwIc8HIAEMtZWW0Q0iXI7T1niBpjvcLlbuwOSmy5O8,130
|
52
52
|
schemathesis/core/curl.py,sha256=yuaCe_zHLGwUjEeloQi6W3tOA3cGdnHDNI17-5jia0o,1723
|
53
53
|
schemathesis/core/deserialization.py,sha256=qjXUPaz_mc1OSgXzTUSkC8tuVR8wgVQtb9g3CcAF6D0,2951
|
54
|
-
schemathesis/core/errors.py,sha256=
|
54
|
+
schemathesis/core/errors.py,sha256=Afs2EFyJpcy9Pr1MvnP-jeoiPiAW14MtV3YJYgio2E8,16313
|
55
55
|
schemathesis/core/failures.py,sha256=MYyRnom-XeUEuBmq2ffdz34xhxmpSHWaQunfHtliVsY,8932
|
56
56
|
schemathesis/core/fs.py,sha256=ItQT0_cVwjDdJX9IiI7EnU75NI2H3_DCEyyUjzg_BgI,472
|
57
57
|
schemathesis/core/hooks.py,sha256=qhbkkRSf8URJ4LKv2wmKRINKpquUOgxQzWBHKWRWo3Q,475
|
@@ -124,17 +124,17 @@ schemathesis/specs/graphql/validation.py,sha256=-W1Noc1MQmTb4RX-gNXMeU2qkgso4mzV
|
|
124
124
|
schemathesis/specs/openapi/__init__.py,sha256=C5HOsfuDJGq_3mv8CRBvRvb0Diy1p0BFdqyEXMS-loE,238
|
125
125
|
schemathesis/specs/openapi/_cache.py,sha256=HpglmETmZU0RCHxp3DO_sg5_B_nzi54Zuw9vGzzYCxY,4295
|
126
126
|
schemathesis/specs/openapi/_hypothesis.py,sha256=H-4pzT7dECY-AcDGhebKdTSELhGOdyA1WCbZQSMZY3E,22309
|
127
|
-
schemathesis/specs/openapi/checks.py,sha256=
|
127
|
+
schemathesis/specs/openapi/checks.py,sha256=t3ZIyzRPd_KnJzdp57Y_9CZLYC98NAqsE3dgNfuCOBA,29971
|
128
128
|
schemathesis/specs/openapi/constants.py,sha256=JqM_FHOenqS_MuUE9sxVQ8Hnw0DNM8cnKDwCwPLhID4,783
|
129
|
-
schemathesis/specs/openapi/converter.py,sha256=
|
129
|
+
schemathesis/specs/openapi/converter.py,sha256=LkpCCAxZzET4Qa_3YStSNuhGlsm5G6TVwpxYu6lPO4g,4169
|
130
130
|
schemathesis/specs/openapi/definitions.py,sha256=8htclglV3fW6JPBqs59lgM4LnA25Mm9IptXBPb_qUT0,93949
|
131
131
|
schemathesis/specs/openapi/examples.py,sha256=V1fbsbMto_So7lTWnyGa7f3u9On2br8yZ-cPzcC2-Bw,21542
|
132
132
|
schemathesis/specs/openapi/formats.py,sha256=8AIS7Uey-Z1wm1WYRqnsVqHwG9d316PdqfKLqwUs7us,3516
|
133
133
|
schemathesis/specs/openapi/media_types.py,sha256=F5M6TKl0s6Z5X8mZpPsWDEdPBvxclKRcUOc41eEwKbo,2472
|
134
134
|
schemathesis/specs/openapi/parameters.py,sha256=ifu_QQCMUzsUHQAkvsOvLuokns6CzesssmQ3Nd3zxII,14594
|
135
|
-
schemathesis/specs/openapi/patterns.py,sha256=
|
135
|
+
schemathesis/specs/openapi/patterns.py,sha256=GqPZEXMRdWENQxanWjBOalIZ2MQUjuxk21kmdiI703E,18027
|
136
136
|
schemathesis/specs/openapi/references.py,sha256=40YcDExPLR2B8EOwt-Csw-5MYFi2xj_DXf91J0Pc9d4,8855
|
137
|
-
schemathesis/specs/openapi/schemas.py,sha256=
|
137
|
+
schemathesis/specs/openapi/schemas.py,sha256=ZhFYxYzm0u9VpPMD5f_tt15l29OMa4-lrofOWf4Q6yM,52790
|
138
138
|
schemathesis/specs/openapi/security.py,sha256=6UWYMhL-dPtkTineqqBFNKca1i4EuoTduw-EOLeE0aQ,7149
|
139
139
|
schemathesis/specs/openapi/serialization.py,sha256=VdDLmeHqxlWM4cxQQcCkvrU6XurivolwEEaT13ohelA,11972
|
140
140
|
schemathesis/specs/openapi/utils.py,sha256=ER4vJkdFVDIE7aKyxyYatuuHVRNutytezgE52pqZNE8,900
|
@@ -157,8 +157,8 @@ schemathesis/transport/prepare.py,sha256=erYXRaxpQokIDzaIuvt_csHcw72iHfCyNq8VNEz
|
|
157
157
|
schemathesis/transport/requests.py,sha256=46aplzhSmBupegPNMawma-iJWCegWkEd6mzdWLTpgM4,10742
|
158
158
|
schemathesis/transport/serialization.py,sha256=igUXKZ_VJ9gV7P0TUc5PDQBJXl_s0kK9T3ljGWWvo6E,10339
|
159
159
|
schemathesis/transport/wsgi.py,sha256=KoAfvu6RJtzyj24VGB8e-Iaa9smpgXJ3VsM8EgAz2tc,6152
|
160
|
-
schemathesis-4.0.
|
161
|
-
schemathesis-4.0.
|
162
|
-
schemathesis-4.0.
|
163
|
-
schemathesis-4.0.
|
164
|
-
schemathesis-4.0.
|
160
|
+
schemathesis-4.0.20.dist-info/METADATA,sha256=diXsxXNsEftDBd6avKFKX7nsuQTNRm3oKazIVDFJlhE,8472
|
161
|
+
schemathesis-4.0.20.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
|
162
|
+
schemathesis-4.0.20.dist-info/entry_points.txt,sha256=hiK3un-xfgPdwj9uj16YVDtTNpO128bmk0U82SMv8ZQ,152
|
163
|
+
schemathesis-4.0.20.dist-info/licenses/LICENSE,sha256=2Ve4J8v5jMQAWrT7r1nf3bI8Vflk3rZVQefiF2zpxwg,1121
|
164
|
+
schemathesis-4.0.20.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|