diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index d1fa5abce369dcb67517221545a7ba485e5ec089_LmdpdGxhYi1jaS55bWw=..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_LmdpdGxhYi1jaS55bWw= 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -6,3 +6,12 @@ TEST_OPTIONS: --test-tags=odoo_addons_mail # Also install mail to run mail dependant tets ODOO_SCRIPTS_MODULE_LIST: mail + +mypy: + variables: + INSTALL_SECTION: "[test,schema-validation]" + +test-schema-validation: + extends: test + variables: + INSTALL_SECTION: "[test,schema-validation]" diff --git a/NEWS.rst b/NEWS.rst index d1fa5abce369dcb67517221545a7ba485e5ec089_TkVXUy5yc3Q=..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_TkVXUy5yc3Q= 100644 --- a/NEWS.rst +++ b/NEWS.rst @@ -1,6 +1,12 @@ Changelog ========= +18.0.6.0.0 +---------- + +fastjsonschema is now an optional dependency. It is listed in the dependencies of section *schema-validation*. +If validation needs to be done and the library is missing, an exception will be raised. + 18.0.5.0.0 ---------- diff --git a/README.rst b/README.rst index d1fa5abce369dcb67517221545a7ba485e5ec089_UkVBRE1FLnJzdA==..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_UkVBRE1FLnJzdA== 100644 --- a/README.rst +++ b/README.rst @@ -18,3 +18,5 @@ |maturity| |license| |ruff| |prettier| Convert odoo records to/from plain data structures. + +section *schema-validation* need to be installed if validation is needed. diff --git a/__manifest__.py b/__manifest__.py index d1fa5abce369dcb67517221545a7ba485e5ec089_X19tYW5pZmVzdF9fLnB5..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_X19tYW5pZmVzdF9fLnB5 100644 --- a/__manifest__.py +++ b/__manifest__.py @@ -21,9 +21,9 @@ "name": "Converter", "license": "AGPL-3", "summary": "Convert odoo records to/from plain data structures.", - "version": "18.0.5.0.0", + "version": "18.0.6.0.0", "category": "Hidden", "author": "XCG Consulting", "website": "https://orbeet.io/", "depends": ["base"], "installable": True, @@ -25,7 +25,6 @@ "category": "Hidden", "author": "XCG Consulting", "website": "https://orbeet.io/", "depends": ["base"], "installable": True, - "external_dependencies": {"python": ["fastjsonschema"]}, } diff --git a/model.py b/model.py index d1fa5abce369dcb67517221545a7ba485e5ec089_bW9kZWwucHk=..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_bW9kZWwucHk= 100644 --- a/model.py +++ b/model.py @@ -23,7 +23,6 @@ from collections.abc import Iterable, Mapping from typing import Any, Final -import fastjsonschema # type: ignore[import-untyped] from odoo import _, api, models # type: ignore[import-untyped] from odoo.exceptions import UserError # type: ignore[import-untyped] @@ -39,6 +38,14 @@ ) from .validate import NotInitialized, Validation, Validator +try: + from fastjsonschema import JsonSchemaException # type: ignore[import-untyped] +except ImportError: + # Ignore no-redef, added for compatibility + class JsonSchemaException(Exception): # type: ignore[no-redef] + """Custom error in case of missing optional requirement""" + + _logger = logging.getLogger(__name__) @@ -129,7 +136,7 @@ if self.validator: try: self.validator.validate(self._jsonschema, message_data) - except (NotInitialized, fastjsonschema.JsonSchemaException): + except (NotInitialized, JsonSchemaException): _logger.warning("Validation failed", exc_info=True) if self.validation == Validation.STRICT: raise @@ -152,7 +159,7 @@ if self.validator: try: self.validator.validate(self._jsonschema, message_value) - except (NotInitialized, fastjsonschema.JsonSchemaException): + except (NotInitialized, JsonSchemaException): _logger.warning("Validation failed", exc_info=True) if self.validation == Validation.STRICT: raise diff --git a/pyproject.toml b/pyproject.toml index d1fa5abce369dcb67517221545a7ba485e5ec089_cHlwcm9qZWN0LnRvbWw=..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_cHlwcm9qZWN0LnRvbWw= 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -15,6 +15,6 @@ "Framework :: Odoo :: 18.0", "License :: OSI Approved :: GNU Affero General Public License v3", ] -dependencies = ["odoo==18.0.*", "fastjsonschema"] +dependencies = ["odoo==18.0.*"] [project.optional-dependencies] @@ -19,5 +19,6 @@ [project.optional-dependencies] +schema-validation = ["fastjsonschema"] doc = ["sphinx"] test = [] diff --git a/tests/test_validate.py b/tests/test_validate.py index d1fa5abce369dcb67517221545a7ba485e5ec089_dGVzdHMvdGVzdF92YWxpZGF0ZS5weQ==..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_dGVzdHMvdGVzdF92YWxpZGF0ZS5weQ== 100644 --- a/tests/test_validate.py +++ b/tests/test_validate.py @@ -18,9 +18,10 @@ # ############################################################################## import json +from unittest import skipUnless from odoo import tests # type: ignore[import-untyped] from ..validate import Validator @@ -21,9 +22,10 @@ from odoo import tests # type: ignore[import-untyped] from ..validate import Validator +@skipUnless(tests.can_import("fastjsonschema"), "fastjsonschema module not available") class TestValidate(tests.TransactionCase): def test_validate(self): validator = Validator( diff --git a/validate.py b/validate.py index d1fa5abce369dcb67517221545a7ba485e5ec089_dmFsaWRhdGUucHk=..dd3bf0df6615bf036e21490a7c9a74f5d9d6199c_dmFsaWRhdGUucHk= 100644 --- a/validate.py +++ b/validate.py @@ -25,6 +25,5 @@ from importlib import import_module from typing import Any, LiteralString -import fastjsonschema # type: ignore[import-untyped] from odoo.exceptions import UserError # type: ignore[import-untyped] @@ -29,5 +28,12 @@ from odoo.exceptions import UserError # type: ignore[import-untyped] +_fastjsonschema: None | Exception = None +try: + import fastjsonschema # type: ignore[import-untyped] +except ImportError as e: + _fastjsonschema = e + + _logger = logging.getLogger(__name__) @@ -101,6 +107,8 @@ # Prepare validators for each schema. We add an HTTPS handler that # points back to our schema definition cache built above. for schema_id, schema in schemas.items(): + if _fastjsonschema is not None: + raise _fastjsonschema self.validators[schema_id] = fastjsonschema.compile( schema, handlers={"https": lambda uri: schemas[uri]},