Ejemplo n.º 1
0
class IDFilter(Agent):
    """Listens to a certain trigger event, and emits a target event once the specified count has been reached."""

    autostart = False

    def __init__(self, ID, target=None):
        Agent.__init__(self)
        self.target = target if target is not None else self.identifier
        self.dispatcher = Dispatcher()
        self.id = ID

    def handle_event(self, event):
        if "id" in event and event["id"] == self.id:
            outgoing_event = Event(type=self.target, data=event["data"])
            self.dispatcher.put_event(outgoing_event)
Ejemplo n.º 2
0
class DispatcherTest(unittest.TestCase):
    def setUp(self):
        self.am = AgentManager()
        self.dispatcher = Dispatcher()
        self.dispatcher.daemon = True
        self.dispatcher.start()

    def test_subscription(self):
        agent = MockAgent()
        self.am.add_agent(agent)
        self.dispatcher.bind(agent, "test")

        agent.create_event()
        agent.start()

        timed_out = not agent.event_received.wait(1)
        if timed_out:
            self.fail("Event not received")

    def tearDown(self):
        AgentManager.reset_singleton()
        Dispatcher.reset_singleton()
Ejemplo n.º 3
0
 def __init__(self, target=None, netmask=24):
     super(DeviceMonitor, self).__init__()
     # Initialize values
     self.target = target if target is not None else self.identifier
     self.dispatcher = Dispatcher()
     self.threadpool = ThreadPool(5)
     self.updateinterval = 30
     self._known_devices = {}
     # Fetch network device IPs
     default_gateway = netifaces.gateways()["default"]
     if default_gateway:
         (gateway_ip, interface) = default_gateway[netifaces.AF_INET]
         self.network = ipaddress.ip_network("%s/%d" % (gateway_ip, netmask), False)
     else:
         logging.error("DeviceMonitor couldn't start, no default gateway available")
         self.stop()
Ejemplo n.º 4
0
class DeviceMonitor(Agent):

    autostart = True

    def __init__(self, target=None, netmask=24):
        super(DeviceMonitor, self).__init__()
        # Initialize values
        self.target = target if target is not None else self.identifier
        self.dispatcher = Dispatcher()
        self.threadpool = ThreadPool(5)
        self.updateinterval = 30
        self._known_devices = {}
        # Fetch network device IPs
        default_gateway = netifaces.gateways()["default"]
        if default_gateway:
            (gateway_ip, interface) = default_gateway[netifaces.AF_INET]
            self.network = ipaddress.ip_network("%s/%d" % (gateway_ip, netmask), False)
        else:
            logging.error("DeviceMonitor couldn't start, no default gateway available")
            self.stop()

    def run(self):
        start_time = time.time()
        available_devices = set()

        while self._enabled:
            # Get current local network devices
            current_devices = self._get_active_devices()
            # Filter out new and lost devices
            new_devices = current_devices - available_devices
            lost_devices = available_devices - current_devices

            for (ip, hostname) in new_devices:
                data = {"data": {"status": "connected", "hostname": hostname}}
                self.dispatcher.put_event(Event(type="device_connection", data=data))
                self._known_devices[hostname] = {"ip": ip, "hostname": hostname, "status": True, "ports": []}

            for (ip, hostname) in lost_devices:
                data = {"data": {"status": "disconnected", "hostname": hostname}}
                self.dispatcher.put_event(Event(type="device_connection", data=data))
                self._known_devices[hostname]["status"] = False

            # Update available devices
            available_devices = current_devices

            # Check all devices open homebrain ports
            openports = self._get_open_ports()
            for item in openports:
                # Get past values
                device = self._known_devices[item[0]]
                currentports = item[1]
                prevports = set(device["ports"])
                # Filter out new and lost ports
                newports = set(currentports) - prevports
                lostports = set(prevports) - set(currentports)
                if newports:
                    logging.info(
                        "New homebrain node(s) from '{}' available: {}".format(device["hostname"], str(newports))
                    )
                if lostports:
                    logging.info(
                        "Homebrain node(s) from '{}' is now unavailable: {}".format(device["hostname"], str(lostports))
                    )
                # Update to new ports
                device["ports"] = currentports

            # Wait for the next update interval
            while start_time + self.updateinterval > time.time():
                time.sleep(1)
            start_time = time.time()

    def _get_active_devices(self):
        hosts = list(map(lambda h: str(h), self.network.hosts()))
        devices = self.threadpool.map(_is_active, hosts)
        return set(filter(None, devices))

    def _get_open_ports(self):
        hosts = list(map(lambda h: str(h), self._known_devices))
        portdevices = self.threadpool.map(_ports_open, hosts)
        return portdevices

    @property
    def known_devices(self):
        return self._known_devices
