Skip to content

Commit

Permalink
Merge pull request #329 from RWTH-EBC/325-Filip-MQTT-Client-still-req…
Browse files Browse the repository at this point in the history
…uire-object_id

325 filip mqtt client still require object
  • Loading branch information
djs0109 authored Oct 1, 2024
2 parents f8660a2 + 25c5f09 commit 5acc5d5
Show file tree
Hide file tree
Showing 2 changed files with 71 additions and 8 deletions.
19 changes: 14 additions & 5 deletions filip/clients/mqtt/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -751,13 +751,22 @@ def publish(self,
msg_payload = payload.copy()
for key in payload.keys():
for attr in device.attributes:
if key in attr.object_id or key == 'timeInstant':
key_constraint = key == "timeInstant"
def elif_action(msg): None

if attr.object_id is not None:
key_constraint = key_constraint or (key in attr.object_id)
def elif_action(msg): msg[attr.object_id] = msg.pop(key)

#could be made more compact by pulling up the second condition
#but would probably make the code less readable...
if key_constraint:
break

elif key == attr.name:
if attr.object_id:
msg_payload[attr.object_id] = \
msg_payload.pop(key)
elif_action(msg_payload)
break

else:
err_msg = f"Attribute key '{key}' is not allowed " \
f"in the message payload for this " \
Expand All @@ -769,7 +778,7 @@ def publish(self,
topic_type=IoTAMQTTMessageType.MULTI)
payload = self._encoders[device.protocol].encode_msg(
device_id=device_id,
payload=payload,
payload=msg_payload,
msg_type=IoTAMQTTMessageType.MULTI)

# create message for command acknowledgement
Expand Down
60 changes: 57 additions & 3 deletions tests/clients/test_mqtt_client.py
Original file line number Diff line number Diff line change
@@ -1,16 +1,18 @@
import logging
import time
import datetime
import unittest
from random import randrange
from paho.mqtt.client import MQTT_CLEAN_START_FIRST_ONLY
from random import randrange,Random
from paho.mqtt.client import MQTT_CLEAN_START_FIRST_ONLY,MQTTv5
from filip.custom_types import AnyMqttUrl
from filip.models import FiwareHeader
from filip.models.ngsi_v2.context import NamedCommand
from filip.models.ngsi_v2.iot import \
Device, \
DeviceAttribute, \
DeviceCommand, \
ServiceGroup, PayloadProtocol
ServiceGroup, PayloadProtocol, \
TransportProtocol
from filip.clients.mqtt import IoTAMQTTClient
from filip.utils.cleanup import clean_test, clear_all
from tests.config import settings
Expand Down Expand Up @@ -131,6 +133,58 @@ def on_message_second(mqttc, obj, msg, properties=None):
# stop network loop and disconnect cleanly
self.mqttc.loop_stop()
self.mqttc.disconnect()

def test_optional_object_id(self):
"""
Test:
Verify the IotaMQTTClient publish function
is not raising when missing an object_id.
The test setup is minimal, we are not concerned
with commands/command callbacks, just that publish
works for a specific device argument
Setup:
publish with:
- attr_name=None
- command_name=None
- Dict payload
- with and without object_id
- with key = attr.name/in object_id
"""
tmp_id="dev_id"
tmp_attrs = [DeviceAttribute(name="temperature",
type="Number"),
DeviceAttribute(name="temperature",
type="Number",
object_id="temp")]

payloads = [{"temperature":Random().randint(0,50)},
{"temp":Random().randint(0,50)}]

for p,attr in zip(payloads,tmp_attrs):
tmp_dev = Device(device_id=tmp_id,
attributes=[attr],
entity_name="tmp_entity",
entity_type="tmp_type",
apikey="tmp_key",
transport=TransportProtocol.MQTT,
protocol=PayloadProtocol.IOTA_JSON)
tmp_mqttc = IoTAMQTTClient(protocol=MQTTv5 ,devices=[tmp_dev])
tmp_mqttc.publish(device_id=tmp_id,payload=p)
tmp_mqttc.delete_device(device_id=tmp_id)

#checking if raises correctly
with self.assertRaises(KeyError):
tmp_dev = Device(device_id=tmp_id,
attributes=[tmp_attrs[0]],
entity_name="tmp_entity",
entity_type="tmp_type",
apikey="tmp_key",
transport=TransportProtocol.MQTT,
protocol=PayloadProtocol.IOTA_JSON)
tmp_mqttc = IoTAMQTTClient(protocol=MQTTv5, devices=[tmp_dev])
tmp_mqttc.publish(device_id=tmp_id,
payload={"t": Random().randint(0,50)})
tmp_mqttc.delete_device(device_id=tmp_id)

def test_init(self):
devices = [self.device_json, self.device_ul]
Expand Down

0 comments on commit 5acc5d5

Please sign in to comment.