diff --git a/monitoring/monitorlib/fetch/__init__.py b/monitoring/monitorlib/fetch/__init__.py index 2cddcc87c2..61625ab2c1 100644 --- a/monitoring/monitorlib/fetch/__init__.py +++ b/monitoring/monitorlib/fetch/__init__.py @@ -180,10 +180,81 @@ def describe_flask_response(resp: flask.Response, elapsed_s: float): class QueryType(str, Enum): - F3411v22aFlights = "astm.f3411.v22a.sp.flights" - F3411v19Flights = "astm.f3411.v19.sp.flights" - F3411v22aFlightDetails = "astm.f3411.v22a.sp.flight_details" - F3411v19aFlightDetails = "astm.f3411.v19.sp.flight_details" + + # ASTM F3411-19 and F3411-22a (RID) + F3411v19DSSSearchIdentificationServiceAreas = ( + "astm.f3411.v19.dss.searchIdentificationServiceAreas" + ) + F3411v22aDSSSearchIdentificationServiceAreas = ( + "astm.f3411.v22a.dss.searchIdentificationServiceAreas" + ) + + F3411v19DSSGetIdentificationServiceArea = ( + "astm.f3411.v19.dss.getIdentificationServiceArea" + ) + F3411v22aDSSGetIdentificationServiceArea = ( + "astm.f3411.v22a.dss.getIdentificationServiceArea" + ) + + F3411v19DSSCreateIdentificationServiceArea = ( + "astm.f3411.v19.dss.createIdentificationServiceArea" + ) + F3411v22aDSSCreateIdentificationServiceArea = ( + "astm.f3411.v22a.dss.createIdentificationServiceArea" + ) + + F3411v19DSSUpdateIdentificationServiceArea = ( + "astm.f3411.v19.dss.updateIdentificationServiceArea" + ) + F3411v22aDSSUpdateIdentificationServiceArea = ( + "astm.f3411.v22a.dss.updateIdentificationServiceArea" + ) + + F3411v19DSSDeleteIdentificationServiceArea = ( + "astm.f3411.v19.dss.deleteIdentificationServiceArea" + ) + F3411v22aDSSDeleteIdentificationServiceArea = ( + "astm.f3411.v22a.dss.deleteIdentificationServiceArea" + ) + + F3411v19DSSSearchFlights = "astm.f3411.v19.dss.searchFlights" + F3411v22aDSSSearchFlights = "astm.f3411.v22a.dss.searchFlights" + + F3411v19DSSSearchSubscriptions = "astm.f3411.v19.dss.searchSubscriptions" + F3411v22aDSSSearchSubscriptions = "astm.f3411.v22a.dss.searchSubscriptions" + + F3411v19DSSGetSubscription = "astm.f3411.v19.dss.getSubscription" + F3411v22aDSSGetSubscription = "astm.f3411.v22a.dss.getSubscription" + + F3411v19DSSCreateSubscription = "astm.f3411.v19.dss.createSubscription" + F3411v22aDSSCreateSubscription = "astm.f3411.v22a.dss.createSubscription" + + F3411v19DSSUpdateSubscription = "astm.f3411.v19.dss.updateSubscription" + F3411v22aDSSUpdateSubscription = "astm.f3411.v22a.dss.updateSubscription" + + F3411v19DSSDeleteSubscription = "astm.f3411.v19.dss.deleteSubscription" + F3411v22aDSSDeleteSubscription = "astm.f3411.v22a.dss.deleteSubscription" + + F3411v19USSPostIdentificationServiceArea = ( + "astm.f3411.v19.uss.postIdentificationServiceArea" + ) + F3411v22aUSSPostIdentificationServiceArea = ( + "astm.f3411.v22a.uss.postIdentificationServiceArea" + ) + + # Flight injection (test harness) + + F3411v19USSCreateTest = "rid.f3411.v19.sp.createTest" + F3411v22aUSSCreateTest = "rid.f3411.v22a.sp.createTest" + + F3411v19USSDeleteTest = "rid.f3411.v19.sp.deleteTest" + F3411v22aUSSDeleteTest = "rid.f3411.v22a.sp.deleteTest" + + # RID flight details endpoint that a USS provides (!= DSS) + F3411v22aUSSGetDisplayData = "rid.f3411.v22a.sp.getDisplayData" + F3411v19USSGetDisplayData = "rid.f3411.v19.sp.getDisplayData" + F3411v22aUSSGetFlightDetails = "rid.f3411.v22a.sp.getDetails" + F3411v19USSGetFlightDetails = "rid.f3411.v19.sp.getDetails" # ASTM F3548-21 F3548v21DSSQueryOperationalIntentReferences = ( @@ -257,9 +328,63 @@ class QueryType(str, Enum): @staticmethod def flight_details(rid_version: RIDVersion): if rid_version == RIDVersion.f3411_19: - return QueryType.F3411v19aFlightDetails + return QueryType.F3411v19USSGetFlightDetails + elif rid_version == RIDVersion.f3411_22a: + return QueryType.F3411v22aUSSGetFlightDetails + else: + raise ValueError(f"Unsupported RID version: {rid_version}") + + @staticmethod + def dss_get_isa(rid_version: RIDVersion): + if rid_version == RIDVersion.f3411_19: + return QueryType.F3411v19DSSGetIdentificationServiceArea + elif rid_version == RIDVersion.f3411_22a: + return QueryType.F3411v22aDSSGetIdentificationServiceArea + else: + raise ValueError(f"Unsupported RID version: {rid_version}") + + @staticmethod + def dss_create_isa(rid_version: RIDVersion): + if rid_version == RIDVersion.f3411_19: + return QueryType.F3411v19DSSCreateIdentificationServiceArea + elif rid_version == RIDVersion.f3411_22a: + return QueryType.F3411v22aDSSCreateIdentificationServiceArea + else: + raise ValueError(f"Unsupported RID version: {rid_version}") + + @staticmethod + def dss_update_isa(rid_version: RIDVersion): + if rid_version == RIDVersion.f3411_19: + return QueryType.F3411v19DSSUpdateIdentificationServiceArea + elif rid_version == RIDVersion.f3411_22a: + return QueryType.F3411v22aDSSUpdateIdentificationServiceArea + else: + raise ValueError(f"Unsupported RID version: {rid_version}") + + @staticmethod + def dss_delete_isa(rid_version: RIDVersion): + if rid_version == RIDVersion.f3411_19: + return QueryType.F3411v19DSSDeleteIdentificationServiceArea + elif rid_version == RIDVersion.f3411_22a: + return QueryType.F3411v22aDSSDeleteIdentificationServiceArea + else: + raise ValueError(f"Unsupported RID version: {rid_version}") + + @staticmethod + def sp_create_test(rid_version: RIDVersion): + if rid_version == RIDVersion.f3411_19: + return QueryType.F3411v19USSCreateTest + elif rid_version == RIDVersion.f3411_22a: + return QueryType.F3411v22aUSSCreateTest + else: + raise ValueError(f"Unsupported RID version: {rid_version}") + + @staticmethod + def sp_delete_test(rid_version: RIDVersion): + if rid_version == RIDVersion.f3411_19: + return QueryType.F3411v19USSDeleteTest elif rid_version == RIDVersion.f3411_22a: - return QueryType.F3411v22aFlightDetails + return QueryType.F3411v22aUSSDeleteTest else: raise ValueError(f"Unsupported RID version: {rid_version}") diff --git a/monitoring/monitorlib/fetch/rid.py b/monitoring/monitorlib/fetch/rid.py index 2c1142a54e..7e5f0cfdb7 100644 --- a/monitoring/monitorlib/fetch/rid.py +++ b/monitoring/monitorlib/fetch/rid.py @@ -687,6 +687,14 @@ def set_participant_id(self, participant_id: str) -> None: else: raise NotImplementedError(f"Cannot set participant_id") + def set_query_type(self, query_type: QueryType) -> None: + if self.v19_query is not None: + self.v19_query.query_type = query_type + elif self.v22a_query is not None: + self.v22a_query.query_type = query_type + else: + raise NotImplementedError(f"Cannot set query_type") + class FetchedISA(RIDQuery): """Version-independent representation of an ISA read from the DSS.""" @@ -773,6 +781,7 @@ def isa( url, scope=v19.constants.Scope.Read, participant_id=participant_id, + query_type=QueryType.F3411v19DSSGetIdentificationServiceArea, ) ) elif rid_version == RIDVersion.f3411_22a: @@ -785,6 +794,7 @@ def isa( url, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aDSSGetIdentificationServiceArea, ) ) else: @@ -915,6 +925,7 @@ def isas( url, scope=v19.constants.Scope.Read, participant_id=participant_id, + query_type=QueryType.F3411v19DSSSearchIdentificationServiceAreas, ) ) elif rid_version == RIDVersion.f3411_22a: @@ -928,6 +939,7 @@ def isas( url, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aDSSSearchIdentificationServiceAreas, ) ) else: @@ -1023,7 +1035,7 @@ def uss_flights( else "false", }, scope=v19.constants.Scope.Read, - query_type=QueryType.F3411v19Flights, + query_type=QueryType.F3411v19USSGetDisplayData, participant_id=participant_id, ) return FetchedUSSFlights(v19_query=query) @@ -1044,7 +1056,7 @@ def uss_flights( flights_url, params=params, scope=v22a.constants.Scope.DisplayProvider, - query_type=QueryType.F3411v22aFlights, + query_type=QueryType.F3411v22aUSSGetDisplayData, participant_id=participant_id, ) return FetchedUSSFlights(v22a_query=query) @@ -1143,13 +1155,20 @@ def flight_details( ) else: kwargs["scope"] = v19.constants.Scope.Read - query = fetch.query_and_describe(session, "GET", url, **kwargs) + query = fetch.query_and_describe( + session, + "GET", + url, + query_type=QueryType.F3411v19USSGetFlightDetails, + **kwargs, + ) return FetchedUSSFlightDetails(v19_query=query) elif rid_version == RIDVersion.f3411_22a: query = fetch.query_and_describe( session, "GET", url, + query_type=QueryType.F3411v22aUSSGetFlightDetails, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, ) @@ -1329,6 +1348,7 @@ def subscription( url, scope=v19.constants.Scope.Read, participant_id=participant_id, + query_type=QueryType.F3411v19DSSGetSubscription, ) ) elif rid_version == RIDVersion.f3411_22a: @@ -1341,6 +1361,7 @@ def subscription( url, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aDSSGetSubscription, ) ) else: @@ -1436,6 +1457,7 @@ def subscriptions( url, scope=v19.constants.Scope.Read, participant_id=participant_id, + query_type=QueryType.F3411v19DSSSearchSubscriptions, ) ) elif rid_version == RIDVersion.f3411_22a: @@ -1448,6 +1470,7 @@ def subscriptions( url, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aDSSSearchSubscriptions, ) ) else: diff --git a/monitoring/monitorlib/mutate/rid.py b/monitoring/monitorlib/mutate/rid.py index 27265e55aa..a896ff9c7e 100644 --- a/monitoring/monitorlib/mutate/rid.py +++ b/monitoring/monitorlib/mutate/rid.py @@ -5,6 +5,7 @@ import s2sphere from uas_standards import Operation +from monitoring.monitorlib.fetch import QueryType from monitoring.monitorlib.fetch.rid import RIDQuery, Subscription, ISA from monitoring.monitorlib.rid import RIDVersion from uas_standards.astm.f3411 import v19, v22a @@ -127,9 +128,11 @@ def upsert_subscription( if subscription_version is None: op = v19.api.OPERATIONS[v19.api.OperationID.CreateSubscription] url = op.path.format(id=subscription_id) + query_type = QueryType.F3411v19DSSCreateSubscription else: op = v19.api.OPERATIONS[v19.api.OperationID.UpdateSubscription] url = op.path.format(id=subscription_id, version=subscription_version) + query_type = QueryType.F3411v19DSSUpdateSubscription return ChangedSubscription( mutation=mutation, v19_query=fetch.query_and_describe( @@ -139,6 +142,7 @@ def upsert_subscription( json=body, scope=v19.constants.Scope.Read, participant_id=participant_id, + query_type=query_type, ), ) elif rid_version == RIDVersion.f3411_22a: @@ -155,9 +159,11 @@ def upsert_subscription( if subscription_version is None: op = v22a.api.OPERATIONS[v22a.api.OperationID.CreateSubscription] url = op.path.format(id=subscription_id) + query_type = QueryType.F3411v22aDSSCreateSubscription else: op = v22a.api.OPERATIONS[v22a.api.OperationID.UpdateSubscription] url = op.path.format(id=subscription_id, version=subscription_version) + query_type = QueryType.F3411v22aDSSUpdateSubscription return ChangedSubscription( mutation=mutation, v22a_query=fetch.query_and_describe( @@ -167,6 +173,7 @@ def upsert_subscription( json=body, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, + query_type=query_type, ), ) else: @@ -193,6 +200,7 @@ def delete_subscription( url, scope=v19.constants.Scope.Read, participant_id=participant_id, + query_type=QueryType.F3411v19DSSDeleteSubscription, ), ) elif rid_version == RIDVersion.f3411_22a: @@ -206,6 +214,7 @@ def delete_subscription( url, scope=v22a.constants.Scope.DisplayProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aDSSDeleteSubscription, ), ) else: @@ -278,6 +287,7 @@ def notify( json=body, scope=v19.constants.Scope.Write, participant_id=participant_id, + query_type=QueryType.F3411v19USSPostIdentificationServiceArea, ) ) elif self.rid_version == RIDVersion.f3411_22a: @@ -296,6 +306,7 @@ def notify( json=body, scope=v22a.constants.Scope.ServiceProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aUSSPostIdentificationServiceArea, ) ) else: @@ -523,7 +534,8 @@ def put_isa( isa_version: Optional[str] = None, participant_id: Optional[str] = None, ) -> ISAChange: - mutation = "create" if isa_version is None else "update" + is_mutation = isa_version is None + mutation = "create" if is_mutation else "update" body = build_isa_request_body( area_vertices, alt_lo, @@ -535,6 +547,11 @@ def put_isa( ) (op, url) = build_isa_url(rid_version, isa_id, isa_version) if rid_version == RIDVersion.f3411_19: + query_type = ( + QueryType.F3411v19DSSUpdateIdentificationServiceArea + if is_mutation + else QueryType.F3411v19DSSCreateIdentificationServiceArea + ) dss_response = ChangedISA( mutation=mutation, v19_query=fetch.query_and_describe( @@ -544,9 +561,15 @@ def put_isa( json=body, scope=v19.constants.Scope.Write, participant_id=participant_id, + query_type=query_type, ), ) elif rid_version == RIDVersion.f3411_22a: + query_type = ( + QueryType.F3411v22aDSSUpdateIdentificationServiceArea + if is_mutation + else QueryType.F3411v22aDSSCreateIdentificationServiceArea + ) dss_response = ChangedISA( mutation=mutation, v22a_query=fetch.query_and_describe( @@ -556,6 +579,7 @@ def put_isa( json=body, scope=v22a.constants.Scope.ServiceProvider, participant_id=participant_id, + query_type=query_type, ), ) else: @@ -591,6 +615,7 @@ def delete_isa( url, scope=v19.constants.Scope.Write, participant_id=participant_id, + query_type=QueryType.F3411v19DSSDeleteIdentificationServiceArea, ), ) elif rid_version == RIDVersion.f3411_22a: @@ -604,6 +629,7 @@ def delete_isa( url, scope=v22a.constants.Scope.ServiceProvider, participant_id=participant_id, + query_type=QueryType.F3411v22aDSSDeleteIdentificationServiceArea, ), ) else: diff --git a/monitoring/uss_qualifier/resources/netrid/observers.py b/monitoring/uss_qualifier/resources/netrid/observers.py index b172672225..21bc4ada53 100644 --- a/monitoring/uss_qualifier/resources/netrid/observers.py +++ b/monitoring/uss_qualifier/resources/netrid/observers.py @@ -34,7 +34,7 @@ def __init__( self.local_debug = local_debug def observe_system( - self, rect: s2sphere.LatLngRect + self, rect: s2sphere.LatLngRect, rid_version: RIDVersion ) -> Tuple[Optional[observation_api.GetDisplayDataResponse], fetch.Query]: url = "/display_data?view={},{},{},{}".format( rect.lo().lat().degrees, @@ -50,6 +50,7 @@ def observe_system( # the standard is updated with https://github.com/interuss/uas_standards/pull/11/files scope="dss.read.identification_service_areas", participant_id=self.participant_id, + query_type=QueryType.flight_details(rid_version), ) try: result = ( diff --git a/monitoring/uss_qualifier/resources/netrid/service_providers.py b/monitoring/uss_qualifier/resources/netrid/service_providers.py index cdbc5a36ea..13e89ca4de 100644 --- a/monitoring/uss_qualifier/resources/netrid/service_providers.py +++ b/monitoring/uss_qualifier/resources/netrid/service_providers.py @@ -5,6 +5,7 @@ from implicitdict import ImplicitDict from monitoring.monitorlib import fetch, infrastructure +from monitoring.monitorlib.rid import RIDVersion from monitoring.monitorlib.rid_automated_testing.injection_api import ( CreateTestParameters, SCOPE_RID_QUALIFIER_INJECT, @@ -59,7 +60,9 @@ def __init__( ) self.local_debug = local_debug - def submit_test(self, request: CreateTestParameters, test_id: str) -> fetch.Query: + def submit_test( + self, request: CreateTestParameters, test_id: str, rid_version: RIDVersion + ) -> fetch.Query: return fetch.query_and_describe( self.injection_client, "PUT", @@ -67,15 +70,19 @@ def submit_test(self, request: CreateTestParameters, test_id: str) -> fetch.Quer json=request, scope=SCOPE_RID_QUALIFIER_INJECT, participant_id=self.participant_id, + query_type=fetch.QueryType.sp_create_test(rid_version), ) - def delete_test(self, test_id: str, version: str) -> fetch.Query: + def delete_test( + self, test_id: str, version: str, rid_version: RIDVersion + ) -> fetch.Query: return fetch.query_and_describe( self.injection_client, "DELETE", url=f"/tests/{test_id}/{version}", scope=SCOPE_RID_QUALIFIER_INJECT, participant_id=self.participant_id, + query_type=fetch.QueryType.sp_delete_test(rid_version), ) diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/common/aggregate_checks.py b/monitoring/uss_qualifier/scenarios/astm/netrid/common/aggregate_checks.py index 6e7a6e2abc..b77831ca3a 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/common/aggregate_checks.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/common/aggregate_checks.py @@ -161,6 +161,9 @@ def _verify_https_everywhere(self): "unattributed-queries", f"found unattributed queries: {unattr_queries}", ) + logger.warning( + f"found unattributed queries: {unattr_queries}", + ) def _inspect_participant_queries( self, participant_id: str, participant_queries: List[fetch.Query] @@ -208,8 +211,8 @@ def _dp_display_data_details_times_step(self): query.status_code == 200 and query.has_field_with_value("query_type") and ( - query.query_type == QueryType.F3411v19aFlightDetails - or query.query_type == QueryType.F3411v22aFlightDetails + query.query_type == QueryType.F3411v19USSGetFlightDetails + or query.query_type == QueryType.F3411v22aUSSGetFlightDetails ) ): relevant_queries.append(query) @@ -254,8 +257,8 @@ def _sp_flights_area_times_step(self): for query in all_queries: if query.has_field_with_value("query_type") and ( # TODO find a cleaner way than checking for version here - query.query_type == QueryType.F3411v19Flights - or query.query_type == QueryType.F3411v22aFlights + query.query_type == QueryType.F3411v19USSGetDisplayData + or query.query_type == QueryType.F3411v22aUSSGetDisplayData ): relevant_queries.append(query) diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/heavy_traffic_concurrent.py b/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/heavy_traffic_concurrent.py index e06453c3f9..13efb3ed38 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/heavy_traffic_concurrent.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/heavy_traffic_concurrent.py @@ -11,6 +11,7 @@ describe_request, Query, describe_aiohttp_response, + QueryType, ) from monitoring.monitorlib.fetch.rid import FetchedISA from monitoring.monitorlib.infrastructure import AsyncUTMTestSession @@ -217,6 +218,7 @@ async def _get_isa(self, isa_id): status, headers, resp_json, duration ), participant_id=self._dss.participant_id, + query_type=QueryType.dss_get_isa(self._dss.rid_version), ) return isa_id, self._wrap_isa_get_query(rq) @@ -245,6 +247,7 @@ async def _create_isa(self, isa_id): status, headers, resp_json, duration ), participant_id=self._dss.participant_id, + query_type=QueryType.dss_create_isa(self._dss.rid_version), ) return isa_id, self._wrap_isa_put_query(rq, "create") @@ -268,6 +271,7 @@ async def _delete_isa(self, isa_id, isa_version): status, headers, resp_json, duration ), participant_id=self._dss.participant_id, + query_type=QueryType.dss_delete_isa(self._dss.rid_version), ) return isa_id, self._wrap_isa_put_query(rq, "delete") diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/isa_validation.py b/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/isa_validation.py index 6831fb0d33..4bedae5672 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/isa_validation.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/isa_validation.py @@ -8,7 +8,7 @@ from monitoring.uss_qualifier.suites.suite import ExecutionContext from uas_standards.astm.f3411 import v19, v22a -from monitoring.monitorlib.fetch import query_and_describe +from monitoring.monitorlib.fetch import query_and_describe, QueryType from monitoring.monitorlib.mutate.rid import ChangedISA from monitoring.monitorlib.rid import RIDVersion from monitoring.prober.infrastructure import register_resource_type @@ -250,8 +250,14 @@ def _isa_missing_outline(self, create_isa_url: str, json_body: Dict[str, Any]): ) if self._dss.rid_version == RIDVersion.f3411_19: rid_query = ChangedISA(v19_query=q) + rid_query.set_query_type( + QueryType.F3411v19DSSCreateIdentificationServiceArea + ) elif self._dss.rid_version == RIDVersion.f3411_22a: rid_query = ChangedISA(v22a_query=q) + rid_query.set_query_type( + QueryType.F3411v22aDSSCreateIdentificationServiceArea + ) else: raise ValueError(f"Unknown RID version: {self._dss.rid_version}") @@ -284,8 +290,14 @@ def _isa_missing_volume(self, create_isa_url: str, json_body: Dict[str, Any]): ) if self._dss.rid_version == RIDVersion.f3411_19: rid_query = ChangedISA(v19_query=q) + rid_query.set_query_type( + QueryType.F3411v19DSSCreateIdentificationServiceArea + ) elif self._dss.rid_version == RIDVersion.f3411_22a: rid_query = ChangedISA(v22a_query=q) + rid_query.set_query_type( + QueryType.F3411v22aDSSCreateIdentificationServiceArea + ) else: raise ValueError(f"Unknown RID version: {self._dss.rid_version}") @@ -315,8 +327,14 @@ def _isa_missing_extents(self, create_isa_url: str, json_body: Dict[str, Any]): ) if self._dss.rid_version == RIDVersion.f3411_19: rid_query = ChangedISA(v19_query=q) + rid_query.set_query_type( + QueryType.F3411v19DSSCreateIdentificationServiceArea + ) elif self._dss.rid_version == RIDVersion.f3411_22a: rid_query = ChangedISA(v22a_query=q) + rid_query.set_query_type( + QueryType.F3411v22aDSSCreateIdentificationServiceArea + ) else: raise ValueError(f"Unknown RID version: {self._dss.rid_version}") diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/token_validation.py b/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/token_validation.py index cf36dd93f1..68ecf37513 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/token_validation.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/common/dss/token_validation.py @@ -8,7 +8,7 @@ from monitoring.monitorlib import fetch, infrastructure from monitoring.monitorlib import rid_v1, rid_v2 from monitoring.monitorlib.auth import InvalidTokenSignatureAuth -from monitoring.monitorlib.fetch import rid as rid_fetch +from monitoring.monitorlib.fetch import rid as rid_fetch, QueryType from monitoring.monitorlib.fetch.rid import FetchedISA, FetchedISAs from monitoring.monitorlib.mutate import rid as mutate from monitoring.monitorlib.mutate.rid import ( @@ -466,11 +466,13 @@ def _put_isa_tweak_auth( v19.api.OperationID.CreateIdentificationServiceArea ] url = op.path.format(id=self._isa_id) + query_type = QueryType.F3411v19DSSCreateIdentificationServiceArea else: op = v19.api.OPERATIONS[ v19.api.OperationID.UpdateIdentificationServiceArea ] url = op.path.format(id=self._isa_id, version=isa_version) + query_type = QueryType.F3411v19DSSUpdateIdentificationServiceArea dss_response = ChangedISA( mutation=mutation, v19_query=fetch.query_and_describe( @@ -479,6 +481,7 @@ def _put_isa_tweak_auth( url, json=body, participant_id=self._dss.participant_id, + query_type=query_type, **({} if query_scope is None else {"scope": query_scope}), ), ) @@ -498,11 +501,13 @@ def _put_isa_tweak_auth( v22a.api.OperationID.CreateIdentificationServiceArea ] url = op.path.format(id=self._isa_id) + query_type = QueryType.F3411v22aDSSCreateIdentificationServiceArea else: op = v22a.api.OPERATIONS[ v22a.api.OperationID.UpdateIdentificationServiceArea ] url = op.path.format(id=self._isa_id, version=isa_version) + query_type = QueryType.F3411v22aDSSUpdateIdentificationServiceArea dss_response = ChangedISA( mutation=mutation, v22a_query=fetch.query_and_describe( @@ -511,6 +516,7 @@ def _put_isa_tweak_auth( url, json=body, participant_id=self._dss.participant_id, + query_type=query_type, **({} if query_scope is None else {"scope": query_scope}), ), ) @@ -586,6 +592,7 @@ def _del_isa_tweak_auth( op.verb, url, participant_id=self._dss.participant_id, + query_type=QueryType.F3411v19DSSDeleteIdentificationServiceArea, **({} if query_scope is None else {"scope": query_scope}), ), ) @@ -601,6 +608,7 @@ def _del_isa_tweak_auth( op.verb, url, participant_id=self._dss.participant_id, + query_type=QueryType.F3411v22aDSSDeleteIdentificationServiceArea, **({} if query_scope is None else {"scope": query_scope}), ), ) @@ -657,6 +665,7 @@ def _search_isas_tweak_auth( op.verb, url, participant_id=self._dss.participant_id, + query_type=QueryType.F3411v19DSSSearchIdentificationServiceAreas, **({} if query_scope is None else {"scope": query_scope}), ) ) @@ -672,6 +681,7 @@ def _search_isas_tweak_auth( op.verb, url, participant_id=self._dss.participant_id, + query_type=QueryType.F3411v22aDSSSearchIdentificationServiceAreas, **({} if query_scope is None else {"scope": query_scope}), ) ) diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/common/misbehavior.py b/monitoring/uss_qualifier/scenarios/astm/netrid/common/misbehavior.py index 2dd5744fc5..618565ead9 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/common/misbehavior.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/common/misbehavior.py @@ -89,7 +89,7 @@ def run(self, context: ExecutionContext): def _inject_flights(self): (self._injected_flights, self._injected_tests) = injection.inject_flights( - self, self._flights_data, self._service_providers + self, self._flights_data, self._service_providers, self._rid_version ) def _poll_unauthenticated_during_flights(self): @@ -238,7 +238,9 @@ def cleanup(self): sp = matching_sps[0] check = self.check("Successful test deletion", [sp.participant_id]) try: - query = sp.delete_test(injected_test.test_id, injected_test.version) + query = sp.delete_test( + injected_test.test_id, injected_test.version, self._rid_version + ) self.record_query(query) if query.status_code != 200: raise ValueError( diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/common/nominal_behavior.py b/monitoring/uss_qualifier/scenarios/astm/netrid/common/nominal_behavior.py index d98e120c2a..83bbde32d5 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/common/nominal_behavior.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/common/nominal_behavior.py @@ -77,7 +77,7 @@ def run(self, context: ExecutionContext): def _inject_flights(self): (self._injected_flights, self._injected_tests) = injection.inject_flights( - self, self._flights_data, self._service_providers + self, self._flights_data, self._service_providers, self._rid_version ) def _poll_during_flights(self): @@ -128,7 +128,9 @@ def cleanup(self): sp = matching_sps[0] check = self.check("Successful test deletion", [sp.participant_id]) try: - query = sp.delete_test(injected_test.test_id, injected_test.version) + query = sp.delete_test( + injected_test.test_id, injected_test.version, self._rid_version + ) self.record_query(query) if query.status_code != 200: raise ValueError( diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/display_data_evaluator.py b/monitoring/uss_qualifier/scenarios/astm/netrid/display_data_evaluator.py index f1795ceea7..1ab50c776a 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/display_data_evaluator.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/display_data_evaluator.py @@ -258,7 +258,7 @@ def evaluate_system_instantaneously( if perform_observation: self._test_scenario.begin_test_step("Observer polling") for observer in observers: - (observation, query) = observer.observe_system(rect) + (observation, query) = observer.observe_system(rect, self._rid_version) self._test_scenario.record_query(query) self._evaluate_observation( observer, diff --git a/monitoring/uss_qualifier/scenarios/astm/netrid/injection.py b/monitoring/uss_qualifier/scenarios/astm/netrid/injection.py index 96452d4c26..afdb61ba51 100644 --- a/monitoring/uss_qualifier/scenarios/astm/netrid/injection.py +++ b/monitoring/uss_qualifier/scenarios/astm/netrid/injection.py @@ -7,6 +7,7 @@ from uas_standards.interuss.automated_testing.rid.v1.injection import ChangeTestResponse from monitoring.monitorlib import geo +from monitoring.monitorlib.rid import RIDVersion from monitoring.monitorlib.rid_automated_testing.injection_api import ( TestFlight, CreateTestParameters, @@ -36,6 +37,7 @@ def inject_flights( test_scenario: TestScenario, flights_data_res: FlightDataResource, service_providers_res: NetRIDServiceProviders, + rid_version: RIDVersion, ) -> Tuple[List[InjectedFlight], List[InjectedTest]]: test_id = str(uuid.uuid4()) test_flights = flights_data_res.get_test_flights() @@ -53,7 +55,7 @@ def inject_flights( with test_scenario.check( "Successful injection", [target.participant_id] ) as check: - query = target.submit_test(p, test_id) + query = target.submit_test(p, test_id, rid_version) test_scenario.record_query(query) if query.status_code != 200: diff --git a/monitoring/uss_qualifier/scenarios/scenario.py b/monitoring/uss_qualifier/scenarios/scenario.py index ccdec94961..f67aa6024a 100644 --- a/monitoring/uss_qualifier/scenarios/scenario.py +++ b/monitoring/uss_qualifier/scenarios/scenario.py @@ -9,6 +9,7 @@ from monitoring import uss_qualifier as uss_qualifier_module from monitoring.monitorlib import fetch, inspection +from monitoring.monitorlib.fetch import QueryType from monitoring.monitorlib.inspection import fullname from monitoring.uss_qualifier import scenarios as scenarios_module from monitoring.uss_qualifier.common_data_definitions import Severity @@ -36,6 +37,17 @@ from monitoring.uss_qualifier.resources.definitions import ResourceTypeName, ResourceID from monitoring.uss_qualifier.scenarios.documentation.parsing import get_documentation +SQUELCH_WARN_ON_QUERY_TYPE = [ + # Posting an ISA is done for notifications: we can't always know the participant ID + QueryType.F3411v19USSPostIdentificationServiceArea, + QueryType.F3411v22aUSSPostIdentificationServiceArea, + # When querying for display data and flight details, we don't always know the participant ID + QueryType.F3411v19USSGetDisplayData, + QueryType.F3411v22aUSSGetDisplayData, + QueryType.F3411v19USSGetFlightDetails, + QueryType.F3411v22aUSSGetFlightDetails, +] + class ScenarioCannotContinueError(Exception): def __init__(self, msg): @@ -374,9 +386,14 @@ def record_query(self, query: fetch.Query) -> None: if not query.has_field_with_value("query_type") else query.query_type ) - logger.debug( - f"Queried {query.request['method']} {query.request['url']} -> {query.response.status_code} ({query.response.elapsed_s:.1f}s); attributed participant {participant} and type {query_type}" - ) + # Log a warning if we are missing query metadata, unless the query type is one for which + # we expect to occasionally not know the participant ID + if ( + participant == "UNKNOWN" or query_type == "UNKNOWN" + ) and query_type not in SQUELCH_WARN_ON_QUERY_TYPE: + logger.warning( + f"Missing query metadata: {query.request['method']} {query.request['url']} has participant {participant} and type {query_type}" + ) def _get_check(self, name: str) -> TestCheckDocumentation: available_checks = {c.name: c for c in self._current_step.checks} diff --git a/schemas/monitoring/monitorlib/fetch/Query.json b/schemas/monitoring/monitorlib/fetch/Query.json index d69788f3cf..8e96b71be9 100644 --- a/schemas/monitoring/monitorlib/fetch/Query.json +++ b/schemas/monitoring/monitorlib/fetch/Query.json @@ -17,10 +17,38 @@ "query_type": { "description": "If specified, the recognized type of this query.", "enum": [ - "astm.f3411.v22a.sp.flights", - "astm.f3411.v19.sp.flights", - "astm.f3411.v22a.sp.flight_details", - "astm.f3411.v19.sp.flight_details", + "astm.f3411.v19.dss.searchIdentificationServiceAreas", + "astm.f3411.v22a.dss.searchIdentificationServiceAreas", + "astm.f3411.v19.dss.getIdentificationServiceArea", + "astm.f3411.v22a.dss.getIdentificationServiceArea", + "astm.f3411.v19.dss.createIdentificationServiceArea", + "astm.f3411.v22a.dss.createIdentificationServiceArea", + "astm.f3411.v19.dss.updateIdentificationServiceArea", + "astm.f3411.v22a.dss.updateIdentificationServiceArea", + "astm.f3411.v19.dss.deleteIdentificationServiceArea", + "astm.f3411.v22a.dss.deleteIdentificationServiceArea", + "astm.f3411.v19.dss.searchFlights", + "astm.f3411.v22a.dss.searchFlights", + "astm.f3411.v19.dss.searchSubscriptions", + "astm.f3411.v22a.dss.searchSubscriptions", + "astm.f3411.v19.dss.getSubscription", + "astm.f3411.v22a.dss.getSubscription", + "astm.f3411.v19.dss.createSubscription", + "astm.f3411.v22a.dss.createSubscription", + "astm.f3411.v19.dss.updateSubscription", + "astm.f3411.v22a.dss.updateSubscription", + "astm.f3411.v19.dss.deleteSubscription", + "astm.f3411.v22a.dss.deleteSubscription", + "astm.f3411.v19.uss.postIdentificationServiceArea", + "astm.f3411.v22a.uss.postIdentificationServiceArea", + "rid.f3411.v19.sp.createTest", + "rid.f3411.v22a.sp.createTest", + "rid.f3411.v19.sp.deleteTest", + "rid.f3411.v22a.sp.deleteTest", + "rid.f3411.v22a.sp.getDisplayData", + "rid.f3411.v19.sp.getDisplayData", + "rid.f3411.v22a.sp.getDetails", + "rid.f3411.v19.sp.getDetails", "astm.f3548.v21.dss.queryOperationalIntentReferences", "astm.f3548.v21.dss.getOperationalIntentReference", "astm.f3548.v21.dss.createOperationalIntentReference",