Get output of a Lambda function back to IoT Core MQTT broker

0

We're using IoT LoRaWAN and have a number of test devices publishing to a Lambda LoRa decoder. The payloads arrive at the message broker, an IoT rule catches them and sends them to Lambda where it is decoded and the resulting message pushed to cloudwatch logs. However, I need to get the decoded payload BACK to the message broker since the broker is connected to our own application which handles the dashboarding and alerting.

Lambda easily connects to IoT on the trigger (input) side, but does not offer a direct connection on the destination (output side). At least I don't see it as part of the default options. I'd rather not add SNS or SQS in between to avoid the additional management, especially since we're really just testing at the moment.

What is the ideal way to do this? Am I missing something?

已提问 2 年前1262 查看次数
3 回答
1
已接受的回答

I sugggest to use the approach described in this sample as it provides the features which you describe above: https://github.com/aws-samples/aws-iot-core-lorawan/tree/main/transform_binary_payload

Instead of adding Lambda as an Action to the AWS IoT Rule, you should use aws_lambda function of AWS IoT SQL and use a Republish Action in AWS IoT Rule.

Further docs:

已回答 2 年前
profile picture
专家
已审核 10 个月前
  • Got it thank you. I didn't get it to work yet, I'm still a little confused by the whole SQL rules concept. Especially confusing is the interplay between rules, destinations and the 'other' destinations. I see the power of rules, but things get complex pretty quickly when you stack them up - gets hard to keep track. The github link you shared was very useful thank you.

0

Hi, I've spent more time looking at the Rules docs, I see how powerful it could be but I'm hitting a wall trying to figure out how to use the aws_lambda function within a rule.

Here's my rule SQL:

SELECT *, aws_lambda("arn:aws:lambda:us-east-1:<<REDACTED>>:function:<<REDACTED>>",*) as output, topic() as RuleMetadata.originalTopic, timestamp() as RuleMetadata.timestamp, clientid() as RuleMetadata.clientid FROM 'test/lorawan/uplink'

I've followed the instructions to grant invoke permissions (using the CLI command in the docs) and can see it was successfully granted in the Lambda's Resource-based policy settings:

Statement ID
TestRepub
Principal
iot.amazonaws.com
Effect
Allow
Action
lambda:InvokeFunction
Conditions
{
 "StringEquals": {
  "AWS:SourceAccount": "<<REDACTED>>"
 },
 "ArnLike": {
  "AWS:SourceArn": "arn:aws:iam::<<REDACTED>>:role/service-role/testrepub"
 }
}

The rule works like a charm when I remove the aws_lambda function from the SQL and can see it on the MQTT tester with the republish action to test/repub. But when I add the lambda function back in, no messages come through MQTT tester and nothing occurs in the logs of the Lambda function. I also have a republish to topic test/error for Error action on the rule, but nothing appears there either making it really hard to debug!

I assume its a permission issue, but I followed the instructions very specifically. Any help would be really appreciated!

已回答 2 年前
  • My mistake! I use the the arn for the role, not the rule! AWS naming conventions are pretty confusing. I needed: "arn:aws:iot:us-east-1:<<REDACTED>>:rule/TestRepub", not "arn:aws:iam::<<REDACTED>>:role/service-role/testrepub"

0

Hi Andrei, I'm trying to get this to work using your response, the docs, and this video as a guide. I have a simple Lambda transformer for a simple LoRa based button device that I cannot reach using this rule:

SELECT aws_lambda("arn:aws:lambda:us-east-1:<<REDACTED>>:function:TransformerRakButtonUplink", *) as event FROM 'devices/lorawan/uplink'

I'm trying to send the entire incoming payload below in its original form (using the , * in the rule) since my Lambda function expects this payload in its entirety.

However, my rule does not appear to even be able to reach the Lambda function. I can see the below payload on the MQTT tester no problem, so the device is able to connect to IoT Core. I just don't understand the rule issue. I checked the Lambda logs and it hasn't been invoked at all.

Example payload I want to get to Lambda using the rule to then republish to a topic like devices/lorawan/transformed

{
  "WirelessDeviceId": "<<REDACTED>>",
  "PayloadData": "Ag==",
  "WirelessMetadata": {
    "LoRaWAN": {
      "ADR": true,
      "Bandwidth": 125,
      "ClassB": false,
      "CodeRate": "4/5",
      "DataRate": "3",
      "DevAddr": "<<REDACTED>>",
      "DevEui": "<<REDACTED>>",
      "FCnt": 337,
      "FOptLen": 0,
      "FPort": 2,
      "Frequency": "904300000",
      "Gateways": [
        {
          "GatewayEui": "<<REDACTED>>",
          "Rssi": -85,
          "Snr": 7.5
        }
      ],
      "MIC": "16613db6",
      "MType": "UnconfirmedDataUp",
      "Major": "LoRaWANR1",
      "Modulation": "LORA",
      "PolarizationInversion": false,
      "SpreadingFactor": 7,
      "Timestamp": "2021-12-24T02:41:19Z"
    }
  }
}
已回答 2 年前

您未登录。 登录 发布回答。

一个好的回答可以清楚地解答问题和提供建设性反馈,并能促进提问者的职业发展。

回答问题的准则