Adds new http bridge and shelly implementation.
This code implements a simple HTTP API and rewrites the HTTP request handling of the shelly plug.
The requests are made with a native library on Linux and Mac and therefore are fast and have a small memory footprint.
Hey, at the moment i don't have Access to a Laptop so i can check your code and idea in detail (as you say in #2100)
For me the Idea of a HttpBridge is very good.
As told above i could not check in detail if you use Functions that blocks handle Event?
If so maybe it's possible for you to Base the Bridge on the GenericHttpWorker (see #2098 ).
For me it should be a non-blocking (worker) task that call's to external Devices via Http (To ensure that the OpenEms Cycle is not blocked because of a external Device that maybe is not reachable at the moment). The GenericHttpWorker Impl. however, is (at the moment) only for Hard-Coded Applications (like Devices where the Url's are always the same -> Shelly, Comexio, Go-E). A Bridge however should be available for more than one Component and also it should be possible to Change the Url (via UI, Apache, ...).
This Concept of Worker and Bridge is interesting for Stuff like Weather-Data. You can than chose a Url to your Weather-Api dynamicly. The "Backbone" of the Bridge than fetches the Result via a Worker and the Bridge "shares" the Value with other components. (Future Thinking ;-) ). In this case you would minimize the internal block time and also the external calls (most Api's are paid by "How many calls" are needed).
@sfeilmeier What do you think about the concept of a HttpBridge based on a HttpWorker or the HttpBridge as is?
@nicoketzer: I do not have time right now to look into this in detail. I am not sure a HTTP-Bridge is a good idea, because it requires an additional OpenEMS Component to be configured, separately to the actual Component. This is ok for 1-to-many cases (like Modbus/RTU) but might be overengineering for 1-to-1 cases (which is the typical case for HTTP - but there are also exceptions of course).
In general I like the idea of generalizing handling of HTTP requests in OpenEMS because it avoids repetitive code and allows for optimizations (see e.g. this discussion: https://community.openems.io/t/http-request-in-welcher-phase/1493/5). That's why I had asked @hydroid7 specifically to review your GenericHttpWorker-branch and join efforts.
Yes, in fact, the library now is blocking. From the discoussions above and the other pull requests, I see the following requirements:
- Background/ Async Processing
- Response should be processed in the caller. There are multiple content types, encodings, status codes. The best place to decide how to proceed is the caller itself.
- Requests should be submitted every time they are required (that means no automatic cycling)
My proposed solution that merges the two approaches is the following. The communication between bridge and component is based on queues. Consumers can create a response queue where the response is stored when it arrives. One queue is exactly linked to one endpoint. Example:
var url = new URL("https://example.com");
// Non blocking call, returns immediately
// Result is placed in a ConcurrentLinkedQueue<HttpResponse>
httpBridge.submitGet(url, statusQueue);
Later, during the cycle processing one can look for a response.
if (statusQueue.poll() != null) {
// We have a response, do process it
}
This way, making the request can happen out of band, but the result can be processed each cycle at fixed intervals.
Also the consumer can now decide what to do in case of failed or partially failed requests, for example with status code 429.
This PR has been automatically marked as stale due to inactivity. It will be closed in 7 days if no further activity occurs.
Closing this PR due to inactivity.