예제 #1
0
def on_message(mosq, userdata, msg):
    """
    Message received from the broker
    """
    topic = msg.topic
    payload = str(msg.payload)
    logging.debug("Message received on %s: %s" % (topic, payload))

    hosts = None
    title = "Notification"
    
    # Try to find matching settings for this topic
    for sub in conf['topichost'].keys():
        if paho.topic_matches_sub(sub, topic):
            hosts = conf['topichost'][sub]
            break

    for sub in conf['topictitle'].keys():
        if paho.topic_matches_sub(sub, topic):
            title = conf['topictitle'][sub]
            break

    for host in hosts:
        logging.debug("Sending XBMC notification to %s [%s]..." % (host, title))
        xbmchost = conf['xbmchost'][host]
        notify_xbmc(xbmchost, title, payload)
예제 #2
0
	def mqtt_on_message(self, client, userdata, msg):
		srv_type = None
		if mqtt.topic_matches_sub(str(self.service_answer_topic), msg.topic):
			srv_type = "answer"
		else:
			for service_sub in self.service_routing:
				if mqtt.topic_matches_sub(service_sub, msg.topic):
					srv_type = self.service_routing[service_sub].typ
					break
		if not srv_type:
			self.logger.error("no registered service for msg topic %s", msg.topic)
			return

		if srv_type == 'channel':
			self.service_routing[service_sub].queue.put(msg)

		elif srv_type in ['server', 'answer']:
			tp = Topic(msg.topic)
			assert tp.client_id == self.my_clientid
			pkt = json.loads(msg.payload.decode('utf-8'))
			pkt['_topic'] = msg.topic
			self.logger.debug("mqtt_on_message %s %s", msg.topic, str(pkt)[:70]+"...")

			if  srv_type is 'answer':
				self.receive_answer(pkt, int(tp.task_id))
			elif srv_type is 'server':
				self.dispatch_service(tp.service, pkt)
예제 #3
0
 def __on_message( self, client, userdata, message ):
     """Executed when an mqtt arrives
     """
     text = message.payload.decode( "utf-8" )
     print( 'Received message "{}"'.format( text ) )
     if( mqtt.topic_matches_sub( self.mqttParams.subscribeTopic, message.topic ) ):
         if( text.find( AlarmCommand.ARM_HOME.name ) > -1 ):
             self.__arm( Status( StatusMain.ARMED_HOME ) )
         elif( text.find( AlarmCommand.ARM_AWAY.name ) > -1 ):
             self.__arm( Status( StatusMain.ARMED_AWAY ) )
         elif( text.find( AlarmCommand.DISARM.name ) > -1 ):
             self.__disarm( text )
         else:
             print( 'Unknown command: [{0}]'.format( text ) )
     else:
         # check for trigger when alarm in one of specific statuses
         if( self.status.main in [ StatusMain.ARMED_AWAY, StatusMain.ARMED_HOME ] ):
             triggers = []
             if( StatusMain.ARMED_AWAY == self.armStatus ):
                 triggers = self.armedAway.triggers
             elif( StatusMain.ARMED_HOME == self.armStatus ):
                 triggers = self.armedHome.triggers
             for t in triggers:
                 for o in t.topics: 
                     if( mqtt.topic_matches_sub( o, message.topic ) and re.search( t.regex, text ) is not None ):
                         self.__logTrigger( message )
                         self.__trigger( message, t.notify )                            
         elif( self.status.main in [ StatusMain.ACTIVATED, StatusMain.TRIGGERED ] ):
             #when already activated or triggered just log the trigger event
             self.__logTrigger( message )
예제 #4
0
    def on_message(self, client, userdata, msg):
        topic_segments = msg.topic.split("/")

        if (mqtt.topic_matches_sub(self.status_topic, msg.topic)):
            item_name = topic_segments[self.status_item_index]
            self.status_callback(item_name, msg.payload.decode('utf-8'))
        elif (mqtt.topic_matches_sub(self.command_topic, msg.topic)):
            item_name = topic_segments[self.command_item_index]
            self.command_callback(item_name, msg.payload.decode('utf-8'))
예제 #5
0
            def _deal_msg():
                topic = msg.topic
                _log.info("msg topic: %s, payload:%s" % (topic, msg.payload))
                try:

                    if mqtt.topic_matches_sub(self.REPLY_TOPIC_MODEL, topic):
                        self.handle_reply_msg(msg)
                    elif mqtt.topic_matches_sub(self.REQUEST_TOPIC_MODEL,topic):
                        self.handle_request_msg(msg)
                    else:
                        _log.warning("handle_unkwon_msg")
                        self.handle_unkwon_msg(msg)
                except Exception as e:
                    _log.error("on_mqtt_msg error: %s" % str(traceback.format_exc()))
                    raise e
예제 #6
0
    def on_message(self,client, userdata, message):
        self.logger.warning("Warning: Uncaptured message topic received: \n\t*Topic '%s'\n\t*Message:'%s'"%(message.topic,message.payload.strip()))
        self.logger.warning("\tIf this happens, make sure to bind the message to a function if subscribed to it.")

        # client.topic_matches_sub("cv/+","cv/a")
        if topic_matches_sub(self._subscribed_topics["receiver_response_targeted"] , message.topic):
            self.logger.info("on_message TODO sloppy fallback. Captured direct response from %s", message.topic.split('/')[-1])
예제 #7
0
    def __on_message(self, client, userdata, message):
        """Executed when an mqtt arrives

        cmd format: 
            "email": { "from": "sender", "to": "recipient", "subject": "the subject", "body": "the body" }
            "im": { "recipients": [ "jabber id of each recipient e.g. [email protected]" ], "message": "the message" }
            "phonecall": [ phonenumber1, phonenumber2, ..., phonenumberN  ] #currently not supported
            "sms": { "text": "the message", "phones": [ phonenumber1, phonenumber2, ..., phonenumberN  ] }
        """
        text = message.payload.decode("utf-8")
        print('Received message "{}"'.format(text).encode('utf-8'))
        if (mqtt.topic_matches_sub(self.mqttParams.subscribeTopic,
                                   message.topic)):
            try:
                cmds = json.loads(text)
            except ValueError, e:
                print('"{}" is not a valid json text, exiting.'.format(text))
                return

            # try:

            if ('email' in cmds and cmds['email'] is not None):
                #note: Email.To param must be a list of recipients (even if it contains only one element )
                # self.email( Email( cmds[ 'email' ][ 'From' ], cmds[ 'email' ][ 'To' ], cmds[ 'email' ][ 'subject' ], cmds[ 'email' ][ 'body' ] ) )
                pass
            if ('im' in cmds and cmds['im'] is not None):
                # wiCmds[ 'im' ] = InstantMessage( cmds[ 'im' ][ 'recipients' ], cmds[ 'im' ][ 'message' ] )
                # wiCmds[ 'im ' ] = jsonpickle.decode( json.dumps( cmds[ 'im' ] ) )
                iMessage = jsonpickle.decode(json.dumps(cmds['im']))
                print('Will send im to:{}, message:{}'.format(
                    iMessage.recipients, iMessage.message.encode('utf-8')))
                self.im(iMessage)
