mirror of
https://github.com/Xevion/go-ha.git
synced 2025-12-07 13:15:19 -06:00
add OnlyOnDates to schedule, change exceptionday to exceptiondates everywhere
This commit is contained in:
60
README.md
60
README.md
@@ -78,10 +78,10 @@ sunset := ga.NewDailySchedule().Call(myFunc).Sunset().Build()
|
||||
|
||||
Daily schedules have other functions to change the behavior.
|
||||
|
||||
| Function | Info |
|
||||
| ------------------------------------ | ----------------------------------------------------------------------------------- |
|
||||
| ExceptionDay(time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. |
|
||||
| Function | Info |
|
||||
| ----------------------------------------- | -------------------------------------------------------------------------------------------------------- |
|
||||
| ExceptionDates(t time.Time, ...time.Time) | Skip the schedule on the given date(s). Functions like a blocklist. Cannot be combined with OnlyOnDates. |
|
||||
| OnlyOnDates(t time.Time, ...time.Time) | Run only on the given date(s). Functions like an allowlist. Cannot be combined with ExceptionDates. |
|
||||
|
||||
#### Schedule Callback function
|
||||
|
||||
@@ -106,18 +106,18 @@ etl := ga.NewEntityListener().EntityIds("binary_sensor.front_door").Call(myFunc)
|
||||
|
||||
Entity listeners have other functions to change the behavior.
|
||||
|
||||
| Function | Info |
|
||||
| ------------------------------------ | ------------------------------------------------------------------------------------------------- |
|
||||
| ToState("on") | Function only called if new state matches argument. |
|
||||
| FromState("on") | Function only called if old state matches argument. |
|
||||
| Throttle("30s") | Minimum time between function calls. |
|
||||
| Duration("30s") | Requires ToState(). Sets how long the entity should be in the state before running your function. |
|
||||
| OnlyAfter("03:00") | Only run your function after a specified time of day. |
|
||||
| OnlyBefore("03:00") | Only run your function before a specified time of day. |
|
||||
| OnlyBetween("03:00", "14:00") | Only run your function between two specified times of day. |
|
||||
| ExceptionDay(time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. |
|
||||
| RunOnStartup() | Run your callback once during App.Start() |
|
||||
| Function | Info |
|
||||
| --------------------------------------- | ----------------------------------------------------------------------------------------------------------------- |
|
||||
| ToState("on") | Function only called if new state matches argument. |
|
||||
| FromState("on") | Function only called if old state matches argument. |
|
||||
| Throttle("30s") | Minimum time between function calls. |
|
||||
| Duration("30s") | Requires ToState(). Sets how long the entity must be in the state before running your function. |
|
||||
| OnlyAfter("03:00") | Only run your function after a specified time of day. |
|
||||
| OnlyBefore("03:00") | Only run your function before a specified time of day. |
|
||||
| OnlyBetween("03:00", "14:00") | Only run your function between two specified times of day. |
|
||||
| ExceptionDates(time.Time, ...time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. Functions like a "blocklist". |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. Functions like a "blocklist". |
|
||||
| RunOnStartup() | Run your callback during `App.Start()`. |
|
||||
|
||||
#### Entity Listener Callback function
|
||||
|
||||
@@ -143,14 +143,14 @@ evl := ga.NewEntityListener().EntityIds("binary_sensor.front_door").Call(myFunc)
|
||||
|
||||
Event listeners have other functions to change the behavior.
|
||||
|
||||
| Function | Info |
|
||||
| ------------------------------------ | ----------------------------------------------------------------------------------- |
|
||||
| Throttle("30s") | Minimum time between function calls. |
|
||||
| OnlyAfter("03:00") | Only run your function after a specified time of day. |
|
||||
| OnlyBefore("03:00") | Only run your function before a specified time of day. |
|
||||
| OnlyBetween("03:00", "14:00") | Only run your function between two specified times of day. |
|
||||
| ExceptionDay(time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. |
|
||||
| Function | Info |
|
||||
| --------------------------------------- | ----------------------------------------------------------------------------------- |
|
||||
| Throttle("30s") | Minimum time between function calls. |
|
||||
| OnlyAfter("03:00") | Only run your function after a specified time of day. |
|
||||
| OnlyBefore("03:00") | Only run your function before a specified time of day. |
|
||||
| OnlyBetween("03:00", "14:00") | Only run your function between two specified times of day. |
|
||||
| ExceptionDates(time.Time, ...time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. |
|
||||
|
||||
#### Event Listener Callback function
|
||||
|
||||
@@ -179,12 +179,12 @@ interval = ga.NewInterval().Call(myFunc).Every("5m").StartingAt("10:00").EndingA
|
||||
|
||||
Intervals have other functions to change the behavior.
|
||||
|
||||
| Function | Info |
|
||||
| ------------------------------------ | ----------------------------------------------------------------------------------- |
|
||||
| StartingAt(TimeString) | What time the interval begins to run each day. |
|
||||
| EndingAt(TimeString) | What time the interval stops running each day. |
|
||||
| ExceptionDay(time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. |
|
||||
| Function | Info |
|
||||
| --------------------------------------- | ----------------------------------------------------------------------------------- |
|
||||
| StartingAt(TimeString) | What time the interval begins to run each day. |
|
||||
| EndingAt(TimeString) | What time the interval stops running each day. |
|
||||
| ExceptionDates(time.Time, ...time.Time) | A one time exception on the given date. Time is ignored, applies to whole day. |
|
||||
| ExceptionRange(time.Time, time.Time) | A one time exception between the two date/times. Both date and time are considered. |
|
||||
|
||||
#### Interval Callback function
|
||||
|
||||
|
||||
@@ -22,7 +22,7 @@ type EntityListener struct {
|
||||
delay time.Duration
|
||||
delayTimer *time.Timer
|
||||
|
||||
exceptionDays []time.Time
|
||||
exceptionDates []time.Time
|
||||
exceptionRanges []timeRange
|
||||
|
||||
runOnStartup bool
|
||||
@@ -133,8 +133,8 @@ func (b elBuilder3) Throttle(s DurationString) elBuilder3 {
|
||||
return b
|
||||
}
|
||||
|
||||
func (b elBuilder3) ExceptionDay(t time.Time) elBuilder3 {
|
||||
b.entityListener.exceptionDays = append(b.entityListener.exceptionDays, t)
|
||||
func (b elBuilder3) ExceptionDates(t time.Time, tl ...time.Time) elBuilder3 {
|
||||
b.entityListener.exceptionDates = append(tl, t)
|
||||
return b
|
||||
}
|
||||
|
||||
@@ -189,7 +189,7 @@ func callEntityListeners(app *App, msgBytes []byte) {
|
||||
if c := checkThrottle(l.throttle, l.lastRan); c.fail {
|
||||
continue
|
||||
}
|
||||
if c := checkExceptionDays(l.exceptionDays); c.fail {
|
||||
if c := checkExceptionDates(l.exceptionDates); c.fail {
|
||||
continue
|
||||
}
|
||||
if c := checkExceptionRanges(l.exceptionRanges); c.fail {
|
||||
|
||||
@@ -17,7 +17,7 @@ type EventListener struct {
|
||||
throttle time.Duration
|
||||
lastRan carbon.Carbon
|
||||
|
||||
exceptionDays []time.Time
|
||||
exceptionDates []time.Time
|
||||
exceptionRanges []timeRange
|
||||
}
|
||||
|
||||
@@ -80,8 +80,8 @@ func (b eventListenerBuilder3) Throttle(s DurationString) eventListenerBuilder3
|
||||
return b
|
||||
}
|
||||
|
||||
func (b eventListenerBuilder3) ExceptionDay(t time.Time) eventListenerBuilder3 {
|
||||
b.eventListener.exceptionDays = append(b.eventListener.exceptionDays, t)
|
||||
func (b eventListenerBuilder3) ExceptionDates(t time.Time, tl ...time.Time) eventListenerBuilder3 {
|
||||
b.eventListener.exceptionDates = append(tl, t)
|
||||
return b
|
||||
}
|
||||
|
||||
@@ -118,7 +118,7 @@ func callEventListeners(app *App, msg ws.ChanMsg) {
|
||||
if c := checkThrottle(l.throttle, l.lastRan); c.fail {
|
||||
continue
|
||||
}
|
||||
if c := checkExceptionDays(l.exceptionDays); c.fail {
|
||||
if c := checkExceptionDates(l.exceptionDates); c.fail {
|
||||
continue
|
||||
}
|
||||
if c := checkExceptionRanges(l.exceptionRanges); c.fail {
|
||||
|
||||
12
interval.go
12
interval.go
@@ -16,12 +16,12 @@ type Interval struct {
|
||||
endTime TimeString
|
||||
nextRunTime time.Time
|
||||
|
||||
exceptionDays []time.Time
|
||||
exceptionDates []time.Time
|
||||
exceptionRanges []timeRange
|
||||
}
|
||||
|
||||
func (i Interval) Hash() string {
|
||||
return fmt.Sprint(i.startTime, i.endTime, i.frequency, i.callback, i.exceptionDays, i.exceptionRanges)
|
||||
return fmt.Sprint(i.startTime, i.endTime, i.frequency, i.callback, i.exceptionDates, i.exceptionRanges)
|
||||
}
|
||||
|
||||
// Call
|
||||
@@ -34,7 +34,7 @@ type intervalBuilderCall struct {
|
||||
interval Interval
|
||||
}
|
||||
|
||||
// Offset, ExceptionDay, ExceptionRange
|
||||
// Offset, ExceptionDates, ExceptionRange
|
||||
type intervalBuilderEnd struct {
|
||||
interval Interval
|
||||
}
|
||||
@@ -93,8 +93,8 @@ func (sb intervalBuilderEnd) EndingAt(s TimeString) intervalBuilderEnd {
|
||||
return sb
|
||||
}
|
||||
|
||||
func (sb intervalBuilderEnd) ExceptionDay(t time.Time) intervalBuilderEnd {
|
||||
sb.interval.exceptionDays = append(sb.interval.exceptionDays, t)
|
||||
func (sb intervalBuilderEnd) ExceptionDates(t time.Time, tl ...time.Time) intervalBuilderEnd {
|
||||
sb.interval.exceptionDates = append(tl, t)
|
||||
return sb
|
||||
}
|
||||
|
||||
@@ -137,7 +137,7 @@ func (i Interval) maybeRunCallback(a *App) {
|
||||
if c := checkStartEndTime(i.endTime /* isStart = */, false); c.fail {
|
||||
return
|
||||
}
|
||||
if c := checkExceptionDays(i.exceptionDays); c.fail {
|
||||
if c := checkExceptionDates(i.exceptionDates); c.fail {
|
||||
return
|
||||
}
|
||||
if c := checkExceptionRanges(i.exceptionRanges); c.fail {
|
||||
|
||||
19
listeners.go
19
listeners.go
@@ -62,7 +62,7 @@ func checkThrottle(throttle time.Duration, lastRan carbon.Carbon) conditionCheck
|
||||
return cc
|
||||
}
|
||||
|
||||
func checkExceptionDays(eList []time.Time) conditionCheck {
|
||||
func checkExceptionDates(eList []time.Time) conditionCheck {
|
||||
cc := conditionCheck{fail: false}
|
||||
for _, e := range eList {
|
||||
y1, m1, d1 := e.Date()
|
||||
@@ -87,6 +87,23 @@ func checkExceptionRanges(eList []timeRange) conditionCheck {
|
||||
return cc
|
||||
}
|
||||
|
||||
func checkAllowlistDates(eList []time.Time) conditionCheck {
|
||||
if len(eList) == 0 {
|
||||
return conditionCheck{fail: false}
|
||||
}
|
||||
|
||||
cc := conditionCheck{fail: true}
|
||||
for _, e := range eList {
|
||||
y1, m1, d1 := e.Date()
|
||||
y2, m2, d2 := time.Now().Date()
|
||||
if y1 == y2 && m1 == m2 && d1 == d2 {
|
||||
cc.fail = false
|
||||
break
|
||||
}
|
||||
}
|
||||
return cc
|
||||
}
|
||||
|
||||
func checkStartEndTime(s TimeString, isStart bool) conditionCheck {
|
||||
cc := conditionCheck{fail: false}
|
||||
// pass immediately if default
|
||||
|
||||
16
schedule.go
16
schedule.go
@@ -23,8 +23,8 @@ type DailySchedule struct {
|
||||
isSunset bool
|
||||
sunOffset DurationString
|
||||
|
||||
exceptionDays []time.Time
|
||||
exceptionRanges []timeRange
|
||||
exceptionDates []time.Time
|
||||
allowlistDates []time.Time
|
||||
}
|
||||
|
||||
func (s DailySchedule) Hash() string {
|
||||
@@ -93,13 +93,13 @@ func (sb scheduleBuilderCall) Sunset(offset ...DurationString) scheduleBuilderEn
|
||||
return scheduleBuilderEnd(sb)
|
||||
}
|
||||
|
||||
func (sb scheduleBuilderEnd) ExceptionDay(t time.Time) scheduleBuilderEnd {
|
||||
sb.schedule.exceptionDays = append(sb.schedule.exceptionDays, t)
|
||||
func (sb scheduleBuilderEnd) ExceptionDates(t time.Time, tl ...time.Time) scheduleBuilderEnd {
|
||||
sb.schedule.exceptionDates = append(tl, t)
|
||||
return sb
|
||||
}
|
||||
|
||||
func (sb scheduleBuilderEnd) ExceptionRange(start, end time.Time) scheduleBuilderEnd {
|
||||
sb.schedule.exceptionRanges = append(sb.schedule.exceptionRanges, timeRange{start, end})
|
||||
func (sb scheduleBuilderEnd) OnlyOnDates(t time.Time, tl ...time.Time) scheduleBuilderEnd {
|
||||
sb.schedule.allowlistDates = append(tl, t)
|
||||
return sb
|
||||
}
|
||||
|
||||
@@ -132,10 +132,10 @@ func runSchedules(a *App) {
|
||||
}
|
||||
|
||||
func (s DailySchedule) maybeRunCallback(a *App) {
|
||||
if c := checkExceptionDays(s.exceptionDays); c.fail {
|
||||
if c := checkExceptionDates(s.exceptionDates); c.fail {
|
||||
return
|
||||
}
|
||||
if c := checkExceptionRanges(s.exceptionRanges); c.fail {
|
||||
if c := checkAllowlistDates(s.allowlistDates); c.fail {
|
||||
return
|
||||
}
|
||||
go s.callback(a.service, a.state)
|
||||
|
||||
Reference in New Issue
Block a user