Skip to content

Commit

Permalink
docs: extend and correct docstrings
Browse files Browse the repository at this point in the history
  • Loading branch information
Ayush5120 authored and uniqueg committed Mar 8, 2023
1 parent 94c6319 commit 4023804
Show file tree
Hide file tree
Showing 6 changed files with 117 additions and 46 deletions.
8 changes: 4 additions & 4 deletions pro_tes/ga4gh/tes/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -666,8 +666,8 @@ class TesEndpoint(CustomBaseModel):
Args:
host: Host at which the TES API is served that is processing this
request; note that this should include the path information but
*not* the base path path defined in the TES API specification;
e.g., specify https://my.tes.com/api if the actual API is hosted at
*not* the base path defined in the TES API specification; e.g.,
specify https://my.tes.com/api if the actual API is hosted a
https://my.tes.com/api/ga4gh/tes/v1.
base_path: Override the default path suffix defined in the TES API
specification, i.e., `/ga4gh/tes/v1`.
Expand All @@ -676,8 +676,8 @@ class TesEndpoint(CustomBaseModel):
Attributes:
host: Host at which the TES API is served that is processing this
request; note that this should include the path information but
*not* the base path path defined in the TES API specification;
e.g., specify https://my.tes.com/api if the actual API is hosted at
*not* the base path defined in the TES API specification; e.g.,
specify https://my.tes.com/api if the actual API is hosted at
https://my.tes.com/api/ga4gh/tes/v1.
base_path: Override the default path suffix defined in the TES API
specification, i.e., `/ga4gh/tes/v1`.
Expand Down
50 changes: 44 additions & 6 deletions pro_tes/ga4gh/tes/task_runs.py
Original file line number Diff line number Diff line change
Expand Up @@ -387,7 +387,7 @@ def _sanitize_request(self, payload: dict) -> Dict:
"""Sanitize request for use with py-tes.
Args:
payloads: Request payload.
payload: Request payload.
Returns:
Sanitized request payload.
Expand Down Expand Up @@ -417,7 +417,7 @@ def _sanitize_request(self, payload: dict) -> Dict:
return payload

def _set_projection(self, view: str) -> Dict:
"""Set database projectoin for selected view.
"""Set database projection for selected view.
Args:
view: View path parameter.
Expand Down Expand Up @@ -453,7 +453,17 @@ def _set_projection(self, view: str) -> Dict:
def _update_task(
self, payload: dict, db_document: DbDocument, start_time: str, **kwargs
) -> DbDocument:
"""Update the task object."""
"""Update the task object.
Args:
payload: A dictionary containing the payload for the update.
db_document: The document in the database to be updated.
start_time: The starting time of the incoming TES request.
**kwargs: Additional keyword arguments passed along with request.
Returns:
DbDocument: The updated database document.
"""
logs = self._set_logs(
payloads=deepcopy(payload), start_time=start_time
)
Expand All @@ -467,7 +477,15 @@ def _update_task(
return db_document

def _set_logs(self, payloads: dict, start_time: str) -> Dict:
"""Set up the logs for the request."""
"""Create or update `TesTask.logs` and set start time.
Args:
payload: A dictionary containing the payload for the update.
start_time: The starting time of the incoming TES request.
Returns:
Task logs with start time set.
"""
if "logs" not in payloads.keys():
logs = [
{
Expand All @@ -491,7 +509,16 @@ def _update_doc_in_db(
tes_uri: str,
remote_task_id: str,
) -> DbDocument:
"""Update the document in the database."""
"""Set end time, task metadata in `TesTask.logs`, and update document.
Args:
db_connector: The database connector.
tes_uri: The TES URI where the task if forwarded.
remote_task_id: Task identifier at the remote TES instance.
Returns:
The updated database document.
"""
time_now = datetime.now().strftime("%m-%d-%Y %H:%M:%S")
tes_endpoint_dict = {"host": tes_uri, "base_path": ""}
db_document = db_connector.upsert_fields_in_root_object(
Expand Down Expand Up @@ -529,7 +556,18 @@ def _update_doc_in_db(
def _update_task_metadata(
self, db_document: DbDocument, tes_uri: str, remote_task_id: str
) -> DbDocument:
"""Update the task metadata."""
"""Update the task metadata.
Set TES endpoint and remote task identifier in `TesTask.logs.metadata`.
Args:
db_document: The document in the database to be updated.
tes_uri: The TES URI where the task if forwarded.
remote_task_id: Task identifier at the remote TES instance.
Returns:
The updated database document.
"""
for logs in db_document.task.logs:
tesNextTes_obj = TesNextTes(id=remote_task_id, url=tes_uri)
if logs.metadata.forwarded_to is None:
Expand Down
22 changes: 19 additions & 3 deletions pro_tes/middleware/middleware.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,24 @@ class AbstractMiddleware(metaclass=abc.ABCMeta):

@abc.abstractmethod
def modify_request(self, request):
"""Modify the request before it is sent to the TES instance."""
"""Modify the incoming task request.
Abstract method.
Args:
request: The incoming request object.
Returns:
The modified request object.
"""


class TaskDistributionMiddleware(AbstractMiddleware):
"""Inject task distribution logic.
Attributes:
tes_uri: TES instance best suited for TES task.
input_uris: A list of input URIs from the incoming request.
"""

def __init__(self) -> None:
Expand All @@ -30,13 +40,19 @@ def __init__(self) -> None:
self.input_uris: List[str] = []

def modify_request(self, request):
"""Add ranked list of TES instances to request body.
"""Modify the incoming task request.
Abstract method
Args:
request: Incoming request object.
Returns:
Tuple of modified request object.
The modified request object.
Raises:
pro_tes.exceptions.NoTesInstancesAvailable: If no valid TES
instances are available.
"""
if "inputs" in request.json.keys():
for index in range(len(request.json["inputs"])):
Expand Down
68 changes: 44 additions & 24 deletions pro_tes/middleware/task_distribution/distance.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,14 +26,12 @@
def task_distribution(input_uri: List) -> List:
"""Task distributor.
Distributes task by selecting the TES instance having minimum
distance between the input files and TES Instance.
Args:
input_uri: List of inputs of a TES task request
Returns:
A list of ranked TES instance.
A list of ranked TES instances, ordered by the minimum distance
between the input files and each TES instance.
"""
foca_conf = current_app.config.foca
tes_uri: List[str] = foca_conf.tes["service_list"]
Expand Down Expand Up @@ -66,12 +64,17 @@ def task_distribution(input_uri: List) -> List:
def get_uri_combination(
input_uri: List, tes_uri: List
) -> AccessUriCombination:
"""Create a combination of input uris and tes uri.
"""Create a combination of input URIs and TES URIs.
Args:
input_uri: List of input uris of TES request.
input_uri: List of input URIs of TES request.
tes_uri: List of TES instance.
Returns:
An AccessUriCombination object, which is a combination of:
:class:`pro_tes.middleware.models.AccessUriCombination`:
Examples:
A AccessUriCombination object of the form like:
{
"task_params": {
Expand Down Expand Up @@ -116,11 +119,21 @@ def ip_combination(input_uri: List[str], tes_uri: List[str]) -> Dict:
"""Create a pair of TES IP and Input IP.
Args:
input_uri: List of input uris of TES request.
tes_uri: List of TES instance.
input_uri: A list of input URIs for a TES task request.
tes_uri: A list of TES instances to choose from.
Returns:
A dictionary of combination of tes ip with all the input ips.
A dictionary where the keys are tuples representing the combination
of TES instance and input URI, and the values are tuples containing
the IP addresses of the TES instance and input URI.
Example:
{
(0, 0): ('10.0.0.1', '192.168.0.1'),
(0, 1): ('10.0.0.1', '192.168.0.2'),
(1, 0): ('10.0.0.2', '192.168.0.1'),
(1, 1): ('10.0.0.2', '192.168.0.2')
}
"""
ips = {}

Expand All @@ -147,19 +160,23 @@ def ip_combination(input_uri: List[str], tes_uri: List[str]) -> Dict:
def ip_distance(
*args: str,
) -> Dict[str, Dict]:
"""Compute ip distance between ip pairs.
"""Compute IP distance between IP pairs.
:param *args: IP addresses of the form '8.8.8.8' without schema and
suffixes.
Args:
*args: IP addresses of the form '8.8.8.8' without schema and
suffixes.
:return: A dictionary with a key for each IP address, pointing to a
dictionary containing city, region and country information for the
IP address, as well as a key "distances" pointing to a dictionary
indicating the distances, in kilometers, between all pairs of IPs,
with the tuple of IPs as the keys. IPs that cannot be located are
skipped from the resulting dictionary.
:raises ValueError: No args were passed.
Returns:
A dictionary with a key for each IP address, pointing to a
dictionary containing city, region and country information for the
IP address, as well as a key "distances" pointing to a dictionary
indicating the distances, in kilometers, between all pairs of IPs,
with the tuple of IPs as the keys. IPs that cannot be located are
skipped from the resulting dictionary.
Raises:
ValueError: No args were passed.
"""
if not args:
raise ValueError("Expected at least one URI or IP address.")
Expand Down Expand Up @@ -195,16 +212,19 @@ def ip_distance(


def calculate_distance(
ips_unique: Dict[Set[str], List[Tuple[int, str]]], tes_uri: List[str]
ips_unique: Dict[Set[str], List[Tuple[int, str]]],
tes_uri: List[str],
) -> Dict[Set[str], float]:
"""Calculate distances between all IPs.
Args:
ips_unique: A dictionary of unique ips.
ips_unique: A dictionary of unique Ips.
tes_uri: List of TES instance.
Returns:
A dictionary of distances between all ips.
A dictionary of distances between all IP addresses.
The keys are sets of IP addresses, and the values are the distances
between them as floats.
"""
distances_unique: Dict[Set[str], float] = {}
ips_all = frozenset().union(*list(ips_unique.keys())) # type: ignore
Expand Down Expand Up @@ -246,13 +266,13 @@ def calculate_distance(
def rank_tes_instances(
access_uri_combination: AccessUriCombination,
) -> List[str]:
"""Rank the tes instance based on the total distance.
"""Rank TES instances in increasing order of total distance.
Args:
access_uri_combination: Combination of task_params and tes_deployments.
Returns:
A list of tes uri in increasing order of total distance.
A list of TES URI in increasing order of total distance.
"""
combination = [
value.dict() for value in access_uri_combination.tes_deployments
Expand Down
9 changes: 3 additions & 6 deletions pro_tes/tasks/track_task_progress.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,14 +45,11 @@ def task__track_task_progress( # pylint: disable=too-many-arguments
but *not* the base path defined in the TES API specification;
e.g., specify https://my.tes.com/api if the actual API is hosted at
https://my.tes.com/api/ga4gh/tes/v1.
remote_base_path: Override the default path suffix defined in the tes
remote_base_path: Override the default path suffix defined in the TES
API specification, i.e., `/ga4gh/tes/v1`.
remote_task_id: task run identifier on remote tes service.
user: User name for basic authentication.
remote_task_id: task run identifier on remote TES service.
user: User-name for basic authentication.
password: Password for basic authentication.
Returns:
Task identifier.
"""
foca_config: Config = current_app.config.foca
controller_config: Dict = foca_config.controllers["post_task"]
Expand Down
6 changes: 3 additions & 3 deletions pro_tes/utils/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@


class TaskModelConverter:
"""Convert py-tes to proTES to proTES TES task model.
"""Convert py-tes to proTES TES task model.
Convert :class:`tes.models.Task` to
:class:`pro_tes.ga4gh.tes.models.TesTask`
Expand All @@ -37,7 +37,7 @@ def __init__(self, task: Task) -> None:
self.task: Task = task

def convert_task(self) -> TesTask:
"""Convert py-tes to proTES TES task to proTES TES task.
"""Convert py-tes to proTES TES task.
Returns:
Instance of :class:`pro_tes.ga4gh.tes.models.TesTask`
Expand Down Expand Up @@ -66,7 +66,7 @@ def convert_task(self) -> TesTask:
)

def convert_state(self) -> TesState:
"""Convert py-tes to proTES TES task state to proTES TES task state.
"""Convert py-tes to proTES TES task state.
Returns:
Instance of :class:`pro_tes.ga4gh.tes.models.TesState`
Expand Down

0 comments on commit 4023804

Please sign in to comment.