示例#1
0
 def __print_summary(self):
     s = "\n######################## FCJP ##########################\n"
     summary = self.summary()
     for item in summary.keys():
         s += '\t[\"{}\"] : {}\n'.format(item, summary.get(item))
     s += "########################################################\n"
     LOG.info(s)
 def setJson(self, json):
     try:
         ljson = loads(json)
         return self.setDict(ljson)
     except JSONDecodeError:
         LOG.exception('Error on getting new device via JSON.')
         return False
示例#3
0
def cimi(key, default=None):
    value = default
    if key == 'leader':
        value = CPARAMS.LEADER_FLAG
    elif key == 'topology':
        value = []
        # 1. Try to get the real topology
        cimi_topology = CIMI.get_topology()
        if len(cimi_topology) > 0:
            used_topology = cimi_topology
            # used_topology = list()
            # for item in cimi_topology:        # TODO: Dataclay doesnt sync device static information to the leader
            #     qdeviceID = CIMI.get_deviceID_from_IP(item[1])
            #     if qdeviceID != '':
            #         used_topology.append((qdeviceID, item[1]))
        else:
            used_topology = CPARAMS.TOPOLOGY_FLAG

        try:
            for item in used_topology:
                i = {'deviceID': item[0], 'deviceIP': item[1]}
                value.append(i)
        except:
            LOG.exception(
                'Topology Environment variable format is not correct.')
            value = []

    return value
示例#4
0
    def getIPfromFile(file_path=CPARAMS.VPN_FILE_PATH):
        """
        Get the IP of the device in the VPN network from the JSON file generated by the VPN client component.

        :param file_path: Path to the VPN JSON file
        :return: string with IP of the device, empty if failure
        """
        ret_ip = ''
        try:
            with open(file_path, mode='r') as json_file:
                json_txt = json_file.readlines()[0]
                ljson = json.loads(json_txt)
                if ljson['status'] == 'connected':
                    ret_ip = str(ljson['ip'])
                    LOG.debug(
                        'VPN IP successfully parsed from JSON file at \'{}\'. Content: {} IP: {}'
                        .format(file_path, str(ljson), ret_ip))
                else:
                    LOG.warning(
                        'VPN JSON status != \'connected\': Content: {}'.format(
                            str(ljson)))
        except OSError:
            LOG.exception('VPN file cannot be open or found at \'{}\'.'.format(
                file_path))
        except (IndexError, KeyError):
            LOG.exception('VPN error on parsing the IP.')
        except:
            LOG.exception('VPN generic error.')
        finally:
            return ret_ip
示例#5
0
 def __keeper(self):
     """
     Thread that reduces the TTL of a backup and demotes if TTL <= 0
     :return:
     """
     LOG.debug('Keeper is running')
     with self.backupDatabaseLock:
         self.backupDatabase = []  # Restart database
     while self._connected:
         with self.backupDatabaseLock:
             for backup in self.backupDatabase:
                 # Reduce TTL
                 backup.TTL -= 1
                 if backup.TTL < 0:
                     # Backup is down
                     LOG.warning(
                         'Backup {}[{}] is DOWN with TTL: {}'.format(
                             backup.deviceID, backup.deviceIP, backup.TTL))
                     self.__send_demotion_message(backup.deviceIP)
                     # Remove from list
                     self.backupDatabase.remove(
                         backup)  # TODO: Inform CIMI?
                     LOG.debug('Backup removed from database.')
                 else:
                     # Backup is ok
                     LOG.debug('Backup {}[{}] is OK with TTL: {}'.format(
                         backup.deviceID, backup.deviceIP, backup.TTL))
         if self._connected:
             sleep(self._lpp.get(self._lpp.TIME_KEEPER))
     LOG.warning('Keeper thread stopped')
示例#6
0
 def createAgentResource(agentResource):
     """
     Create a new Agent Resource in CIMI
     :param agentResource: Agent resource dicc formated
     :return: Agent resource ID
     """
     URL = CIMIcalls.CIMI_URL + CIMIcalls.CIMI_AGENT_RESOURCE
     payload = agentResource
     try:
         r = requests.post(URL,
                           headers=CIMIcalls.CIMI_HEADERS,
                           verify=False,
                           json=payload)
         rjson = r.json()
         LOG.debug(
             'CIMI create agent [{}] status_code {} resource-id {}'.format(
                 URL, r.status_code, rjson.get('resource-id')))
         LOG.debug('CIMI reply: {}'.format(r.text))
         if r.status_code == 409:
             LOG.error(
                 'CIMI create agent already exists! resource-id {}'.format(
                     rjson.get('resource-id')))
         elif r.status_code not in [200, 201]:
             LOG.error(
                 'CIMI create Agent error dettected! Payload Sent: {}'.
                 format(payload))
         return str(rjson.get('resource-id'))
     except:
         LOG.exception('CIMI agent [{}] failed'.format(URL))
         return ''
示例#7
0
    def __trigger_triggerCAUclient(self):
        # payload = {
        #     'MACaddr': self.MACaddr,
        #     'detectedLeaderID': self.detectedLeaderID,
        #     'deviceID': self.deviceID,
        #     'IDkey': self.IDkey
        # }
        s_caucl = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        s_caucl.connect(CPARAMS.CAU_CLIENT_ADDR)
        s_caucl.settimeout(15.)
        s_caucl.send('detectedLeaderID={},deviceID={}\n'.format(
            self.detectedLeaderID, self.deviceID).encode())
        reply = s_caucl.recv(4092).decode()
        LOG.debug(self.TAG + 'CAU_client reply: {}'.format(reply))
        s_caucl.close()

        if 'OK' in reply:
            self.isAuthenticated = True
            self.secureConnection = True
            return True
        else:
            LOG.warning(
                self.TAG +
                'CAU_client reply \'{}\' evaluated as error'.format(reply))
            self.isAuthenticated = False
            self.secureConnection = False
            return False
示例#8
0
    def __becomeLeader(self):  # TODO
        """

        :return:
        """
        # 1- Shutdown/Notify all the modules involving Agent to Leader transiction.
        if self._leaderFailed:
            # Only if leader fails, triggers are needed, otherwise no action is required
            try:
                r = requests.get(
                    URLS.build_url_address(
                        '{}leader'.format(URLS.URL_POLICIES_ROLECHANGE),
                        portaddr=(
                            '127.0.0.1',
                            '46050')))  #TODO Addr+Prt by CPARAMS; Parametrize
                LOG.info(
                    self.TAG +
                    'Trigger to AgentStart Switch done. {}'.format(r.json()))
                self._imLeader = True
                self._imBackup = False
            except Exception as ex:
                LOG.exception(self.TAG +
                              '_becomeLeader trigger to AgentStart failed')
        self.th_keep = threading.Thread(name='ar_keeper',
                                        target=self.__keeper,
                                        daemon=True)
        self.th_keep.start()
示例#9
0
    def post(self):
        """Reelection of the Leader"""
        found = False
        deviceIP = ''
        deviceID = api.payload['deviceID']
        for device in cimi('topology', default=[]):  # TODO: use real topology
            if device.get('deviceID') == deviceID:
                found = True
                deviceIP = device.get('deviceIP')
                break

        if not found:
            LOG.error('Device {} not found in the topology'.format(deviceID))
            return {'deviceID': deviceID, 'deviceIP': deviceIP}, 404
        if not arearesilience.imLeader():
            LOG.error(
                'Device is not a Leader, cannot perform a reelection in a non-leader device.'
            )
            return {'deviceID': deviceID, 'deviceIP': deviceIP}, 401

        correct = LeaderReelection.reelection(arearesilience, deviceID,
                                              deviceIP)
        if correct:
            return {'deviceID': deviceID, 'deviceIP': deviceIP}, 200
        else:
            return {'deviceID': deviceID, 'deviceIP': deviceIP}, 403
示例#10
0
    def post(self):
        """Keepalive entrypoint for Leader"""
        if not arearesilience.imLeader():
            # It's not like I don't want you to send me messages or anything, b-baka!
            return {
                'deviceID': agentstart.deviceID,
                'backupPriority': arearesilience.PRIORITY_ON_FAILURE
            }, 405

        deviceIP = '' if 'deviceIP' not in api.payload else api.payload[
            'deviceIP']
        correct, priority = arearesilience.receive_keepalive(
            api.payload['deviceID'], deviceIP)
        LOG.debug(
            'Device {} has sent a keepalive. Result correct: {}, Priority: {}, deviceIP: {}'
            .format(api.payload['deviceID'], correct, priority, deviceIP))
        if correct:
            # Authorized
            return {
                'deviceID': agentstart.deviceID,
                'backupPriority': priority
            }, 200
        else:
            # Not Authorized
            return {
                'deviceID': agentstart.deviceID,
                'backupPriority': priority
            }, 403
 def receivePolicies(self, payload):
     for key in payload:
         if key in self.__POLICIES.keys():
             self.__POLICIES[key].set_json(payload[key])
     LOG.info('Policies Received from Leader.')
     for policy in self.__POLICIES.keys():
         LOG.debug('[{}] - {}'.format(policy, self.__POLICIES[policy].get_json()))
     return True
示例#12
0
 def get_topology():
     resource, CIMIid = CIMIcalls.getAgentResource()
     topology = []
     device_id = 0
     if 'childrenIPs' in resource:
         for childrenIP in resource['childrenIPs']:
             topology.append((str(device_id), str(childrenIP)))
     LOG.debug('{} devices found in childrenIPs Agent Resource.'.format(
         len(topology)))
     return topology
 def recv_reply(self, payload, deviceIP):
     try:
         dev_obj = DeviceInformation(dict=payload)
         dev_obj.deviceIP = deviceIP
         with self._db_lock:
             self._db.update({dev_obj.deviceID: dev_obj})
         LOG.debug('Topology added/modified device: {}'.format(dev_obj))
         return True
     except:
         LOG.exception('Error on receiving reply from device to a beacon.')
         return False
 def setDict(self, dict):
     try:
         self.deviceID = str(dict.get('deviceID'))
         self.deviceIP = str(dict.get('deviceIP'))
         self.cpu_cores = int(dict.get('cpu_cores'))
         self.mem_avail = float(dict.get('mem_avail'))
         self.stg_avail = float(dict.get('stg_avail'))
         return True
     except:
         LOG.exception('Error on getting new device via Dict.')
         return False
 def set_json(self, json):
     with self.__lock:
         try:
             ljson = loads(json)
             for key in ljson.keys():
                 if key in self.POLICIES.keys():
                     self.POLICIES[key] = ljson[key]
             return True
         except JSONDecodeError:
             LOG.exception('Error on getting new policies.')
             return False
示例#16
0
def recommender_get_ips():
    topology = CIMI.get_topology()
    agent_res, res_id = CIMI.getAgentResource()
    if res_id != '' and 'device_ip' in agent_res:
        self_device_ip = agent_res['device_ip']
    else:
        self_device_ip = None
    response = [{'ipaddress': ip[1]} for ip in topology]
    if self_device_ip is not None:
        response.append({'ipaddress': self_device_ip})
    LOG.debug('Recommender API response: \"{}\"'.format(response))
    return jsonify(response), 200
示例#17
0
 def receive_keepalive(self, deviceID):
     with self.backupDatabaseLock:
         for backup in self.backupDatabase:
             if backup.deviceID == deviceID:
                 # It's a match
                 backup.TTL = int(self._lpp.get(self._lpp.MAX_TTL))
                 LOG.debug(
                     'backupID: {}; backupIP: {}; priority: {}; Keepalive received correctly'
                     .format(backup.deviceID, backup.deviceIP,
                             backup.priority))
                 return True, backup.priority
     return False, self.PRIORITY_ON_DEMOTION
示例#18
0
 def __trigger_startScan(self):
     r = requests.get(self.URL_DISCOVERY)
     rjson = r.json()
     if 'found_leaders' in rjson and 'used_mac' in rjson and len(
             rjson['found_leaders']) > 0:
         self.detectedLeaderID, self.MACaddr, self.bssid = rjson[
             'found_leaders'][0]['Leader ID'], rjson['used_mac'], rjson[
                 'found_leaders'][0]['Bssid']
     else:
         LOG.error(
             self.TAG +
             'Discovery is not detecting a Leader \'{}\''.format(rjson))
         self.detectedLeaderID, self.MACaddr, self.bssid = None, None, None
