API Developer Needed

I’m looking for someone to develop a Hubitat app for me that will download API data from a 3rd party and place values into variables in Hubitat. Can anyone here do it or can you recommend someone to do it? Paid work no problem.

Probably should give a little information on the API so that people can gauge their knowledge vs. the requirements of the API. API documentation location would be a good starting point, as well as how you plan on utilizing the data (RM, hub variables, attributes, etc.) - usage could determine app vs device vs app w/child device, etc.

2 Likes

I already have the API key from the third-party.

This application I am asking for will poll every 5 minutes and place the returned values into hub variables. I can take it from there.

Essentially, we are pulling sensor values from the third-party into Hubitat to make decisions upon. Temperature, pH, EC, etc.

There are about 10 variables. No arrays.

Documentation:

Version 1.1 by Evan
How to work?
Example:
curl -X POST "https://api.trolmaster.com/aquax" -H "accept: application/json" -H "x-api-key: 5QvxxxxxxMsor2jPgg1xxxxxxXoFDtP" -H "Content-Type: application/json" -d "{ "cmd": "getSensorData", "params": { "mac": "xxxxxxxxxx", "model":"Aqua-X" }}"

Real-time-data will refresh in 5min

Request:
{
"cmd": "getSensorData",
"params": {
"mac": "xxxxxxx",
"model":"Aqua-X"
}
}

Response:
{
"Item": {
"ph": "11.0",
"wc": "13.8",
"ec": "1.86",
"ct_tm": "2 Apr 2021 20:00",
"mac": "00149727FE426C36",
"timestamp": 1602818400,
"tp": "82.5"

Might just take a second. Let me see real quick.

if he cannot do it .. it should take about 1 hour to do a real driver with attributes and parameters such as user name password mac refresh time etc..

if you pm me the api key and the mac i can take a look

This might be close:

ProtoType
/*
 * 
 *
 *  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
 *    ----         ---           ----
*/

import groovy.json.JsonOutput
import groovy.json.JsonSlurper

@SuppressWarnings('unused')
static String version() {return "0.0.0"}

metadata {
    definition (
        name: "ProtoType", 
        namespace: "thebearmay", 
        author: "Jean P. May, Jr.",
        description: "",
        importUrl:"https://raw.githubusercontent.com/thebearmay/hubitat/main/xxxx.groovy"
    ) {
 
        capability "Actuator"
        capability "Initialize"
        
        attribute "ec2", "number"
        attribute "tp2", "number"
        attribute "ec", "number"
        attribute "tp", "number"
        attribute "ph", "number"
        attribute "wc", "number"
        attribute "timestamp", "string"
        attribute "ct_tm", "string"
        attribute "mac", "string"
        
 
        command "pollSite"
    }   
}

preferences {
    input("debugEnabled", "bool", title: "Enable debug logging?")
    input("pollRate", "number", title: "Poll Rate in minutes (0 = No Polling)", defaultValue:0)
    
    input("sitePath", "string", title: "URL for site ", required: false)
    input("siteApiKey", "string", title: "API Key", required: false)
    input("macAddr", "string", title: "MAC address", required: false)
    input("model", "string", title: "Model", required:false)
}

@SuppressWarnings('unused')
def installed() {

}
@SuppressWarnings('unused')
def updateAttr(String aKey, aValue, String aUnit = ""){
    if(aValue.length() > 1024) aValue = aValue.substring(0,1023)
    sendEvent(name:aKey, value:aValue, unit:aUnit)
}

void initialize() {
    updated()
}

void updated(){
    if(debugEnabled) {
        log.debug "updated()"
        runIn(1800,"logsOff")
    } 
    if(pollRate > 0) 
        runIn(pollRate*60, "pollSite")
    else
        unschedule("pollSite")
}


void pollSite(){

    def bodyText = JsonOutput.toJson([cmd: "getSensorData", params: [mac: "$macAddr", model: "$model"]])
    def params = [
        uri: sitePath,
        requestContentType: 'application/json',
		contentType: 'application/json',
        headers: [
            "x-api-key" : siteApiKey
                 ],
        body: "$bodyText"        
    ]
    asynchttpPost("getResponse", params)

    if(pollRate > 0) 
        runIn(pollRate*60, "pollSite")
}
       
        
void getResponse(resp, data) {       
     try {
         if(resp.getStatus() == 200) {
            if(resp!= null) {
                def slurper = new groovy.json.JsonSlurper()
                jsonData = slurper.parseText(resp.data)
                setVariables(jsonData)
            }else {
                log.error "Null Response"
            }
        }
    } catch (exception) {
        log.error "Read Ext Error: ${exception.message}"
    }
}

void setVariables(jsonData){
    if(debugEnabled) log.debug "setVar ${jsonData.Item}"
    jsonData.Item.each{
        if(debugEnabled) log.debug "${it.key} : ${it.value}"
        updateAttr("$it.key", "$it.value")
        //success = this.setGlobalVar("variableName${it.key}", "${it.value}")
    }
        
}
    
          
@SuppressWarnings('unused')
void logsOff(){
     device.updateSetting("debugEnabled",[value:"false",type:"bool"])
}
5 Likes

One more thing. There are two models of controllers. Each model returns different sensor values.

There are multiple controllers in my building of both models.

For now, I only want to retrieve data for one of the two models. However, I have three of that model and would like to collect data from all three.

So something that allows multiple instances is necessary.

We can work on the second model of controller at a later date.

Does the code above produce any results for you?

I will be home in four or five hours. I can check this then.

No rush, but if the above works then you’re about 85-90% there.

1 Like

OK I'm working with the manufacturer because I'm not even getting a response from the test function of their portal. Give me some time to assess what's going on there.

1 Like

The manufacturer finally got me the info, and @thebearmay came through for me today. Thanks @thebearmay and everyone!!

6 Likes

@thebearmay did something similar for me last week. He's a great guy.

3 Likes