예제 #8
0
    def on_message(self, state, event):
        topic = event.cargo[MQTT_EVENT_TOPIC]

        if topic_matches_sub(self.job_pending_response, topic):
            payload = json.loads(event.cargo[MQTT_EVENT_PAYLOAD])

            in_progress_job_executions = filter_upparat_job_exectutions(
                payload["jobs"].get(JOBS_IN_PROGRESS, []))

            queued_job_executions = filter_upparat_job_exectutions(
                payload["jobs"].get(JOBS_QUEUED, []))

            # If there are jobs available go to job selection state
            if in_progress_job_executions or queued_job_executions:
                logger.debug("Job executions available.")
                self.publish(
                    Event(
                        JOBS_AVAILABLE, **{
                            JOB_EXECUTION_SUMMARIES: {
                                JOB_EXECUTION_SUMMARIES_PROGRESS:
                                in_progress_job_executions,
                                JOB_EXECUTION_SUMMARIES_QUEUED:
                                queued_job_executions,
                            }
                        }))
예제 #9
0
    def on_message(self, state, event):
        topic = event.cargo[MQTT_EVENT_TOPIC]
        payload = json.loads(event.cargo[MQTT_EVENT_PAYLOAD])

        # Handle accepted pending jobs executions
        if topic_matches_sub(self.get_pending_job_executions_response, topic):
            in_progress_job_executions = filter_upparat_job_exectutions(
                payload.get(IN_PROGRESS_JOBS, []))

            queued_job_executions = filter_upparat_job_exectutions(
                payload.get(QUEUED_JOBS, []))

            # If there are jobs available go to prepare state
            if in_progress_job_executions or queued_job_executions:
                logger.debug("Job executions available.")
                self.publish(
                    Event(
                        JOBS_AVAILABLE, **{
                            JOB_EXECUTION_SUMMARIES: {
                                JOB_EXECUTION_SUMMARIES_PROGRESS:
                                in_progress_job_executions,
                                JOB_EXECUTION_SUMMARIES_QUEUED:
                                queued_job_executions,
                            }
                        }))
            else:
                logger.debug("No pending job executions available.")
                return self.publish(Event(NO_JOBS_PENDING))
    def on_stream_message_cb (self, client, obj, msg):
        """
        This callback function will be used for Thrift streaming messages
        and won't be encoded in JSON Format but the thrift wire format.
        The read method corresponding to this data structure needs to be used
        to decode the data

        @param client: the client instance for this callback
        @param obj: the private user data as set in Client() or userdata_set()
        @param msg: an instance of Message. This is a class with members topic, payload, qos, retain

        """
        
        payload = msg.payload
        topic = msg.topic

        callback_called = False
        for cbs in self.handlers:
            if cbs != '#':
                if mqtt.topic_matches_sub(cbs, topic):
                    for cb in self.handlers.get(cbs, []):
                        cb(payload)
                        callback_called = True
        if callback_called == False:
            for cb in self.handlers.get('#', []):
                logger.debug('Sending data to callback %s' % cb)
                cb(payload)
예제 #11
0
파일: mqtt.py 프로젝트: tuarrep/CO2
    def __on_message(self, client, obj, msg):
        """
        A message has been received from a server

        :param client: Client that received the message
        :param obj: *Unused*
        :param msg: A Message bean
        """
        try:
            # Get the topic
            topic = msg.topic

            # Get all listeners matching this topic
            all_listeners = set()
            for subscription, listeners in self._topics.items():
                if paho.topic_matches_sub(subscription, topic):
                    all_listeners.update(listeners)

            # Notify them using the pool
            self._pool.enqueue(self.__notify_listeners, all_listeners, topic,
                               msg.payload, msg.qos)

        except KeyError:
            # No listener for this topic
            pass
예제 #12
0
def _on_message_cb(client, obj, msg):
        """
        This method will invoke the specified callback handler by the client app
        when a notification is received by the app based on the notification type.
        :param client: the client instance for this callback
        :param obj: the private user data as set in Client() or userdata_set()
        :param msg: an instance of Message. This is a class with members topic, payload, qos, retain
        """
        payload = msg.payload
        topic = msg.topic
        json_data = None
        decoder = json.JSONDecoder()
        json_data, end = decoder.raw_decode(payload)
        if json_data is None:
            logger.error('Received event has invalid JSON format')
            logger.error('Received payload: %s' % payload)
        if len(payload) != end:
            logger.error('Received event has additional invalid JSON format')
            logger.error('It has the following additional content: %s'
                         % payload[end:])
        callback_called = False
        for cbs in handlers:
            if cbs != '#':
                if mqtt.topic_matches_sub(cbs, topic):
                    for cb in handlers.get(cbs, []):
                        cb(json_data)
                        callback_called = True

        if callback_called is False:
            for cb in handlers.get('#', []):
                logger.debug('Sending data to callback %s' % cb)
                cb(json_data)
예제 #13
0
    def _mqtt_on_message(self, client, userdata, message):
        logging.debug('mqtt_on_message %s %s', message.topic, message.payload)

        payload = message.payload.decode('utf-8')

        try:
            payload = json.loads(payload, use_decimal=True)
        except Exception as e:
            raise
            logging.error(e)

        if self.on_message:
            self.on_message(self, message.topic, payload)

        if self._response_topic and topic_matches_sub(self._response_topic,
                                                      message.topic):

            response = {"payload": payload, "topic": message.topic}

            if self._response_list:
                if not self._response:
                    self._response = []
                self._response.append(response)

            else:

                self._response = response
                self._response_condition = 0
def on_message_cb(client, obj, msg):

    global handlers

    payload = msg.payload
    topic = msg.topic
    json_data = None
    json_data, end = decoder.raw_decode(payload)
    if json_data is None:
        logger.error('Received event has invalid JSON format')
        logger.error('Received payload: %s' % payload)
    if len(payload) != end:
        logger.error('Received event has additional invalid JSON format')
        logger.error('It has the following additional content: %s' %
                     payload[end:])
    callback_called = False
    for cbs in handlers:
        if cbs != '#':
            if mqtt.topic_matches_sub(cbs, topic):
                for cb in handlers.get(cbs, []):
                    cb(json_data)
                    callback_called = True

    if callback_called == False:
        for cb in handlers.get('#', []):
            logger.debug('Sending data to callback %s' % cb)
            cb(json_data)
예제 #15
0
파일: mqttwarn.py 프로젝트: sfromm/mqttwarn
def on_message(mosq, userdata, msg):
    """
    Message received from the broker
    """

    topic = msg.topic
    payload = str(msg.payload)
    logging.debug("Message received on %s: %s" % (topic, payload))

    if msg.retain == 1:
        if cf.skipretained:
            logging.debug("Skipping retained message on %s" % topic)
            return

    # Try to find matching settings for this topic
    for section in get_sections():
        # Get the topic for this section (usually the section name but optionally overridden)
        match_topic = get_topic(section)
        if paho.topic_matches_sub(match_topic, topic):
            logging.debug("Section [%s] matches message on %s. Processing..." % (section, topic))
            # Check for any message filters
            if is_filtered(section, topic, payload):
                logging.debug("Filter in section [%s] has skipped message on %s" % (section, topic))
                continue
            
            targetlist = cf.getlist(section, 'targets')
            if type(targetlist) != list:
                logging.error("Target definition in section [%s] is incorrect" % section)
                cleanup(0)
                return

            for t in targetlist:
                logging.debug("Message on %s going to %s" % (topic, t))
                # Each target is either "service" or "service:target"
                # If no target specified then notify ALL targets
                service = t
                target = None

                # Check if this is for a specific target
                if t.find(':') != -1:
                    try:
                        service, target = t.split(':', 2)
                    except:
                        logging.warn("Invalid target %s - should be 'service:target'" % (t))
                        continue

                if not service in service_plugins:
                    logging.error("Invalid configuration: topic %s points to non-existing service %s" % (topic, service))
                    return

                sendtos = None
                if target is None:
                    sendtos = get_service_targets(service)
                else:
                    sendtos = [target]
                
                for sendto in sendtos:
                    job = Job(1, service, section, topic, payload, sendto)
                    q_in.put(job)
    return
예제 #16
0
def on_message(mosq, userdata, msg):
    """
    Message received from the broker
    """
    topic = msg.topic
    payload = str(msg.payload)
    logging.debug("Message received on %s: %s" % (topic, payload))

    if msg.retain == 1:
        if cf.skipretained:
            logging.debug("Skipping retained message on %s" % topic)
            return

    # Try to find matching settings for this topic
    for section in get_sections():
        # Get the topic for this section (usually the section name but optionally overridden)
        match_topic = get_topic(section)
        if paho.topic_matches_sub(match_topic, topic):
            logging.debug("Section [%s] matches message on %s. Processing..." % (section, topic))
            # Check for any message filters
            if is_filtered(section, topic, payload):
                logging.debug("Filter in section [%s] has skipped message on %s" % (section, topic))
                continue
            # Send the message to any targets specified
            send_to_targets(section, topic, payload)
예제 #17
0
def _on_message(client, userdata, msg):
    print(msg.topic + ' ' + str(msg.payload))

    for subscriber in _subscribers:
        if paho_client.topic_matches_sub(sub=subscriber['topic'],
                                         topic=msg.topic):
            subscriber['handler'](msg.payload)
예제 #18
0
def on_message(mosq, userdata, msg):
    """
    Message received from the broker
    """
    topic = msg.topic
    payload = str(msg.payload)
    logging.debug("Message received on %s: %s" % (topic, payload))

    username = conf['mailusername']
    password = conf['mailpassword']
    recipients = conf['recipient']
    subject = None

    # Try to find matching settings for this topic
    for sub in conf['topicsubject'].keys():
        if paho.topic_matches_sub(sub, topic):
            subject = conf['topicsubject'][sub]
            break
    
    if subject is None:
        return
        
    for recipient in recipients:
        logging.debug("Sending email to %s [%s]..." % (recipient, subject))
        send_mail(username, password, [recipient], subject, payload)
예제 #19
0
파일: mqtt_client.py 프로젝트: gonicus/gosa
 def get_subscriptions(self, topic):
     """
     Find the subscriptions that match the given topic
     :param topic: Topic to check
     :return: list of found subscriptions
     """
     return [self.subscriptions[t] for t in self.subscriptions if mqtt.topic_matches_sub(t, topic)]
예제 #20
0
파일: core.py 프로젝트: ligzy/mqttwarn
def on_message(mosq, userdata, msg):
    """
    Message received from the broker
    """

    topic = msg.topic
    payload = msg.payload
    logger.debug("Message received on %s: %s" % (topic, payload))

    if msg.retain == 1:
        if cf.skipretained:
            logger.debug("Skipping retained message on %s" % topic)
            return

    # Try to find matching settings for this topic
    for section in context.get_sections():
        # Get the topic for this section (usually the section name but optionally overridden)
        match_topic = context.get_topic(section)
        if paho.topic_matches_sub(match_topic, topic):
            logger.debug("Section [%s] matches message on %s. Processing..." % (section, topic))
            # Check for any message filters
            if context.is_filtered(section, topic, payload):
                logger.debug("Filter in section [%s] has skipped message on %s" % (section, topic))
                continue
            # Send the message to any targets specified
            send_to_targets(section, topic, payload)
예제 #21
0
파일: mqtt.py 프로젝트: tcalmant/ipopo
    def __on_message(self, client, obj, msg):
        # pylint: disable=W0613
        """
        A message has been received from a server

        :param client: Client that received the message
        :param obj: *Unused*
        :param msg: A Message bean
        """
        try:
            # Get the topic
            topic = msg.topic

            # Get all listeners matching this topic
            all_listeners = set()
            for subscription, listeners in self._topics.items():
                if paho.topic_matches_sub(subscription, topic):
                    all_listeners.update(listeners)

            # Notify them using the pool
            self._pool.enqueue(
                self.__notify_listeners,
                all_listeners,
                topic,
                msg.payload,
                msg.qos,
            )
        except KeyError:
            # No listener for this topic
            pass
