Use Nabu Casa URL to use HA API?

I’ve got a couple of automations running on my mobile device that sends data to HA via the local api.

The API calls this URL using the local IP

http://LOCAL_IP_ADDRESS:8123/api/states/sensor.test

Is it possible to use the Nabu Casa IP?


If so, can this method be used to remotely log the data from am ESP rather than using MQTT?


UPDATE:
Just tried this with the Nabu Casa URL and it works (just need to remove the port).

https://NABU_CASA_IP_ADDRESS/api/states/sensor.test

Questions still remains - can I use the Web Server API or the HTTP Request to push the data over the Nabu Casa IP?

Ok… So I managed to get this working both locally and via the Nabu Casa URL.

It would be useful if this was more integrated with the API and/or Logger(?) so you could define the URL.

This method works great but as you can probably tell - I’m not too familiar with ESP … yet.


Use:
To send data to Home Assistant via Nabu Casa’s remote access (or other alterative) from any ESP device that has a WiFi connection.
This means you can connect to any WiFi network and send updates remotely.

Requirements:
-You must have remote connection on your Home Assistant (e.g. Nabu Casa)

Example: https://YOUR_NABU_CASA_URL_HERE.ui.nabu.casa

-Generate a Long-Lived Access Token
– This is stored in the secrets.yaml as bearer_token

Substitutions / basic config
Firstly I checked everything was working good with the local IP.
I then changed the code (as-is now) to work with the Nabu Casa IP.

I’ve also included some basic config for the espnodemcu.

substitutions:
  hostname: AnyTestName
  
  BearerLocalIP: http://YOUR_LOCAL_IP_HERE:8123
  
  NabuCasaAddress: https://YOUR_NABU_CASA_URL_HERE.ui.nabu.casa
  
  BearerSensorName: sensor.YOUR_SENSOR_NAME_HERE

esphome:
  name: testnodemcuv2
  platform: ESP8266
  board: nodemcuv2

logger:

api:

ota:

web_server:
  port: 80

wifi:
  ssid: !secret wifi_ssid
  password: !secret wifi_password

captive_portal:

Adding a test sensor
I added the Uptime Sensor on the ESP as a test to send the data over the HTTP command.
This uses the ID ‘uptime_sensor’ which is used in the HTTP command but this can be changed to which ever ID you like.

sensor:
  - platform: uptime
    name: $hostname Uptime Sensor
    id: uptime_sensor
    update_interval: 60s
    on_raw_value:
      then:
        - text_sensor.template.publish:
            id: uptime_human
            state: !lambda |-
              int seconds = round(id(uptime_sensor).raw_state);
              int days = seconds / (24 * 3600);
              seconds = seconds % (24 * 3600);
              int hours = seconds / 3600;
              seconds = seconds % 3600;
              int minutes = seconds /  60;
              seconds = seconds % 60;
              return (
                (days ? to_string(days) + "d " : "") +
                (hours ? to_string(hours) + "h " : "") +
                (minutes ? to_string(minutes) + "m " : "") +
                (to_string(seconds) + "s")
              ).c_str();

Adding a Button to call the HTTP command
I then added a test Button which would call the HTTP on press.

button:
  # Button on press calls the http command
  - platform: template
    name: $BearerSensorName
    on_press:
        then:
        - http_request.post:
              method: POST
              ####
              ## Change IP and Sensor name within the substitutions
              ## You can use the local or remote IP
              ## Remember the URL has /api/states/ hard coded
              ####
              url: $NabuCasaAddress/api/states/$BearerSensorName
              headers:
                Authorization: !secret bearer_token
                Content-Type: application/json
              verify_ssl: false
              json:
              ####
              ## You can customize this part but remember to include 'state'
               root["state"] = id(uptime_human).state;
               ####
               ## Add more data / attributes here
               ## Refer to Home Assistant API Docs
               ## https://developers.home-assistant.io/docs/api/rest/
               ####

Bumping this thread as I’m looking to use similar to the above, but for all my sensors.
Is there an easier way to do this other than adding the - http_request.post: for each sensor?

Can it be called once? or some sort of variable/substitution

I’m trying to use this for the Torque integration, and I believe using the Nabu casa url is the way to do it in my case. Unfortunately, I’m not having much luck.

1 Like

As above, I got this working for sending updates to HA via NabuCasa.

The worst part, you have to build each sensor in ESP to send the data that way.

I honestly don’t know why this isn’t a standard integration yet.

MQTT is, but why not HA + API + NabuCasa?

1 Like

This looks promising…
Just need some time to see if it’ll work.

Actually need a little help here formatting the attributes in too?

Within the JSON format, I’m wanting to add two test attributes from the Home Assistant REST API Documentation.

{
    "state": "below_horizon",
    "attributes": {
        "next_rising":"2016-05-31T03:39:14+00:00",
        "next_setting":"2016-05-31T19:16:42+00:00"
    }
}

The ESP Home documentation does help a little but I’m still getting stuck.

