-
Robert Latta authoredRobert Latta authored
classifier.py 3.56 KiB
import functools
from flask import Blueprint, request, Response, current_app, jsonify
import json
import jsonschema
from inventory_provider import db
routes = Blueprint("inventory-data-classifier-support-routes", __name__)
def require_accepts_json(f):
"""
used as a route handler decorator to return an error
unless the request allows responses with type "application/json"
:param f: the function to be decorated
:return: the decorated function
"""
@functools.wraps(f)
def decorated_function(*args, **kwargs):
# TODO: use best_match to disallow */* ...?
if not request.accept_mimetypes.accept_json:
return Response(
response="response will be json",
status=406,
mimetype="text/html")
return f(*args, **kwargs)
return decorated_function
@routes.route("/infinera-dna-addresses", methods=['GET', 'POST'])
@require_accepts_json
def infinera_addresses():
infinera_config = current_app.config[
"INVENTORY_PROVIDER_CONFIG"]["infinera-dna"]
return jsonify([dna['address'] for dna in infinera_config])
@routes.route("/coriant-tnms-addresses", methods=['GET', 'POST'])
@require_accepts_json
def coriant_addresses():
coriant_config = current_app.config[
"INVENTORY_PROVIDER_CONFIG"]["coriant-tnms"]
return jsonify([tnms['address'] for tnms in coriant_config])
@routes.route("/juniper-server-addresses", methods=['GET', 'POST'])
@require_accepts_json
def juniper_addresses():
backend_data_schema = {
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "array",
"items": {
"type": "object",
"properties": {
"ip_address": {"type": "string"}
},
"required": ["ip_address"]
}
}
servers = db.get_redis().get('alarmsdb:juniper_servers')
if not servers:
return Response(
response="no juniper server data found",
status=404,
mimetype="text/html")
servers = json.loads(servers.decode('utf-8'))
jsonschema.validate(servers, backend_data_schema)
return jsonify([s['ip_address'] for s in servers])
@routes.route("/trap-metadata/<trap_type>/<source_equipment>/<path:interface>",
methods=['GET', 'POST'])
@require_accepts_json
def get_trap_metadata(trap_type, source_equipment, interface):
# todo - Move this to config
interface_info_key = "interface_services"
r = db.get_redis()
# todo - Change this to a call to the yet-to-be-created one source of all
# relevant information
# This could be different calls dependant on vendor, in which case we may
# need to check the trap type, or it could be a case of a key check for
# each possible data source
interface_info = r.hget(interface_info_key,
"{}::{}".format(source_equipment, interface))
if not interface_info:
return Response(
response="no available info for {} {}".format(
source_equipment, interface),
status=404,
mimetype="text/html")
interface_info = json.loads(interface_info.decode('utf-8'))
# todo - refactor once structure of new source is decided, currently this
# is just a list of services
vendor = interface_info[0]['manufacturer']
hostname = interface_info[0]['equipment']
result = {
"vendor": vendor,
"equipment-name": hostname,
"interface-name": interface,
"services": interface_info,
"type": trap_type
}
return jsonify(result)