Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[sendtohttp] Add Open-Meteo events + JSON event #5207

Open
wants to merge 24 commits into
base: mega
Choose a base branch
from

Conversation

chromoxdor
Copy link
Contributor

@chromoxdor chromoxdor commented Jan 2, 2025

To-do:

  • Lots of documentation and examples
  • Some more annotation in the code probably

As being asked here: https://www.letscontrolit.com/forum/viewtopic.php?p=72083#p72083 i do a PR for Open-Meteo events

  1. It parses url for the variable type (current,hourly, daily)
  2. Contrains the response and parses this for the variables
  3. depending on the variable type it generates an event (e.g. On OpenMeteo#current Do... )

It works but responses can get quite long, especially for hourly variables and also when all types combined together.
But for now it was working fine on an esp32 classic even with very long resonses > 6kb

I tried to kind of create a size check but i am no expert for memory constraint systems. Maybe you can help out here with some recommendations.

I guess when calling this it is already to late 🙂 :

 if (uri.length() > 5000) {
        addLog(LOG_LEVEL_ERROR, F("Response exceeds 5000 characters"));
      }
      else {

How to use:

  1. visit https://open-meteo.com/en/docs
  2. click together what you need and scroll down to the API Response section where you find this:
Bildschirmfoto 2025-01-02 um 14 59 15
  1. usesendtohttp api.open-meteo.com,80,/v1/forecast?...

Issues:

  1. ESPEasy throws a "Too many arguments" error but it still works fine
  2. In the log only 25 eventvalues are displayed. But you can still access all of them with rules. I wonder where the limit is?

@chromoxdor
Copy link
Contributor Author

chromoxdor commented Jan 2, 2025

Command:
sendtohttp api.open-meteo.com,80,"/v1/forecast?latitude=52.5244&longitude=13.4105&current=temperature_2m,relative_humidity_2m&daily=temperature_2m_max,temperature_2m_min,uv_index_max&timezone=Europe%2FLondon&forecast_days=3"

Response:

2580494: EVENT: OpenMeteo#current=4.3,76
2580503: EVENT: OpenMeteo#daily=7.5,2.4,1.2,1.5,-1.0,-1.1,1.00,0.95,0.70

@tonhuisman
Copy link
Contributor

tonhuisman commented Jan 2, 2025

  1. ESPEasy throws a "Too many arguments" error but it still works fine

Wrap the (long) url, that contains several commas, in quotes, and this issue should be resolved 😉
Alternative: url-encode the commas to %2C so ESPEasy doesn't see them as commas

@chromoxdor
Copy link
Contributor Author

Wrap the (long) url, that contains several commas, in quotes, and this issue should be resolved 😉

I tried that and it didn't work...but now i think i know what happend. I have this auto correction plugin in my browser. Disabling it helped :)

- added FEATURE_OPENMETEO_EVENT to Custom-sample.h
- disabled FEATURE_THINGSPEAK_EVENT and FEATURE_OPENMETEO_EVENT on default
- both got the same structure in define_plugin_sets.h
@chromoxdor
Copy link
Contributor Author

Thanks for helping me...

@chromoxdor
Copy link
Contributor Author

I combined the two functions because there is actually no need for that

@chromoxdor
Copy link
Contributor Author

I don't understand why the action runs are failing. For me these builds are working just fine fine...

@chromoxdor chromoxdor changed the title [sendtohttp] Add Open-Meteo events + Inverter event [sendtohttp] Add Open-Meteo events + JSON event Jan 4, 2025
@chromoxdor
Copy link
Contributor Author

chromoxdor commented Jan 4, 2025

OK, hopefully this time the action run finishes without errors.
I changed the "inverter" function for a more universal approach.
Therefore i added a function to parse the content of a file called json.keys line by line.

example content:

Body.Data.DAY_ENERGY.Values.1
Body.Data.PAC.Values.1

For the URL: There needs to be &json added to the end of it to tell the parser that there is a JSON-response.
SendToHTTP 192.168.1.199,80,"/solar_api/v1/GetInverterRealtimeData.cgi?Scope=System?json"

Actually i would like to see this as an plugin, where you enter your URL and store your keys in the same manner. But that not only mean to create a new plugin but also to deduplicate code because of P037.
At the moment this is too complicated as the structure is far too complex for a beginner like me.

@chromoxdor
Copy link
Contributor Author

chromoxdor commented Jan 4, 2025

For the URL: There needs to be &json added to the end of it to tell the parser that there is a JSON-response.
SendToHTTP 192.168.1.199,80,"/solar_api/v1/GetInverterRealtimeData.cgi?Scope=System?json"

Usually adding a parameter that is not existent on the server side causes no issues.
I had no choice for that one since i can not pass a parameter

- add array output to the json parser
- add grouping of keys for individual requests
@tonhuisman
Copy link
Contributor

2. In the log only 25 eventvalues are displayed. But you can still access all of them with rules. I wonder where the limit is?

Is that the web-based log (Tools/Log), or via the serial console?

@TD-er
Copy link
Member

TD-er commented Jan 5, 2025

  1. In the log only 25 eventvalues are displayed. But you can still access all of them with rules. I wonder where the limit is?

Is that the web-based log (Tools/Log), or via the serial console?

Both are truncated to some fixed max. size (though not the same max.)

- add: log error for json parsing
- change: decimals for float and double reduced by 1 (6,15)
- inceased json buffer
unsing double for double now
@chromoxdor
Copy link
Contributor Author

Should I add a whole new page for documentation of the these parser?
Adding it to the SendToHTTP section is probably way too much information. I would prefer to add a link from there.

- There is no difference between is<float>() and is<double>() as a value check. Keeping <float>
-#define ARDUINOJSON_USE_DOUBLE 1 does not seem to be needed (only for serializeJson)
@chromoxdor
Copy link
Contributor Author

chromoxdor commented Jan 6, 2025

I am inclined to use this for convenience. On a scale of 1-10, how bad is this idea?

#  if ESP8266
        root = new (std::nothrow) DynamicJsonDocument(ESP.getMaxFreeBlockSize() - 512);
  #  else // if ESP8266
        root = new (std::nothrow) DynamicJsonDocument(ESP.getMaxAllocHeap());
  #  endif // if ESP8266

found here: https://arduinojson.org/v6/how-to/determine-the-capacity-of-the-jsondocument/#technique-4-use-whatever-ram-is-available

Edit: Our scenario would match this: https://arduinojson.org/v6/how-to/determine-the-capacity-of-the-jsondocument/#what-if-i-dont-know-my-input-ahead-of-time

@TD-er
Copy link
Member

TD-er commented Jan 6, 2025

It won't even fit on the 0...10 scale.
This is really a bad idea as it will cause lots and lots of issues when creating Strings or any other heap allocation.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants