You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@trafficcontrol.apache.org by er...@apache.org on 2023/05/09 19:56:41 UTC
[trafficcontrol] branch master updated: Added divisions test case (#7453)
This is an automated email from the ASF dual-hosted git repository.
ericholguin pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/trafficcontrol.git
The following commit(s) were added to refs/heads/master by this push:
new 62c7a084c7 Added divisions test case (#7453)
62c7a084c7 is described below
commit 62c7a084c7feb85908363696c96120ddbdf69196
Author: Kashatlast2 <10...@users.noreply.github.com>
AuthorDate: Tue May 9 15:56:34 2023 -0400
Added divisions test case (#7453)
* Added divisions test case
* resolve linting issues
* trailing new lines removed
* resolved comments
* resolved comments
* Update conftest.py by fixing tabbing issues
* Update request_template.json by fixing tabbing issues
* fixed inconsistent use of tabs and spaces - Update conftest.py
* Changed all tabs to spaces - Update request_template.json
* Converted all spaces to tabs - Update conftest.py
* Update response_template.json
---------
Co-authored-by: yblanc545 <Yv...@comcast.com>
---
traffic_ops/testing/api_contract/v4/conftest.py | 52 ++++++++-
.../testing/api_contract/v4/request_template.json | 119 +++++++++++----------
.../testing/api_contract/v4/response_template.json | 14 +++
.../testing/api_contract/v4/test_divisions.py | 94 ++++++++++++++++
traffic_ops/testing/api_contract/v4/to_data.json | 4 +-
5 files changed, 220 insertions(+), 63 deletions(-)
diff --git a/traffic_ops/testing/api_contract/v4/conftest.py b/traffic_ops/testing/api_contract/v4/conftest.py
index 0d58cc0a27..ad721b3f5f 100644
--- a/traffic_ops/testing/api_contract/v4/conftest.py
+++ b/traffic_ops/testing/api_contract/v4/conftest.py
@@ -336,7 +336,7 @@ def request_prerequiste_data(pytestconfig: pytest.Config, request: pytest.Fixtur
@pytest.fixture()
def response_template_data(pytestconfig: pytest.Config
) -> dict[str, primitive | list[primitive |
- dict[str, object] | list[object]] | dict[object, object]]:
+ dict[str, object] | list[object]] | dict[object, object]]:
"""
PyTest Fixture to store response template data for api endpoint.
:param pytestconfig: Session-scoped fixture that returns the session's pytest.Config object.
@@ -572,7 +572,7 @@ def role_post_data(to_session: TOSession, request_template_data: list[JSONData]
@pytest.fixture()
def profile_post_data(to_session: TOSession, request_template_data: list[JSONData]
- ) -> dict[str, object]:
+ ) -> dict[str, object]:
"""
PyTest Fixture to create POST data for profile endpoint.
@@ -681,9 +681,8 @@ def server_capabilities_post_data(to_session: TOSession, request_template_data:
:param to_session: Fixture to get Traffic Ops session.
:param request_template_data: Fixture to get server_capabilities data from a prerequisites file.
- :returns: Sample POST data and the actual API response.
+ :returns: Sample POST data and the actual API response.
"""
-
try:
server_capabilities = request_template_data[0]
except IndexError as e:
@@ -716,3 +715,48 @@ def server_capabilities_post_data(to_session: TOSession, request_template_data:
except IndexError:
logger.error("No server_capabilities response data from server_capabilities POST request.")
sys.exit(1)
+
+
+@pytest.fixture()
+def division_post_data(to_session: TOSession, request_template_data: list[JSONData]
+ ) -> dict[str, object]:
+ """
+ PyTest Fixture to create POST data for divisions endpoint.
+
+ :param to_session: Fixture to get Traffic Ops session.
+ :param request_template_data: Fixture to get divisions request template data from
+ request_template file.
+ :returns: Sample POST data and the actual API response.
+ """
+
+ try:
+ division = request_template_data[0]
+ except IndexError as e:
+ raise TypeError(
+ "malformed prerequisite data; no division present in 'division' array property") from e
+
+ if not isinstance(division, dict):
+ raise TypeError(
+ f"malformed prerequisite data; divisions must be objects, not '{type(division)}'")
+
+ # Return new post data and post response from division POST request
+ randstr = str(randint(0, 1000))
+ try:
+ name = division["name"]
+ if not isinstance(name, str):
+ raise TypeError(f"name must be str, not '{type(name)}'")
+ division["name"] = name[:4] + randstr
+ except KeyError as e:
+ raise TypeError(f"missing Parameter property '{e.args[0]}'") from e
+
+ logger.info("New division data to hit POST method %s", request_template_data)
+ # Hitting division POST methed
+ response: tuple[JSONData, requests.Response] = to_session.create_division(data=division)
+ try:
+ resp_obj = response[0]
+ if not isinstance(resp_obj, dict):
+ raise TypeError("malformed API response; division is not an object")
+ return resp_obj
+ except IndexError:
+ logger.error("No division response data from division POST request.")
+ sys.exit(1)
diff --git a/traffic_ops/testing/api_contract/v4/request_template.json b/traffic_ops/testing/api_contract/v4/request_template.json
index 0404cd3704..89d575da4a 100644
--- a/traffic_ops/testing/api_contract/v4/request_template.json
+++ b/traffic_ops/testing/api_contract/v4/request_template.json
@@ -1,59 +1,64 @@
{
- "cdns": [
- {
- "name": "test",
- "domainName": "quest",
- "dnssecEnabled": false
- }
- ],
- "cachegroup": [
- {
- "name": "test",
- "shortName": "test",
- "latitude": 38.897663,
- "longitude": -77.036574,
- "fallbackToClosest": true,
- "localizationMethods": [
- "DEEP_CZ",
- "CZ",
- "GEO"
- ],
- "typeId": 23
- }
- ],
- "parameters": [
- {
- "name": "test",
- "value": "quest",
- "configFile": "records.config",
- "secure": false
- }
- ],
- "roles": [
- {
- "name": "test",
- "description": "quest"
- }
- ],
- "profiles": [
- {
- "name": "test",
- "description": "A test profile for API examples",
- "cdn": 2,
- "type": "UNK_PROFILE",
- "routingDisabled": true
- }
- ],
- "tenants": [
- {
- "active": true,
- "name": "test",
- "parentId": 1
- }
- ],
- "server_capabilities": [
- {
- "name": "RAM"
- }
- ]
+ "cdns": [
+ {
+ "name": "test",
+ "domainName": "quest",
+ "dnssecEnabled": false
+ }
+ ],
+ "cachegroup": [
+ {
+ "name": "test",
+ "shortName": "test",
+ "latitude": 38.897663,
+ "longitude": -77.036574,
+ "fallbackToClosest": true,
+ "localizationMethods": [
+ "DEEP_CZ",
+ "CZ",
+ "GEO"
+ ],
+ "typeId": 23
+ }
+ ],
+ "parameters": [
+ {
+ "name": "test",
+ "value": "quest",
+ "configFile": "records.config",
+ "secure": false
+ }
+ ],
+ "roles": [
+ {
+ "name": "test",
+ "description": "quest"
+ }
+ ],
+ "profiles": [
+ {
+ "name": "test",
+ "description": "A test profile for API examples",
+ "cdn": 2,
+ "type": "UNK_PROFILE",
+ "routingDisabled": true
+ }
+ ],
+ "tenants": [
+ {
+ "active": true,
+ "name": "test",
+ "parentId": 1
+ }
+ ],
+ "server_capabilities": [
+ {
+ "name": "RAM"
+ }
+ ],
+ "divisions":[
+ {
+ "name":"test"
+ }
+ ]
}
diff --git a/traffic_ops/testing/api_contract/v4/response_template.json b/traffic_ops/testing/api_contract/v4/response_template.json
index 1b63bce1d4..7e26105dde 100644
--- a/traffic_ops/testing/api_contract/v4/response_template.json
+++ b/traffic_ops/testing/api_contract/v4/response_template.json
@@ -183,5 +183,19 @@
"type": "str"
}
}
+ },
+ "divisions": {
+ "type": "object",
+ "properties": {
+ "id": {
+ "type": "int"
+ },
+ "lastUpdated": {
+ "type": "str"
+ },
+ "name": {
+ "type": "str"
+ }
+ }
}
}
diff --git a/traffic_ops/testing/api_contract/v4/test_divisions.py b/traffic_ops/testing/api_contract/v4/test_divisions.py
new file mode 100644
index 0000000000..a3da4c1bd1
--- /dev/null
+++ b/traffic_ops/testing/api_contract/v4/test_divisions.py
@@ -0,0 +1,94 @@
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+
+"""API Contract Test Case for divisions endpoint."""
+import logging
+import pytest
+import requests
+
+from trafficops.tosession import TOSession
+
+# Create and configure logger
+logger = logging.getLogger()
+
+primitive = bool | int | float | str | None
+
+@pytest.mark.parametrize('request_template_data', ["divisions"], indirect=True)
+def test_division_contract(
+ to_session: TOSession,
+ request_template_data: list[dict[str, object] | list[object] | primitive],
+ response_template_data: list[dict[str, object] | list[object] | primitive],
+ division_post_data: dict[str, object]
+) -> None:
+ """
+ Test step to validate keys, values and data types from divisions endpoint
+ response.
+ :param to_session: Fixture to get Traffic Ops session.
+ :param get_division_data: Fixture to get division data from a prerequisites file.
+ :param division_prereq: Fixture to get sample division data and actual division response.
+ """
+ # validate division keys from divisions get response
+ logger.info("Accessing divisions endpoint through Traffic ops session.")
+
+ division = request_template_data[0]
+ if not isinstance(division, dict):
+ raise TypeError("malformed division in prerequisite data; not an object")
+
+ division_name = division.get("name")
+ if not isinstance(division_name, str):
+ raise TypeError("malformed division in prerequisite data; 'name' not a string")
+
+ division_get_response: tuple[
+ dict[str, object] | list[dict[str, object] | list[object] | primitive] | primitive,
+ requests.Response
+ ] = to_session.get_divisions(query_params={"name": division_name})
+ try:
+ division_data = division_get_response[0]
+ if not isinstance(division_data, list):
+ raise TypeError("malformed API response; 'response' property not an array")
+
+ first_division = division_data[0]
+ if not isinstance(first_division, dict):
+ raise TypeError("malformed API response; first division in response is not an object")
+ division_keys = set(first_division.keys())
+
+ logger.info("division Keys from divisions endpoint response %s", division_keys)
+ response_template = response_template_data.get("divisions").get("properties")
+ # validate division values from prereq data in divisions get response.
+ prereq_values = [
+ division_post_data["name"]]
+ get_values = [first_division["name"]]
+ get_types = {}
+ for key, value in first_division.items():
+ get_types[key] = type(value).__name__
+ logger.info("types from division get response %s", get_types)
+ response_template_types= {}
+ for key, value in response_template.items():
+ response_template_types[key] = value.get("type")
+ logger.info("types from division response template %s", response_template_types)
+
+ assert division_keys == set(response_template.keys())
+ assert dict(sorted(get_types.items())) == dict(sorted(response_template_types.items()))
+ assert get_values == prereq_values
+ except IndexError:
+ logger.error("Either prerequisite data or API response was malformed")
+ pytest.fail("Failed due to malformation")
+ finally:
+ # Delete division after test execution to avoid redundancy.
+ try:
+ division_id = division_post_data["id"]
+ to_session.delete_division(division_id=division_id)
+ except IndexError:
+ logger.error("Division returned by Traffic Ops is missing an 'id' property")
+ pytest.fail("Response from delete request is empty, Failing test_get_division")
diff --git a/traffic_ops/testing/api_contract/v4/to_data.json b/traffic_ops/testing/api_contract/v4/to_data.json
index 903a0434a8..c7b1fbec34 100644
--- a/traffic_ops/testing/api_contract/v4/to_data.json
+++ b/traffic_ops/testing/api_contract/v4/to_data.json
@@ -1,6 +1,6 @@
{
"user": "admin",
- "password": "twelve12",
+ "password": "twelve",
"url": "https://localhost/api/4.0",
"port": 443
-}
\ No newline at end of file
+}