dsp-tools 9.1.0.post11__py3-none-any.whl → 18.3.0.post13__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.
- dsp_tools/__init__.py +4 -0
- dsp_tools/cli/args.py +36 -0
- dsp_tools/cli/call_action.py +51 -231
- dsp_tools/cli/call_action_files_only.py +101 -0
- dsp_tools/cli/call_action_with_network.py +207 -0
- dsp_tools/cli/create_parsers.py +156 -58
- dsp_tools/cli/entry_point.py +56 -26
- dsp_tools/cli/utils.py +87 -0
- dsp_tools/clients/CLAUDE.md +420 -0
- dsp_tools/clients/authentication_client.py +14 -0
- dsp_tools/clients/authentication_client_live.py +66 -0
- dsp_tools/{utils → clients}/connection.py +2 -18
- dsp_tools/clients/connection_live.py +233 -0
- dsp_tools/clients/fuseki_metrics.py +60 -0
- dsp_tools/clients/group_user_clients.py +35 -0
- dsp_tools/clients/group_user_clients_live.py +181 -0
- dsp_tools/clients/legal_info_client.py +23 -0
- dsp_tools/clients/legal_info_client_live.py +132 -0
- dsp_tools/clients/list_client.py +49 -0
- dsp_tools/clients/list_client_live.py +166 -0
- dsp_tools/clients/metadata_client.py +24 -0
- dsp_tools/clients/metadata_client_live.py +47 -0
- dsp_tools/clients/ontology_clients.py +49 -0
- dsp_tools/clients/ontology_create_client_live.py +166 -0
- dsp_tools/clients/ontology_get_client_live.py +80 -0
- dsp_tools/clients/permissions_client.py +68 -0
- dsp_tools/clients/project_client.py +16 -0
- dsp_tools/clients/project_client_live.py +66 -0
- dsp_tools/commands/create/communicate_problems.py +24 -0
- dsp_tools/commands/create/create.py +134 -0
- dsp_tools/commands/create/create_on_server/cardinalities.py +111 -0
- dsp_tools/commands/create/create_on_server/classes.py +99 -0
- dsp_tools/commands/create/create_on_server/complete_ontologies.py +116 -0
- dsp_tools/commands/create/create_on_server/default_permissions.py +134 -0
- dsp_tools/commands/create/create_on_server/group_users.py +165 -0
- dsp_tools/commands/create/create_on_server/lists.py +163 -0
- dsp_tools/commands/create/create_on_server/mappers.py +12 -0
- dsp_tools/commands/create/create_on_server/onto_utils.py +74 -0
- dsp_tools/commands/create/create_on_server/ontology.py +52 -0
- dsp_tools/commands/create/create_on_server/project.py +68 -0
- dsp_tools/commands/create/create_on_server/properties.py +119 -0
- dsp_tools/commands/create/exceptions.py +29 -0
- dsp_tools/commands/create/lists_only.py +66 -0
- dsp_tools/commands/create/models/create_problems.py +87 -0
- dsp_tools/commands/create/models/parsed_ontology.py +88 -0
- dsp_tools/commands/create/models/parsed_project.py +81 -0
- dsp_tools/commands/create/models/rdf_ontology.py +12 -0
- dsp_tools/commands/create/models/server_project_info.py +100 -0
- dsp_tools/commands/create/parsing/parse_lists.py +45 -0
- dsp_tools/commands/create/parsing/parse_ontology.py +243 -0
- dsp_tools/commands/create/parsing/parse_project.py +149 -0
- dsp_tools/commands/create/parsing/parsing_utils.py +40 -0
- dsp_tools/commands/create/project_validate.py +595 -0
- dsp_tools/commands/create/serialisation/ontology.py +119 -0
- dsp_tools/commands/create/serialisation/project.py +44 -0
- dsp_tools/commands/excel2json/CLAUDE.md +101 -0
- dsp_tools/commands/excel2json/json_header.py +57 -23
- dsp_tools/commands/excel2json/{new_lists → lists}/compliance_checks.py +26 -26
- dsp_tools/commands/excel2json/{new_lists/make_new_lists.py → lists/make_lists.py} +19 -18
- dsp_tools/commands/excel2json/{new_lists → lists}/models/input_error.py +1 -12
- dsp_tools/commands/excel2json/{new_lists → lists}/models/serialise.py +9 -5
- dsp_tools/commands/excel2json/{new_lists → lists}/utils.py +4 -4
- dsp_tools/commands/excel2json/models/input_error.py +31 -11
- dsp_tools/commands/excel2json/models/json_header.py +53 -15
- dsp_tools/commands/excel2json/models/ontology.py +4 -3
- dsp_tools/commands/excel2json/{lists.py → old_lists.py} +26 -112
- dsp_tools/commands/excel2json/project.py +78 -34
- dsp_tools/commands/excel2json/properties.py +57 -36
- dsp_tools/commands/excel2json/resources.py +32 -12
- dsp_tools/commands/excel2json/utils.py +20 -1
- dsp_tools/commands/excel2xml/__init__.py +2 -2
- dsp_tools/commands/excel2xml/excel2xml_cli.py +7 -15
- dsp_tools/commands/excel2xml/excel2xml_lib.py +138 -493
- dsp_tools/commands/excel2xml/propertyelement.py +5 -5
- dsp_tools/commands/{project → get}/get.py +29 -13
- dsp_tools/commands/get/get_permissions.py +257 -0
- dsp_tools/commands/get/get_permissions_legacy.py +89 -0
- dsp_tools/commands/{project/models → get/legacy_models}/context.py +6 -6
- dsp_tools/commands/{project/models → get/legacy_models}/group.py +5 -10
- dsp_tools/commands/{project/models → get/legacy_models}/listnode.py +5 -35
- dsp_tools/commands/{project/models → get/legacy_models}/model.py +1 -1
- dsp_tools/commands/{project/models → get/legacy_models}/ontology.py +9 -14
- dsp_tools/commands/{project/models → get/legacy_models}/project.py +13 -6
- dsp_tools/commands/{project/models → get/legacy_models}/propertyclass.py +9 -16
- dsp_tools/commands/{project/models → get/legacy_models}/resourceclass.py +8 -46
- dsp_tools/commands/{project/models → get/legacy_models}/user.py +19 -60
- dsp_tools/commands/get/models/permissions_models.py +10 -0
- dsp_tools/commands/id2iri.py +20 -10
- dsp_tools/commands/ingest_xmlupload/bulk_ingest_client.py +81 -56
- dsp_tools/commands/ingest_xmlupload/create_resources/apply_ingest_id.py +4 -10
- dsp_tools/commands/ingest_xmlupload/create_resources/upload_xml.py +97 -37
- dsp_tools/commands/ingest_xmlupload/create_resources/user_information.py +2 -2
- dsp_tools/commands/ingest_xmlupload/ingest_files/ingest_files.py +9 -10
- dsp_tools/commands/ingest_xmlupload/upload_files/filechecker.py +3 -3
- dsp_tools/commands/ingest_xmlupload/upload_files/input_error.py +2 -10
- dsp_tools/commands/ingest_xmlupload/upload_files/upload_failures.py +12 -2
- dsp_tools/commands/ingest_xmlupload/upload_files/upload_files.py +8 -9
- dsp_tools/commands/resume_xmlupload/resume_xmlupload.py +18 -18
- dsp_tools/commands/start_stack.py +126 -77
- dsp_tools/commands/update_legal/CLAUDE.md +344 -0
- dsp_tools/commands/update_legal/__init__.py +0 -0
- dsp_tools/commands/update_legal/core.py +182 -0
- dsp_tools/commands/update_legal/csv_operations.py +135 -0
- dsp_tools/commands/update_legal/models.py +87 -0
- dsp_tools/commands/update_legal/xml_operations.py +247 -0
- dsp_tools/commands/validate_data/CLAUDE.md +159 -0
- dsp_tools/commands/validate_data/__init__.py +0 -0
- dsp_tools/commands/validate_data/constants.py +59 -0
- dsp_tools/commands/validate_data/mappers.py +143 -0
- dsp_tools/commands/validate_data/models/__init__.py +0 -0
- dsp_tools/commands/validate_data/models/api_responses.py +45 -0
- dsp_tools/commands/validate_data/models/input_problems.py +119 -0
- dsp_tools/commands/validate_data/models/rdf_like_data.py +117 -0
- dsp_tools/commands/validate_data/models/validation.py +106 -0
- dsp_tools/commands/validate_data/prepare_data/__init__.py +0 -0
- dsp_tools/commands/validate_data/prepare_data/get_rdf_like_data.py +296 -0
- dsp_tools/commands/validate_data/prepare_data/make_data_graph.py +91 -0
- dsp_tools/commands/validate_data/prepare_data/prepare_data.py +184 -0
- dsp_tools/commands/validate_data/process_validation_report/__init__.py +0 -0
- dsp_tools/commands/validate_data/process_validation_report/get_user_validation_message.py +358 -0
- dsp_tools/commands/validate_data/process_validation_report/query_validation_result.py +507 -0
- dsp_tools/commands/validate_data/process_validation_report/reformat_validation_results.py +150 -0
- dsp_tools/commands/validate_data/shacl_cli_validator.py +70 -0
- dsp_tools/commands/validate_data/sparql/__init__.py +0 -0
- dsp_tools/commands/{xml_validate/sparql/resource_shacl.py → validate_data/sparql/cardinality_shacl.py} +45 -47
- dsp_tools/commands/validate_data/sparql/construct_shacl.py +92 -0
- dsp_tools/commands/validate_data/sparql/legal_info_shacl.py +36 -0
- dsp_tools/commands/validate_data/sparql/value_shacl.py +357 -0
- dsp_tools/commands/validate_data/utils.py +59 -0
- dsp_tools/commands/validate_data/validate_data.py +283 -0
- dsp_tools/commands/validate_data/validation/__init__.py +0 -0
- dsp_tools/commands/validate_data/validation/check_duplicate_files.py +55 -0
- dsp_tools/commands/validate_data/validation/check_for_unknown_classes.py +67 -0
- dsp_tools/commands/validate_data/validation/get_validation_report.py +94 -0
- dsp_tools/commands/validate_data/validation/validate_ontology.py +107 -0
- dsp_tools/commands/xmlupload/CLAUDE.md +292 -0
- dsp_tools/commands/xmlupload/make_rdf_graph/__init__.py +0 -0
- dsp_tools/commands/xmlupload/make_rdf_graph/constants.py +63 -0
- dsp_tools/commands/xmlupload/make_rdf_graph/jsonld_utils.py +44 -0
- dsp_tools/commands/xmlupload/make_rdf_graph/make_file_value.py +77 -0
- dsp_tools/commands/xmlupload/make_rdf_graph/make_resource_and_values.py +114 -0
- dsp_tools/commands/xmlupload/make_rdf_graph/make_values.py +262 -0
- dsp_tools/commands/xmlupload/models/bitstream_info.py +18 -0
- dsp_tools/commands/xmlupload/models/formatted_text_value.py +0 -25
- dsp_tools/commands/xmlupload/models/ingest.py +56 -70
- dsp_tools/commands/xmlupload/models/input_problems.py +6 -14
- dsp_tools/commands/xmlupload/models/lookup_models.py +21 -0
- dsp_tools/commands/xmlupload/models/permission.py +0 -39
- dsp_tools/commands/xmlupload/models/{deserialise/xmlpermission.py → permissions_parsed.py} +2 -2
- dsp_tools/commands/xmlupload/models/processed/__init__.py +0 -0
- dsp_tools/commands/xmlupload/models/processed/file_values.py +29 -0
- dsp_tools/commands/xmlupload/models/processed/res.py +27 -0
- dsp_tools/commands/xmlupload/models/processed/values.py +101 -0
- dsp_tools/commands/xmlupload/models/rdf_models.py +26 -0
- dsp_tools/commands/xmlupload/models/upload_clients.py +3 -3
- dsp_tools/commands/xmlupload/models/upload_state.py +2 -4
- dsp_tools/commands/xmlupload/prepare_xml_input/__init__.py +0 -0
- dsp_tools/commands/xmlupload/{ark2iri.py → prepare_xml_input/ark2iri.py} +1 -1
- dsp_tools/commands/xmlupload/prepare_xml_input/get_processed_resources.py +252 -0
- dsp_tools/commands/xmlupload/{iiif_uri_validator.py → prepare_xml_input/iiif_uri_validator.py} +2 -14
- dsp_tools/commands/xmlupload/{list_client.py → prepare_xml_input/list_client.py} +15 -10
- dsp_tools/commands/xmlupload/prepare_xml_input/prepare_xml_input.py +67 -0
- dsp_tools/commands/xmlupload/prepare_xml_input/read_validate_xml_file.py +58 -0
- dsp_tools/commands/xmlupload/prepare_xml_input/transform_input_values.py +118 -0
- dsp_tools/commands/xmlupload/resource_create_client.py +7 -468
- dsp_tools/commands/xmlupload/richtext_id2iri.py +37 -0
- dsp_tools/commands/xmlupload/stash/{construct_and_analyze_graph.py → analyse_circular_reference_graph.py} +64 -157
- dsp_tools/commands/xmlupload/stash/create_info_for_graph.py +53 -0
- dsp_tools/commands/xmlupload/stash/graph_models.py +13 -8
- dsp_tools/commands/xmlupload/stash/stash_circular_references.py +48 -115
- dsp_tools/commands/xmlupload/stash/stash_models.py +4 -9
- dsp_tools/commands/xmlupload/stash/upload_stashed_resptr_props.py +34 -40
- dsp_tools/commands/xmlupload/stash/upload_stashed_xml_texts.py +98 -108
- dsp_tools/commands/xmlupload/upload_config.py +8 -0
- dsp_tools/commands/xmlupload/write_diagnostic_info.py +14 -9
- dsp_tools/commands/xmlupload/xmlupload.py +214 -192
- dsp_tools/config/__init__.py +0 -0
- dsp_tools/config/logger_config.py +69 -0
- dsp_tools/{utils → config}/warnings_config.py +4 -1
- dsp_tools/error/__init__.py +0 -0
- dsp_tools/error/custom_warnings.py +39 -0
- dsp_tools/error/exceptions.py +204 -0
- dsp_tools/error/problems.py +10 -0
- dsp_tools/error/xmllib_errors.py +20 -0
- dsp_tools/error/xmllib_warnings.py +54 -0
- dsp_tools/error/xmllib_warnings_util.py +159 -0
- dsp_tools/error/xsd_validation_error_msg.py +19 -0
- dsp_tools/legacy_models/__init__.py +0 -0
- dsp_tools/{models → legacy_models}/datetimestamp.py +7 -7
- dsp_tools/{models → legacy_models}/langstring.py +1 -1
- dsp_tools/{models → legacy_models}/projectContext.py +4 -4
- dsp_tools/resources/schema/data.xsd +108 -83
- dsp_tools/resources/schema/lists-only.json +4 -23
- dsp_tools/resources/schema/project.json +80 -35
- dsp_tools/resources/schema/properties-only.json +1 -4
- dsp_tools/resources/start-stack/docker-compose.override-host.j2 +11 -0
- dsp_tools/resources/start-stack/docker-compose.yml +34 -30
- dsp_tools/resources/start-stack/dsp-app-config.json +45 -0
- dsp_tools/resources/start-stack/dsp-app-config.override-host.j2 +26 -0
- dsp_tools/resources/validate_data/api-shapes-resource-cardinalities.ttl +191 -0
- dsp_tools/resources/validate_data/api-shapes.ttl +804 -0
- dsp_tools/resources/validate_data/shacl-cli-image.yml +4 -0
- dsp_tools/resources/validate_data/validate-ontology.ttl +99 -0
- dsp_tools/utils/ansi_colors.py +32 -0
- dsp_tools/utils/data_formats/__init__.py +0 -0
- dsp_tools/utils/{date_util.py → data_formats/date_util.py} +13 -1
- dsp_tools/utils/data_formats/iri_util.py +30 -0
- dsp_tools/utils/{shared.py → data_formats/shared.py} +1 -35
- dsp_tools/utils/{uri_util.py → data_formats/uri_util.py} +12 -2
- dsp_tools/utils/fuseki_bloating.py +63 -0
- dsp_tools/utils/json_parsing.py +22 -0
- dsp_tools/utils/rdf_constants.py +42 -0
- dsp_tools/utils/rdflib_utils.py +10 -0
- dsp_tools/utils/replace_id_with_iri.py +66 -0
- dsp_tools/utils/request_utils.py +238 -0
- dsp_tools/utils/xml_parsing/__init__.py +0 -0
- dsp_tools/utils/xml_parsing/get_lookups.py +32 -0
- dsp_tools/utils/xml_parsing/get_parsed_resources.py +325 -0
- dsp_tools/utils/xml_parsing/models/__init__.py +0 -0
- dsp_tools/utils/xml_parsing/models/parsed_resource.py +76 -0
- dsp_tools/utils/xml_parsing/parse_clean_validate_xml.py +137 -0
- dsp_tools/xmllib/CLAUDE.md +302 -0
- dsp_tools/xmllib/__init__.py +49 -0
- dsp_tools/xmllib/general_functions.py +877 -0
- dsp_tools/xmllib/internal/__init__.py +0 -0
- dsp_tools/xmllib/internal/checkers.py +162 -0
- dsp_tools/xmllib/internal/circumvent_circular_imports.py +36 -0
- dsp_tools/xmllib/internal/constants.py +46 -0
- dsp_tools/xmllib/internal/input_converters.py +155 -0
- dsp_tools/xmllib/internal/serialise_file_value.py +57 -0
- dsp_tools/xmllib/internal/serialise_resource.py +177 -0
- dsp_tools/xmllib/internal/serialise_values.py +152 -0
- dsp_tools/xmllib/internal/type_aliases.py +11 -0
- dsp_tools/xmllib/models/config_options.py +28 -0
- dsp_tools/xmllib/models/date_formats.py +48 -0
- dsp_tools/xmllib/models/dsp_base_resources.py +1380 -400
- dsp_tools/xmllib/models/internal/__init__.py +0 -0
- dsp_tools/xmllib/models/internal/file_values.py +172 -0
- dsp_tools/xmllib/models/internal/geometry.py +162 -0
- dsp_tools/xmllib/models/{migration_metadata.py → internal/migration_metadata.py} +14 -10
- dsp_tools/xmllib/models/internal/serialise_permissions.py +66 -0
- dsp_tools/xmllib/models/internal/values.py +342 -0
- dsp_tools/xmllib/models/licenses/__init__.py +0 -0
- dsp_tools/xmllib/models/licenses/other.py +59 -0
- dsp_tools/xmllib/models/licenses/recommended.py +107 -0
- dsp_tools/xmllib/models/permissions.py +41 -0
- dsp_tools/xmllib/models/res.py +1782 -0
- dsp_tools/xmllib/models/root.py +313 -26
- dsp_tools/xmllib/value_checkers.py +310 -47
- dsp_tools/xmllib/value_converters.py +765 -8
- dsp_tools-18.3.0.post13.dist-info/METADATA +90 -0
- dsp_tools-18.3.0.post13.dist-info/RECORD +286 -0
- dsp_tools-18.3.0.post13.dist-info/WHEEL +4 -0
- {dsp_tools-9.1.0.post11.dist-info → dsp_tools-18.3.0.post13.dist-info}/entry_points.txt +1 -0
- dsp_tools/commands/project/create/project_create.py +0 -1107
- dsp_tools/commands/project/create/project_create_lists.py +0 -204
- dsp_tools/commands/project/create/project_validate.py +0 -453
- dsp_tools/commands/project/models/project_definition.py +0 -12
- dsp_tools/commands/rosetta.py +0 -124
- dsp_tools/commands/template.py +0 -30
- dsp_tools/commands/xml_validate/api_connection.py +0 -122
- dsp_tools/commands/xml_validate/deserialise_input.py +0 -135
- dsp_tools/commands/xml_validate/make_data_rdf.py +0 -193
- dsp_tools/commands/xml_validate/models/data_deserialised.py +0 -108
- dsp_tools/commands/xml_validate/models/data_rdf.py +0 -214
- dsp_tools/commands/xml_validate/models/input_problems.py +0 -191
- dsp_tools/commands/xml_validate/models/validation.py +0 -29
- dsp_tools/commands/xml_validate/reformat_validaton_result.py +0 -89
- dsp_tools/commands/xml_validate/sparql/construct_shapes.py +0 -16
- dsp_tools/commands/xml_validate/xml_validate.py +0 -151
- dsp_tools/commands/xmlupload/check_consistency_with_ontology.py +0 -253
- dsp_tools/commands/xmlupload/models/deserialise/deserialise_value.py +0 -236
- dsp_tools/commands/xmlupload/models/deserialise/xmlresource.py +0 -171
- dsp_tools/commands/xmlupload/models/namespace_context.py +0 -39
- dsp_tools/commands/xmlupload/models/ontology_lookup_models.py +0 -161
- dsp_tools/commands/xmlupload/models/ontology_problem_models.py +0 -178
- dsp_tools/commands/xmlupload/models/serialise/jsonld_serialiser.py +0 -40
- dsp_tools/commands/xmlupload/models/serialise/serialise_value.py +0 -51
- dsp_tools/commands/xmlupload/ontology_client.py +0 -92
- dsp_tools/commands/xmlupload/project_client.py +0 -91
- dsp_tools/commands/xmlupload/read_validate_xml_file.py +0 -99
- dsp_tools/models/custom_warnings.py +0 -31
- dsp_tools/models/exceptions.py +0 -90
- dsp_tools/resources/0100-template-repo/template.json +0 -45
- dsp_tools/resources/0100-template-repo/template.xml +0 -27
- dsp_tools/resources/start-stack/docker-compose-validation.yml +0 -5
- dsp_tools/resources/start-stack/start-stack-config.yml +0 -4
- dsp_tools/resources/xml_validate/api-shapes.ttl +0 -411
- dsp_tools/resources/xml_validate/replace_namespace.xslt +0 -61
- dsp_tools/utils/connection_live.py +0 -383
- dsp_tools/utils/iri_util.py +0 -14
- dsp_tools/utils/logger_config.py +0 -41
- dsp_tools/utils/set_encoder.py +0 -20
- dsp_tools/utils/xml_utils.py +0 -145
- dsp_tools/utils/xml_validation.py +0 -197
- dsp_tools/utils/xml_validation_models.py +0 -68
- dsp_tools/xmllib/models/file_values.py +0 -78
- dsp_tools/xmllib/models/resource.py +0 -415
- dsp_tools/xmllib/models/values.py +0 -428
- dsp_tools-9.1.0.post11.dist-info/METADATA +0 -130
- dsp_tools-9.1.0.post11.dist-info/RECORD +0 -167
- dsp_tools-9.1.0.post11.dist-info/WHEEL +0 -4
- dsp_tools-9.1.0.post11.dist-info/licenses/LICENSE +0 -674
- /dsp_tools/{commands/excel2json/new_lists → clients}/__init__.py +0 -0
- /dsp_tools/commands/{excel2json/new_lists/models → create}/__init__.py +0 -0
- /dsp_tools/commands/{project → create/create_on_server}/__init__.py +0 -0
- /dsp_tools/commands/{project/create → create/models}/__init__.py +0 -0
- /dsp_tools/commands/{project/models → create/parsing}/__init__.py +0 -0
- /dsp_tools/commands/{xml_validate → create/serialisation}/__init__.py +0 -0
- /dsp_tools/commands/{xml_validate/models → excel2json/lists}/__init__.py +0 -0
- /dsp_tools/commands/{xml_validate/sparql → excel2json/lists/models}/__init__.py +0 -0
- /dsp_tools/commands/excel2json/{new_lists → lists}/models/deserialise.py +0 -0
- /dsp_tools/commands/{xmlupload/models/deserialise → get}/__init__.py +0 -0
- /dsp_tools/commands/{xmlupload/models/serialise → get/legacy_models}/__init__.py +0 -0
- /dsp_tools/commands/{project/models → get/legacy_models}/helpers.py +0 -0
- /dsp_tools/{models → commands/get/models}/__init__.py +0 -0
|
@@ -1,24 +1,102 @@
|
|
|
1
|
-
import json
|
|
2
1
|
from typing import Any
|
|
3
2
|
|
|
4
3
|
import pandas as pd
|
|
5
4
|
import regex
|
|
6
5
|
|
|
6
|
+
from dsp_tools.error.xmllib_warnings import MessageInfo
|
|
7
|
+
from dsp_tools.error.xmllib_warnings_util import emit_xmllib_input_warning
|
|
8
|
+
from dsp_tools.xmllib.internal.circumvent_circular_imports import parse_richtext_as_xml
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
def is_nonempty_value(value: Any) -> bool:
|
|
12
|
+
"""
|
|
13
|
+
Check if a value is not None-like
|
|
14
|
+
or that its string representation contains at least one of the following characters:
|
|
15
|
+
|
|
16
|
+
- ``\\p{S}`` = symbols and special characters
|
|
17
|
+
- ``\\p{P}`` = punctuation
|
|
18
|
+
- ``\\w`` = all Unicode letters, numbers, and _
|
|
19
|
+
|
|
20
|
+
If the value is a collection (i.e. list, tuple, set or dictionary)
|
|
21
|
+
all the elements must be non-empty to return True.
|
|
22
|
+
|
|
23
|
+
Args:
|
|
24
|
+
value: value of any type
|
|
25
|
+
|
|
26
|
+
Returns:
|
|
27
|
+
True if the value is not None-like and contains at least one of the above-mentioned characters
|
|
28
|
+
|
|
29
|
+
Examples:
|
|
30
|
+
```python
|
|
31
|
+
# True values:
|
|
32
|
+
assert xmllib.is_nonempty_value("word") == True
|
|
33
|
+
assert xmllib.is_nonempty_value(["word"]) == True
|
|
34
|
+
assert xmllib.is_nonempty_value("None") == True
|
|
35
|
+
assert xmllib.is_nonempty_value("-") == True
|
|
36
|
+
assert xmllib.is_nonempty_value(0) == True
|
|
37
|
+
assert xmllib.is_nonempty_value(1) == True
|
|
38
|
+
assert xmllib.is_nonempty_value("0") == True
|
|
39
|
+
assert xmllib.is_nonempty_value("1") == True
|
|
40
|
+
assert xmllib.is_nonempty_value(True) == True
|
|
41
|
+
assert xmllib.is_nonempty_value(False) == True
|
|
42
|
+
assert xmllib.is_nonempty_value("עִבְרִית") == True
|
|
43
|
+
|
|
44
|
+
# False values:
|
|
45
|
+
assert xmllib.is_nonempty_value(pd.NA) == False
|
|
46
|
+
assert xmllib.is_nonempty_value(None) == False
|
|
47
|
+
assert xmllib.is_nonempty_value("") == False
|
|
48
|
+
assert xmllib.is_nonempty_value(["", "some-content"]) == False
|
|
49
|
+
assert xmllib.is_nonempty_value({"dict-key": ""}) == False
|
|
50
|
+
assert xmllib.is_nonempty_value(" ") == False
|
|
51
|
+
assert xmllib.is_nonempty_value("\\n") == False
|
|
52
|
+
```
|
|
53
|
+
"""
|
|
54
|
+
if isinstance(value, (tuple, list, set)):
|
|
55
|
+
all_vals = [is_nonempty_value(v) for v in value]
|
|
56
|
+
return all(all_vals)
|
|
57
|
+
if isinstance(value, dict):
|
|
58
|
+
all_vals = []
|
|
59
|
+
for k, v in value.items():
|
|
60
|
+
all_vals.append(is_nonempty_value(k))
|
|
61
|
+
all_vals.append(is_nonempty_value(v))
|
|
62
|
+
return all(all_vals)
|
|
63
|
+
if pd.isna(value):
|
|
64
|
+
return False
|
|
65
|
+
if regex.search(r"[\p{S}\p{P}\w]", str(value), flags=regex.UNICODE):
|
|
66
|
+
return True
|
|
67
|
+
return False
|
|
68
|
+
|
|
7
69
|
|
|
8
70
|
def is_bool_like(value: Any) -> bool:
|
|
9
71
|
"""
|
|
10
72
|
Checks if a value is a bool or can be converted into a bool.
|
|
73
|
+
It is case-insensitive, meaning that the words can also be capitalised.
|
|
74
|
+
|
|
75
|
+
Accepted values:
|
|
76
|
+
- `false`, `0`, `0.0`, `no`, `non`, `nein` -> `False`
|
|
77
|
+
- `true`, `1`, `1.0`, `yes`, `oui`, `ja` -> `True`
|
|
11
78
|
|
|
12
79
|
Args:
|
|
13
80
|
value: value to check
|
|
14
81
|
|
|
15
82
|
Returns:
|
|
16
83
|
True if it conforms
|
|
84
|
+
|
|
85
|
+
Examples:
|
|
86
|
+
```python
|
|
87
|
+
result = xmllib.is_bool_like("yes")
|
|
88
|
+
# result == True
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
```python
|
|
92
|
+
result = xmllib.is_bool_like("not like a bool")
|
|
93
|
+
# result == False
|
|
94
|
+
```
|
|
17
95
|
"""
|
|
18
96
|
value = str(value).lower().strip()
|
|
19
|
-
if value in ("false", "0", "0.0", "no"):
|
|
97
|
+
if value in ("false", "0", "0.0", "no", "non", "nein"):
|
|
20
98
|
return True
|
|
21
|
-
elif value in ("true", "1", "1.0", "yes"):
|
|
99
|
+
elif value in ("true", "1", "1.0", "yes", "oui", "ja"):
|
|
22
100
|
return True
|
|
23
101
|
return False
|
|
24
102
|
|
|
@@ -32,8 +110,18 @@ def is_color(value: Any) -> bool:
|
|
|
32
110
|
|
|
33
111
|
Returns:
|
|
34
112
|
True if it conforms
|
|
35
|
-
"""
|
|
36
113
|
|
|
114
|
+
Examples:
|
|
115
|
+
```python
|
|
116
|
+
result = xmllib.is_color("#00ff66")
|
|
117
|
+
# result == True
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
```python
|
|
121
|
+
result = xmllib.is_color("not a color")
|
|
122
|
+
# result == False
|
|
123
|
+
```
|
|
124
|
+
"""
|
|
37
125
|
return bool(regex.search(r"^#[0-9a-f]{6}$", str(value).strip(), flags=regex.IGNORECASE))
|
|
38
126
|
|
|
39
127
|
|
|
@@ -46,18 +134,34 @@ def is_date(value: Any) -> bool:
|
|
|
46
134
|
|
|
47
135
|
Returns:
|
|
48
136
|
True if it conforms
|
|
49
|
-
"""
|
|
50
137
|
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
138
|
+
Examples:
|
|
139
|
+
```python
|
|
140
|
+
result = xmllib.is_date("GREGORIAN:CE:2014-01-31:CE:2014-01-31")
|
|
141
|
+
# result == True
|
|
142
|
+
```
|
|
143
|
+
|
|
144
|
+
```python
|
|
145
|
+
result = xmllib.is_date("not a date")
|
|
146
|
+
# result == False
|
|
147
|
+
```
|
|
148
|
+
"""
|
|
149
|
+
calendar_optional = r"(?:(GREGORIAN|JULIAN|ISLAMIC):)?"
|
|
150
|
+
first_era_optional = r"(?:(CE|BCE|BC|AD):)?"
|
|
151
|
+
second_area_optional = r"(?::(CE|BCE|BC|AD))?"
|
|
54
152
|
date = r"\d{1,4}(?:-\d{1,2}){0,2}"
|
|
55
153
|
date_mandatory = rf"({date})"
|
|
56
154
|
date_optional = rf"(:{date})?"
|
|
57
155
|
full_date_pattern = (
|
|
58
156
|
rf"^{calendar_optional}{first_era_optional}{date_mandatory}{second_area_optional}{date_optional}$"
|
|
59
157
|
)
|
|
60
|
-
|
|
158
|
+
found = regex.search(full_date_pattern, str(value))
|
|
159
|
+
if not found:
|
|
160
|
+
return False
|
|
161
|
+
if found.group(1) == "ISLAMIC" and (found.group(2) or found.group(4)):
|
|
162
|
+
# eras are not supported yet for the islamic calendar
|
|
163
|
+
return False
|
|
164
|
+
return True
|
|
61
165
|
|
|
62
166
|
|
|
63
167
|
def is_geoname(value: Any) -> bool:
|
|
@@ -69,6 +173,17 @@ def is_geoname(value: Any) -> bool:
|
|
|
69
173
|
|
|
70
174
|
Returns:
|
|
71
175
|
True if it conforms
|
|
176
|
+
|
|
177
|
+
Examples:
|
|
178
|
+
```python
|
|
179
|
+
result = xmllib.is_geoname("8879000")
|
|
180
|
+
# result == True
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
```python
|
|
184
|
+
result = xmllib.is_geoname("not a geoname code")
|
|
185
|
+
# result == False
|
|
186
|
+
```
|
|
72
187
|
"""
|
|
73
188
|
return is_integer(value)
|
|
74
189
|
|
|
@@ -82,13 +197,38 @@ def is_decimal(value: Any) -> bool:
|
|
|
82
197
|
|
|
83
198
|
Returns:
|
|
84
199
|
True if conforms to the above-mentioned criteria.
|
|
200
|
+
|
|
201
|
+
Examples:
|
|
202
|
+
```python
|
|
203
|
+
result = xmllib.is_decimal("0.1")
|
|
204
|
+
# result == True
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
```python
|
|
208
|
+
# because this is equivalent to 9.0 it is accepted
|
|
209
|
+
|
|
210
|
+
result = xmllib.is_decimal(9)
|
|
211
|
+
# result == True
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
```python
|
|
215
|
+
result = xmllib.is_decimal("not a decimal")
|
|
216
|
+
# result == False
|
|
217
|
+
```
|
|
85
218
|
"""
|
|
86
|
-
if
|
|
87
|
-
|
|
219
|
+
if pd.isna(value):
|
|
220
|
+
return False
|
|
221
|
+
|
|
222
|
+
match value:
|
|
223
|
+
case bool():
|
|
224
|
+
return False
|
|
225
|
+
case int() | float():
|
|
88
226
|
return True
|
|
89
|
-
|
|
227
|
+
try:
|
|
228
|
+
float(value)
|
|
90
229
|
return True
|
|
91
|
-
|
|
230
|
+
except ValueError:
|
|
231
|
+
return False
|
|
92
232
|
|
|
93
233
|
|
|
94
234
|
def is_integer(value: Any) -> bool:
|
|
@@ -100,28 +240,104 @@ def is_integer(value: Any) -> bool:
|
|
|
100
240
|
|
|
101
241
|
Returns:
|
|
102
242
|
True if conforms to the above-mentioned criteria.
|
|
243
|
+
|
|
244
|
+
Examples:
|
|
245
|
+
```python
|
|
246
|
+
result = xmllib.is_integer("1")
|
|
247
|
+
# result == True
|
|
248
|
+
```
|
|
249
|
+
|
|
250
|
+
```python
|
|
251
|
+
result = xmllib.is_integer(9.1)
|
|
252
|
+
# result == False
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
```python
|
|
256
|
+
result = xmllib.is_integer("not an integer")
|
|
257
|
+
# result == False
|
|
258
|
+
```
|
|
103
259
|
"""
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
260
|
+
match value:
|
|
261
|
+
case bool():
|
|
262
|
+
return False
|
|
263
|
+
case int():
|
|
264
|
+
return True
|
|
265
|
+
case str():
|
|
266
|
+
return bool(regex.search(r"^\d+$", value))
|
|
267
|
+
case _:
|
|
268
|
+
return False
|
|
107
269
|
|
|
108
270
|
|
|
109
|
-
def
|
|
271
|
+
def is_link_value(value: Any) -> bool:
|
|
110
272
|
"""
|
|
111
|
-
|
|
273
|
+
Check if a value is a valid internal ID of a resource (xsd:ID) or a valid internal DSP IRI.
|
|
274
|
+
Both of these values are allowed in LinkValues.
|
|
112
275
|
|
|
113
276
|
Args:
|
|
114
|
-
value:
|
|
277
|
+
value: the target ID of a LinkValue
|
|
115
278
|
|
|
116
279
|
Returns:
|
|
117
|
-
True if it is a
|
|
280
|
+
True if it is a permissible value.
|
|
281
|
+
|
|
282
|
+
Examples:
|
|
283
|
+
```python
|
|
284
|
+
result = xmllib.is_link_value("1_must_not_start_with_number")
|
|
285
|
+
# result == False
|
|
286
|
+
```
|
|
287
|
+
|
|
288
|
+
```python
|
|
289
|
+
result = xmllib.is_link_value("characters|not|allowed")
|
|
290
|
+
# result == False
|
|
291
|
+
```
|
|
292
|
+
|
|
293
|
+
```python
|
|
294
|
+
result = xmllib.is_link_value("resource_id_1")
|
|
295
|
+
# result == True
|
|
296
|
+
```
|
|
297
|
+
|
|
298
|
+
```python
|
|
299
|
+
result = xmllib.is_link_value("http://rdfh.ch/4123/54SYvWF0QUW6a")
|
|
300
|
+
# result == True
|
|
301
|
+
```
|
|
118
302
|
"""
|
|
119
|
-
if
|
|
120
|
-
return
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
303
|
+
if is_valid_resource_id(value):
|
|
304
|
+
return True
|
|
305
|
+
return is_dsp_iri(value)
|
|
306
|
+
|
|
307
|
+
|
|
308
|
+
def is_valid_resource_id(value: Any) -> bool:
|
|
309
|
+
"""
|
|
310
|
+
Check if a value is a valid internal ID of a resource (xsd:ID).
|
|
311
|
+
|
|
312
|
+
Args:
|
|
313
|
+
value: the ID of a Resource
|
|
314
|
+
|
|
315
|
+
Returns:
|
|
316
|
+
True if it is a permissible value.
|
|
317
|
+
|
|
318
|
+
Examples:
|
|
319
|
+
```python
|
|
320
|
+
result = xmllib.is_valid_resource_id("1_must_not_start_with_number")
|
|
321
|
+
# result == False
|
|
322
|
+
```
|
|
323
|
+
|
|
324
|
+
```python
|
|
325
|
+
result = xmllib.is_valid_resource_id("characters|not|allowed")
|
|
326
|
+
# result == False
|
|
327
|
+
```
|
|
328
|
+
|
|
329
|
+
```python
|
|
330
|
+
result = xmllib.is_valid_resource_id("resource_id_1")
|
|
331
|
+
# result == True
|
|
332
|
+
```
|
|
333
|
+
"""
|
|
334
|
+
allowed_letters = "a-zA-Zàáâäèéêëìíîïòóôöùúûüçñß_"
|
|
335
|
+
if is_nonempty_value(value):
|
|
336
|
+
# None, etc. would not be recognised as invalid since it is converted into a string.
|
|
337
|
+
return bool(
|
|
338
|
+
regex.search(rf"^[{allowed_letters}][{allowed_letters}\d.\-]*$", str(value)),
|
|
339
|
+
)
|
|
340
|
+
return False
|
|
125
341
|
|
|
126
342
|
|
|
127
343
|
def is_timestamp(value: Any) -> bool:
|
|
@@ -133,39 +349,86 @@ def is_timestamp(value: Any) -> bool:
|
|
|
133
349
|
|
|
134
350
|
Returns:
|
|
135
351
|
True if it conforms
|
|
352
|
+
|
|
353
|
+
Examples:
|
|
354
|
+
```python
|
|
355
|
+
result = xmllib.is_timestamp("2019-10-23T13:45:12Z")
|
|
356
|
+
# result == True
|
|
357
|
+
```
|
|
358
|
+
|
|
359
|
+
```python
|
|
360
|
+
result = xmllib.is_timestamp("not a time stamp")
|
|
361
|
+
# result == False
|
|
362
|
+
```
|
|
136
363
|
"""
|
|
137
|
-
validation_regex = r"^\d{4}-[0-1]\d-[0-3]\dT[0-2]\d:[0-5]\d:[0-5]\d(
|
|
364
|
+
validation_regex = r"^\d{4}-[0-1]\d-[0-3]\dT[0-2]\d:[0-5]\d:[0-5]\d(\.\d{1,12})?(Z|[+-][0-1]\d:[0-5]\d)$"
|
|
138
365
|
return bool(regex.search(validation_regex, str(value)))
|
|
139
366
|
|
|
140
367
|
|
|
141
|
-
def
|
|
368
|
+
def is_dsp_iri(value: Any) -> bool:
|
|
142
369
|
"""
|
|
143
|
-
|
|
370
|
+
Check if a value is a valid internal DSP IRI.
|
|
144
371
|
|
|
145
372
|
Args:
|
|
146
|
-
value:
|
|
373
|
+
value: IRI
|
|
147
374
|
|
|
148
375
|
Returns:
|
|
149
|
-
|
|
376
|
+
True if it is valid, else false
|
|
377
|
+
|
|
378
|
+
Examples:
|
|
379
|
+
```python
|
|
380
|
+
result = xmllib.is_dsp_iri("http://rdfh.ch/4123/54SYvWF0QUW6a")
|
|
381
|
+
# result == True
|
|
382
|
+
```
|
|
383
|
+
|
|
384
|
+
```python
|
|
385
|
+
result = xmllib.is_dsp_iri("http://dbpedia.org/resource/Internationalized_Resource_Identifier")
|
|
386
|
+
# result == False
|
|
387
|
+
```
|
|
150
388
|
"""
|
|
151
|
-
|
|
152
|
-
try:
|
|
153
|
-
value_as_dict = json.loads(str(value))
|
|
154
|
-
if value_as_dict["type"] not in ["rectangle", "circle", "polygon"]:
|
|
155
|
-
msg += "\nThe 'type' of the JSON geometry object must be 'rectangle', 'circle', or 'polygon'."
|
|
156
|
-
|
|
157
|
-
if not isinstance(value_as_dict["points"], list):
|
|
158
|
-
msg += "\nThe 'points' of the JSON geometry object must be a list of points."
|
|
159
|
-
except (json.JSONDecodeError, TypeError, IndexError, KeyError, AssertionError):
|
|
160
|
-
msg += f"\n'{value}' is not a valid JSON geometry object."
|
|
161
|
-
return msg
|
|
389
|
+
return bool(regex.search(r"^http://rdfh\.ch/[\dA-F]{4}/", str(value)))
|
|
162
390
|
|
|
163
391
|
|
|
164
|
-
def
|
|
165
|
-
"""
|
|
166
|
-
|
|
392
|
+
def is_dsp_ark(value: Any) -> bool:
|
|
393
|
+
"""
|
|
394
|
+
Checks if a value is a valid ARK.
|
|
167
395
|
|
|
396
|
+
Args:
|
|
397
|
+
value: ARK
|
|
168
398
|
|
|
169
|
-
|
|
170
|
-
|
|
399
|
+
Returns:
|
|
400
|
+
True if it is valid, else false
|
|
401
|
+
|
|
402
|
+
Examples:
|
|
403
|
+
```python
|
|
404
|
+
result = xmllib.is_dsp_ark("ark:/72163/4123-31ec6eab334-a.2022829")
|
|
405
|
+
# result == True
|
|
406
|
+
```
|
|
407
|
+
|
|
408
|
+
```python
|
|
409
|
+
result = xmllib.is_dsp_ark("http://rdfh.ch/4123/54SYvWF0QUW6a")
|
|
410
|
+
# result == False
|
|
411
|
+
```
|
|
412
|
+
"""
|
|
171
413
|
return bool(regex.search(r"^ark:/", str(value)))
|
|
414
|
+
|
|
415
|
+
|
|
416
|
+
def check_richtext_syntax(richtext: str) -> None:
|
|
417
|
+
"""
|
|
418
|
+
DSP richtexts must be convertible into valid XML.
|
|
419
|
+
This checker escapes the reserved characters `<`, `>` and `&`,
|
|
420
|
+
but only if they are not part of a standard standoff tag or escape sequence.
|
|
421
|
+
Then, it tries to parse the resulting XML.
|
|
422
|
+
|
|
423
|
+
Note: Only DSP standard standoff tags are allowed in richtexts. They are documented
|
|
424
|
+
[here](https://docs.dasch.swiss/latest/DSP-API/03-endpoints/api-v2/text/standard-standoff/).
|
|
425
|
+
|
|
426
|
+
Args:
|
|
427
|
+
richtext: richtext to check
|
|
428
|
+
|
|
429
|
+
Warns:
|
|
430
|
+
XmllibInputWarning: if the input contains XML syntax problems
|
|
431
|
+
"""
|
|
432
|
+
result = parse_richtext_as_xml(richtext)
|
|
433
|
+
if isinstance(result, MessageInfo):
|
|
434
|
+
emit_xmllib_input_warning(result)
|