Skip to content

Commit

Permalink
validate and validate_url shortcuts
Browse files Browse the repository at this point in the history
  • Loading branch information
p1c2u committed Oct 13, 2023
1 parent 5f24987 commit 8564cc6
Show file tree
Hide file tree
Showing 8 changed files with 77 additions and 38 deletions.
8 changes: 4 additions & 4 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -98,15 +98,15 @@ Python package

.. code:: python
from openapi_spec_validator import validate_spec
from openapi_spec_validator import validate
from openapi_spec_validator.readers import read_from_filename
spec_dict, base_uri = read_from_filename('openapi.yaml')
# If no exception is raised by validate_spec(), the spec is valid.
validate_spec(spec_dict)
# If no exception is raised by validate(), the spec is valid.
validate(spec_dict)
validate_spec({'openapi': '3.1.0'})
validate({'openapi': '3.1.0'})
Traceback (most recent call last):
...
Expand Down
20 changes: 10 additions & 10 deletions docs/python.rst
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,15 @@ By default, OpenAPI spec version is detected. To validate spec:

.. code:: python
from openapi_spec_validator import validate_spec
from openapi_spec_validator import validate
from openapi_spec_validator.readers import read_from_filename
spec_dict, base_uri = read_from_filename('openapi.yaml')
# If no exception is raised by validate_spec(), the spec is valid.
validate_spec(spec_dict)
# If no exception is raised by validate(), the spec is valid.
validate(spec_dict)
validate_spec({'openapi': '3.1.0'})
validate({'openapi': '3.1.0'})
Traceback (most recent call last):
...
Expand All @@ -23,28 +23,28 @@ Add ``base_uri`` to validate spec with relative files:

.. code:: python
validate_spec(spec_dict, base_uri='file:///path/to/spec/openapi.yaml')
validate(spec_dict, base_uri='file:///path/to/spec/openapi.yaml')
You can also validate spec from url:

.. code:: python
from openapi_spec_validator import validate_spec_url
from openapi_spec_validator import validate_url
# If no exception is raised by validate_spec_url(), the spec is valid.
validate_spec_url('http://example.com/openapi.json')
# If no exception is raised by validate_url(), the spec is valid.
validate_url('http://example.com/openapi.json')
In order to explicitly validate a:

* Swagger / OpenAPI 2.0 spec, import ``OpenAPIV2SpecValidator``
* OpenAPI 3.0 spec, import ``OpenAPIV30SpecValidator``
* OpenAPI 3.1 spec, import ``OpenAPIV31SpecValidator``

and pass the validator class to ``validate_spec`` or ``validate_spec_url`` function:
and pass the validator class to ``validate`` or ``validate_url`` function:

.. code:: python
validate_spec(spec_dict, cls=OpenAPIV31SpecValidator)
validate(spec_dict, cls=OpenAPIV31SpecValidator)
You can also explicitly import ``OpenAPIV3SpecValidator`` which is a shortcut to the latest v3 release.

Expand Down
4 changes: 4 additions & 0 deletions openapi_spec_validator/__init__.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
"""OpenAPI spec validator module."""
from openapi_spec_validator.shortcuts import validate
from openapi_spec_validator.shortcuts import validate_spec
from openapi_spec_validator.shortcuts import validate_spec_url
from openapi_spec_validator.shortcuts import validate_url
from openapi_spec_validator.validation import OpenAPIV2SpecValidator
from openapi_spec_validator.validation import OpenAPIV3SpecValidator
from openapi_spec_validator.validation import OpenAPIV30SpecValidator
Expand All @@ -25,6 +27,8 @@
"OpenAPIV3SpecValidator",
"OpenAPIV30SpecValidator",
"OpenAPIV31SpecValidator",
"validate",
"validate_url",
"validate_spec",
"validate_spec_url",
]
11 changes: 4 additions & 7 deletions openapi_spec_validator/__main__.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@

from openapi_spec_validator.readers import read_from_filename
from openapi_spec_validator.readers import read_from_stdin
from openapi_spec_validator.shortcuts import get_validator_cls
from openapi_spec_validator.shortcuts import validate
from openapi_spec_validator.validation import OpenAPIV2SpecValidator
from openapi_spec_validator.validation import OpenAPIV30SpecValidator
from openapi_spec_validator.validation import OpenAPIV31SpecValidator
Expand Down Expand Up @@ -91,22 +91,19 @@ def main(args: Optional[Sequence[str]] = None) -> None:

