diff --git a/tenable/apa/vectors/api.py b/tenable/apa/vectors/api.py index 45d519741..b5771c9d9 100644 --- a/tenable/apa/vectors/api.py +++ b/tenable/apa/vectors/api.py @@ -32,11 +32,11 @@ def _get_page(self) -> None: Request the next page of data """ payload = copy(self._payload) - payload["pageNumber"] = self._next_page + payload["page_number"] = self._next_page resp = self._api.get("apa/api/discover/v1/vectors", params=payload, box=True) - self._next_page = resp.get("pageNumber") + 1 + self._next_page = resp.get("page_number") + 1 self.page = resp.data self.total = resp.get("total") @@ -112,11 +112,11 @@ def list( """ payload = { - "pageNumber": page_number, + "page_number": page_number, "limit": limit, "filter": filter, - "sortField": sort_field, - "sortOrder": sort_order} + "sort_field": sort_field, + "sort_order": sort_order} if return_iterator: return VectorIterator(self._api, _payload=payload) return self._schema.load( diff --git a/tenable/apa/vectors/schema.py b/tenable/apa/vectors/schema.py index 313de9cc7..96534fcc3 100644 --- a/tenable/apa/vectors/schema.py +++ b/tenable/apa/vectors/schema.py @@ -1,4 +1,4 @@ -from marshmallow import fields, Schema, validates_schema, ValidationError +from marshmallow import fields, Schema class SourceInformationSchema(Schema): @@ -16,7 +16,7 @@ class SourceInformationSchema(Schema): class TechniqueSchema(Schema): source_information = fields.Str(allow_none=True) name = fields.Str(allow_none=True) - fullName = fields.Str(allow_none=True) + full_name = fields.Str(allow_none=True) asset_id = fields.Str(allow_none=True) id = fields.Int(allow_none=True) labels = fields.List(fields.Str(), allow_none=True) @@ -25,27 +25,27 @@ class TechniqueSchema(Schema): class NodeSchema(Schema): name = fields.Str(allow_none=True) - fullName = fields.Str(allow_none=True) + full_name = fields.Str(allow_none=True) asset_id = fields.Str(allow_none=True) id = fields.Int(allow_none=True) labels = fields.List(fields.Str(), allow_none=True) class VectorSchema(Schema): - isNew = fields.Bool(allow_none=True) - vectorId = fields.Str(allow_none=True) + is_new = fields.Bool(allow_none=True) + vector_id = fields.Str(allow_none=True) path = fields.Raw(allow_none=True) techniques = fields.List(fields.Nested(TechniqueSchema), allow_none=True) nodes = fields.List(fields.Nested(NodeSchema), allow_none=True) - findingsNames = fields.List(fields.Str(), allow_none=True) + findings_names = fields.List(fields.Str(), allow_none=True) name = fields.Str(allow_none=True) summary = fields.Str(allow_none=True) - firstAES = fields.Raw(allow_none=True) - lastACR = fields.Int(allow_none=True) + first_aes = fields.Raw(allow_none=True) + last_acr = fields.Int(allow_none=True) class VectorsPageSchema(Schema): data = fields.List(fields.Nested(VectorSchema), allow_none=True) - pageNumber = fields.Int(allow_none=True) + page_number = fields.Int(allow_none=True) count = fields.Int(allow_none=True) total = fields.Int(allow_none=True) diff --git a/tests/apa/vectors/test_vectors_api.py b/tests/apa/vectors/test_vectors_api.py index 54166b237..9f8b2ac50 100644 --- a/tests/apa/vectors/test_vectors_api.py +++ b/tests/apa/vectors/test_vectors_api.py @@ -8,14 +8,14 @@ @pytest.fixture def vector(): return { - "isNew": False, - "vectorId": "FFF93960363C0755F8C9D93E241DD26E", + "is_new": False, + "vector_id": "FFF93960363C0755F8C9D93E241DD26E", "path": None, "techniques": [ { "source_information": "[{\"provider_detection_id\":\"71246\",\"detection_code\":\"Enumerate Local Group Memberships\",\"reason_code_name\":null,\"asset_id\":\"0bd1382d-8ba7-41d7-bc27-0e874c655737\",\"id\":\"nessus:71246\",\"provider_code\":\"NESSUS\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"44401\",\"detection_code\":\"Microsoft Windows SMB Service Config Enumeration\",\"reason_code_name\":null,\"asset_id\":\"0bd1382d-8ba7-41d7-bc27-0e874c655737\",\"id\":\"nessus:44401\",\"provider_code\":\"NESSUS\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"64582\",\"detection_code\":\"Netstat Connection Information\",\"reason_code_name\":null,\"asset_id\":\"0bd1382d-8ba7-41d7-bc27-0e874c655737\",\"id\":\"nessus:64582\",\"provider_code\":\"NESSUS\",\"type\":\"nessus plugin\",\"reason_id\":null}]", "name": "Remote Desktop Protocol-251714", - "fullName": "Remote Desktop Protocol-251714", + "full_name": "Remote Desktop Protocol-251714", "asset_id": "", "id": 82656, "labels": [ @@ -26,7 +26,7 @@ def vector(): { "source_information": "[{\"provider_detection_id\":\"64582\",\"detection_code\":\"Netstat Connection Information\",\"reason_code_name\":null,\"asset_id\":\"fa6ed6d3-9426-4f7e-b414-373eace37f5f\",\"id\":\"nessus:64582\",\"provider_code\":\"NESSUS\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"191947\",\"detection_code\":null,\"reason_code_name\":null,\"asset_id\":\"fa6ed6d3-9426-4f7e-b414-373eace37f5f\",\"id\":\"nessus:191947\",\"provider_code\":\"NESSUS\",\"plugin_name\":\"\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"191947\",\"detection_code\":null,\"reason_code_name\":null,\"asset_id\":\"fa6ed6d3-9426-4f7e-b414-373eace37f5f\",\"id\":\"nessus:191947\",\"provider_code\":\"NESSUS\",\"plugin_name\":\"KB5035857: Windows 2022 / Azure Stack HCI 22H2 Security Update (March 2024)\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"CVE-2024-21444\",\"detection_code\":\"CVE-2024-21444\",\"reason_code_name\":null,\"id\":\"CVE-2024-21444\",\"provider_code\":\"NVD\",\"type\":\"CVE\",\"reason_id\":null}]", "name": "Exploitation of Remote Services-20940:251097", - "fullName": "Exploitation of Remote Services-20940:251097", + "full_name": "Exploitation of Remote Services-20940:251097", "asset_id": "", "id": 117132, "labels": [ @@ -37,7 +37,7 @@ def vector(): { "source_information": "[{\"provider_detection_id\":\"64582\",\"detection_code\":\"Netstat Connection Information\",\"reason_code_name\":null,\"asset_id\":\"037cb20a-5b0a-40d2-b5cc-3306ee005429\",\"id\":\"nessus:64582\",\"provider_code\":\"NESSUS\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"160937\",\"detection_code\":null,\"reason_code_name\":null,\"asset_id\":\"037cb20a-5b0a-40d2-b5cc-3306ee005429\",\"id\":\"nessus:160937\",\"provider_code\":\"NESSUS\",\"plugin_name\":\"\",\"type\":\"nessus plugin\",\"reason_id\":null},{\"provider_detection_id\":\"CVE-2022-26936\",\"detection_code\":\"CVE-2022-26936\",\"reason_code_name\":null,\"id\":\"CVE-2022-26936\",\"provider_code\":\"NVD\",\"type\":\"CVE\",\"reason_id\":null}]", "name": "Exploitation of Remote Services-12298:19222", - "fullName": "Exploitation of Remote Services-12298:19222", + "full_name": "Exploitation of Remote Services-12298:19222", "asset_id": "", "id": 27049, "labels": [ @@ -49,7 +49,7 @@ def vector(): "nodes": [ { "name": "Domain Users", - "fullName": "APADOMAIN\\domain users", + "full_name": "APADOMAIN\\domain users", "asset_id": "", "id": 252949, "labels": [ @@ -60,7 +60,7 @@ def vector(): }, { "name": "APAENG", - "fullName": "apaeng.apadomain.internal", + "full_name": "apaeng.apadomain.internal", "asset_id": "0bd1382d-8ba7-41d7-bc27-0e874c655737", "id": 251098, "labels": [ @@ -72,7 +72,7 @@ def vector(): }, { "name": "APADC", - "fullName": "apadc.apadomain.internal", + "full_name": "apadc.apadomain.internal", "asset_id": "fa6ed6d3-9426-4f7e-b414-373eace37f5f", "id": 251097, "labels": [ @@ -85,7 +85,7 @@ def vector(): }, { "name": "baaaaacnet", - "fullName": "baaaaacnet.indegy.local", + "full_name": "baaaaacnet.indegy.local", "asset_id": "037cb20a-5b0a-40d2-b5cc-3306ee005429", "id": 19222, "labels": [ @@ -94,30 +94,30 @@ def vector(): ] } ], - "findingsNames": [], + "findings_names": [], "name": "Domain Users can reach baaaaacnet by exploiting CVE-2024-21444 and CVE-2022-26936", "summary": "An attacker can use Domain Users to access baaaaacnet by exploiting two vulnerabilities. First, the attacker exploits CVE-2024-21444 on APAENG to gain access to APADC. Then, the attacker exploits CVE-2022-26936 on APADC to gain access to baaaaacnet. This attack path is possible because Domain Users is a member of Remote Desktop Users, which has remote desktop access to APAENG. This attack path is dangerous because it allows an attacker to gain access to a critical asset, baaaaacnet, by exploiting two vulnerabilities.", - "firstAES": None, - "lastACR": 9 + "first_aes": None, + "last_acr": 9 } @responses.activate def test_vectors_list_iterator(api, vector): responses.get('https://cloud.tenable.com/apa/api/discover/v1/vectors', - json={"pageNumber": 1, "count": 10, "total": 21, + json={"page_number": 1, "count": 10, "total": 21, "data": [vector for _ in range(10)]}, match=[responses.matchers.query_param_matcher({"limit": 10})]) responses.get('https://cloud.tenable.com/apa/api/discover/v1/vectors', - json={"pageNumber": 2, "count": 10, "total": 21, + json={"page_number": 2, "count": 10, "total": 21, "data": [vector for _ in range(10)]}, - match=[responses.matchers.query_param_matcher({"limit": 10, "pageNumber": 2})]) + match=[responses.matchers.query_param_matcher({"limit": 10, "page_number": 2})]) responses.get('https://cloud.tenable.com/apa/api/discover/v1/vectors', - json={"pageNumber": 3, "count": 10, "total": 21, + json={"page_number": 3, "count": 10, "total": 21, "data": [vector for _ in range(1)]}, - match=[responses.matchers.query_param_matcher({"limit": 10, "pageNumber": 3})]) + match=[responses.matchers.query_param_matcher({"limit": 10, "page_number": 3})]) vectors: VectorIterator = api.vectors.list() @@ -129,7 +129,7 @@ def test_vectors_list_iterator(api, vector): @responses.activate def test_vectors_list_vector_page_response(api, vector): - vectors_page_response = {"pageNumber": 1, "count": 10, "total": 10, + vectors_page_response = {"page_number": 1, "count": 10, "total": 10, "data": [vector for _ in range(10)]} responses.get('https://cloud.tenable.com/apa/api/discover/v1/vectors', json=vectors_page_response,