My take on Astro rules

I’ve read through Rich’s design pattern on the time-of-day and astro mess at least 10 times now. It’s extremely convoluted and confusing to me. Am I the only one?

Anyway I had been using my system and having a “dummy switch” turn on at sunrise and off at sunset. This let me run rules and check for whether the sun was out. Sure, worked great.

But what about restarts?

I came up with a better plan. All of my “where’s the sun” questions are now handled by the astro binding’s sun elevation channel. All I have to do is check where the sun is, for example:

if (SunElevation.state > 1)  //the sun is "out" - it's daytime
if (SunElevation.state > 20) //the sun is brighter

I don’t know why I fought that design pattern so long. This is all I actually need and it works great for where I live (Texas - it’s flat and we never have “midnight sun”).

What are you trying to achieve with the Astro binding? I use a rule and trigger on the sunrise and sunset event. I don’t use a dummy switch at all to do this.

The two I can think of are I have a motion detector I only want to have trigger when the sun is less than 0 elevation and a few switches that turn on dim at night but full bright during the day - when I send “on” the system checks sun location.

1 Like

If you explain where you had confusion perhaps the DP can be improved.

The over all concept is relatively simple.

Trigger a role at the start of each timer prod you care about.

Do some comparisons to see which time period you are in India the rule.

Set the Time of day Item with the name of the time period you are in.

1 Like

In my case I just have the one question: is the sun up?

I don’t need to have 3 or 5 it however many periods of the day. The DP has multiple items that need to be updated with new times (in the rule) and the rule that runs at startup and on event changes. I know that it’s a quick and not processor intense rule - but it’s more than I need. I got ready to set it up a few times but I wanted to simplify it (simple day or night) and never got around to reading through the rule to see where to slim it down.

While I was pondering I realized that I didn’t need so much. I have 3 items now: sun elevation, sunset event, and sunrise event. The sunset and sunrise turn my porch lights on and off. The elevation is my check to see if it’s day or night. No rules to figure out what time it is, nothing in startup, nothing at midnight to run the new days things, no daylight saving to worry about, etc.

I’m happy with it, got bored at work, and thought “hey maybe someone else reading hasn’t thought of this and would like it.”

In that case the DP was never intended to solve your problem.

rule "Calculate time of day state"
when
    System started or
    Channel 'astro:sun:home:rise#event' triggered START or
    Channel 'astro:sun:home:rise#event' triggered START
then
    val day_start = new DateTime(vSunrise_Time.state.toString)
    val night_start = new DateTime(vSunset_Time.state.toString)

    val isDay = if(now.isAfter(day_start) && now.isBefore(night_start)) ON else OFF
    if(TimeOfDay.state != isDay) TimeOfDay.sendCommand(isDay)
end

The Rule is only triggered by three events, system started, sunrise, and sunset. First we get the sunrise and sunset times as a DateTime. If it is currently between day_start and night_start we send ON to the TimeOfDay. Otherwise we send OFF. You only have two states so TimeOfDay need only be a Switch.

But like you discovered, if you only care about whether the sun is up or not, just use the sun angle. Of course, should you discover later that you do need more, you will have to move to something a little more complex.

You’re correct. The DP is much more than I need - which is why I made this post to say “here’s my take on astro rules for a simplified setup.” It seems the DP is the “popular” way people on OH are doing this. I thought I’d take a minute to discuss another option.

Looking at your simple rule for my case is helpful. I always got stuck on the difference between Astro’s time format and now’s time format. This little rule is a good starting point for me.

I’m sure there are good reasons why to put so many time formats into the program (joda, cron, whatever astro uses) but it sure doesn’t make things straightforward for a rule writer like me.

There were and sadly it does cause problems. Unfortunately I don’t think there is a viable way to normalize them all (cron times are really addressing a different problem so really shouldn’t be in this same collection, DateTime and DateTimeType define an instant in time where as cron defines periodicity). Ultimately I think this problem will remain until replacements for Rules DSL come along.

But the key insight I had a couple of months ago that both Joda DateTime and DateTimeType print in ISO 8601 format and both can take ISO 8601 formatted strings so we can just use .toString to build one from the other.