# choose the validator
validators = {
"detect": None,
"2.0": OpenAPIV2SpecValidator,
"3.0": OpenAPIV30SpecValidator,
"3.1": OpenAPIV31SpecValidator,
# backward compatibility
"3.0.0": OpenAPIV30SpecValidator,
"3.1.0": OpenAPIV31SpecValidator,
}
if args_parsed.schema == "detect":
validator_cls = get_validator_cls(spec)
else:
validator_cls = validators[args_parsed.schema]
validator_cls = validators[args_parsed.schema]

validator = validator_cls(spec, base_uri=base_uri)
# validate
try:
validator.validate()
validate(spec, base_uri=base_uri, cls=validator_cls)
except ValidationError as exc:
print_validationerror(filename, exc, args_parsed.errors)
sys.exit(1)
Expand Down
39 changes: 37 additions & 2 deletions openapi_spec_validator/shortcuts.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
from typing import Optional
from typing import Type

from jsonschema_path import SchemaPath
from jsonschema_path.handlers import all_urls_handler
from jsonschema_path.typing import Schema

Expand Down Expand Up @@ -35,13 +36,37 @@ def get_validator_cls(spec: Schema) -> SpecValidatorType:
return SPEC2VALIDATOR[spec_version]


def validate(
spec: Schema,
base_uri: str = "",
cls: Optional[SpecValidatorType] = None,
) -> None:
if cls is None:
cls = get_validator_cls(spec)
sp = SchemaPath.from_dict(spec, base_uri=base_uri)
v = cls(sp)
return v.validate()


def validate_url(
spec_url: str,
cls: Optional[Type[SpecValidator]] = None,
) -> None:
spec = all_urls_handler(spec_url)
return validate(spec, base_uri=spec_url, cls=cls)


