diff --git a/openml/datasets/functions.py b/openml/datasets/functions.py index a9840cc82..746285650 100644 --- a/openml/datasets/functions.py +++ b/openml/datasets/functions.py @@ -873,6 +873,47 @@ def fork_dataset(data_id: int) -> int: return int(data_id) +def _topic_add_dataset(data_id: int, topic: str): + """ + Adds a topic for a dataset. + This API is not available for all OpenML users and is accessible only by admins. + Parameters + ---------- + data_id : int + id of the dataset for which the topic needs to be added + topic : str + Topic to be added for the dataset + """ + if not isinstance(data_id, int): + raise TypeError("`data_id` must be of type `int`, not {}.".format(type(data_id))) + form_data = {"data_id": data_id, "topic": topic} + result_xml = openml._api_calls._perform_api_call("data/topicadd", "post", data=form_data) + result = xmltodict.parse(result_xml) + data_id = result["oml:data_topic"]["oml:id"] + return int(data_id) + + +def _topic_delete_dataset(data_id: int, topic: str): + """ + Removes a topic from a dataset. + This API is not available for all OpenML users and is accessible only by admins. + Parameters + ---------- + data_id : int + id of the dataset to be forked + topic : str + Topic to be deleted + + """ + if not isinstance(data_id, int): + raise TypeError("`data_id` must be of type `int`, not {}.".format(type(data_id))) + form_data = {"data_id": data_id, "topic": topic} + result_xml = openml._api_calls._perform_api_call("data/topicdelete", "post", data=form_data) + result = xmltodict.parse(result_xml) + data_id = result["oml:data_topic"]["oml:id"] + return int(data_id) + + def _get_dataset_description(did_cache_dir, dataset_id): """Get the dataset description as xml dictionary. diff --git a/tests/test_datasets/test_dataset_functions.py b/tests/test_datasets/test_dataset_functions.py index 32f4575a5..ec9dd6c53 100644 --- a/tests/test_datasets/test_dataset_functions.py +++ b/tests/test_datasets/test_dataset_functions.py @@ -37,6 +37,8 @@ _get_online_dataset_format, DATASETS_CACHE_DIR_NAME, _get_dataset_parquet, + _topic_add_dataset, + _topic_delete_dataset, ) from openml.datasets import fork_dataset, edit_dataset from openml.tasks import TaskType, create_task @@ -911,6 +913,24 @@ def test_get_online_dataset_arff(self): "ARFF files are not equal", ) + def test_topic_api_error(self): + # Check server exception when non-admin accessses apis + self.assertRaisesRegex( + OpenMLServerException, + "Topic can only be added/removed by admin.", + _topic_add_dataset, + data_id=31, + topic="business", + ) + # Check server exception when non-admin accessses apis + self.assertRaisesRegex( + OpenMLServerException, + "Topic can only be added/removed by admin.", + _topic_delete_dataset, + data_id=31, + topic="business", + ) + def test_get_online_dataset_format(self): # Phoneme dataset