예제 #22
0
 def _get_vehicle_type(self, topic: str):
     # Make sure we only ingest desired event and vehicle types
     for event, vehicle in itertools.product(self.event_types,
                                             self.vehicle_types):
         if mqtt.topic_matches_sub(
                 f"/hfp/v2/journey/ongoing/{event}/{vehicle}/#", topic):
             return vehicle
예제 #23
0
 def on_subscription(self, state, event):
     topic = event.cargo[MQTT_EVENT_TOPIC]
     # Get pending job executions once subscribed to accepted_job_executions_topic
     if topic_matches_sub(self.get_pending_job_executions_response, topic):
         self.mqtt_client.publish(get_pending_job_executions(
             settings.broker.thing_name),
                                  qos=1)
예제 #24
0
def on_message(mosq, userdata, msg):

    sock = userdata['sock']
    host = userdata['carbon_server']
    port = userdata['carbon_port']
    lines = []
    now = int(time.time())

    map = userdata['map']
    # Find out how to handle the topic in this message: slurp through
    # our map 
    for t in map:
        if paho.topic_matches_sub(t, msg.topic):
            # print "%s matches MAP(%s) => %s" % (msg.topic, t, map[t])

            # Must we rename the received msg topic into a different
            # name for Carbon? In any case, replace MQTT slashes (/)
            # by Carbon periods (.)
            (type, remap) = map[t]
            if remap is None:
                carbonkey = msg.topic.replace('/', '.')
            else:
                carbonkey = remap.replace('/', '.')
            logging.debug("CARBONKEY is [%s]" % carbonkey)

            if type == 'n':
                '''Number: obtain a float from the payload'''
                try:
                    number = float(msg.payload)
                    #lines.append("%s %f %d" % (carbonkey, number, now))
                    lines.append("%s %f" % (carbonkey, number))
                except ValueError:
                    logging.info("Topic %s contains non-numeric payload [%s]" % 
                            (msg.topic, msg.payload))
                    return

            elif type == 'j':
                '''JSON: try and load the JSON string from payload and use
                   subkeys to pass to Carbon'''
                try:
                    st = json.loads(msg.payload)
                    for k in st:
                        if is_number(st[k]):
                            #lines.append("%s.%s %f %d" % (carbonkey, k, float(st[k]), now))
                            lines.append("%s.%s %f" % (carbonkey, k, float(st[k])))

                except:
                    logging.info("Topic %s contains non-JSON payload [%s]" %
                            (msg.topic, msg.payload))
                    return

            else:
                logging.info("Unknown mapping key [%s]", type)
                return

            message = '\n'.join(lines) + '\n'
            logging.debug("%s", message)

            sock.sendto(message, (host, port))
예제 #25
0
def _on_message(client, userdata, message):
    callbacks_to_run = []
    for sub in _topic_callbacks.keys():
        if topic_matches_sub(sub, message.topic):
            callbacks_to_run += _topic_callbacks[sub]

    for callback in callbacks_to_run:
        threading.Thread(target=callback, args=(message.topic, message.payload)).start()
예제 #26
0
    def _matched_server(self, req_topic):
        regs = self._reg_servers
        matched = []
        for topic, data in regs.items():
            if Mqtt.topic_matches_sub(data[2], req_topic):
                matched.append(data)

        return matched
예제 #27
0
    def _match_subscriber(self, sub_topic):
        subs = self._reg_subscribes
        matched = []
        for topic, data in subs.items():
            if Mqtt.topic_matches_sub(topic, sub_topic):
                matched.append(data)

        return matched
예제 #28
0
    def on_message(self, client, userdata, msg):
        # Find correct rule from RuleList
        # Pass message JSON Payload to Rule for action

        # Loop through RuleList and find if message topic applies
        for aRule in self.RuleList:
            if mqtt.topic_matches_sub(aRule.getTopic(), msg.topic):
                aRule.message_in(msg=msg)
예제 #29
0
 def on_message(client, userdata, msg):
     try:
         # find the sensor matching the topic
         for sensor_id in self.sensors:
             sensor = self.sensors[sensor_id]
             if mqtt.topic_matches_sub(sensor["topic"], msg.topic):
                 self.log_debug("received " + str(msg.payload) +
                                " for " + sensor_id + " on topic " +
                                str(msg.topic))
                 # if JSON payload is expected
                 if "key" in sensor:
                     try:
                         data = json.loads(msg.payload)
                         if sensor["key"] not in data:
                             return
                         # apply the filter if any
                         if "filter" in sensor:
                             search = {}
                             if "&" in sensor["filter"]:
                                 key_values = sensor["filter"].split(
                                     "&")
                             else:
                                 key_values = [sensor["filter"]]
                             for key_value in key_values:
                                 if "=" not in key_value: continue
                                 key, value = key_value.split("=")
                                 search[key] = value
                             # check if the output matches the search string
                             found = True
                             for key, value in search.iteritems():
                                 # check every key/value pair
                                 if key not in data: found = False
                                 if key in data and str(value).lower(
                                 ) != str(data[key]).lower():
                                     found = False
                             # not matching, skip to the next sensor
                             if not found: continue
                         value = data[sensor["key"]]
                     except Exception, e:
                         self.log_warning(
                             "Unable to parse JSON payload " +
                             str(msg.payload) + ": " + exception.get(e))
                         return
                 # else consider the entire payload
                 else:
                     value = msg.payload
                 # prepare the message
                 message = Message(self)
                 message.recipient = "controller/hub"
                 message.command = "IN"
                 message.args = sensor_id
                 message.set("value", value)
                 # send the measure to the controller
                 self.send(message)
     except Exception, e:
         self.log_warning("runtime error during on_message(): " +
                          exception.get(e))
         return
예제 #30
0
def get_messagefilter(topic):
    ''' Find the message filter from the topic '''
    filter = None
    if 'filtermap' in conf:
        for key in conf['filtermap'].keys():
            if paho.topic_matches_sub(key, topic):
                filter = conf['filtermap'][key]
                break
    return filter
예제 #31
0
    def topic_matches(cls, subscription_filter, topic):
        """
        Checks if the given topic matches the given subscription filter

        :param subscription_filter: A MQTT subscription filter
        :param topic: A topic
        :return: True if the topic matches the filter
        """
        return paho.topic_matches_sub(subscription_filter, topic)
