From e400507cff593d3ecbec2e71e93dd90d86406482 Mon Sep 17 00:00:00 2001 From: Anders Albert <60234212+doctrino@users.noreply.github.com> Date: Fri, 26 Apr 2024 10:02:12 +0200 Subject: [PATCH] [NEAT-208] Pydantic v2 model_copy instead of copy (#416) * fix: pydantic v2 model_copy instead of copy * build: changelog * build; bump --- Makefile | 2 +- cognite/neat/_version.py | 2 +- cognite/neat/rules/exporters/_rules2dms.py | 4 ++-- cognite/neat/rules/models/rules/_dms_architect_rules.py | 4 ++-- cognite/neat/rules/models/rules/_domain_rules.py | 2 +- cognite/neat/rules/models/rules/_information_rules.py | 2 +- docs/CHANGELOG.md | 5 ++++- pyproject.toml | 2 +- tests/tests_unit/graph/transformations/test_transformer.py | 2 +- tests/tests_unit/rules/test_exporters/test_rules2excel.py | 2 +- .../rules/test_models/test_dms_architect_rules.py | 6 +++--- .../tests_unit/rules/test_models/test_information_rules.py | 2 +- 12 files changed, 19 insertions(+), 16 deletions(-) diff --git a/Makefile b/Makefile index 7b68f74f6..46f16a012 100644 --- a/Makefile +++ b/Makefile @@ -1,6 +1,6 @@ .PHONY: run-explorer run-tests run-linters build-ui build-python build-docker run-docker compose-up -version="0.75.5" +version="0.75.6" run-explorer: @echo "Running explorer API server..." # open "http://localhost:8000/static/index.html" || true diff --git a/cognite/neat/_version.py b/cognite/neat/_version.py index 22b2dd90f..5600e5291 100644 --- a/cognite/neat/_version.py +++ b/cognite/neat/_version.py @@ -1 +1 @@ -__version__ = "0.75.5" +__version__ = "0.75.6" diff --git a/cognite/neat/rules/exporters/_rules2dms.py b/cognite/neat/rules/exporters/_rules2dms.py index c35e783c9..b279eb64e 100644 --- a/cognite/neat/rules/exporters/_rules2dms.py +++ b/cognite/neat/rules/exporters/_rules2dms.py @@ -118,12 +118,12 @@ def export(self, rules: Rules) -> DMSSchema: return dms_rules.as_schema(self.export_pipeline, self.instance_space) # This is an extension of an existing model. - reference_rules = cast(DMSRules, dms_rules.reference).copy(deep=True) + reference_rules = cast(DMSRules, dms_rules.reference).model_copy(deep=True) reference_schema = reference_rules.as_schema(self.export_pipeline) # Todo Move this to an appropriate location # Merging Reference with User Rules - combined_rules = dms_rules.copy(deep=True) + combined_rules = dms_rules.model_copy(deep=True) existing_containers = {container.class_ for container in combined_rules.containers or []} if combined_rules.containers is None: combined_rules.containers = SheetList[DMSContainer](data=[]) diff --git a/cognite/neat/rules/models/rules/_dms_architect_rules.py b/cognite/neat/rules/models/rules/_dms_architect_rules.py index c653bab11..9efe92388 100644 --- a/cognite/neat/rules/models/rules/_dms_architect_rules.py +++ b/cognite/neat/rules/models/rules/_dms_architect_rules.py @@ -582,7 +582,7 @@ def validate_schema(self) -> "DMSRules": "The schema is set to 'extended', but no reference rules are provided to validate against" ) # This is an extension of the reference rules, we need to merge the two - rules = self.copy(deep=True) + rules = self.model_copy(deep=True) rules.properties.extend(self.reference.properties.data) existing_views = {view.view.as_id(False) for view in rules.views} rules.views.extend([view for view in self.reference.views if view.view.as_id(False) not in existing_views]) @@ -680,7 +680,7 @@ def as_domain_expert_rules(self) -> DomainRules: return _DMSRulesConverter(self).as_domain_rules() def reference_self(self) -> Self: - new_rules = self.copy(deep=True) + new_rules = self.model_copy(deep=True) for prop in new_rules.properties: prop.reference = ReferenceEntity( prefix=prop.view.prefix, suffix=prop.view.suffix, version=prop.view.version, property_=prop.property_ diff --git a/cognite/neat/rules/models/rules/_domain_rules.py b/cognite/neat/rules/models/rules/_domain_rules.py index cfcd9ba51..3fada34ab 100644 --- a/cognite/neat/rules/models/rules/_domain_rules.py +++ b/cognite/neat/rules/models/rules/_domain_rules.py @@ -64,4 +64,4 @@ def domain_rules_serializer(self, info: SerializationInfo) -> dict[str, Any]: def reference_self(self) -> "DomainRules": """DomainRules does not have reference field, so it returns a copy of itself.""" - return self.copy(deep=True) + return self.model_copy(deep=True) diff --git a/cognite/neat/rules/models/rules/_information_rules.py b/cognite/neat/rules/models/rules/_information_rules.py index 7f5a08c68..b6cc0e3d1 100644 --- a/cognite/neat/rules/models/rules/_information_rules.py +++ b/cognite/neat/rules/models/rules/_information_rules.py @@ -354,7 +354,7 @@ def as_dms_architect_rules(self) -> "DMSRules": return _InformationRulesConverter(self).as_dms_architect_rules() def reference_self(self) -> "InformationRules": - new_self = self.copy(deep=True) + new_self = self.model_copy(deep=True) for prop in new_self.properties: prop.reference = ReferenceEntity( prefix=prop.class_.prefix, diff --git a/docs/CHANGELOG.md b/docs/CHANGELOG.md index c1b39fe36..cee3c5a0a 100644 --- a/docs/CHANGELOG.md +++ b/docs/CHANGELOG.md @@ -15,7 +15,7 @@ Changes are grouped as follows: - `Fixed` for any bug fixes. - `Security` in case of vulnerabilities. -## TBD +## [0.75.6] - 26-05-24 ### Changed - All `NEAT` importers does not have `is_reference` parameter in `.to_rules()` method. This has been moved to the `ExcelExporter` `__init__` method. This is because this is the only place where this parameter was used. @@ -23,6 +23,9 @@ Changes are grouped as follows: ### Added - `DMSExporter` now supports skipping of export of `node_types`. +### Fixed +- When importing an `Excel` rules set with a reference model, the `ExcelImporter` would produce the warning + `The copy method is deprecated; use the model_copy instead`. This is now fixed. ## [0.75.5] - 24-05-24 ### Fixed diff --git a/pyproject.toml b/pyproject.toml index 4450417f0..ec260761c 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [tool.poetry] name = "cognite-neat" -version = "0.75.5" +version = "0.75.6" readme = "README.md" description = "Knowledge graph transformation" authors = [ diff --git a/tests/tests_unit/graph/transformations/test_transformer.py b/tests/tests_unit/graph/transformations/test_transformer.py index 9634fc65e..33a14985b 100644 --- a/tests/tests_unit/graph/transformations/test_transformer.py +++ b/tests/tests_unit/graph/transformations/test_transformer.py @@ -24,7 +24,7 @@ def test_domain2app_knowledge_graph(transformation_rules: Rules, source_knowledg def test_domain2app_knowledge_graph_raw_lookup(transformation_rules: Rules, source_knowledge_graph: Graph): # Arrange - rules = transformation_rules.copy(deep=True) + rules = transformation_rules.model_copy(deep=True) rules.properties["row 18"].rule += " | TerminalName(NordicName, TNTName)" rules.properties["row 18"].rule_type = TransformationRuleType.rawlookup domain_graph = source_knowledge_graph diff --git a/tests/tests_unit/rules/test_exporters/test_rules2excel.py b/tests/tests_unit/rules/test_exporters/test_rules2excel.py index 91b86438a..39d64f98d 100644 --- a/tests/tests_unit/rules/test_exporters/test_rules2excel.py +++ b/tests/tests_unit/rules/test_exporters/test_rules2excel.py @@ -67,7 +67,7 @@ def test_export_rules_with_reference(self, olav_rules: InformationRules) -> None assert olav_rules.reference is not None, "Olav rules are expected to have a reference set" expected_sheet_names = {"Metadata", "Classes", "Properties", "RefMetadata", "RefClasses", "RefProperties"} # Make a copy of the rules to avoid changing the original - olav_copy = olav_rules.copy(deep=True) + olav_copy = olav_rules.model_copy(deep=True) workbook = exporter.export(olav_copy) diff --git a/tests/tests_unit/rules/test_models/test_dms_architect_rules.py b/tests/tests_unit/rules/test_models/test_dms_architect_rules.py index ae9c4f2a5..536d90d55 100644 --- a/tests/tests_unit/rules/test_models/test_dms_architect_rules.py +++ b/tests/tests_unit/rules/test_models/test_dms_architect_rules.py @@ -1417,7 +1417,7 @@ def invalid_extended_rules_test_cases() -> Iterable[ParameterSet]: id="Addition extension, changing view", ) - changing_container2 = changing_container.copy(deep=True) + changing_container2 = changing_container.model_copy(deep=True) changing_container2.metadata.extension = ExtensionCategory.reshape yield pytest.param( @@ -1468,7 +1468,7 @@ def test_load_inconsistent_container_definitions( def test_alice_to_and_from_DMS(self, alice_rules: DMSRules) -> None: schema = alice_rules.as_schema() - rules = alice_rules.copy() + rules = alice_rules.model_copy() recreated_rules = DMSImporter(schema).to_rules(errors="raise") # Sorting to avoid order differences @@ -1580,7 +1580,7 @@ def test_dump_skip_default_space_and_version(self) -> None: assert actual_dump == expected_dump def test_olav_as_information(self, olav_dms_rules: DMSRules) -> None: - info_rules_copy = olav_dms_rules.copy(deep=True) + info_rules_copy = olav_dms_rules.model_copy(deep=True) # In Olav's Rules, the references are set for traceability. We remove it # to test that the references are correctly set in the conversion. for prop in info_rules_copy.properties: diff --git a/tests/tests_unit/rules/test_models/test_information_rules.py b/tests/tests_unit/rules/test_models/test_information_rules.py index d95a0e6f3..98521549a 100644 --- a/tests/tests_unit/rules/test_models/test_information_rules.py +++ b/tests/tests_unit/rules/test_models/test_information_rules.py @@ -217,7 +217,7 @@ def test_david_as_dms(self, david_spreadsheet: dict[str, dict[str, Any]]) -> Non assert isinstance(dms_rules, DMSRules) def test_olav_as_dms(self, olav_rules: InformationRules) -> None: - olav_rules_copy = olav_rules.copy(deep=True) + olav_rules_copy = olav_rules.model_copy(deep=True) # Todo: Remove this line when Olav's Information .xlsx file is available new_classes = SheetList[InformationClass](data=[]) for cls_ in olav_rules_copy.classes: