pymetadataeditor 0.3.0__tar.gz → 0.3.1__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.
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/PKG-INFO +2 -2
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pymetadataeditor/interface.py +78 -6
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pymetadataeditor/templates.py +17 -2
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pyproject.toml +2 -2
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/LICENSE +0 -0
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/README.md +0 -0
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pymetadataeditor/__init__.py +0 -0
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pymetadataeditor/llm_helpers.py +0 -0
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pymetadataeditor/requester.py +0 -0
- {pymetadataeditor-0.3.0 → pymetadataeditor-0.3.1}/pymetadataeditor/utils.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.1
|
|
2
2
|
Name: pymetadataeditor
|
|
3
|
-
Version: 0.3.
|
|
3
|
+
Version: 0.3.1
|
|
4
4
|
Summary: Metadata Editor client for python
|
|
5
5
|
License: MIT
|
|
6
6
|
Author: Gordon Blackadder
|
|
@@ -11,7 +11,7 @@ Classifier: Programming Language :: Python :: 3
|
|
|
11
11
|
Classifier: Programming Language :: Python :: 3.11
|
|
12
12
|
Classifier: Programming Language :: Python :: 3.12
|
|
13
13
|
Requires-Dist: markitdown (>=0.0.1a3,<0.0.2)
|
|
14
|
-
Requires-Dist: metadataschemas (>=0.1.
|
|
14
|
+
Requires-Dist: metadataschemas (>=0.1.3,<0.2.0)
|
|
15
15
|
Requires-Dist: openai (>=1.59.4,<2.0.0)
|
|
16
16
|
Requires-Dist: pandas (>=2.2.2,<3.0.0)
|
|
17
17
|
Requires-Dist: pydantic (>=2.7.4,<3.0.0)
|
|
@@ -427,12 +427,21 @@ class MetadataEditor:
|
|
|
427
427
|
else:
|
|
428
428
|
metadata_type = self._templates[template_uid]["metadata_type"]
|
|
429
429
|
if "class" not in self._templates[template_uid] or apply_template_rules is False:
|
|
430
|
-
|
|
430
|
+
try:
|
|
431
|
+
parent_schema = self._mm.metadata_class_from_name(metadata_type)
|
|
432
|
+
except ValueError:
|
|
433
|
+
warnings.warn(
|
|
434
|
+
f"Could not find a metadata class for template type '{metadata_type}', UID '{template_uid}'. "
|
|
435
|
+
f"Building a class from the template without a parent schema."
|
|
436
|
+
)
|
|
437
|
+
parent_schema = SchemaBaseModel
|
|
438
|
+
|
|
431
439
|
klass = pydantic_from_template(
|
|
432
440
|
temp.template,
|
|
433
441
|
parent_schema=parent_schema,
|
|
434
442
|
uid=template_uid,
|
|
435
443
|
name=temp.name,
|
|
444
|
+
metadata_type=metadata_type,
|
|
436
445
|
apply_rules=apply_template_rules,
|
|
437
446
|
)
|
|
438
447
|
if apply_template_rules:
|
|
@@ -1043,7 +1052,7 @@ class MetadataEditor:
|
|
|
1043
1052
|
document, geospatial, image, indicator, indicators_db, microdata, resource, script, table, video
|
|
1044
1053
|
In this case we will use the default template for that metadata type.
|
|
1045
1054
|
Alternatively you can pass in the UID of a template. This is required if the metadata is a dictionary
|
|
1046
|
-
otherwise
|
|
1055
|
+
otherwise the UID associated with the pydantic model or the Excel file will be used.
|
|
1047
1056
|
|
|
1048
1057
|
Returns:
|
|
1049
1058
|
int: The ID of the newly created document metadata
|
|
@@ -1063,6 +1072,37 @@ class MetadataEditor:
|
|
|
1063
1072
|
)
|
|
1064
1073
|
return ret["id"]
|
|
1065
1074
|
|
|
1075
|
+
# def log_project_admin_metadata(
|
|
1076
|
+
# self, id: int, metadata: Union[BaseModel, Dict, str], metadata_type_or_template_uid: Optional[str] = None
|
|
1077
|
+
# ) -> int:
|
|
1078
|
+
# """Validates and logs admin metadata which can be a dictionary, a pydantic model or a path to an Excel file.
|
|
1079
|
+
|
|
1080
|
+
# Args:
|
|
1081
|
+
# id (int): The ID of the project to associate the metadata with.
|
|
1082
|
+
# metadata (dictionary or BaseModel or str): If str, it's assumed this is a path to an appropriately
|
|
1083
|
+
# formatted Excel file.
|
|
1084
|
+
# admin_metadata_template_uid (str, optional): The UID of the admin metadata template to use.
|
|
1085
|
+
# otherwise the UID associated with the pydantic model or the Excel file will be used.
|
|
1086
|
+
|
|
1087
|
+
# Returns:
|
|
1088
|
+
# int: The ID of the newly created admin metadata
|
|
1089
|
+
# """
|
|
1090
|
+
# metadata, metadata_type, uid = self._process_metadata_input(metadata, metadata_type_or_template_uid)
|
|
1091
|
+
# post_request_pth = "admin-metadata/data/"
|
|
1092
|
+
# post_json = {
|
|
1093
|
+
# "project_id": id,
|
|
1094
|
+
# "template_uid": uid,
|
|
1095
|
+
# "metadata": remove_empty_from_dict(metadata.model_dump(mode="json",
|
|
1096
|
+
# exclude_none=True,
|
|
1097
|
+
# exclude_unset=True)),
|
|
1098
|
+
# }
|
|
1099
|
+
# ret = self._apinterface.post_request(
|
|
1100
|
+
# pth=post_request_pth,
|
|
1101
|
+
# json=post_json,
|
|
1102
|
+
# id=id,
|
|
1103
|
+
# )
|
|
1104
|
+
# return ret
|
|
1105
|
+
|
|
1066
1106
|
def update_project_log_by_id(self, id: int, new_metadata: Union[BaseModel, Dict, str]):
|
|
1067
1107
|
"""Updates the record of the metadata.
|
|
1068
1108
|
|
|
@@ -1252,7 +1292,6 @@ class MetadataEditor:
|
|
|
1252
1292
|
new_index = templates.index.astype(int)
|
|
1253
1293
|
except ValueError:
|
|
1254
1294
|
pass
|
|
1255
|
-
else:
|
|
1256
1295
|
templates.index = new_index
|
|
1257
1296
|
return templates
|
|
1258
1297
|
|
|
@@ -1272,10 +1311,23 @@ class MetadataEditor:
|
|
|
1272
1311
|
raise KeyError(f"No result returned.\nResponse: {response}")
|
|
1273
1312
|
|
|
1274
1313
|
temp = pd.Series(response["result"], name=response["result"]["name"])
|
|
1275
|
-
self._templates[uid] = {"template": temp, "metadata_type": self._mm.standardize_metadata_name(temp.data_type)}
|
|
1276
1314
|
try:
|
|
1277
|
-
|
|
1278
|
-
|
|
1315
|
+
standard_type_name = self._mm.standardize_metadata_name(temp.data_type)
|
|
1316
|
+
except ValueError:
|
|
1317
|
+
standard_type_name = temp.data_type
|
|
1318
|
+
self._templates[uid] = {"template": temp, "metadata_type": standard_type_name}
|
|
1319
|
+
try:
|
|
1320
|
+
try:
|
|
1321
|
+
parent_schema = self._mm.metadata_class_from_name(temp.data_type)
|
|
1322
|
+
except ValueError:
|
|
1323
|
+
warnings.warn(
|
|
1324
|
+
f"Could not find a metadata class for template type '{standard_type_name}', UID '{uid}'. "
|
|
1325
|
+
f"Building a class from the template without a parent schema."
|
|
1326
|
+
)
|
|
1327
|
+
parent_schema = SchemaBaseModel
|
|
1328
|
+
klass = pydantic_from_template(
|
|
1329
|
+
temp.template, parent_schema=parent_schema, uid=uid, name=temp.name, metadata_type=standard_type_name
|
|
1330
|
+
)
|
|
1279
1331
|
self._templates[uid]["class"] = klass
|
|
1280
1332
|
finally:
|
|
1281
1333
|
return temp
|
|
@@ -1474,6 +1526,26 @@ class MetadataEditor:
|
|
|
1474
1526
|
metadata["description"] = description
|
|
1475
1527
|
self._apinterface.post_request("collections/update/{}", id=id, json=metadata)
|
|
1476
1528
|
|
|
1529
|
+
def copy_collection(self, source_id: int, target_id: int):
|
|
1530
|
+
"""Copy projects and users from one collection to another.
|
|
1531
|
+
|
|
1532
|
+
Args:
|
|
1533
|
+
source_id (int): The ID of the source collection.
|
|
1534
|
+
target_id (int): The ID of the target collection.
|
|
1535
|
+
|
|
1536
|
+
"""
|
|
1537
|
+
self._apinterface.post_request("collections/copy/", json={"source_id": source_id, "target_id": target_id})
|
|
1538
|
+
|
|
1539
|
+
def move_collection(self, source_id, target_id):
|
|
1540
|
+
"""Move source collection to be a sub-collection of the target collection.
|
|
1541
|
+
|
|
1542
|
+
Args:
|
|
1543
|
+
source_id (int): The ID of the source collection.
|
|
1544
|
+
target_id (int): The ID of the target collection.
|
|
1545
|
+
|
|
1546
|
+
"""
|
|
1547
|
+
self._apinterface.post_request("collections/move/", json={"source_id": source_id, "target_id": target_id})
|
|
1548
|
+
|
|
1477
1549
|
def count_projects_in_collection(self, collection: int) -> int:
|
|
1478
1550
|
"""Count the number of projects you have access to.
|
|
1479
1551
|
|
|
@@ -617,7 +617,12 @@ def append_variables_and_data_files(model_elements, parent_schema, apply_rules:
|
|
|
617
617
|
|
|
618
618
|
|
|
619
619
|
def pydantic_from_template(
|
|
620
|
-
template: Dict,
|
|
620
|
+
template: Dict,
|
|
621
|
+
parent_schema: Type[SchemaBaseModel],
|
|
622
|
+
uid: str,
|
|
623
|
+
name: Optional[str] = None,
|
|
624
|
+
metadata_type: Optional[str] = None,
|
|
625
|
+
apply_rules: bool = True,
|
|
621
626
|
) -> Type[BaseModel]:
|
|
622
627
|
"""Generate a Pydantic model from a given template.
|
|
623
628
|
|
|
@@ -626,6 +631,8 @@ def pydantic_from_template(
|
|
|
626
631
|
parent_schema (Type[SchemaBaseModel]): The parent schema model to base the new model on.
|
|
627
632
|
uid (str): A unique identifier for the new model.
|
|
628
633
|
name (Optional[str], optional): The name of the new model. Defaults to None.
|
|
634
|
+
metadata_type (Optional[str], optional): The metadata type for the new model used if the parent_schema is
|
|
635
|
+
SchemaBaseModel. Otherwise the metadata_type of the parent_schema is used. Defaults to None.
|
|
629
636
|
apply_rules (bool, optional): Whether to apply rules to the model elements. Defaults to True.
|
|
630
637
|
|
|
631
638
|
Returns:
|
|
@@ -659,4 +666,12 @@ def pydantic_from_template(
|
|
|
659
666
|
hasattr(parent_schema._metadata_type__, "default") and parent_schema._metadata_type__.default == "microdata"
|
|
660
667
|
):
|
|
661
668
|
model_elements = append_variables_and_data_files(model_elements, parent_schema, apply_rules=apply_rules)
|
|
662
|
-
|
|
669
|
+
new_model = create_model_for_template(model_elements, parent_schema, name, uid=uid)
|
|
670
|
+
if parent_schema is SchemaBaseModel:
|
|
671
|
+
if metadata_type is None:
|
|
672
|
+
raise ValueError("metadata_type must be provided if parent_schema is SchemaBaseModel. ")
|
|
673
|
+
new_model._template_name__ = f"{name.replace('-', '_').replace(' ', '_')}"
|
|
674
|
+
new_model._template_uid__ = uid
|
|
675
|
+
new_model._metadata_type__ = metadata_type.replace("-", "_").replace(" ", "_")
|
|
676
|
+
new_model._metadata_type_version__ = "unknown"
|
|
677
|
+
return new_model
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[tool.poetry]
|
|
2
2
|
name = "pymetadataeditor"
|
|
3
|
-
version = "0.3.
|
|
3
|
+
version = "0.3.1"
|
|
4
4
|
description = "Metadata Editor client for python"
|
|
5
5
|
authors = ["Gordon Blackadder <gblackadder@worldbank.org>"]
|
|
6
6
|
readme = "README.md"
|
|
@@ -15,7 +15,7 @@ pydantic = "^2.7.4"
|
|
|
15
15
|
openai = "^1.59.4"
|
|
16
16
|
tiktoken = "^0.8.0"
|
|
17
17
|
markitdown = "^0.0.1a3"
|
|
18
|
-
metadataschemas = "^0.1.
|
|
18
|
+
metadataschemas = "^0.1.3"
|
|
19
19
|
|
|
20
20
|
[tool.poetry.group.dev.dependencies]
|
|
21
21
|
pytest = "^8.2.2"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|