예제 #32
0
def get_messagefmt(topic):
    ''' Find the message format from the topic '''
    fmt = None
    if 'formatmap' in conf:
        for key in conf['formatmap'].keys():
            if paho.topic_matches_sub(key, topic):
                fmt = conf['formatmap'][key]
                break
    return fmt
예제 #33
0
def on_message(mosq, userdata, msg):

    sock = userdata['sock']
    lines = []
    now = int(time.time())

    map = userdata['map']
    # Find out how to handle the topic in this message: slurp through
    # our map
    for t in map:
        if paho.topic_matches_sub(t, msg.topic):
            # print "%s matches MAP(%s) => %s" % (msg.topic, t, map[t])

            # Must we rename the received msg topic into a different
            # name for Carbon? In any case, replace MQTT slashes (/)
            # by Carbon periods (.)
            (type, remap) = map[t]
            if remap is None:
                carbonkey = msg.topic.replace('/', '.')
            else:
                if '#' in remap:
                    remap = remap.replace('#', msg.topic.replace('/', '.'))
                carbonkey = remap.replace('/', '.')
            logging.debug("CARBONKEY is [%s]" % carbonkey)

            if type == 'n':
                '''Number: obtain a float from the payload'''
                try:
                    number = float(msg.payload)
                    lines.append("%s %f %d" % (carbonkey, number, now))
                except ValueError:
                    logging.info("Topic %s contains non-numeric payload [%s]" %
                                 (msg.topic, msg.payload))
                    return

            elif type == 'j':
                '''JSON: try and load the JSON string from payload and use
                   subkeys to pass to Carbon'''
                try:
                    st = json.loads(msg.payload)
                    for k in st:
                        if is_number(st[k]):
                            lines.append("%s.%s %f %d" %
                                         (carbonkey, k, float(st[k]), now))
                except:
                    logging.info("Topic %s contains non-JSON payload [%s]" %
                                 (msg.topic, msg.payload))
                    return

            else:
                logging.info("Unknown mapping key [%s]", type)
                return

            message = '\n'.join(lines) + '\n'
            logging.debug("%s", message)

            sock.sendto(message, (CARBON_SERVER, CARBON_PORT))
예제 #34
0
def get_priority(topic):
    ''' Find the "priority" (for pushover)
        from the topic. '''
    priority = None
    if 'prioritymap' in conf:
        for key in conf['prioritymap'].keys():
            if paho.topic_matches_sub(key, topic):
                priority = conf['prioritymap'][key]
                break
    return priority
예제 #35
0
파일: tut.py 프로젝트: ericl/risecamp
 def on_message(self, client, userdata, msg):
     try:
         self.mu.acquire()
         for k in self.callbacks:
             if mqtt.topic_matches_sub(k, msg.topic):
                 self.callbacks[k](msg)
     except:
         traceback.print_exc()
     finally:
         self.mu.release()
def on_message(client, userdata, msg):
    userdata.idMap_lock.acquire()
    try:
        for key in userdata.idMap.keys():
            if(mqtt.topic_matches_sub(key, str(msg.topic))): # check for wildcard matching
                ino_id = userdata.idMap[key]
                userdata.msgQ.put(str(ino_id) + " " + str(msg.payload)) # protocol-style convention needed
    except BaseException as e: # ignore clean session = false: msg from pre-subscribed topics
        pass
    userdata.idMap_lock.release()
예제 #37
0
def get_title(topic):
    ''' Find the "title" (for pushover) or "subject" (for smtp)
        from the topic. '''
    title = None
    if 'titlemap' in conf:
        for key in conf['titlemap'].keys():
            if paho.topic_matches_sub(key, topic):
                title = conf['titlemap'][key]
                break
    return title
예제 #38
0
 def get_subscriptions(self, topic):
     """
     Find the subscriptions that match the given topic
     :param topic: Topic to check
     :return: list of found subscriptions
     """
     return [
         self.subscriptions[t] for t in self.subscriptions
         if mqtt.topic_matches_sub(t, topic)
     ]
예제 #39
0
	def _on_mqtt_message(self, client, userdata, msg):
		if not client == self._mqtt:
			return

		from paho.mqtt.client import topic_matches_sub
		for subscription in self._mqtt_subscriptions:
			topic, callback, args, kwargs = subscription
			if topic_matches_sub(topic, msg.topic):
				args = [msg.topic, msg.payload] + args
				kwargs.update(dict(retained=msg.retain, qos=msg.qos))
				callback(*args, **kwargs)
예제 #40
0
	def _callTriggers(self, topic, data):
		for t in self.triggers:
			#print("testing topic: %s %s" % (t[0], topic) )
			if mqtt.topic_matches_sub(t[0], topic):
				#print "Trigger matches: %s %s" % (t[0] , t[1] )
				if (t[2]): # wants json
					#print("decoding json")
					#pprint(data)
					data = self._decodeJSON(str(data))
					#pprint(data)
				t[1](topic, data)
예제 #41
0
    def process_data(self, topic, value):
        for subscription, key in self.key_mapping.items():
            if topic_matches_sub(subscription, topic):
                send_to_zabbix([Metric(MQTT_AGENT_HOST_NAME, key, value)],
                               ZABBIX_SERVER_HOST,
                               ZABBIX_SERVER_PORT
                               )
                return True

        logging.error("No such subscription: {}".format(topic))
        return False
예제 #42
0
	def _on_mqtt_message(self, client, userdata, msg):
		if not client == self._mqtt:
			return

		from paho.mqtt.client import topic_matches_sub
		for subscription in self._mqtt_subscriptions:
			topic, callback, args, kwargs = subscription
			if topic_matches_sub(topic, msg.topic):
				args = [msg.topic, msg.payload] + args
				kwargs.update(dict(retained=msg.retain, qos=msg.qos))
				callback(*args, **kwargs)
예제 #43
0
 def _callTriggers(self, topic, data):
     for t in self.triggers:
         #print("testing topic: %s %s" % (t[0], topic) )
         if mqtt.topic_matches_sub(t[0], topic):
             #print "Trigger matches: %s %s" % (t[0] , t[1] )
             if (t[2]):  # wants json
                 #print("decoding json")
                 #pprint(data)
                 data = self._decodeJSON(str(data))
                 #pprint(data)
             t[1](topic, data)
