Jump to content

Welcome to Smart Home Forum by FIBARO

Dear Guest,

 

as you can notice parts of Smart Home Forum by FIBARO is not available for you. You have to register in order to view all content and post in our community. Don't worry! Registration is a simple free process that requires minimal information for you to sign up. Become a part of of Smart Home Forum by FIBARO by creating an account.

 

As a member you can:

  •     Start new topics and reply to others
  •     Follow topics and users to get email updates
  •     Get your own profile page and make new friends
  •     Send personal messages
  •     ... and learn a lot about our system!

 

Regards,

Smart Home Forum by FIBARO Team


[TUTORIAL} Introduction to API calls and http requests


AutoFrank

Recommended Posts

Introduction to API and http requests

Like the other 'Introduction to' posts I'm h0ping this may help some of the people begining their HC2 and lua journey

Corrections and suggestions to improve always welcome.

 

What is an API
An API can be used to execute commands but the majority are used to request a response or status. Most API’s are interrogated through a http or https request. Some API’s require authentication in the form of a username or a password or an API key. There are public API’s and private API’s. There are a number of API types and the one of the most widely used is a called RESTAPI. This type of API is supported by the HC2 but there are others such MQTT, SOAP, etc


The following are API’s that you may have come across in this forum and there are many others

  • Home Center 2 :

    Please login or register to see this link.

     (where hc2-ip is the ipaddress of your hc2 192.168.x.x  
  • OWN : open weather map (

    Please login or register to see this link.

    )
  • Sonos-http-api : (

    Please login or register to see this link.

    )
  • AWS Polly: used for TTS (http://docs.aws.amazon.com/polly/latest/dg/API_Reference.html )
  • VoiceRSS : used for TTS (http://www.voicerss.org/api/documentation.aspx )

 

Some organisations like AWS or Google have multiple API’s that are used for different purposes

 

Structure
All API’s has a set of web methods with a set structure. An API call or request can be either a GET, DELETE, POST, PUT and for this introduction we will focus on the GET
This means that the data format is predictable and as such is easy to traverse and extract responses. Most RESTAPI responses have a format that conforms to json standard. Json is a way to store information in an organized, easy-to-access manner. It gives us a human-readable collection of data that we can access in a really logical manner. All public API’s are documented like the ones outlined above so a under will know what to expect when they issue a http request.
A simple json example would be something like 

 

Please login or register to see this code.



A slightly more complicated json string could be be 

 

Please login or register to see this code.


This could also be referreed to as a tbale because of it's structured format. Fortunately there are websites like

Please login or register to see this link.

that make these json strings easier to read

 

Please login or register to see this code.


To access an api you need 2 things

 

  • ip address, port, etc to make the http/https request
  • Structure/format of the response so you know how to traverse it and extract what you want


The easiest way to explain and learn is by example. As it is highly likely that everybody reading this will have a HC2 we can use to demonstrate the principles. 
The HC2 RESTAPI is documented on the Fibaro developer site at

Please login or register to see this link.


The one we will look at is devices. This the first one under the General category at the developers website above. The developer website shows the various parameters that are returned with this call. The API can be used to request information or complete an action.
We will look at the request for information


If you go to http://,hc2-ip./docs you will see the interactive or inline documentation for web API

Please login or register to see this attachment.


Go to the section on devices and select deviceid

Please login or register to see this attachment.


 enter a device number ( I selected device 176 which is a dimmer module ) and click Try It. 
You will see the json formatted or encoded response for that API call. You will also see the full url for the call.


Please login or register to see this attachment.

 

If you copy the url and paste it into a browser you will get the same thing (except as one long string)

 

Please login or register to see this code.

 

EXAMPLE - API Call from a Virtual Device
The following is a http request to the HC2 api. Copy the following in a button or main loop in a virtual device
 

Please login or register to see this code.


run the vd and open the debug window

Please login or register to see this attachment.


You’ll see the name and value of the device you selected. If you look through the json response from further up in the tutorial you’ll see the correlation between the results and the json 

There are some examples of how to iterate through an array in another one of the tutorials I posted. Please see my signature…

 

One last one in case you have difficulty sleeping :-) and the if the above was too simple


This function iterates through all the virtual devices on your HC2 and looks for one called 'LAN Network 2.0'
The 'LAN Network 2.0' virtual device has multiple labels

 

  1. The function iterates through the virtual device and counts all the labels ( in the json for the virtual device these are called rows) 
  2. For each row above it looks for an element type ‘Label’
  3. It then iterates through all the labels checking that they match the default format of Label1, Lable2, etc.

Please login or register to see this code.

The result is a loop inside a loop inside another loop, iterating and checking at each step

 

full code for function to pick through when you have some time.

 

Please login or register to see this code.

 

Happy coding and suggestions to improve/correct always welcome

 

-f


 

Edited by AutoFrank
  • Like 6
  • Thanks 1
Link to comment
Share on other sites

  • 2 weeks later...

can I make a Net.FHttp call from a Scene instead of a Device? I have lifted the code out of a device and it is really angry at me trying to index 'Net'(a nil value)

Link to comment
Share on other sites

  • Topic Author
  • 1 hour ago, shaunfrost said:

    can I make a Net.FHttp call from a Scene instead of a Device? I have lifted the code out of a device and it is really angry at me trying to index 'Net'(a nil value)

     

    Hi @shaunfrost

     

    For some reason the http calls are different between scene and vd

     

    Here is an example of a http call from a scene

    This call is a POST and creates a table through the HC2 api but the principle is the same of you want to access another api

    Please login or register to see this code.

    Does this help ?

    -f

    Link to comment
    Share on other sites

    2 hours ago, AutoFrank said:

     

    Hi @shaunfrost

     

    For some reason the http calls are different between scene and vd

     

    Here is an example of a http call from a scene

    This call is a POST and creates a table through the HC2 api but the principle is the same of you want to access another api

    Please login or register to see this code.

    Does this help ?

    -f

     

    I will play around with it.. it was such a simple thing when it started..

    I just wanted to turn this below into a scene!

    -- Initialistation
    aeonID = 213;
    apiKey = "xxxxxxxxxx"
    feed = "Watt"
    local Emon = Net.FHttp("emoncms.org")
    local payload = "?json={"
    local key = "&apikey="..apiKey

    payload = payload..feed..":"..fibaro:getValue(aeonID, "power")
    payload = payload.."}"

    tsresponse, tsstatus, tserrorCode = Emon:POST("/input/post.json"..payload..key , "" ) ;
    fibaro:debug(tsresponse)
    Link to comment
    Share on other sites

    On 2/27/2017 at 7:06 PM, AutoFrank said:

    Here is an example of a http call from a scene

     

    Hi @AutoFrank

     

    I'm sure you're aware of this, but for the purpose of this tutorial, another way to do this in a scene, if the requirement is to simply call the HC2 API, is to use the built-in api function.  I find this easier to use than net.HTTPClient, as it doesn't require the use of the asynchronous success and error callback functions.  Here's an example of a function that creates a global variable:

     

    Please login or register to see this code.

    Dave

    Link to comment
    Share on other sites

  • Topic Author
  • 2 minutes ago, Dave Harrison said:

     

    Hi @AutoFrank

     

    I'm sure you're aware of this, but for the purpose of this tutorial, another way to do this in a scene, if the requirement is to simply call the HC2 API, is to use the built-in api function.  I find this easier to use than net.HTTPClient, as it doesn't require the use of the asynchronous success and error callback functions.  Here's an example of a function that creates a global variable:

     

    Please login or register to see this code.

    Dave

     

    HI @Dave Harrison

     

    Thanks !!, I've never see that direct an approach.

    Thanks for adding to the post and I must have a play around with that....

     

    -f

     

     

    Link to comment
    Share on other sites

    One question here.

    What if there is a need to make few calls one after another but in between HC2 needs to wait for successful execution of the predecessor? I was struggling with it for some time and did not found any smart solution...

    Link to comment
    Share on other sites

  • Topic Author
  • 36 minutes ago, jcichon01 said:

    One question here.

    What if there is a need to make few calls one after another but in between HC2 needs to wait for successful execution of the predecessor? I was struggling with it for some time and did not found any smart solution...

     

     

    @jcichon01

     

    I think it depends on where you are making the api calls to ?.. ( internal to the hc2 or external to it )

    I have a scene that uses the HC2 api to create 5 variables and they are effectively created them in parallel because of the way the HC2 operates. The api seems to be predictable and has no issue processing these requests.

     

    external to the system is a different story and it depends on the api

    There is a setTimeout(function, duration) that may help here

     

    @petergebruers posted a post on setTimeout that you may find useful - 

    Please login or register to see this link.

     

     

     

     

     

     

     

     

     

    • Like 1
    Link to comment
    Share on other sites

    10 godzin temu, AutoFrank napisał:

     

    @jcichon01

     

    I think it depends on where you are making the api calls to ?.. ( internal to the hc2 or external to it )

    I have a scene that uses the HC2 api to create 5 variables and they are effectively created them in parallel because of the way the HC2 operates. The api seems to be predictable and has no issue processing these requests.

     

    external to the system is a different story and it depends on the api

    There is a setTimeout(function, duration) that may help here

     

    @petergebruers posted a post on setTimeout that you may find useful - 

    Please login or register to see this link.

     

    @AutoFrank
    Thank you for quick answer and sorry that I did not provide the details before.

     

    Actually I'm calling node-sonos-http-api's say function. In my setup I'm using google TTS engine which does have some limitations on an input text's length. When I'm calling say api with the text which is longer then x characters it does not produce any TTS output so what I had to do is to cut the output into few independent strings. After that I'm calling the TTS engine few times. If there is no "wait until successes" implemented TTS outputs only the content of the last string which was sent... 

    If I remember correctly I did try setTimeout between HTTP requests but it did not work. HC2 is somehow "caching" the requests before sending it out...

    Link to comment
    Share on other sites

  • Topic Author
  • 37 minutes ago, jcichon01 said:

     

    @AutoFrank
    Thank you for quick answer and sorry that I did not provide the details before.

     

    Actually I'm calling node-sonos-http-api's say function. In my setup I'm using google TTS engine which does have some limitations on an input text's length. When I'm calling say api with the text which is longer then x characters it does not produce any TTS output so what I had to do is to cut the output into few independent strings. After that I'm calling the TTS engine few times. If there is no "wait until successes" implemented TTS outputs only the content of the last string which was sent... 

    If I remember correctly I did try setTimeout between HTTP requests but it did not work. HC2 is somehow "caching" the requests before sending it out...

     

    @petergebruers is a http expert so his advise is probably the best

     

    Another approach would be have a timer that runs in parallel with http request and dynamically adjust it based on the number of chars you're trying to announce.

    This may allow you make a best 'guestimate' as to how long the TTS takes to finish 

     

    Link to comment
    Share on other sites

    On 27-2-2017 at 8:06 PM, AutoFrank said:

     

    Hi @shaunfrost

     

    For some reason the http calls are different between scene and vd

     

    Here is an example of a http call from a scene

    This call is a POST and creates a table through the HC2 api but the principle is the same of you want to access another api

    Please login or register to see this code.

    Does this help ?

    -f

    Hi Frank, 

    Thanks! i got this working but how do I get the variable status.data outside the http:request.. so after }). I cant get it there.

     

    Are the variable 'succes' and 'error' cant be renamed?

    Link to comment
    Share on other sites

    Hi Frank, 

    Thanks! i got this working but how do I get the variable status.data outside the http:request.. so after }). I cant get it there.

     

    Are the variable 'succes' and 'error' cant be renamed?

     

    Thanks!

    Martijn

    Link to comment
    Share on other sites

  • Topic Author
  • On 3/9/2017 at 10:50 PM, mdejager said:

    Hi Frank, 

    Thanks! i got this working but how do I get the variable status.data outside the http:request.. so after }). I cant get it there.

     

    Are the variable 'succes' and 'error' cant be renamed?

     

    Thanks!

    Martijn

     

    Hi @mdejager

     

    I've added a little more to the http post the creates a global variable.

    One way is to assign it to a global variable and but it depends on what you're trying to so with the parameter.

    I added some extra code to to print out some extra inforamtion

    Please login or register to see this code.

     

    Please login or register to see this code.

    this is the response code 201/200 if it all went okay, 400/500 if there was a problem (roughly)

     

    Please login or register to see this code.

    This is the actual response to the http request and is returned mostly in the form is a table that contains a json encoded string

     

    Please login or register to see this code.

    - this means you need to decode it and select different parts depending on what you want to do

     

    Please login or register to see this code.

    This reads through the key / value pairs and displays them (this helps show the structure of the response)

     

    in this case the output is 

     

    Please login or register to see this code.

     

    after you find the part of the response you';re interested in you can print it out or assign it to a variable

     

    Please login or register to see this code.

    You can then use this within the scene or of you want to use it outside you can save the value in a global variable using <fibaro:setGlobal> ad retrieve from there

     

    if you run the above it will create a global variable and the debug window will display the following in the debug window

    Please login or register to see this code.

    Apologies for the long generic answer but I wasn't too sure what you wanted to do specifically

    hope some of it is helpful

    -f

     

     

     

     

     

     

     

     

     

     

    Link to comment
    Share on other sites

    • T.Konopka featured this topic
    • 1 year later...

    The topic has been moved from "

    Please login or register to see this link.

    " to "

    Please login or register to see this link.

    ".

     

    Temat został przeniesiony z "

    Please login or register to see this link.

    " do "

    Please login or register to see this link.

    ".

    Link to comment
    Share on other sites

    • 2 weeks later...

    Hi

     

    Thanks a lot for the tutorial!

    I'd like to access data of my Fibaro Home Center 2 from a cloud. Does someone know how to get remote access?

    Port forwarding is not really an option, since I'm using the Home Center for demo purposes at different locations.

     

    Thanks,

    Cornelia

    Link to comment
    Share on other sites

    Join the conversation

    You can post now and register later. If you have an account, sign in now to post with your account.

    Guest
    Reply to this topic...

    ×   Pasted as rich text.   Paste as plain text instead

      Only 75 emoji are allowed.

    ×   Your link has been automatically embedded.   Display as a link instead

    ×   Your previous content has been restored.   Clear editor

    ×   You cannot paste images directly. Upload or insert images from URL.

    ×
    ×
    • Create New...