Creating Rules & Automations with commands + argument

I’m finally taking the plunge with the Rules API and creating my first rule. However, I’m getting this obtuse error and I can’t figure out what the problem is:

Error: Request failed with status code 422: {"requestId":"DAE87465-8814-4A89-8896-7CDD8B679B82","error":{"code":"ConstraintViolationError","message":"The 
    request is malformed.","details":[{"code":"BodyMalformedError","target":"Unknown target","message":"Malformed body on line 1","details":[]}]}}

Here is my rule:

{
  "name": "Test Web Requestor",
  "actions": [
    {
      "if": {
        "equals": {
          "left": {
            "device": {
              "devices": [
                "724861a2-2c0b-462b-84cc-0e3850920984"
              ],
              "component": "main",
              "capability": "presenceSensor",
              "attribute": "presence"
            }
          },
          "right": {
            "string": "present"
          }
        },
        "then": [
          {
            "command": {
              "devices": [
                "0a90aa3d-e0c3-47da-9922-c060368000ae"
              ],
              "commands": [
                {
                  "component": "main",
                  "capability": "partyvoice23922.webrequest",
                  "command": "POST",
                  "arguments": [
                    "http://192.168.1.104:1755/blah"
                  ]
                }
              ]
            }
          }
        ]
      }
    }
  ]
}

If anyone can point out my error, I’d be very appreciative!

I think you might need to write:

"string": "http://192.168.1.104:1755/blah"

I only have one Rule that uses an argument and I found I had to do that. I have absolutely no idea why.

Oh, and I really recommend YAML for Rules. You trade ridiculous amounts of brackets for ridiculous space based indentation but it is still an improvement

Update: I missed the braces because I was reading a YAML file where indentation replaces the braces.

1 Like

You’re right, Graham. The “argument” property can receive an array of objects, therefore, you need to add that value inside one. Eg.

"commands": [
    {
        "component": "main",
        "capability": "partyvoice23922.webrequest",
        "command": "POST",
        "arguments": [{"string":"http://192.168.1.104:1755/blah"}]
    }
]

The value type depends on the one defined in the capability’s command (string, integer, etc.)

I think it gets confusing because when you look at the ‘Response samples’ in the API documentation you see things like:

"actions": [
"commands": [
    {
        "component": "main",
        "capability": "switchLevel",
        "command": "setLevel",
        "arguments": [
            80
        ]
}

I don’t know if that is correct but to be consistent with the string I’d expect it to be { "integer": 80 }.

EXACTLY what I was going to say, Graham! It was this documentation that I was looking at that caused me this wasted time. I couldn’t find any of the example rules in github using arguments, but that doesn’t mean there might be one buried somewhere I just didn’t see.

THANK-YOU both for giving me the solution!

Thank you both for your comments.
I’ll report this because we need the value of { "integer": 80 } for the setLevel command argument as well.
Cheers! :smiley:

1 Like

@nayelyz:

On a related point, is this the right presentation json syntax for enabling an automation command+argument?:

{
    "dashboard": {
        "states": [],
        "actions": [],
        "basicPlus": []
    },
    "automation": {
        "conditions": [],
        "actions": [
            {
                "label": "POST",
                "displayType": "multiArgCommand",
                "multiArgCommand": {
                    "command": "POST",
                    "arguments": [
                        {
                            "label": "URL",
                            "displaytype": "textField",
                            "textField": {
                                "name": "url"
                            }
                        }
                    ]
                }
            },
            {
                "label": "GET",
                "displayType": "multiArgCommand",
                "multiArgCommand": {
                    "command": "GET",
                    "arguments": [
                        {
                            "label": "URL",
                            "displaytype": "textField",
                            "textField": {
                                "name": "url"
                            }
                        }
                    ]
                }
            }
        ]
    },
    "id": "partyvoice23922.webrequest",
    "version": 1
}

This doesn’t appear to be working at the moment; the POST and GET commands are listed in the automations app ‘Then’ menu, but if you try to tap on either of them (to provide the argument), nothing happens. So I’m guessing something is wrong with this too!

BTW, my rule above is working great!

Ok, please, allow me some time to review this and I’ll let you know. :smiley:

Silly question but is your rule for TTS?

TTS is all I’m using webcore for at the moment. I’ve been considering trying to use rules api to try to get off webcore but it’s a bit over my head.

I like the ability to store multiple phrases with webcore and then use the random syntax for TTS. It’s fun getting different voice announcements for when someone comes home :slight_smile:

Yes I have a TTS app that runs on a Raspberry Pi. I’ve recently moved the driver to Edge and can now also move off Webcore and use Rules to keep everything running locally.

My post wasn’t specifically for that but as you surmised, it will apply to that as well!

3 Likes