Here’s the full code…

  - platform: template
    name: POST $BearerSensorName
    on_press:
        then:
        - http_request.post:
              method: POST
              ####
              ## Change IP and Sensor name within the substitutions
              ####
              url: $NabuCasaAddress/api/states/$BearerSensorName
              headers:
                Authorization: !secret bearer_token
                Content-Type: application/json
              verify_ssl: false
              json:
               root["state"] = id(uptime_human).state;
               ####
               ## Add more data / attributes here
               ####
              on_response:
                then:
                  - logger.log:
                      format: "Response status: %d"
                      args:
                        - status_code

I’m trying to get this working as well (hopefully) for a fingerprint scanner. I tried using your code from 2022 that you said was working however I’m getting errors when trying to compile. I kept all of the sensor and button config the same. Probably with the evolution of ESPhome how the code is written structured has changed. Are you able to send me a full working example?

This is the errors I get when trying to compile.

INFO Reading configuration /config/esphome/fingerprint-scanner.yaml...
Failed config

sensor.uptime: [source /config/esphome/fingerprint-scanner.yaml:47]
  platform: uptime
  name: FingerprintScanner Uptime Sensor
  id: uptime_sensor
  update_interval: 60s
  on_raw_value: 
    then: 
      - 
        Unable to find action with the name 'text_sensor.template.publish'.
        text_sensor.template.publish: 
          id: uptime_human
          state: !lambda |-
            int seconds = round(id(uptime_sensor).raw_state);
            int days = seconds / (24 * 3600);
            seconds = seconds % (24 * 3600);
            int hours = seconds / 3600;
            seconds = seconds % 3600;
            int minutes = seconds /  60;
            seconds = seconds % 60;
            return (
              (days ? to_string(days) + "d " : "") +
              (hours ? to_string(hours) + "h " : "") +
              (minutes ? to_string(minutes) + "m " : "") +
              (to_string(seconds) + "s")
            ).c_str();
button.template: [source /config/esphome/fingerprint-scanner.yaml:72]
  platform: template
  name: sensor.fingerprint_scanner
  on_press: 
    then: 
      - 
        Unable to find action with the name 'http_request.post'.
        http_request.post: 
          method: POST
          url: |-
            https://mynabucasaurl/api/states/sensor.fingerprint_scanner
          headers: 
            Authorization: !secret bearer_token
            Content-Type: application/json
          verify_ssl: False
          json: root["state"] = id(uptime_human).state;

I’m still using the same code so should be working fine.
Maybe it’s the “publish value” not sure if you need that…

I think you only need “on press > then”

Just a ‘stab in the dark’ - But I would start with something like this…

on_finger_scan_matched THEN call the http request.

on_finger_scan_matched:
        then:
        - http_request.post:
              method: POST
              ####
              ## Change IP and Sensor name within the substitutions
              ## You can use the local or remote IP
              ## Remember the URL has /api/states/ hard coded
              ####
              url: $NabuCasaAddress/api/states/$BearerSensorName
              headers:
                Authorization: !secret bearer_token
                Content-Type: application/json
              verify_ssl: false
              json:
              ####
              ## You can customize this part but remember to include 'state'
               root["state"] = id(uptime_human).state;
               ####
               ## Add more data / attributes here
               ## Refer to Home Assistant API Docs
               ## https://developers.home-assistant.io/docs/api/rest/
               ####

Don’t forget to change the id / sensor name to the information you actually want to send.

               root["state"] = id(uptime_human).state;

Thank you for getting back to me!

To start I’d like to get your configuration working then I’ll start figuring out how to convert it to the actual fingerprint scanner.

Here is the code that I’m trying to use, throwing up errors.

substitutions:
  hostname: FingerPrintScanner
  
  BearerLocalIP: http://10.4.20.50:8123
  
  NabuCasaAddress: https://redacted.ui.nabu.casa
  
  BearerSensorName: sensor.fingerprint_scanner

esphome:
  name: nabucasa-fingerprint
  friendly_name: nabucasa-fingerprint

esp32:
  board: esp32dev
  framework:
    type: arduino

# Enable logging
logger:

# Enable Home Assistant API
api:

ota:

wifi:
  ssid: !secret wifi_ssid
  password: !secret wifi_password

sensor:
  - platform: uptime
    name: $hostname Uptime Sensor
    id: uptime_sensor
    update_interval: 60s
    on_raw_value:
      then:
        - text_sensor.template.publish:
            id: uptime_human
            state: !lambda |-
              int seconds = round(id(uptime_sensor).raw_state);
              int days = seconds / (24 * 3600);
              seconds = seconds % (24 * 3600);
              int hours = seconds / 3600;
              seconds = seconds % 3600;
              int minutes = seconds /  60;
              seconds = seconds % 60;
              return (
                (days ? to_string(days) + "d " : "") +
                (hours ? to_string(hours) + "h " : "") +
                (minutes ? to_string(minutes) + "m " : "") +
                (to_string(seconds) + "s")
              ).c_str();