示例#19
0
def debug():
    sleep(10)   # Give some time to the webservice
    LOG.info('Starting LDiscovery...')
    if CPARAMS.LEADER_FLAG:
        r = requests.get(URLS.build_url_address('{}beacon/start'.format(URLS.URL_LDISCOVERY_CONTROL), portaddr=('127.0.0.1', CPARAMS.POLICIES_PORT)))
    else:
        r = requests.get(URLS.build_url_address('{}scan/start'.format(URLS.URL_LDISCOVERY_CONTROL), portaddr=('127.0.0.1', CPARAMS.POLICIES_PORT)))
    LOG.info('LDiscovery started with status_code = {}'.format(r.status_code))
    LOG.info('Starting Area Resilience...')
    r = requests.get(URLS.build_url_address(URLS.URL_POLICIES, portaddr=('127.0.0.1', CPARAMS.POLICIES_PORT)))
    LOG.debug('Area Resilience request result: {}'.format(r.json()))
    LOG.debug('Stopping thread activity.')
    return
示例#20
0
 def __trigger_switch_discovery(self):
     payload = {
         'broadcast_frequency': 100,
         'interface_name': CPARAMS.WIFI_DEV_FLAG,
         'config_file': CPARAMS.WIFI_CONFIG_FILE,
         'leader_id': self.deviceID
     }
     r = requests.post(self.URL_DISCOVERY_SWITCH_LEADER, json=payload)
     rjson = r.json()
     LOG.debug(
         self.TAG +
         'Discovery broadcast start trigger received code: {} with msg: {}'.
         format(r.status_code, rjson['message']))
     self.discovery_switched = rjson['message']
     if r.status_code != 200:
         LOG.warning(
             self.TAG +
             'Discovery broadcast failed with code {}. DHCP trigger is not performed.'
             .format(r.status_code))
     else:
         payload2 = {'interface_name': CPARAMS.WIFI_DEV_FLAG}
         r2 = requests.post(self.URL_DISCOVERY_DHCP, json=payload2)
         rjson2 = r2.json()
         self.discovery_switched += '|| DHCP: ' + rjson2['message']
         if r2.status_code == 200:
             LOG.debug(
                 self.TAG +
                 'Discovery DHCP trigger successfully done with message: {}.'
                 .format(rjson2['message']))
             return True
         else:
             LOG.warning(self.TAG +
                         'Discovery DHCP trigger failed with code {}'.
                         format(r2.status_code))
     return False
示例#21
0
 def checkCIMIstarted():
     """
     Check if CIMI is up.
     :return: True if CIMI is started, False otherwise.
     """
     URL = CIMIcalls.CIMI_URL + CIMIcalls.CIMI_API_ENTRY
     try:
         r = requests.get(URL, headers=CIMIcalls.CIMI_HEADERS, verify=False)
         LOG.debug('CIMI [{}] status_code {}, content {}'.format(
             URL, r.status_code, r.text))
         return True
     except Exception as ex:
         LOG.debug('CIMI [{}] failed. Exception: {}'.format(URL, ex))
         return False
示例#22
0
    def stop(self):
        """
        Stop all the module activity
        :return:
        """
        if self.isStarted:
            self._connected = False
            if self.th_proc is not None:
                while self.th_proc.is_alive():
                    LOG.debug(self.TAG +
                              'Waiting {} to resume activity...'.format(
                                  self.th_proc.name))
                    sleep(0.5)

            if self.th_keep is not None:
                while self.th_keep.is_alive():
                    LOG.debug(self.TAG +
                              'Waiting {} to resume activity...'.format(
                                  self.th_keep.name))
                    sleep(0.1)
            LOG.info(self.TAG +
                     'All threads stoped. AreaResilience module is stopped.')
        else:
            LOG.info(self.TAG + 'Module is not started')
        return
示例#23
0
 def get_resource(resource_id):
     """
     Get resource by ID if exists
     :param resource_id: CIMI resource id
     :return: status_code and resource if successful, None otherwise
     """
     URL = CIMIcalls.CIMI_URL + '/' + resource_id
     try:
         r = requests.get(URL, headers=CIMIcalls.CIMI_HEADERS, verify=False)
         rjson = r.json()
         LOG.debug('CIMI GET resource [{}] status_code {}'.format(
             URL, r.status_code))
         return r.status_code, rjson
     except:
         LOG.exception('CIMI GET resource [{}] failed.'.format(URL))
         return None, None