Ejemplo n.º 5
0
 def __init__(self, ID, target=None):
     Agent.__init__(self)
     self.target = target if target is not None else self.identifier
     self.dispatcher = Dispatcher()
     self.id = ID
Ejemplo n.º 6
0
 def tearDown(self):
     AgentManager.reset_singleton()
     Dispatcher.reset_singleton()
Ejemplo n.º 7
0
 def setUp(self):
     self.am = AgentManager()
     self.dispatcher = Dispatcher()
     self.dispatcher.daemon = True
     self.dispatcher.start()
Ejemplo n.º 8
0
    def __init__(self):
        super(RestListener, self).__init__()
        self.target = self.identifier
        self.dispatcher = Dispatcher()
        self.app = Flask(__name__, static_url_path='', static_folder=get_cwd() + '/site')

        #
        #   HTTP Static Files
        #

        @self.app.route("/")
        @self.app.route("/<_>")
        @self.app.route("/<_>/<__>")
        @self.app.route("/<_>/<__>/<___>")
        def index(**_):
            return self.app.send_static_file("index.html")

        @self.app.route("/styles/<filename>")
        def styles(filename):
            return self.app.send_static_file("styles/" + filename)

        @self.app.route("/scripts/<filename>")
        def scripts(filename):
            return self.app.send_static_file("scripts/" + filename)

        @self.app.route("/templates/<filename>")
        def templates(filename):
            return self.app.send_static_file("templates/" + filename)

        # Agent specific static files
        @self.app.route("/agent/<agent>/<filename>")
        def agentfile(agent, filename):
            agentfolder = filelocation = get_cwd()+"/agents/"+agent.lower()+"/site/"
            return flask.send_from_directory(agentfolder, filename)

        #
        #	WEB API
        #

        # TODO: Rename resource to devices
        @self.app.route("/api/v0/nodes")
        def get_nodes():
            devicemonitor = None
            for agent in AgentManager().agents:
                if agent.__class__.__name__ is DeviceMonitor.__name__:
                    devicemonitor = agent
            if not devicemonitor or not devicemonitor.enabled:
                return make_response("DeviceMonitor is not running, cannot fetch nodes", 500)
            else:
                return json.dumps(devicemonitor.known_devices)

        @self.app.route("/api/v0/nodes/<node_id>")
        def get_agent(node_id):
            devicemonitor = None
            for agent in AgentManager().agents:
                if agent.__class__.__name__ is DeviceMonitor.__name__:
                    devicemonitor = agent
            if not devicemonitor or not devicemonitor.enabled:
                return make_response("DeviceMonitor is not running, cannot fetch nodes", 500)
            else:
                devices = devicemonitor.known_devices
                if node_id in devices:
                    return json.dumps(devices[node_id])
                else:
                    return make_response("Resource not found", 400)

        @self.app.route("/api/v0/agents")
        def get_agents():
            agents = {}
            for agent in AgentManager().agents:
                agents[agent.identifier] = agent.to_json_dict()
            return json.dumps(agents)

        @self.app.route('/api/v0/modules')
        def get_modules():
            modules = {}
            for module in ModuleManager().modules:
                modules[module.__name__] = {
                    "name": module.__name__,
                    "autostart": module.autostart}
            return json.dumps(modules)

        @self.app.route('/api/v0/chains')
        def get_chains():
            chains = {}
            # Not the cleanest code for tree generation, but works
            for agent in AgentManager().agents:
                if agent.target != agent.identifier:
                    links = agent.target.split('->')
                    prelink = chains
                    for link in range(len(links)):
                        i = links[link]
                        if not i in prelink:
                            prelink[i] = {}
                        prelink = prelink[i]
            return json.dumps(chains)

        """EVENT API"""

        @self.app.route("/api/v0/event", methods=["POST"])
        def post_event():
            msg = request.json
            if type(msg) is str:
                event = json.loads(msg)
            else:
                event = msg
            self.dispatcher.put_event(event)
            return ""