button:
  # Button on press calls the http command
  - platform: template
    name: $BearerSensorName
    on_press:
        then:
        - http_request.post:
              method: POST
              ####
              ## Change IP and Sensor name within the substitutions
              ## You can use the local or remote IP
              ## Remember the URL has /api/states/ hard coded
              ####
              url: $NabuCasaAddress/api/states/$BearerSensorName
              headers:
                Authorization: !secret bearer_token
                Content-Type: application/json
              verify_ssl: false
              json:
              ####
              ## You can customize this part but remember to include 'state'
               root["state"] = id(uptime_human).state;
               ####
               ## Add more data / attributes here
               ## Refer to Home Assistant API Docs
               ## https://developers.home-assistant.io/docs/api/rest/
               ####

Here is the error I get

INFO Reading configuration /config/esphome/nabucasa-fingerprint.yaml...
Failed config

sensor.uptime: [source /config/esphome/nabucasa-fingerprint.yaml:32]
  platform: uptime
  name: FingerPrintScanner Uptime Sensor
  id: uptime_sensor
  update_interval: 60s
  on_raw_value: 
    then: 
      - 
        Unable to find action with the name 'text_sensor.template.publish'.
        text_sensor.template.publish: 
          id: uptime_human
          state: !lambda |-
            int seconds = round(id(uptime_sensor).raw_state);
            int days = seconds / (24 * 3600);
            seconds = seconds % (24 * 3600);
            int hours = seconds / 3600;
            seconds = seconds % 3600;
            int minutes = seconds /  60;
            seconds = seconds % 60;
            return (
              (days ? to_string(days) + "d " : "") +
              (hours ? to_string(hours) + "h " : "") +
              (minutes ? to_string(minutes) + "m " : "") +
              (to_string(seconds) + "s")
            ).c_str();
button.template: [source /config/esphome/nabucasa-fingerprint.yaml:57]
  platform: template
  name: sensor.fingerprint_scanner
  on_press: 
    then: 
      - 
        Unable to find action with the name 'http_request.post'.
        http_request.post: 
          method: POST
          url: |-
            https://redacted.ui.nabu.casa/api/states/sensor.fingerprint_scanner
          headers: 
            Authorization: !secret bearer_token
            Content-Type: application/json
          verify_ssl: False
          json: root["state"] = id(uptime_human).state;

I appreciate you taking the time to try and help me with this. Another user suggested trying a webhook, which I did and was able to get working.

1 Like

Webhooks are made for this scenario!

Also see this discussion:

1 Like

Sorry to revive a fairly old thread - I’m just getting started trying to set up the Garmin app on my ForeRunner 945 watch through Nabu Casa and I’m stuck. I’m completely new to JSON and just trying to get anything to show up on the dashboard so I can confirm the basic connection is there and then work on setting up my dashboard.

I’m stuck here:

I also can’t get to the menu.json file pasting the https://MY-ID.ui.nabu.casa/local/garmin/menu.json url in my browser - I get a 404 error

Here’s what I’ve done so far - the step I can’t get past is an error message that says “No JSON returned from HTTP request” as soon as I open the app on my watch. I was getting error messages saying something like “check the internet connection” before I think I sorted out the urls to use, so I think I might have made enough progress to get the watch connected to the JSON file, but that’s where I’m stuck.

  • I’ve generated a long-lived access token in HA and have that in the API Key for HomeAssistant field in the App Settings.

  • I have [u]https://MY-ID.ui.nabu.casa/api[/u] in the URL for HomeAssistant API field in the App Settings

  • I have [u]https://MY-ID.ui.nabu.casa/local/garmin/menu.json[/u] in the URL for menu configuration (JSON) field in the App Settings

  • I’ve created the file /homeassistant/config/www/garmin/menu.json in the Home Assistant File Editor

  • I’ve added this to my configuration.yaml file and rebooted HA:

http:
  cors_allowed_origins:
    - https://house-of-abbey.github.io
  • I have the following JSON code in that file - just trying to get a single switch to show up in the dashboard for the watch app so I can go from there:
{
  "$schema": "https://raw.githubusercontent.com/house-of-abbey/GarminHomeAssistant/main/config.schema.json",
  "title": "Home",
  "items": [
    {
      "entity": "switch.victron_system_relay_0",
      "name": "Van Engine",
      "type": "toggle"
    }
  ]
}

Could it be related to the Nabu Casa certificate? I saw a post about including these two lines in the HTTP section of the confiuration.yaml file, but I can’t restart HA due to an invalid configuration error with these lines in there and I don’t know how to include the certificate from Nabu Casa there if that’s what I need to do…

Thanks in advance for any help!

1 Like

I think I figured it out by finding this.

It looks like maybe this line in the Github readme file is out of date? Always putting the json file in the www folder within the config folder in HA is what was making it not work. As soon as I moved the json file to the www folder in HA at “root” (not in the config folder), it’s been working fine…

We have used /config/www/garmin/<something>.json on our Home Assistant’s file system. That equates to a URL of https://homeassistant.local/local/garmin/<something>.json.

1 Like