[SOLVED] Disable http check temporarily/ignore unreachable host

Hi there,

I have several http items, which control a device, which is not online all the time, e.g.

String yam_get_power { http="<[http://192.168.0.55/YamahaExtendedControl/v1/main/getStatus:60000:JSONPATH($.power)]"}

Now my problem is, when the device is offline, I get exceptions all the time:

2019-10-25 21:33:37.350 [ERROR] [org.openhab.io.net.http.HttpUtil    ] - Fatal transport error: java.net.NoRouteToHostException: No route to host (Host unreachable)
2019-10-25 21:33:37.353 [ERROR] [ab.binding.http.internal.HttpBinding] - No response received from 'http://192.168.0.55/YamahaExtendedControl/v1/main/getStatus'

I know that in that time the device cannot be reached. Is it possible to disable http checks temporarily?

Best regards,
cyb

Hi,
check the device first with a ping (network binding) If this ping is successful send the request .

Andy

I do not actively send the request. I just configured the item and http binding is executing the request automatically in background, even if I did not use that item anywhere.

then you can build a rule which first checks the ext. server
if this is successfull you can work with your item

As Andreas indicates, the answer is no. You either need to reimplant this in a rules or dinner or the error messages in your log in the logger config.

But how can I implement this in a rule? Some of those http items just get values from the device, e.g. power state on/off or current volume. I want to use those values in my HabPanel.

In all rules I built so far I have entries for Items which receive a command or which change their state. How can I build a rule for a getValue-method?

I understand that in a rule I could trigger sending the http request and maybe catch those Exceptions described above but I do not know how to build a rule for a getValue-Method at all.

Best regards,
cyb

That is the general idea; you can trigger time based rules for every N seconds.

Ah okay, thanks. I did not know or use them yet.

Is there anything special to do to enable those time-based rules? The following rule does not trigger at all. It should trigger every 30 seconds.

rule "Get power state"
when
	Time cron "3/30 0 0 ? * * *"
then
	logInfo("GetPowerState", "Requesting power state...")
end

Only at time 00:00, I believe.
Rules DSL uses Quartz based timing, this may help -
https://www.freeformatter.com/cron-expression-generator-quartz.html

Oh man, you are right, sorry. Actually I did use that page you linked but did not get the right expression. "3/30 * * ? * * *" is working as expected.

But by using sendHttpGetRequest I am not able to catch the java.net.NoRouteToHostException by myself. It is already caught inside the http action and will also be logged automatically:
2019-10-27 13:34:06.158 [ERROR] [.smarthome.model.script.actions.HTTP] - Fatal transport error: java.util.concurrent.ExecutionException: java.net.NoRouteToHostException: No route to host

So all I have won is that not the complete stack trace is logged but only the non-reachable host. So I do have to ping the host first to avoid any exception in logfile (which is what I want to have, because it is kind of a normal state for me).

Does that still happen if you capture results?
var results = sendHttpGetRequest(...

Rather than a regular poll, you can make a smart one. If your device is “broken”, only poll every tenth time around.

Does that still happen if you capture results?

Yes, there is no difference, the exception is handled and logged inside the http action.

Rather than a regular poll, you can make a smart one. If your device is “broken”, only poll every tenth time around.

Yeah, there is still a lot to improve, but first I have to get it working. I have to find out how to ping a device in a rule first…

You could use the network binding for ping, and monitor the status Item.

You could use the network binding for ping, and monitor the status Item.

Yeah, that works.

For anybody interested:

network.things:
network:pingdevice:a5100 [ hostname="192.168.0.55", retry=1, timeout=5000, refreshInterval=10000 ]

network.items:
Switch a5100_online { channel="network:pingdevice:a5100:online" }

http.items:
Switch yam_power_state

http.rules:

rule “Get power state”
when
Time cron “3/30 * * ? * * *”
then
if(a5100_online.state == ON)
{
val String httpRequest = “http://192.168.0.55/YamahaExtendedControl/v1/main/getStatus
val String resultJson = sendHttpGetRequest(httpRequest)
val powerState = transform(“JSONPATH”, “$.power”, resultJson)
if(powerState == “on”)
{
yam_power_state.postUpdate(ON)
}
else
{
yam_power_state.postUpdate(OFF)
}
}
else
{
yam_power_state.postUpdate(OFF)
}
end

1 Like