From 59ffb7bec9e4cc51f11c20f84df0b49ebcacc03c Mon Sep 17 00:00:00 2001 From: Erik Reid <erik.reid@geant.org> Date: Sun, 14 Feb 2021 13:07:41 +0100 Subject: [PATCH] implemented logical-system-peerings handler, added tests --- inventory_provider/routes/msr.py | 65 +++++++++++++++++++++----------- test/test_msr_routes.py | 31 ++++++++++++++- 2 files changed, 72 insertions(+), 24 deletions(-) diff --git a/inventory_provider/routes/msr.py b/inventory_provider/routes/msr.py index e8018baf..0420367d 100644 --- a/inventory_provider/routes/msr.py +++ b/inventory_provider/routes/msr.py @@ -1,3 +1,4 @@ +import itertools import json from flask import Blueprint, jsonify, Response @@ -80,6 +81,7 @@ def access_services(): .. asjson:: inventory_provider.routes.msr.ACCESS_SERVICES_LIST_SCHEMA + :param name: :return: """ redis = common.get_current_redis() @@ -111,40 +113,57 @@ def access_services(): @routes.route("/logical-system-peerings", methods=['GET', 'POST']) @routes.route("/logical-system-peerings/<name>", methods=['GET', 'POST']) @common.require_accepts_json -def access_services(): +def logical_system_peerings(name=None): """ - Handler for `/msr/access-services`. + Handler for `/msr/logical-system-peerings - This method is in development, not yet used. + This method will return a list of all peerings configured + for the requested logical-system name on any router, or for any + logical system if no parameter is given. The response will be formatted according to the following schema: .. asjson:: - inventory_provider.routes.msr.ACCESS_SERVICES_LIST_SCHEMA + inventory_provider.routes.msr.LOGICAL_SYSTEM_PEERING_LIST_SCHEMA :return: """ - redis = common.get_current_redis() - def _services(): - for k in redis.scan_iter('opsdb:access_services:*'): - service = redis.get(k.decode('utf-8')).decode('utf-8') - yield json.loads(service) + r = common.get_current_redis() - cache_key = 'classifier-cache:msr:access-services' - result = redis.get(cache_key) + def _get_all_ls_keys(): + keys = [] + for k in r.scan_iter(f'juniper-peerings:logical-system:*', count=1000): + keys.append(k.decode('utf-8')) + return keys - if result: - result = json.loads(result.decode('utf-8')) - else: - result = list(_services()) - # cache this data for the next call - redis.set(cache_key, json.dumps(result).encode('utf-8')) + def _load_list_items(key): + value = r.get(key) + if value: + yield from json.loads(value.decode('utf-8')) - if not result: - return Response( - response='no access services found', - status=404, - mimetype="text/html") + cache_key = 'classifier-cache:msr:logical-system-peerings' + if name: + cache_key = f'{cache_key}:name' - return jsonify(result) + items = r.get(cache_key) + + if items: + items = json.loads(items.decode('utf-8')) + else: + if name: + items = _load_list_items(f'juniper-peerings:logical-system:{name}') + else: + gen_list = list(map(_load_list_items, _get_all_ls_keys())) + items = itertools.chain(*gen_list) + + items = list(items) + if not items: + return Response( + response='no peerings found', + status=404, + mimetype="text/html") + + r.set(cache_key, json.dumps(items).encode('utf-8')) + + return jsonify(items) diff --git a/test/test_msr_routes.py b/test/test_msr_routes.py index b842938d..d2f812f3 100644 --- a/test/test_msr_routes.py +++ b/test/test_msr_routes.py @@ -1,6 +1,10 @@ import json import jsonschema -from inventory_provider.routes.msr import ACCESS_SERVICES_LIST_SCHEMA + +import pytest + +from inventory_provider.routes.msr \ + import ACCESS_SERVICES_LIST_SCHEMA, LOGICAL_SYSTEM_PEERING_LIST_SCHEMA DEFAULT_REQUEST_HEADERS = { "Content-type": "application/json", @@ -18,3 +22,28 @@ def test_access_services(client): jsonschema.validate(response_data, ACCESS_SERVICES_LIST_SCHEMA) assert response_data # test data is non-empty + + +def test_logical_system_peerings_all(client): + rv = client.get( + '/msr/logical-system-peerings', + headers=DEFAULT_REQUEST_HEADERS) + assert rv.status_code == 200 + assert rv.is_json + response_data = json.loads(rv.data.decode('utf-8')) + jsonschema.validate(response_data, LOGICAL_SYSTEM_PEERING_LIST_SCHEMA) + + assert response_data # test data is non-empty + + +@pytest.mark.parametrize('name', ['VRR', 'VPN-PROXY']) +def test_logical_system_peerings_specific(client, name): + rv = client.get( + f'/msr/logical-system-peerings/{name}', + headers=DEFAULT_REQUEST_HEADERS) + assert rv.status_code == 200 + assert rv.is_json + response_data = json.loads(rv.data.decode('utf-8')) + jsonschema.validate(response_data, LOGICAL_SYSTEM_PEERING_LIST_SCHEMA) + + assert response_data # test data is non-empty -- GitLab