예제 #44
0
 def on_mqtt_message(self, client, obj, message):
     if message.retain:
         return
     self.logger.info(
         "topic %s, payload: %s" %
         (message.topic,
          "[binary]" if len(message.payload) > 10 else message.payload))
     for sensor in self.sensors:
         if topic_matches_sub(sensor.topic, message.topic):
             return sensor.process(message.topic, message.payload)
     pass
예제 #45
0
def on_message(mosq, userdata, msg):
    """
    Message received from the broker
    """
    topic = msg.topic
    payload = str(msg.payload)
    logging.debug("Message received on %s: %s" % (topic, payload))

    # Try to find matching settings for this topic
    for sub in conf['topics']:
        if paho.topic_matches_sub(sub, topic):
            tweet(payload[0:138])
            break
예제 #46
0
 def _on_message(self, mqttc, userdata, msg):
     """
     接收消息处理
     :param mqttc:
     :param userdata:
     :param msg:
     :return:
     """
     #logger.info("MQTTCallback::on_message, mqttc:%s, userdata:%s, topic:%s, payload:%s" % (self, userdata, msg.topic, msg.payload))
     [handle_fun(self, userdata=userdata, topic=msg.topic, payload=msg.payload)
      for sub, handle_fun in self.topic_to_fun_dic.items()
      if topic_matches_sub(sub, msg.topic)]
     return True
예제 #47
0
def get_topic_data(topic):
    ''' Find out if there is a function in topicdatamap{} for
        adding topic into data. If there is, invoke that
        and return a dict of it '''
    data = None
    if 'topicdatamap' in conf:
        for key in conf['topicdatamap'].keys():
            if paho.topic_matches_sub(key, topic):
                func = conf['topicdatamap'][key]
                if hasattr(func, '__call__'):
                    try:
                        data = func(topic)
                    except Exception, e:
                        logging.warn("Cannot invoke func(%s): %s" % (topic, str(e)))
                break
예제 #48
0
파일: ypom-cli.py 프로젝트: jpmens/ypom-cli
def on_message(mosq, userdata, msg):
    # print "%s (qos=%s, r=%s) %s" % (msg.topic, str(msg.qos), msg.retain, str(msg.payload))

    topic = msg.topic
    payload = msg.payload

    if paho.topic_matches_sub('ypom/+/+', topic):
        prefix, toidentifier, fromidentifier = topic.split('/', 3)

        try:
            u_from = userlist[fromidentifier]
            u_to = userlist[toidentifier]

            tst, msg = u_from.decrypt(msg.payload)
            msg = msg.decode('utf-8')
            print u'%s: %s  [%s]' % (u_from.identifier, msg, tst)
        except:
            raise
            print "SOMETHING WRONG"
예제 #49
0
def on_message_cb(client, obj, msg):
    global handlers
    payload = msg.payload
    topic = msg.topic
    json_data = None
    json_data, end = decoder.raw_decode(payload)
    if json_data is None:
        logger.error('Received event has invalid JSON format')
        logger.error('Received payload: %s' % payload)
    if len(payload) != end:
        logger.error('Received event has additional invalid JSON format')
        logger.error('It has the following additional content: %s' % payload[end:])
    callback_called = False
    for cbs in handlers:
        if cbs != '#':
            if mqtt.topic_matches_sub(cbs, topic):
                for cb in handlers.get(cbs, []):
                    cb(json_data)
                    callback_called = True

    if callback_called == False:
        for cb in handlers.get('#', []):
            logger.debug('Sending data to callback %s' % cb)
            cb(json_data)
예제 #50
0
 def mqtt_on_message(self, mqttc, obj, msg):
     if mqtt.topic_matches_sub("basement/mist/confirm/#", msg.topic):
         self.onmsg_pi(msg)
     elif mqtt.topic_matches_sub("basement/mist/errors/#", msg.topic):
         self.onmsg_error(msg)
예제 #51
0
    payload = str(msg.payload)
    logging.debug("Message received on %s: %s" % (topic, payload))

    # Check for any message filters
    filter = get_messagefilter(topic)
    if hasattr(filter, '__call__'):
        try:
            if filter(topic, payload):
                logging.debug("Message on %s has been filtered. Skipping." % (topic))
                return
        except Exception, e:
            logging.warn("Cannot invoke filter(%s): %s" % (topic, str(e)))

    # Try to find matching settings for this topic
    for key in conf['topicmap'].keys():
        if paho.topic_matches_sub(key, topic):
            targetlist = conf['topicmap'][key]
            logging.debug("Topic [%s] going to %s" % (topic, targetlist))

            for t in targetlist:
                # Each target is either "service" or "service:target"
                # If no target specified then notify ALL targets
                service = t
                target = None

                # Check if this is for a specific target
                if t.find(':') != -1:
                    try:
                        service, target = t.split(':', 2)
                    except:
                        logging.warn("Invalid target %s - should be 'service:target'" % (t))
예제 #52
0
  def on_message(self,mosq, userdata, msg):

    sock = self.sock
    host = self.carbon_server
    port = self.carbon_port
    lines = []
    now = int(time.time())

    # Find out how to handle the topic in this message: slurp through
    # our map 
    for t in self.map:
        if paho.topic_matches_sub(t, msg.topic):
            # print "%s matches MAP(%s) => %s" % (msg.topic, t, self.map[t])

            # Must we rename the received msg topic into a different
            # name for Carbon? In any case, replace MQTT slashes (/)
            # by Carbon periods (.)
            (type, remap) = self.map[t]
            if remap is None:
                carbonkey = msg.topic.replace('/', '.').replace(',','_')
            else:
                carbonkey = remap.replace('/', '.')
            logging.debug("CARBONKEY is [%s]" % carbonkey)

            if type == 'n':
                '''Number: obtain a float from the payload'''
                try:
                    number = float(msg.payload)
                    lines.append("%s %f %d" % (carbonkey, number, now))
                except ValueError:
                    logging.info("Topic %s contains non-numeric payload [%s]" % 
                            (msg.topic, msg.payload))
                    return

            elif type == 'j':
                '''JSON: try and load the JSON string from payload and use
                   subkeys to pass to Carbon'''
                try:
                    st = json.loads(msg.payload)
                    # get timestamp fron json or set it to now
                    # todo : optional seconds and milliseconds
                    try:
                        ts=time.strptime(st.pop("t",time.strftime("%Y-%m-%dT%H:%M:%S",time.gmtime(now))),"%Y-%m-%dT%H:%M:%S")
                        timestamp=int(time.mktime(ts))
                    except:
                        #timestamp=now
                        raise

                    for k in st:
                        if is_number(st[k]):
                            lines.append("%s.%s %f %d" % (carbonkey, k, float(st[k]), timestamp))

                except:
                    logging.info("Topic %s contains non-JSON payload [%s]" %
                            (msg.topic, msg.payload))
                    return

            else:
                logging.info("Unknown mapping key [%s]", type)
                return

            message = '\n'.join(lines) + '\n'
            logging.debug("%s", message)

            self.sock.sendto(message, (host, port))
