1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283 |
- # SPDX-License-Identifier: Apache-2.0
- # Copyright 2020 Contributors to OpenLEADR
- # 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.
- from asyncio import iscoroutine
- from http import HTTPStatus
- import os
- from aiohttp import web
- from jinja2 import Environment, PackageLoader, select_autoescape
- from .. import errors
- from ..messaging import create_message, parse_message
- from ..utils import generate_id
- from dataclasses import is_dataclass, asdict
- class VTNService:
- def __init__(self, vtn_id):
- self.vtn_id = vtn_id
- self.handlers = {}
- for method in [getattr(self, attr) for attr in dir(self) if callable(getattr(self, attr))]:
- if hasattr(method, '__message_type__'):
- self.handlers[method.__message_type__] = method
- async def handler(self, request):
- """
- Handle all incoming POST requests.
- """
- content = await request.read()
- message_type, message_payload = self._parse_message(content)
- if message_type in self.handlers:
- handler = self.handlers[message_type]
- result = handler(message_payload)
- if iscoroutine(result):
- result = await result
- if result is not None:
- response_type, response_payload = result
- if is_dataclass(response_payload):
- response_payload = asdict(response_payload)
- else:
- response_type, response_payload = 'oadrResponse', {}
- response_payload['vtn_id'] = self.vtn_id
- if 'ven_id' in message_payload:
- response_payload['ven_id'] = message_payload['ven_id']
- response_payload['response'] = {'request_id': message_payload.get('request_id', None),
- 'response_code': 200,
- 'response_description': 'OK'}
- response_payload['request_id'] = generate_id()
- # Create the XML response
- msg = self._create_message(response_type, **response_payload)
- response = web.Response(text=msg,
- status=HTTPStatus.OK,
- content_type='application/xml')
- else:
- msg = self._create_message('oadrResponse',
- ven_id=message_payload.get('ven_id'),
- status_code=errorcodes.COMPLIANCE_ERROR,
- status_description=f"A message of type {message_type} should not be sent to this endpoint")
- response = web.Response(
- text=msg,
- status=HTTPStatus.BAD_REQUEST,
- content_type='application/xml')
- return response
|