Skip to content

Commit

Permalink
[qualifier] DSS0210,A2-7-2,7 validate authentication for subscription…
Browse files Browse the repository at this point in the history
… CRUD+search endpoints (#514)

* DSS02120,A2-7-2,7

Implement comments

* Address latest PR comments
  • Loading branch information
Shastick authored Mar 19, 2024
1 parent f36f171 commit 46c020a
Show file tree
Hide file tree
Showing 22 changed files with 1,196 additions and 46 deletions.
53 changes: 40 additions & 13 deletions monitoring/monitorlib/mutate/scd.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,12 @@
import s2sphere
import yaml
from implicitdict import ImplicitDict
from uas_standards.astm.f3548.v21.api import OPERATIONS, OperationID, Subscription
from uas_standards.astm.f3548.v21.api import (
OPERATIONS,
OperationID,
Subscription,
PutSubscriptionParameters,
)
from yaml.representer import Representer

from monitoring.monitorlib import fetch
Expand Down Expand Up @@ -74,18 +79,16 @@ def upsert_subscription(
path = op.path.format(subscriptionid=subscription_id, version=version)
query_type = QueryType.F3548v21DSSUpdateSubscription

body = {
"extents": Volume4D.from_values(
start_time,
end_time,
min_alt_m,
max_alt_m,
polygon=Polygon.from_latlng_rect(latlngrect=area),
).to_f3548v21(),
"uss_base_url": base_url,
"notify_for_operational_intents": notify_for_op_intents,
"notify_for_constraints": notify_for_constraints,
}
body = build_upsert_subscription_params(
area_vertices=area,
start_time=start_time,
end_time=end_time,
base_url=base_url,
notify_for_op_intents=notify_for_op_intents,
notify_for_constraints=notify_for_constraints,
min_alt_m=min_alt_m,
max_alt_m=max_alt_m,
)

result = MutatedSubscription(
fetch.query_and_describe(
Expand All @@ -102,6 +105,30 @@ def upsert_subscription(
return result


def build_upsert_subscription_params(
area_vertices: s2sphere.LatLngRect,
start_time: datetime.datetime,
end_time: datetime.datetime,
base_url: str,
notify_for_op_intents: bool,
notify_for_constraints: bool,
min_alt_m: float,
max_alt_m: float,
) -> PutSubscriptionParameters:
return PutSubscriptionParameters(
extents=Volume4D.from_values(
start_time,
end_time,
min_alt_m,
max_alt_m,
polygon=Polygon.from_latlng_rect(latlngrect=area_vertices),
).to_f3548v21(),
uss_base_url=base_url,
notify_for_operational_intents=notify_for_op_intents,
notify_for_constraints=notify_for_constraints,
)


def delete_subscription(
utm_client: infrastructure.UTMClientSession,
subscription_id: str,
Expand Down
1 change: 1 addition & 0 deletions monitoring/monitorlib/schema_validation.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ class F3411_22a(str, Enum):

class F3548_21(str, Enum):
OpenAPIPath = "interfaces/astm-utm/Protocol/utm.yaml"
ErrorResponse = "components.schemas.ErrorResponse"
GetOperationalIntentDetailsResponse = (
"components.schemas.GetOperationalIntentDetailsResponse"
)
Expand Down
2 changes: 1 addition & 1 deletion monitoring/prober/infrastructure.py
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ def wrapper_default_scope(*args, **kwargs):
resource_type_code_descriptions: Dict[ResourceType, str] = {}


# Next code: 380
# Next code: 381
def register_resource_type(code: int, description: str) -> ResourceType:
"""Register that the specified code refers to the described resource.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,9 @@ v1:
# ASTM F3548-21 USS emulation roles
- utm.strategic_coordination
- utm.availability_arbitration
# For authentication test purposes.
# Remove if the authentication provider pointed to by AUTH_SPEC does not support it.
- ""

# Means by which uss_qualifier can discover which subscription ('sub' claim of its tokes) it is described by
utm_client_identity:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,9 @@ utm_auth:
- utm.availability_arbitration
# InterUSS versioning automated testing
- interuss.versioning.read_system_versions
# For authentication test purposes.
# Remove if the authentication provider pointed to by AUTH_SPEC does not support it.
- ""

second_utm_auth:
$content_schema: monitoring/uss_qualifier/resources/definitions/ResourceDeclaration.json
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,8 @@ utm_auth:
- utm.availability_arbitration
# InterUSS versioning automated testing
- interuss.versioning.read_system_versions
# For authentication test purposes
- ""

second_utm_auth:
$content_schema: monitoring/uss_qualifier/resources/definitions/ResourceDeclaration.json
Expand Down
3 changes: 3 additions & 0 deletions monitoring/uss_qualifier/resources/astm/f3548/v21/dss.py
Original file line number Diff line number Diff line change
Expand Up @@ -510,6 +510,9 @@ def __init__(
def can_use_scope(self, scope: str) -> bool:
return scope in self._auth_adapter.scopes

def get_authorized_scopes(self) -> Set[str]:
return self._auth_adapter.scopes.copy()

def get_instance(self, scopes_required: Dict[str, str]) -> DSSInstance:
"""Get a client object ready to be used.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,16 +68,18 @@ def get_new_operational_intent_ref_params(
uss_base_url: UssBaseURL,
time_start: datetime.datetime,
time_end: datetime.datetime,
subscription_id: Optional[EntityID] = None,
subscription_id: Optional[EntityID],
implicit_sub_base_url: Optional[UssBaseURL] = None,
implicit_sub_for_constraints: Optional[bool] = None,
) -> PutOperationalIntentReferenceParameters:
"""
Builds a PutOperationalIntentReferenceParameters object that can be used against the DSS OIR API.
The extents contained in these parameters contain a single 4DVolume, which may not be entirely realistic,
but is sufficient in situations where the content of the OIR is irrelevant as long as it is valid, such
as for testing authentication or parameter validation.
Note that this method allows building inconsistent parameters.
Note that this method allows building inconsistent parameters:
"""
return PutOperationalIntentReferenceParameters(
extents=[
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
import datetime
from typing import List, Optional, Self

import s2sphere
from implicitdict import ImplicitDict
from uas_standards.astm.f3548.v21.api import PutSubscriptionParameters

from monitoring.monitorlib.geo import LatLngPoint
from monitoring.monitorlib.mutate import scd as mutate


class SubscriptionParams(ImplicitDict):
Expand Down Expand Up @@ -44,3 +47,28 @@ class SubscriptionParams(ImplicitDict):

def copy(self) -> Self:
return SubscriptionParams(super().copy())

def to_upsert_subscription_params(
self, area: s2sphere.LatLngRect
) -> PutSubscriptionParameters:
"""
Prepares the subscription parameters to be used in the body of an HTTP request
to create or update a subscription on the DSS in the SCD context.
Args:
area: area to include in the subscription parameters
Returns:
A dict to be passed as the request body when calling the subscription creation or update API.
"""
return mutate.build_upsert_subscription_params(
area_vertices=area,
start_time=self.start_time,
end_time=self.end_time,
base_url=self.base_url,
notify_for_op_intents=self.notify_for_op_intents,
notify_for_constraints=self.notify_for_constraints,
min_alt_m=self.min_alt_m,
max_alt_m=self.max_alt_m,
)
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from .authentication_validation import AuthenticationValidation
Original file line number Diff line number Diff line change
@@ -0,0 +1,178 @@
# ASTM SCD DSS: Interfaces authentication test scenario

## Overview

Ensures that a DSS properly authenticates requests to all its endpoints.

Note that this does not cover authorization.

## Resources

### dss

[`DSSInstanceResource`](../../../../../resources/astm/f3548/v21/dss.py) to be tested in this scenario.

Note that to benefit from the maximum coverage, the DSS' AuthAdapterResource must be able to obtain credentials
for multiple scopes (so that a wrong scope may be used in place of the correct one) as well as an empty scope (that is, provide credentials where the scope is an empty string).

This scenario will check for the scope's availability and transparently ignore checks that can't be conducted.

Required scopes for running this scenario:

- `utm.strategic_coordination`

Optional scopes that will allow the scenario to provide additional coverage:

- `utm.availability_arbitration`
- `""` (empty string)

### id_generator

[`IDGeneratorResource`](../../../../../resources/interuss/id_generator.py) providing the Subscription ID for this scenario.

### planning_area

[`PlanningAreaResource`](../../../../../resources/astm/f3548/v21/planning_area.py) describes the 3D volume in which entities will be created.

## Setup test case

### [Ensure clean workspace test step](../clean_workspace.md)

This step ensures that no entity with the known test IDs exists in the DSS.

## Endpoint authorization test case

This test case ensures that the DSS properly authenticates requests to all its endpoints.

### Subscription endpoints authentication test step

#### 🛑 Unauthorized requests return the proper error message body check

If the DSS under test does not return a proper error message body when an unauthorized request is received, it fails to properly implement the OpenAPI specification that is part of **[astm.f3548.v21.DSS0005,5](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Create subscription with missing credentials check

If the DSS under test allows the creation of a subscription without any credentials being presented, it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Create subscription with invalid credentials check

If the DSS under test allows the creation of a subscription with credentials that are well-formed but invalid,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Create subscription with missing scope check

If the DSS under test allows the creation of a subscription with valid credentials but a missing scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Create subscription with incorrect scope check

If the DSS under test allows the creation of a subscription with valid credentials but an incorrect scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Create subscription with valid credentials check

If the DSS does not allow the creation of a subscription when valid credentials are presented,
it is in violation of **[astm.f3548.v21.DSS0005,5](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Get subscription with missing credentials check

If the DSS under test allows the fetching of a subscription without any credentials being presented, it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Get subscription with invalid credentials check

If the DSS under test allows the fetching of a subscription with credentials that are well-formed but invalid,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Get subscription with missing scope check

If the DSS under test allows the fetching of a subscription with valid credentials but a missing scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Get subscription with incorrect scope check

If the DSS under test allows the fetching of a subscription with valid credentials but an incorrect scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Get subscription with valid credentials check

If the DSS does not allow fetching a subscription when valid credentials are presented,
it is in violation of **[astm.f3548.v21.DSS0005,5](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Mutate subscription with missing credentials check

If the DSS under test allows the mutation of a subscription without any credentials being presented,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Mutate subscription with invalid credentials check

If the DSS under test allows the mutation of a subscription with credentials that are well-formed but invalid,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Mutate subscription with missing scope check

If the DSS under test allows the mutation of a subscription with valid credentials but a missing scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Mutate subscription with incorrect scope check

If the DSS under test allows the mutation of a subscription with valid credentials but an incorrect scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Mutate subscription with valid credentials check

If the DSS does not allow the mutation of a subscription when valid credentials are presented,
it is in violation of **[astm.f3548.v21.DSS0005,5](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Delete subscription with missing credentials check

If the DSS under test allows the deletion of a subscription without any credentials being presented,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Delete subscription with invalid credentials check

If the DSS under test allows the deletion of a subscription with credentials that are well-formed but invalid,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Delete subscription with missing scope check

If the DSS under test allows the deletion of a subscription with valid credentials but a missing scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Delete subscription with incorrect scope check

If the DSS under test allows the deletion of a subscription with valid credentials but an incorrect scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Delete subscription with valid credentials check

If the DSS does not allow the deletion of a subscription when valid credentials are presented,
it is in violation of **[astm.f3548.v21.DSS0005,5](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Search subscriptions with missing credentials check

If the DSS under test allows searching for subscriptions without any credentials being presented,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Search subscriptions with invalid credentials check

If the DSS under test allows searching for subscriptions with credentials that are well-formed but invalid,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Search subscriptions with missing scope check

If the DSS under test allows searching for subscriptions with valid credentials but a missing scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Search subscriptions with incorrect scope check

If the DSS under test allows searching for subscriptions with valid credentials but an incorrect scope,
it is in violation of **[astm.f3548.v21.DSS0210,A2-7-2,7](../../../../../requirements/astm/f3548/v21.md)**.

#### 🛑 Search subscriptions with valid credentials check

If the DSS does not allow searching for subscriptions when valid credentials are presented,
it is in violation of **[astm.f3548.v21.DSS0005,5](../../../../../requirements/astm/f3548/v21.md)**.

## [Cleanup](../clean_workspace.md)

The cleanup phase of this test scenario removes the subscription with the known test ID if it has not been removed before.
Loading

0 comments on commit 46c020a

Please sign in to comment.