Can a rule issue GET and POST commands

I saw that a rule (Rules 4) can be trigger as an endpoint, so I figured rules might also be able to do GETs and/or POSTs. But, I couldn't find that in the documentation.

I'm thinking I need a new device type (driver) for a virtual device that does the http stuff?

This is for controlling legacy audio/video equipment via IR. Currently every IR command is mapped to an endpoint. This allows my old scripts running on an RPI to have "scenes" that include configuration of the equipment to select correct the correct audio and video inputs, sound mode, and other things I can only control via IR.

Works fine for me using scripts on RPI, but I'm trying to migrate everyting to HE.

If I interpret you post correctly, a short-term option may be to continue to receive the HTTP requests on your rpi and pass them on to your HE hub using Maker API commands? In theory calling a scene in HE exposed as a device via Maker API.

Just took a quick look at Maker API. It looks that provides a mechanism for accessing a device as an endpoint.

I need the opposite--sending Http requests, not receiving them. The rpi receiving the http requests has the IR sender. It uses LIRC and lirc_web to provide the endpoints.

1 Like

Ahhh, should have read the "issue" part of your thread title.... :slight_smile:

Just found this reply in a thread #3:

That's what I was thinking I'd do. Just wanted to know if that seemed like the best (or at least a good) approach.

Thanks.

1 Like

The only issue with this is that I think I need a device for each unique IR command. That's several hundred!

New to HE, maybe I can use a device with a parameterized input from which the endpoint ID can be derived.

There are probably equivalent numbers of users who can assist... :slight_smile:

Here they come.... Well at least one of them..

1 Like

Threw this together the other day for testing something else, but if it helps:

HTTP Get/Post Test Driver
/*
 * HTTP Get/Post Test
 *
 *  Licensed Virtual the Apache License, Version 2.0 (the "License"); you may not use this file except
 *  in compliance with the License. You may obtain a copy of the License at:
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software distributed under the License is distributed
 *  on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License
 *  for the specific language governing permissions and limitations under the License.
 *
 *  Change History:
 *
 *    Date        Who            What
 *    ----        ---            ----
 *    2021-05-21  thebearmay	 Original version 0.1.0
 *
 */

static String version()	{  return '0.1.0'  }

metadata {
    definition (
		name: "HttpGetPost Tester", 
		namespace: "thebearmay", 
		author: "Jean P. May, Jr.",
	        importUrl:""
	) {
        capability "Actuator"
        capability "Configuration"
        capability "PresenceSensor"
       
        attribute "getReturn", "string"
        
        
        command "sendGet", [[name:"ipAddress*", type:"STRING", description:"Site to send Get"], [name:"path*", type:"STRING", description:"Path for Get"]]   
        command "sendPost", [[name:"ipAddress*", type:"STRING", description:"Site to send Get"], [name:"path*", type:"STRING", description:"Path for Get"]]       
            
    }   
}

preferences {
    input("debugEnable", "bool", title: "Enable debug logging?")
    input("security", "bool", title: "Hub Security Enabled", defaultValue: false, submitOnChange: true)
    if (security) { 
        input("username", "string", title: "Hub Security Username", required: false)
        input("password", "password", title: "Hub Security Password", required: false)
    }
}

def installed() {
	log.trace "installed()"
}

def configure() {
    if(debugEnable) log.debug "configure()"
    updateAttr("getReturn"," ")

}

def updateAttr(aKey, aValue){
    sendEvent(name:aKey, value:aValue)
}

def updateAttr(aKey, aValue, aUnit){
    sendEvent(name:aKey, value:aValue, unit:aUnit)
}

def initialize(){

}


def sendGet(ipAddress, path){
        if(security) {
            httpPost(
                [
                    uri: "http://127.0.0.1:8080",
                    path: "/login",
                    query: [ loginRedirect: "/" ],
                    body: [
                        username: username,
                        password: password,
                        submit: "Login"
                    ]
                ]
            ) { resp -> cookie = resp?.headers?.'Set-Cookie'?.split(';')?.getAt(0) }
        }    
        params = [
            uri: ipAddress,
            path: path,
            headers: [ "Cookie": cookie ]
        ]  
	
        asynchttpGet("sendGetHandler", params)
    
}

def sendPost(ipAddress, path){
        if(security) {
            httpPost(
                [
                    uri: "http://127.0.0.1:8080",
                    path: "/login",
                    query: [ loginRedirect: "/" ],
                    body: [
                        username: username,
                        password: password,
                        submit: "Login"
                    ]
                ]
            ) { resp -> cookie = resp?.headers?.'Set-Cookie'?.split(';')?.getAt(0) }
        }    
        params = [
            uri: ipAddress,
            path: path,
            headers: [ "Cookie": cookie ]
        ]  
	
        asynchttpPost("sendGetHandler", params)
    
}

def sendGetHandler(resp, data) {
    def errFlag = 0
    try {
	    if(resp.getStatus() == 200 || resp.getStatus() == 207) {
		    strWork = resp.data.toString()
    		if(debugEnable) log.debug strWork
	        sendEvent(name:"getReturn",value:strWork)
  	    }
    } catch(Exception ex) { 
        
    } 

}

def updated(){
	log.trace "updated()"
	if(debugEnable) runIn(1800,logsOff)
}

void logsOff(){
     device.updateSetting("debugEnable",[value:"false",type:"bool"])
}
3 Likes

Before they come--

I'm aware that I could buy a different IR send solution and get a cleaner interface. Maybe I'll do that, but first I want to understand if it's really that painful to use what I have (X10 was simple)

I'd give the Community here the benefit of the doubt for the time being, there are plenty of willing and able contributors who may be able to assist you. If you can't get what you need here, then start to look elsewhere....

1 Like

Thanks!

Looks like it's probably what I need. But,

I'm so new to HE. I take it there's a way to run the sendGet and sendPost commands passing them ip address, path, etc?

Don't bother to tell me how--I'll go away and do my homework.

Thanks!

2 Likes

You're more diligent than me.... :slight_smile:

1 Like

So, the documentation for "custom actions" for Rules 4.0 I see this:

*Send, Speak, or Log a Message, Send HTTP Request *

  • Send or Speak a Message*
    
  • Log a Message*
    
  • Send HTTP Get*
    
  • Send HTTP Post*
    

Does that mean by using a virtual device command like thebearmay implementation, or directly in an action? I couldn't find a way to do it in the hubitat UI.

This might help with the post from a RM action:

2 Likes

Perfect!

Don't know how I missed. Probably skimming too fast and saw send, speak or log a message and missed the stuff after the comma.

Thanks!

1 Like

Feel stupid, but I can't seem to figure out how to fill the action form for the post.

For example, when I use postman, this works:

192.168.0.222:3000/remotes/STR-DE985/PowerOff

I leave the body field empty.

But, when I try using 192.168.0.222:3000/remotes/STR-DE985/PowerOff as the "URL in rules, the post isn't recognized.

Also tried using 192.168.0.222:3000 as the URL and /remotes/STR-DE985/PowerOff as the body.

(I know the rule is getting triggered, since I see a message log from another action of the same rule.)

I suggest that you use Postman to see what's going on (post to its url). URL should all be in the URL field, Perhaps content type should be 'text'

Yes, as I indicated I'm using postman. URL is what I posted above (from the Postman UI)

Tried text, didn't work.

Starting to think the action won't work with and empty body.

This is what I'm doing in postman (that works):

Maybe Bruce meant to say try it with postman echo. You can pay your request to the relevant URL on their server and it will echo back the called URL, headers, and body of the request. You could post to postman echo from both Hubitat and postman to see what is different between the working and non working requests.

1 Like