def validate_spec(
spec: Schema,
base_uri: str = "",
validator: Optional[SupportsValidation] = None,
cls: Optional[SpecValidatorType] = None,
spec_url: Optional[str] = None,
) -> None:
warnings.warn(
"validate_spec shortcut is deprecated. Use validate instead.",
DeprecationWarning,
)
if validator is not None:
warnings.warn(
"validator parameter is deprecated. Use cls instead.",
Expand All @@ -59,5 +84,15 @@ def validate_spec_url(
validator: Optional[SupportsValidation] = None,
cls: Optional[Type[SpecValidator]] = None,
) -> None:
spec = all_urls_handler(spec_url)
return validate_spec(spec, base_uri=spec_url, validator=validator, cls=cls)
warnings.warn(
"validate_spec_url shortcut is deprecated. Use validate_url instead.",
DeprecationWarning,
)
if validator is not None:
warnings.warn(
"validator parameter is deprecated. Use cls instead.",
DeprecationWarning,
)
spec = all_urls_handler(spec_url)
return validator.validate(spec, base_uri=spec_url)
return validate_url(spec_url, cls=cls)
1 change: 0 additions & 1 deletion openapi_spec_validator/validation/validators.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@
from jsonschema.protocols import Validator
from jsonschema_path.handlers import default_handlers
from jsonschema_path.paths import SchemaPath
from jsonschema_path.typing import Schema

from openapi_spec_validator.schemas import openapi_v2_schema_validator
from openapi_spec_validator.schemas import openapi_v30_schema_validator
Expand Down
30 changes: 17 additions & 13 deletions tests/integration/test_shortcuts.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@
from openapi_spec_validator import OpenAPIV30SpecValidator
from openapi_spec_validator import openapi_v2_spec_validator
from openapi_spec_validator import openapi_v30_spec_validator
from openapi_spec_validator import validate
from openapi_spec_validator import validate_spec
from openapi_spec_validator import validate_spec_url
from openapi_spec_validator import validate_url
from openapi_spec_validator.validation.exceptions import OpenAPIValidationError
from openapi_spec_validator.validation.exceptions import ValidatorDetectError

Expand All @@ -15,7 +17,7 @@ def test_spec_schema_version_not_detected(self):
spec = {}

with pytest.raises(ValidatorDetectError):
validate_spec(spec)
validate(spec)


class TestLocalValidateSpecUrl:
Expand All @@ -24,7 +26,7 @@ def test_spec_schema_version_not_detected(self, factory):
spec_url = factory.spec_file_url(spec_path)

with pytest.raises(ValidatorDetectError):
validate_spec_url(spec_url)
validate_url(spec_url)


class TestLiocalValidatev2Spec:
Expand All @@ -43,8 +45,8 @@ def test_valid(self, factory, spec_file):
spec_path = self.local_test_suite_file_path(spec_file)
spec = factory.spec_from_file(spec_path)

validate_spec(spec)
validate_spec(spec, cls=OpenAPIV2SpecValidator)
validate(spec)
validate(spec, cls=OpenAPIV2SpecValidator)
with pytest.warns(DeprecationWarning):
validate_spec(spec, validator=openapi_v2_spec_validator)

Expand All @@ -59,7 +61,7 @@ def test_falied(self, factory, spec_file):
spec = factory.spec_from_file(spec_path)

with pytest.raises(OpenAPIValidationError):
validate_spec(spec, cls=OpenAPIV2SpecValidator)
validate(spec, cls=OpenAPIV2SpecValidator)
with pytest.warns(DeprecationWarning):
with pytest.raises(OpenAPIValidationError):
validate_spec(spec, validator=openapi_v2_spec_validator)
Expand All @@ -82,9 +84,10 @@ def test_valid(self, factory, spec_file):
spec = factory.spec_from_file(spec_path)
spec_url = factory.spec_file_url(spec_path)

validate_spec(spec)
validate_spec(spec, spec_url=spec_url)
validate_spec(spec, cls=OpenAPIV30SpecValidator)
validate(spec)
with pytest.warns(DeprecationWarning):
validate_spec(spec, spec_url=spec_url)
validate(spec, cls=OpenAPIV30SpecValidator)
with pytest.warns(DeprecationWarning):
validate_spec(spec, validator=openapi_v30_spec_validator)

Expand All @@ -99,7 +102,7 @@ def test_falied(self, factory, spec_file):
spec = factory.spec_from_file(spec_path)

with pytest.raises(OpenAPIValidationError):
validate_spec(spec, cls=OpenAPIV30SpecValidator)
validate(spec, cls=OpenAPIV30SpecValidator)
with pytest.warns(DeprecationWarning):
with pytest.raises(OpenAPIValidationError):
validate_spec(spec, validator=openapi_v30_spec_validator)
Expand Down Expand Up @@ -128,9 +131,10 @@ def remote_test_suite_file_path(self, test_file):
def test_valid(self, spec_file):
spec_url = self.remote_test_suite_file_path(spec_file)

validate_spec_url(spec_url)
validate_spec_url(spec_url, cls=OpenAPIV2SpecValidator)
validate_url(spec_url)
validate_url(spec_url, cls=OpenAPIV2SpecValidator)
with pytest.warns(DeprecationWarning):
validate_spec_url(spec_url)
validate_spec_url(spec_url, validator=openapi_v2_spec_validator)


Expand All @@ -157,7 +161,7 @@ def remote_test_suite_file_path(self, test_file):
def test_valid(self, spec_file):
spec_url = self.remote_test_suite_file_path(spec_file)

validate_spec_url(spec_url)
validate_spec_url(spec_url, cls=OpenAPIV30SpecValidator)
validate_url(spec_url)
validate_url(spec_url, cls=OpenAPIV30SpecValidator)
with pytest.warns(DeprecationWarning):
validate_spec_url(spec_url, validator=openapi_v30_spec_validator)
2 changes: 1 addition & 1 deletion tests/integration/validation/test_validators.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import pytest
from jsonschema_path import SchemaPath
from referencing.exceptions import Unresolvable

from jsonschema_path import SchemaPath
from openapi_spec_validator import OpenAPIV2SpecValidator
from openapi_spec_validator import OpenAPIV30SpecValidator
from openapi_spec_validator import OpenAPIV31SpecValidator
Expand Down

0 comments on commit 8564cc6

Please sign in to comment.