12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273 |
- #!/usr/bin/env python3
- import socket
- import select
- import struct
- import json
- from lib.ratelimit import rateLimit
- from lib.nodeinfo import Nodeinfo
- from lib.neighbours import Neighbours
- from lib.statistics import Statistics
- class ResponddClient:
- def __init__(self, config):
- self._config = config
- if 'rate_limit' in self._config:
- if 'rate_limit_burst' not in self._config:
- self._config['rate_limit_burst'] = 10
- self.__RateLimit = rateLimit(self._config['rate_limit'], self._config['rate_limit_burst'])
- else:
- self.__RateLimit = None
- self._nodeinfo = Nodeinfo(self._config)
- self._neighbours = Neighbours(self._config)
- self._statistics = Statistics(self._config)
- self._sock = socket.socket(socket.AF_INET6, socket.SOCK_DGRAM)
- def start(self):
- if_idx = socket.if_nametoindex(self._config['bridge'])
- group = socket.inet_pton(socket.AF_INET6, self._config['addr']) + struct.pack('I', if_idx)
- self._sock.setsockopt(socket.IPPROTO_IPV6, socket.IPV6_JOIN_GROUP, group)
- self._sock.bind(('::', self._config['port']))
- while True:
- msg, sourceAddress = self._sock.recvfrom(2048)
- msgSplit = str(msg, 'UTF-8').split(' ')
- if msgSplit[0] == 'GET': # multi_request
- for request in msgSplit[1:]:
- self.sendResponse(sourceAddress, request, True)
- else: # single_request
- self.sendResponse(sourceAddress, msgSplit[0], False)
- def sendResponse(self, destAddress, responseType, withCompression):
- if self.__RateLimit is not None and not self.__RateLimit.limit():
- print('rate limit reached!')
- return
- responseClass = None
- if responseType == 'statistics':
- responseClass = self._statistics
- elif responseType == 'nodeinfo':
- responseClass = self._nodeinfo
- elif responseType == 'neighbours':
- responseClass = self._neighbours
- else:
- print('unknown command: ' + responseType)
- return
- if not self._config['dry_run']:
- if withCompression:
- self._sock.sendto(responseClass.getJSONCompressed(responseType), destAddress)
- else:
- self._sock.sendto(responseClass.getJSON(responseType), destAddress)
- if self._config['verbose'] or self._config['dry_run']:
- print('%35s %5d %13s: ' % (destAddress[0], destAddress[1], responseType), end='')
- print(json.dumps(responseClass.getStruct(responseType), sort_keys=True, indent=4))
|