diff --git a/apiserver/config/__init__.py b/apiserver/config/__init__.py new file mode 100644 index 0000000000000000000000000000000000000000..094d3cd993c1d36caf251bfc714135cc52f3fa75 --- /dev/null +++ b/apiserver/config/__init__.py @@ -0,0 +1 @@ +from .settings import Settings \ No newline at end of file diff --git a/apiserver/config/config.env b/apiserver/config/config.env new file mode 100644 index 0000000000000000000000000000000000000000..93c325d208f31ed20ee38c6a032d0a4cc61ff9b5 --- /dev/null +++ b/apiserver/config/config.env @@ -0,0 +1,3 @@ +DATACATALOG_APISERVER_HOST="0.0.0.0", +DATACATALOG_APISERVER_PORT=80 +DATACATALOG_APISERVER_JSON_STORAGE_PATH="./app/data" \ No newline at end of file diff --git a/apiserver/config/settings.py b/apiserver/config/settings.py new file mode 100644 index 0000000000000000000000000000000000000000..4c1559a3a7ef003f36702f45752d0c1550e8b1d9 --- /dev/null +++ b/apiserver/config/settings.py @@ -0,0 +1,14 @@ +from pydantic import BaseSettings + +DEFAULT_JSON_FILEPATH: str = "./app/data" + +## Additional Settings can be made available by adding them as properties to this class +# At launch they will be read from environment variables (case-INsensitive) + +class Settings(BaseSettings): + datacatalog_apiserver_host: str = "0.0.0.0" + datacatalog_apiserver_port: int = 80 + datacatalog_apiserver_json_storage_path: str = DEFAULT_JSON_FILEPATH + + class Config: + env_file = "config.env" \ No newline at end of file diff --git a/apiserver/main.py b/apiserver/main.py index 91fd2b513c9a8475664edf344e1b5f370ee580fa..64b30d01719f5061c37b27873d45e4d413c36aa8 100644 --- a/apiserver/main.py +++ b/apiserver/main.py @@ -7,18 +7,22 @@ from fastapi import HTTPException from pydantic import BaseModel from .storage import JsonFileStorageAdapter - from .storage import AbstractLocationDataStorageAdapter from .storage import LocationData from .storage import LocationDataType +from .config import Settings + from enum import Enum + +settings = Settings() + app = FastAPI( title="API-Server for the Data Catalogue" ) -adapter: AbstractLocationDataStorageAdapter = JsonFileStorageAdapter() +adapter: AbstractLocationDataStorageAdapter = JsonFileStorageAdapter(settings) #### A NOTE ON IDS # the id of a dataset is not yet defined, it could be simply generated, it could be based on some hash of the metadata or simple be the name, which would then need to be enforced to be unique @@ -53,7 +57,17 @@ def get_specific_dataset(location_data_type : LocationDataType, dataset_id: str) # update the information about a specific dataset, identified by id @app.put("/{location_data_type}/{dataset_id}") def update_specific_dataset(location_data_type : LocationDataType, dataset_id: str, dataset : LocationData): + usr: str = "testuser" try: return adapter.updateDetails(location_data_type, dataset_id, dataset, usr) except FileNotFoundError: raise HTTPException(status_code=404, detail='The provided id does not exist for this datatype.') + +# delete a specific dataset +@app.delete("/{location_data_type}/{dataset_id}") +def delete_specific_dataset(location_data_type : LocationDataType, dataset_id: str): + usr: str = "testuser" + try: + return adapter.delete(location_data_type, dataset_id, usr) + except FileNotFoundError: + raise HTTPException(status_code=404, detail='The provided id does not exist for this datatype.') \ No newline at end of file diff --git a/apiserver/storage/JsonFileStorageAdapter.py b/apiserver/storage/JsonFileStorageAdapter.py index 97ecef81240e2ce1d46b567745cdc5e1f275b853..55f7aaae61eb0224dfe27baaa90fdacb66885226 100644 --- a/apiserver/storage/JsonFileStorageAdapter.py +++ b/apiserver/storage/JsonFileStorageAdapter.py @@ -4,9 +4,9 @@ import uuid from .LocationStorage import AbstractLocationDataStorageAdapter, LocationData, LocationDataType -from typing import List +from apiserver.config import Settings -DEFAULT_JSON_FILEPATH: str = "./app/data" +from typing import List class StoredData: actualData: LocationData @@ -23,9 +23,9 @@ class StoredData: class JsonFileStorageAdapter(AbstractLocationDataStorageAdapter): data_dir: str - def __init__(self, data_directory: str = DEFAULT_JSON_FILEPATH): + def __init__(self, settings: Settings): AbstractLocationDataStorageAdapter.__init__(self) - self.data_dir = data_directory + self.data_dir = settings.datacatalog_apiserver_json_storage_path if not (os.path.exists(self.data_dir) and os.path.isdir(self.data_dir)): raise Exception('Data Directory \"' + self.data_dir + '\" does not exist.') @@ -77,17 +77,20 @@ class JsonFileStorageAdapter(AbstractLocationDataStorageAdapter): raise FileNotFoundError('The requested Object does not exist.') toStore = StoredData() + toStore.actualData = data # get permissions from old file with open(fullpath) as file: - data = json.load(file) - toStore.users = data['users'] + old_data = json.load(file) + toStore.users = old_data['users'] - toStore.actualData = data with open(fullpath, 'w') as file: json.dump(toStore.toDict(), file) return {id : data} + def delete(self, type:LocationDataType, id:str, usr: str): + pass + def getOwner(self, type: LocationDataType, id: str): raise NotImplementedError() diff --git a/apiserver/storage/LocationStorage.py b/apiserver/storage/LocationStorage.py index d80c07117f2fd2b60cf9f7fed5772b47b88373b4..28b4796a27ea602b8b0d5730924a64a03e69a36a 100644 --- a/apiserver/storage/LocationStorage.py +++ b/apiserver/storage/LocationStorage.py @@ -43,6 +43,9 @@ class AbstractLocationDataStorageAdapter: def updateDetails(self, type:LocationDataType, id:str, data: LocationData, usr: str): raise NotImplementedError() + def delete(self, type:LocationDataType, id:str, usr: str): + raise NotImplementedError() + # return the owner of the requested object; if multiple owners are set, return them is a list def getOwner(self, type: LocationDataType, id: str): raise NotImplementedError() diff --git a/requirements.txt b/requirements.txt index fe7d70a70123621c6d4561a9f48e2b3a784429af..b2592d9e0b620d92fd1821c3025920d9e79b640b 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,4 +1,5 @@ fastapi==0.63.0 pytest==6.2.4 requests==2.25.1 -uvicorn==0.13.4 \ No newline at end of file +uvicorn==0.13.4 +python-dotenv==0.17.1 \ No newline at end of file