예제 #53
0
파일: ctrld.py 프로젝트: dhozac/pista
    # Get list of topics from ACL table and compare. Caveat: %c escapes are
    # not supported here and will thus not match.

    track_authorized = False
    message = "Not authorized"
    status = 403

    try:
        query = (Acl.select(Acl). where(
                    (Acl.username == username)
                    ))
        for s in query.naive():
            sub    = s.topic

            new_sub = sub.replace('%u', username)
            matches = paho.topic_matches_sub(sub, topic)
            log.debug("sub %s (%s) => %s" % (sub, new_sub, matches))
            if matches:
                track_authorized = True
                status = 200
                break
    except Exception, e:
        log.error("Can't query ACL: %s" % (str(e)))



    if nrecs is None or int(nrecs) < 1:
        nrecs = 50
    if nrecs > 600:
        nrecs = 600
예제 #54
0
def on_message(mosq, userdata, msg):

    sock     = userdata['sock']
    host     = userdata['carbon_host']
    port     = userdata['carbon_port']
    now = int(time.time())
    tuples = ([])

    map = userdata['map']
    # Find out how to handle the topic in this message: slurp through
    # our map 
    for t in map:
        if paho.topic_matches_sub(t, msg.topic):
            # print "%s matches MAP(%s) => %s" % (msg.topic, t, map[t])

            # Must we rename the received msg topic into a different
            # name for Carbon? In any case, replace MQTT slashes (/)
            # by Carbon periods (.)
            (type, remap) = map[t]
            if remap is None:
                carbonkey = msg.topic.replace('/', '.')
            else:
                carbonkey = remap.replace('/', '.')
            logging.debug("CARBONKEY is [%s]" % carbonkey)

            if type == 'n':
                '''Number: obtain a float from the payload'''
                try:
                    number = float(msg.payload)
                    tuples.append((carbonkey, (now,number)))
                except ValueError:
                    logging.info("Topic %s contains non-numeric payload [%s]" % 
                            (msg.topic, msg.payload))
                    return

            elif type == 'j':
                '''JSON: try and load the JSON string from payload and use
                   subkeys to pass to Carbon'''
                try:
                    st = json.loads(msg.payload)
                    for k in st:
                        if is_number(st[k]):
                            tuples.append(("%s.%s" % (carbonkey, k), (now,float(st[k]))))
                except:
                    logging.info("Topic %s contains non-JSON payload [%s]" %
                            (msg.topic, msg.payload))
                    return

            else:
                logging.info("Unknown mapping key [%s]", type)
                return

            # prepare data
            package = pickle.dumps(tuples, 1)
            size = struct.pack('!L', len(package))
            logging.debug("%s", str(tuples))

            # send to carbon pickle
            try:
                sent = sock.sendall(size)
            except:
                sent = 0
            if sent == 0:
                logging.error("Error sending data to carbon server via TCP")
            try:
                sent = sock.sendall(package)
            except:
                sent = 0
            if sent == 0:
                logging.error("Error sending data to carbon server via TCP")
예제 #55
0
파일: pista.py 프로젝트: dhozac/pista
    else:
        sublist.append('#')

    # Find distinct topic, tid combinations in Locations table and
    # let Paho check if subscription matches

    topiclist = []
    tidlist = []

    query = (Location.select(Location.tid, Location.topic)
                    .distinct()
                    .order_by(Location.tid)
                    )
    for q in query:
        for sub in sublist:
            if paho.topic_matches_sub(sub, q.topic):
                tidlist.append(q.tid)
                topiclist.append(q.topic)

    log.debug("User {0} gets tidlist={1}".format(username, ",".join(tidlist)))

    return sorted(set(tidlist))

def getinventorytopics(username):
    ''' username is probably a logged-in user. Obtain a list of TIDs
        that user is allowed to see '''

    # First, get a list of ACL topics the user is authorized for. If the
    # `username' is a superuser, add '#' to the subscription list, so
    # that paho matches that as true in any case. (Superusers possibly
    # don't have ACL entries in the database.)