示例#24
0
 def addBackup(self, deviceID, deviceIP, priority):
     found = False
     with self.backupDatabaseLock:
         for backup in self.backupDatabase:
             if backup.deviceID == deviceID:
                 LOG.debug(self.TAG + 'Backup {} found!'.format(deviceID))
                 found = True
                 break
     if not found:
         correct = self.__send_election_message(deviceIP)
         if correct:
             new_backup = BackupEntry(deviceID, deviceIP, priority)
             with self.backupDatabaseLock:
                 self.backupDatabase.append(new_backup)
             LOG.info('Backup {}[{}] added with priority {}'.format(
                 deviceID, deviceIP, priority))
         return correct
示例#25
0
    def start(self, deviceID):  # TODO: Give deviceID at startup?
        """

        :return:
        """
        self._deviceID = deviceID
        if self.isStarted:
            LOG.warning(self.TAG + 'Procedure is already started...')
            return False
        else:
            self.th_proc = threading.Thread(name='area_res',
                                            target=self.__common_flow,
                                            daemon=True)
            self.th_proc.start()
            self.isStarted = True
            LOG.info(self.TAG + 'Module Started')
            return True
 def startScanning(self):
     if self._isStarted or self._isScanning:
         LOG.warning(
             'LDiscovery is already started: isStarted={} isScanning={}'.
             format(self._isStarted, self._isScanning))
         return False
     self._th_proc = threading.Thread(name='LDiscS',
                                      target=self.__scanning_flow,
                                      daemon=True)
     self._connected = True
     self._isStarted = True
     self._isScanning = True
     self.leaderIP = None
     self.leaderID = None
     self._th_proc.start()
     LOG.info('LDiscovery successfully started in Scan Mode.')
     return True
 def __categorize_device(self):
     try:
         cpu_cores = int(
             psutil.cpu_count()) if psutil.cpu_count() is not None else -1
         mem_avail = float(psutil.virtual_memory().available / (2**30))
         storage_avail = float(
             sum([
                 psutil.disk_usage(disk.mountpoint).free
                 for disk in psutil.disk_partitions()
             ]) / 2**30)
     except:
         LOG.exception('Categorization not successful')
         cpu_cores = 0
         mem_avail = .0
         storage_avail = .0
     finally:
         return cpu_cores, mem_avail, storage_avail
示例#28
0
 def delete_resource(resource_id):
     """
     Delete resource by ID in CIMI
     :param resource_id: CIMI resource ID
     :return: status_code if successful, None otherwise
     """
     URL = CIMIcalls.CIMI_URL + '/' + resource_id
     try:
         r = requests.delete(URL,
                             headers=CIMIcalls.CIMI_HEADERS,
                             verify=False)
         # rjson = r.json()
         LOG.debug('CIMI DELETE resource [{}] status_code {}'.format(
             URL, r.status_code))
         return r.status_code
     except:
         LOG.exception('CIMI DELETE resource [{}] failed.'.format(URL))
         return None
 def startBeaconning(self):
     if self._isStarted or self._isBroadcasting:
         LOG.warning(
             'LDiscovery is already started: isStarted={} isBroadcasting={}'
             .format(self._isStarted, self._isBroadcasting))
         return False
     self._th_proc = threading.Thread(name='LDiscB',
                                      target=self.__beaconning_flow,
                                      daemon=True)
     self._connected = True
     self._isStarted = True
     self._isBroadcasting = True
     self.leaderIP = None
     self.leaderID = self._deviceID
     self._db = {}
     self._th_proc.start()
     LOG.info('LDiscovery successfully started in Beacon Mode.')
     return True
示例#30
0
 def modify_resource(resource_id, payload):
     """
     Modify resource by ID in CIMI
     :param resource_id: CIMI resource id
     :param payload: new content of the resource
     :return: status_code if successful, None otherwise
     """
     URL = CIMIcalls.CIMI_URL + '/' + resource_id
     try:
         r = requests.put(URL,
                          headers=CIMIcalls.CIMI_HEADERS,
                          verify=False,
                          json=payload)
         # rjson = r.json()
         LOG.debug(
             'CIMI EDIT resource [{}] status_code {} content {}'.format(
                 URL, r.status_code, r.content))
         return r.status_code
     except:
         LOG.exception('CIMI EDIT resource [{}] failed.'.format(URL))
         return None