def on_message(client, userdata, msg):
    userdata.idMap_lock.acquire()
    try:
        for key in userdata.idMap.keys():
            if mqtt.topic_matches_sub(key.topic, str(msg.topic)):  # check for wildcard matching
                idMap_entry = userdata.idMap[key]
                if idMap_entry.get_is_ThingShadow():  # A ThingShadow-related new message
                    # find out the clientToken
                    JSON_dict = json.loads(str(msg.payload))
                    my_clientToken = JSON_dict.get(u'clientToken')
                    msg_Version = JSON_dict.get(u'version')  # could be None
                    # look up this clientToken in req_Map to check timeout
                    userdata.req_Map_lock.acquire()
                    # NO timeout
                    if my_clientToken in userdata.req_Map and my_clientToken == key.clientToken:
                        my_Type = userdata.req_Map[my_clientToken].getType()
                        my_ThingName = userdata.req_Map[my_clientToken].getThingName()
                        del userdata.req_Map[my_clientToken]
                        # now check ref_cnt_Map_get/update to see if necessary to unsub
                        need2unsub = False
                        # check version, see if this is a message containing version regarding thisThingName
                        if msg_Version is not None and userdata.thisThingNameVersionControl.thisThingName == my_ThingName:
                            if msg_Version > userdata.thisThingNameVersionControl.currLocalVersion:
                                userdata.thisThingNameVersionControl.currLocalVersion = msg_Version  # new message, update thisThingName version
                        topic_accept = "$aws/things/" + my_ThingName + "/shadow/" + my_Type + "/accepted"
                        topic_reject = "$aws/things/" + my_ThingName + "/shadow/" + my_Type + "/rejected"
                        if my_Type == "get":
                            new_ref_CNT = userdata.ref_cnt_Map_get[my_ThingName] - 1
                            if new_ref_CNT == 0:  # need to unsub
                                need2unsub = True
                            else:
                                userdata.ref_cnt_Map_get[my_ThingName] = new_ref_CNT
                        elif my_Type == "update":
                            new_ref_CNT = userdata.ref_cnt_Map_update[my_ThingName] - 1
                            if new_ref_CNT == 0:  # need to unsub
                                need2unsub = True
                            else:
                                userdata.ref_cnt_Map_update[my_ThingName] = new_ref_CNT
                        elif my_Type == "delete":  # should reset version number if it is an accepted DELETE
                            msg_topic_str = str(msg.topic)
                            msg_pieces = msg_topic_str.split('/')
                            if msg_pieces[5] == "accepted":  # if it is an accepted DELETE
                                userdata.thisThingNameVersionControl.currLocalVersion = 0  # reset local version number
                            new_ref_CNT = userdata.ref_cnt_Map_delete[my_ThingName] - 1
                            if new_ref_CNT == 0:  # need to unsub
                                need2unsub = True
                            else:
                                userdata.ref_cnt_Map_delete[my_ThingName] = new_ref_CNT
                        else:  # broken Type
                            pass
                        # by this time, we already have idMap_lock
                        if need2unsub:
                            userdata._iot_mqtt_client_handler.unsubscribe(topic_accept)
                            new_key = idMap_key(topic_accept, my_clientToken)
                            if userdata.idMap.get(new_key) is not None:
                                del userdata.idMap[new_key]
                            userdata._iot_mqtt_client_handler.unsubscribe(topic_reject)
                            new_key = idMap_key(topic_reject, my_clientToken)
                            if userdata.idMap.get(new_key) is not None:
                                del userdata.idMap[new_key]
                        # add the feedback to msgQ
                        ino_id = idMap_entry.get_ino_id()
                        userdata.msgQ.put(str(ino_id) + " " + str(msg.payload))  # protocol-style convention needed
                    # timeout, ignore this message
                    else:
                        pass
                    userdata.req_Map_lock.release()
                elif idMap_entry.get_is_delta():  # a delta message, need to check version
                    userdata.req_Map_lock.acquire()
                    JSON_dict = json.loads(str(msg.payload))
                    msg_Version = JSON_dict.get(u'version')
                    # see if the version from the message is newer/bigger regarding thisThingName
                    # parse out to see what thing name of this delta message is...
                    msg_topic_str = str(msg.topic)
                    msg_pieces = msg_topic_str.split('/')
                    msg_ThingName = msg_pieces[2]  # now we have thingName...
                    if msg_Version is not None and msg_ThingName == userdata.thisThingNameVersionControl.thisThingName:
                        if msg_Version <= userdata.thisThingNameVersionControl.currLocalVersion:
                            pass  # ignore delta message with old version number
                        else:  # now add this delta message to msgQ
                            # update local version
                            userdata.thisThingNameVersionControl.currLocalVersion = msg_Version
                            ino_id = idMap_entry.get_ino_id()
                            userdata.msgQ.put(str(ino_id) + " " + str(msg.payload))
                    userdata.req_Map_lock.release()
                else:  # A normal new message
                    ino_id = idMap_entry.get_ino_id()
                    userdata.msgQ.put(str(ino_id) + " " + str(msg.payload))  # protocol-style convention needed
    except BaseException:  # ignore clean session = false: msg from pre-subscribed topics
        pass
    userdata.idMap_lock.release()
예제 #57
0
def send_to_targets(section, topic, payload):
    if cf.has_section(section) == False:
        logging.warn("Section [%s] does not exist in your INI file, skipping message on %s" % (section, topic))
        return

    dispatcher_dict = cf.getdict(section, 'targets')
    if type(dispatcher_dict) == dict:
        def get_key(item):
            # precede a key with the number of topic levels and then use reverse alphabetic sort order
            # '+' is after '#' in ascii table
            # caveat: for instance space is allowed in topic name but will be less specific than '+', '#'
            # so replace '#' with first ascii character and '+' with second ascii character
            # http://public.dhe.ibm.com/software/dw/webservices/ws-mqtt/mqtt-v3r1.html#appendix-a

            # item[0] represents topic. replace wildcard characters to ensure the right order
            modified_topic = item[0].replace('#', chr(0x01)).replace('+', chr(0x02))
            levels = len(item[0].split('/'))
            # concatenate levels with leading zeros and modified topic and return as a key
            return "{:03d}{}".format(levels, modified_topic)

        # produce a sorted list of topic/targets with longest and more specific first
        sorted_dispatcher = sorted(dispatcher_dict.items(), key=get_key, reverse=True)
        for match_topic, targets in sorted_dispatcher:
            if paho.topic_matches_sub(match_topic, topic):
                # hocus pocus, let targets become a list
                targetlist = targets if type(targets) == list else [targets]
                logging.debug("Most specific match %s dispatched to %s" % (match_topic, targets))
                # first most specific topic matches then stops processing
                break
        else:
            # Not found then no action. This could be configured intentionally.
            logging.debug("Dispatcher definition does not contain matching topic/target pair in section [%s]" % section)
            return
    else:
        targetlist = cf.getlist(section, 'targets')
        if type(targetlist) != list:
            # if targets is neither dict nor list
            logging.error("Target definition in section [%s] is incorrect" % section)
            cleanup(0)
            return

    for t in targetlist:
        logging.debug("---------------- %s ------------------" % (t))
        logging.debug("Message on %s going to %s" % (topic, t))
        # Each target is either "service" or "service:target"
        # If no target specified then notify ALL targets
        service = t
        target = None

        # Check if this is for a specific target
        if t.find(':') != -1:
            try:
                service, target = t.split(':', 2)
            except:
                logging.warn("Invalid target %s - should be 'service:target'" % (t))
                continue

        if not service in service_plugins:
            logging.error("Invalid configuration: topic %s points to non-existing service %s" % (topic, service))
            return

        sendtos = None
        if target is None:
            sendtos = get_service_targets(service)
        else:
            sendtos = [target]

        for sendto in sendtos:
            job = Job(1, service, section, topic, payload, sendto)
            q_in.put(job)
예제 #58
0
 def test_not_matching(self, sub, topic):
     assert not client.topic_matches_sub(sub, topic)