openhab-scripting 4.23.0 → 4.26.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/openhab/core/openhab_setup.rb +2 -3
- data/lib/openhab/core/services.rb +26 -0
- data/lib/openhab/dsl/dsl.rb +13 -11
- data/lib/openhab/dsl/group.rb +2 -1
- data/lib/openhab/dsl/items/location_item.rb +8 -1
- data/lib/openhab/dsl/openhab.rb +23 -0
- data/lib/openhab/dsl/rules/guard.rb +6 -5
- data/lib/openhab/dsl/rules/rule.rb +7 -9
- data/lib/openhab/dsl/rules/rule_config.rb +9 -8
- data/lib/openhab/dsl/rules/triggers/watch.rb +213 -0
- data/lib/openhab/dsl/time/month_day.rb +15 -0
- data/lib/openhab/dsl/timers/manager.rb +6 -2
- data/lib/openhab/dsl/types/date_time_type.rb +2 -0
- data/lib/openhab/dsl/types/point_type.rb +24 -1
- data/lib/openhab/version.rb +1 -1
- data/lib/openhab.rb +1 -0
- metadata +5 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6e4ca97d24c3811cfeba0faba93e2cdafb9a55f1ed7001cac8789baaf6a7f92c
|
4
|
+
data.tar.gz: 5eaeee1232c3e4252ae6396513e2a654727af1fd7075cb6ef9386c4b5e7b4c9a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0ee0e18e0e4bb8818d405998d2209f24b8b03651195a18fa76e97e417a0696b178cf3dcb431f7c42b3895dc15c29f3fb24d77bc3580ef35e6d37131725cc4ae8
|
7
|
+
data.tar.gz: 17afc1eed167b1d0dca764c2962727b770eeab95d53413fc85e54694bace8866260445d73a58da817ff65a1388c81999cc42fc05a25d22d0cd72028312a4dd63
|
@@ -1,6 +1,7 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
require 'openhab/log/logger'
|
4
|
+
require 'openhab/core/services'
|
4
5
|
|
5
6
|
module OpenHAB
|
6
7
|
#
|
@@ -19,12 +20,10 @@ module OpenHAB
|
|
19
20
|
#
|
20
21
|
def self.wait_till_openhab_ready
|
21
22
|
logger.trace('Checking readyness of OpenHAB')
|
22
|
-
|
23
|
-
until $scriptExtension.get('automationManager')
|
23
|
+
until OpenHAB::Core.automation_manager
|
24
24
|
logger.trace("Automation manager not loaded, checking again in #{CHECK_DELAY} seconds.")
|
25
25
|
sleep CHECK_DELAY
|
26
26
|
end
|
27
|
-
# rubocop: enable Style/GlobalVars
|
28
27
|
logger.trace 'Automation manager instantiated, OpenHAB ready for rule processing.'
|
29
28
|
end
|
30
29
|
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module OpenHAB
|
4
|
+
#
|
5
|
+
# Core support for OpenHAB JRuby Library
|
6
|
+
#
|
7
|
+
module Core
|
8
|
+
#
|
9
|
+
# Access OpenHAB services
|
10
|
+
#
|
11
|
+
|
12
|
+
# Get the OpenHAB automation manager
|
13
|
+
# @return [AutomationManager] OpenHAB Automation manager
|
14
|
+
# rubocop:disable Style/GlobalVars
|
15
|
+
def self.automation_manager
|
16
|
+
$scriptExtension.get('automationManager')
|
17
|
+
end
|
18
|
+
|
19
|
+
# Get the OpenHAB rule registry
|
20
|
+
# @return [Registory] OpenHAB rule registry
|
21
|
+
def self.rule_registry
|
22
|
+
$scriptExtension.get('ruleRegistry')
|
23
|
+
end
|
24
|
+
# rubocop:enable Style/GlobalVars
|
25
|
+
end
|
26
|
+
end
|
data/lib/openhab/dsl/dsl.rb
CHANGED
@@ -11,17 +11,18 @@ require 'openhab/dsl/monkey_patch/events/events'
|
|
11
11
|
require 'openhab/dsl/monkey_patch/actions/actions'
|
12
12
|
require 'openhab/dsl/rules/rule'
|
13
13
|
require 'openhab/dsl/rules/terse'
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
14
|
+
require_relative 'actions'
|
15
|
+
require_relative 'channel'
|
16
|
+
require_relative 'timers'
|
17
|
+
require_relative 'group'
|
18
|
+
require_relative 'things'
|
19
|
+
require_relative 'between'
|
20
|
+
require_relative 'gems'
|
21
|
+
require_relative 'persistence'
|
22
|
+
require_relative 'uid'
|
23
|
+
require_relative 'units'
|
24
|
+
require_relative 'states'
|
25
|
+
require_relative 'openhab'
|
25
26
|
|
26
27
|
module OpenHAB
|
27
28
|
#
|
@@ -34,6 +35,7 @@ module OpenHAB
|
|
34
35
|
def self.extended(base)
|
35
36
|
base.send :include, OpenHAB::DSL::Actions
|
36
37
|
base.send :include, OpenHAB::DSL::Between
|
38
|
+
base.send :include, OpenHAB::DSL::Core
|
37
39
|
base.send :include, OpenHAB::DSL::Groups
|
38
40
|
base.send :include, OpenHAB::DSL::Items
|
39
41
|
base.send :include, OpenHAB::DSL::Persistence
|
data/lib/openhab/dsl/group.rb
CHANGED
@@ -3,6 +3,7 @@
|
|
3
3
|
require 'singleton'
|
4
4
|
|
5
5
|
require 'openhab/dsl/lazy_array'
|
6
|
+
require 'openhab/core/entity_lookup'
|
6
7
|
|
7
8
|
module OpenHAB
|
8
9
|
module DSL
|
@@ -24,7 +25,7 @@ module OpenHAB
|
|
24
25
|
# @return [Set] of OpenHAB Groups
|
25
26
|
#
|
26
27
|
def [](name)
|
27
|
-
group = Core::EntityLookup.lookup_item(name)
|
28
|
+
group = OpenHAB::Core::EntityLookup.lookup_item(name)
|
28
29
|
group.is_a?(Items::GroupItem) ? group : nil
|
29
30
|
end
|
30
31
|
alias include? []
|
@@ -25,7 +25,14 @@ module OpenHAB
|
|
25
25
|
super
|
26
26
|
end
|
27
27
|
|
28
|
-
#
|
28
|
+
# Support conversion to location items from a hash
|
29
|
+
# @!visibility private
|
30
|
+
def format_type(command)
|
31
|
+
return PointType.new(command.to_hash) if command.respond_to?(:to_hash)
|
32
|
+
|
33
|
+
super
|
34
|
+
end
|
35
|
+
|
29
36
|
# Type Coercion
|
30
37
|
#
|
31
38
|
# Coerce object to a PointType
|
@@ -0,0 +1,23 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'pathname'
|
4
|
+
|
5
|
+
module OpenHAB
|
6
|
+
module DSL
|
7
|
+
#
|
8
|
+
# Provides access to OpenHAB attributes
|
9
|
+
#
|
10
|
+
module Core
|
11
|
+
include OpenHAB::Log
|
12
|
+
|
13
|
+
#
|
14
|
+
# Return the OpenHAB conf directory as a ruby pathname
|
15
|
+
#
|
16
|
+
# @return [Pathname] OpenHAB conf path
|
17
|
+
#
|
18
|
+
def __conf__
|
19
|
+
Pathname.new(ENV['OPENHAB_CONF'])
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -36,7 +36,8 @@ module OpenHAB
|
|
36
36
|
# @param [Object] only_if Item or Proc to use as guard
|
37
37
|
# @param [Object] not_if Item or Proc to use as guard
|
38
38
|
#
|
39
|
-
def initialize(only_if: nil, not_if: nil)
|
39
|
+
def initialize(run_context:, only_if: nil, not_if: nil)
|
40
|
+
@run_context = run_context
|
40
41
|
@only_if = only_if
|
41
42
|
@not_if = not_if
|
42
43
|
end
|
@@ -106,27 +107,27 @@ module OpenHAB
|
|
106
107
|
#
|
107
108
|
# Check not_if guard
|
108
109
|
#
|
109
|
-
# @param [OpenHAB Event] event
|
110
|
+
# @param [OpenHAB Event] event to check if meets guard
|
110
111
|
# @param [Array<Item>] items to check if satisfy criteria
|
111
112
|
# @param [Array] procs to check if satisfy criteria
|
112
113
|
#
|
113
114
|
# @return [Boolean] True if criteria are satisfied, false otherwise
|
114
115
|
#
|
115
116
|
def process_not_if(event, items, procs)
|
116
|
-
items.flatten.none?(&:truthy?) && procs.none? { |proc|
|
117
|
+
items.flatten.none?(&:truthy?) && procs.none? { |proc| @run_context.instance_exec(event, &proc) }
|
117
118
|
end
|
118
119
|
|
119
120
|
#
|
120
121
|
# Check only_if guard
|
121
122
|
#
|
122
|
-
# @param [OpenHAB Event] event
|
123
|
+
# @param [OpenHAB Event] event to check if meets guard
|
123
124
|
# @param [Array<Item>] items to check if satisfy criteria
|
124
125
|
# @param [Array] procs to check if satisfy criteria
|
125
126
|
#
|
126
127
|
# @return [Boolean] True if criteria are satisfied, false otherwise
|
127
128
|
#
|
128
129
|
def process_only_if(event, items, procs)
|
129
|
-
items.flatten.all?(&:truthy?) && procs.all? { |proc|
|
130
|
+
items.flatten.all?(&:truthy?) && procs.all? { |proc| @run_context.instance_exec(event, &proc) }
|
130
131
|
end
|
131
132
|
end
|
132
133
|
end
|
@@ -1,6 +1,7 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
require 'openhab/core/thread_local'
|
4
|
+
require 'openhab/core/services'
|
4
5
|
require 'openhab/log/logger'
|
5
6
|
require_relative 'rule_config'
|
6
7
|
require_relative 'automation_rule'
|
@@ -21,14 +22,11 @@ module OpenHAB
|
|
21
22
|
|
22
23
|
@script_rules = []
|
23
24
|
|
24
|
-
|
25
|
-
@
|
26
|
-
@registry = $scriptExtension.get('ruleRegistry')
|
27
|
-
# rubocop: enable Style/GlobalVars
|
28
|
-
|
25
|
+
@automation_manager = OpenHAB::Core.automation_manager
|
26
|
+
@registry = OpenHAB::Core.rule_registry
|
29
27
|
class << self
|
30
28
|
attr_reader :script_rules, :automation_manager, :registry
|
31
|
-
|
29
|
+
end
|
32
30
|
|
33
31
|
#
|
34
32
|
# Create a new rule
|
@@ -37,13 +35,13 @@ module OpenHAB
|
|
37
35
|
# @yield [] Block executed in context of a RuleConfig
|
38
36
|
#
|
39
37
|
#
|
40
|
-
# rubocop: disable Metrics
|
38
|
+
# rubocop: disable Metrics
|
41
39
|
def rule(rule_name, &block)
|
42
40
|
thread_local(RULE_NAME: rule_name) do
|
43
41
|
@rule_name = rule_name
|
44
42
|
config = RuleConfig.new(rule_name, block.binding)
|
45
43
|
config.instance_exec(config, &block)
|
46
|
-
config.guard = Guard::Guard.new(only_if: config.only_if, not_if: config.not_if)
|
44
|
+
config.guard = Guard::Guard.new(run_context: config.caller, only_if: config.only_if, not_if: config.not_if)
|
47
45
|
logger.trace { config.inspect }
|
48
46
|
process_rule_config(config)
|
49
47
|
nil # Must return something other than the rule object. See https://github.com/boc-tothefuture/openhab-jruby/issues/438
|
@@ -52,7 +50,7 @@ module OpenHAB
|
|
52
50
|
puts "#{e.class}: #{e.message}"
|
53
51
|
re_raise_with_backtrace(e)
|
54
52
|
end
|
55
|
-
# rubocop: enable Metrics
|
53
|
+
# rubocop: enable Metrics
|
56
54
|
|
57
55
|
#
|
58
56
|
# Cleanup rules in this script file
|
@@ -2,14 +2,15 @@
|
|
2
2
|
|
3
3
|
require 'java'
|
4
4
|
require 'pp'
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
5
|
+
require_relative 'property'
|
6
|
+
require_relative 'triggers/cron'
|
7
|
+
require_relative 'triggers/changed'
|
8
|
+
require_relative 'triggers/channel'
|
9
|
+
require_relative 'triggers/command'
|
10
|
+
require_relative 'triggers/updated'
|
11
|
+
require_relative 'triggers/generic'
|
12
|
+
require_relative 'triggers/watch'
|
13
|
+
require_relative 'guard'
|
13
14
|
require 'openhab/core/entity_lookup'
|
14
15
|
require 'openhab/dsl/between'
|
15
16
|
require 'openhab/dsl/dsl'
|
@@ -0,0 +1,213 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'java'
|
4
|
+
require 'openhab/log/logger'
|
5
|
+
require 'openhab/core/services'
|
6
|
+
|
7
|
+
module OpenHAB
|
8
|
+
module DSL
|
9
|
+
module Rules
|
10
|
+
#
|
11
|
+
# Module holds rule triggers
|
12
|
+
#
|
13
|
+
module Triggers
|
14
|
+
#
|
15
|
+
# Module for watching directories/files
|
16
|
+
#
|
17
|
+
module Watch
|
18
|
+
include OpenHAB::Log
|
19
|
+
|
20
|
+
# Characters in an fnmatch compatible glob
|
21
|
+
GLOB_CHARS = ['**', '*', '?', '[', ']', '{', '}'].freeze
|
22
|
+
|
23
|
+
#
|
24
|
+
# Creates trigger types and trigger type factories for OpenHAB
|
25
|
+
#
|
26
|
+
def self.add_watch_handler
|
27
|
+
java_import org.openhab.core.automation.type.TriggerType
|
28
|
+
OpenHAB::Core.automation_manager.add_trigger_handler(
|
29
|
+
OpenHAB::DSL::Rules::Triggers::Watch::WATCH_TRIGGER_MODULE_ID,
|
30
|
+
OpenHAB::DSL::Rules::Triggers::Watch::WatchTriggerHandlerFactory.new
|
31
|
+
)
|
32
|
+
|
33
|
+
OpenHAB::Core.automation_manager.add_trigger_type(watch_trigger_type)
|
34
|
+
OpenHAB::Log.logger(self).trace('Added watch trigger handler')
|
35
|
+
end
|
36
|
+
|
37
|
+
#
|
38
|
+
# Creates trigger types and trigger type factories for OpenHAB
|
39
|
+
#
|
40
|
+
private_class_method def self.watch_trigger_type
|
41
|
+
TriggerType.new(
|
42
|
+
OpenHAB::DSL::Rules::Triggers::Watch::WATCH_TRIGGER_MODULE_ID,
|
43
|
+
nil,
|
44
|
+
'A path change event is detected',
|
45
|
+
'Triggers when a path change event is detected',
|
46
|
+
nil,
|
47
|
+
org.openhab.core.automation.Visibility::VISIBLE,
|
48
|
+
nil
|
49
|
+
)
|
50
|
+
end
|
51
|
+
|
52
|
+
# Struct for Watch Events
|
53
|
+
WatchEvent = Struct.new(:type, :path, :attachment)
|
54
|
+
|
55
|
+
# Trigger ID for Watch Triggers
|
56
|
+
WATCH_TRIGGER_MODULE_ID = 'jsr223.jruby.WatchTrigger'
|
57
|
+
|
58
|
+
# Extends the OpenHAB watch service to watch directories
|
59
|
+
#
|
60
|
+
# Must match java method name style
|
61
|
+
# rubocop:disable Naming/MethodName
|
62
|
+
class Watcher < org.openhab.core.service.AbstractWatchService
|
63
|
+
java_import java.nio.file.StandardWatchEventKinds
|
64
|
+
|
65
|
+
# Hash of event symbols as strings to map to NIO events
|
66
|
+
STRING_TO_EVENT = {
|
67
|
+
created: StandardWatchEventKinds::ENTRY_CREATE,
|
68
|
+
deleted: StandardWatchEventKinds::ENTRY_DELETE,
|
69
|
+
modified: StandardWatchEventKinds::ENTRY_MODIFY
|
70
|
+
}.transform_keys(&:to_s).freeze
|
71
|
+
|
72
|
+
# Hash of NIO event kinds to ruby symbols
|
73
|
+
EVENT_TO_SYMBOL = STRING_TO_EVENT.invert.transform_values(&:to_sym).freeze
|
74
|
+
|
75
|
+
# Creates a new Watch Service
|
76
|
+
def initialize(path, types, &block)
|
77
|
+
super(path)
|
78
|
+
@types = types.map { |type| STRING_TO_EVENT[type] }
|
79
|
+
@block = block
|
80
|
+
end
|
81
|
+
|
82
|
+
# Invoked by java super class to get type of events to watch for
|
83
|
+
# @param [String] _path ignored
|
84
|
+
#
|
85
|
+
# @return [Array] array of NIO event kinds
|
86
|
+
def getWatchEventKinds(_path)
|
87
|
+
@types
|
88
|
+
end
|
89
|
+
|
90
|
+
# Invoked by java super class to check if sub directories should be watched
|
91
|
+
# @return [false] false
|
92
|
+
def watchSubDirectories
|
93
|
+
false
|
94
|
+
end
|
95
|
+
|
96
|
+
# Invoked by java super class when an watch event occurs
|
97
|
+
# @param [String] _event ignored
|
98
|
+
# @param [StandardWatchEventKind] kind NIO watch event kind
|
99
|
+
# @param [java.nio.Path] Path that had an event
|
100
|
+
def processWatchEvent(_event, kind, path)
|
101
|
+
@block.call(WatchEvent.new(EVENT_TO_SYMBOL[kind], Pathname.new(path.to_s)))
|
102
|
+
end
|
103
|
+
end
|
104
|
+
# rubocop:enable Naming/MethodName
|
105
|
+
|
106
|
+
# Implements the OpenHAB TriggerHandler interface to process Watch Triggers
|
107
|
+
class WatchTriggerHandler
|
108
|
+
include OpenHAB::Log
|
109
|
+
include org.openhab.core.automation.handler.TriggerHandler
|
110
|
+
|
111
|
+
# Creates a new WatchTriggerHandler
|
112
|
+
# @param [Trigger] OpenHAB trigger associated with handler
|
113
|
+
#
|
114
|
+
def initialize(trigger)
|
115
|
+
@trigger = trigger
|
116
|
+
config = trigger.configuration.properties.to_hash.transform_keys(&:to_sym)
|
117
|
+
@path = config[:path]
|
118
|
+
@watcher = Watcher.new(@path, config[:types], &watch_event_handler(config[:glob]))
|
119
|
+
@watcher.activate
|
120
|
+
logger.trace("Created watcher for #{@path}")
|
121
|
+
end
|
122
|
+
|
123
|
+
# Create a lambda to use to invoke rule engine when file watch notification happens
|
124
|
+
# @param [String] glob to match for notification events
|
125
|
+
#
|
126
|
+
# @return [Lambda] lambda to execute on notification events
|
127
|
+
#
|
128
|
+
def watch_event_handler(glob)
|
129
|
+
lambda { |watch_event|
|
130
|
+
logger.trace("Received event(#{watch_event})")
|
131
|
+
if watch_event.path.fnmatch?(glob)
|
132
|
+
@rule_engine_callback&.triggered(@trigger, { 'event' => watch_event })
|
133
|
+
else
|
134
|
+
logger.trace("Event #{watch_event} did not match glob(#{glob})")
|
135
|
+
end
|
136
|
+
}
|
137
|
+
end
|
138
|
+
|
139
|
+
# Called by OpenHAB to set the rule engine to invoke when triggered
|
140
|
+
# Must match java method name style
|
141
|
+
# rubocop:disable Naming/MethodName
|
142
|
+
def setCallback(callback)
|
143
|
+
@rule_engine_callback = callback
|
144
|
+
end
|
145
|
+
# rubocop:enable Naming/MethodName
|
146
|
+
|
147
|
+
#
|
148
|
+
# Dispose of handler which deactivates watcher
|
149
|
+
#
|
150
|
+
def dispose
|
151
|
+
logger.trace("Deactivating watcher for #{@path}")
|
152
|
+
@watcher&.deactivate
|
153
|
+
end
|
154
|
+
end
|
155
|
+
|
156
|
+
# Implements the ScriptedTriggerHandlerFactory interface to create a new Trigger Handler
|
157
|
+
class WatchTriggerHandlerFactory
|
158
|
+
include org.openhab.core.automation.module.script.rulesupport.shared.factories.ScriptedTriggerHandlerFactory
|
159
|
+
|
160
|
+
# Invoked by the OpenHAB core to get a trigger handler for the supllied trigger
|
161
|
+
# @param [Trigger] OpenHAB trigger
|
162
|
+
#
|
163
|
+
# @return [WatchTriggerHandler] trigger handler for supplied trigger
|
164
|
+
def get(trigger)
|
165
|
+
WatchTriggerHandler.new(trigger)
|
166
|
+
end
|
167
|
+
end
|
168
|
+
end
|
169
|
+
|
170
|
+
#
|
171
|
+
# Create a trigger to watch a path
|
172
|
+
#
|
173
|
+
# @param [String] path to watch
|
174
|
+
#
|
175
|
+
# @return [Trigger] Trigger object
|
176
|
+
#
|
177
|
+
def watch(path, glob: '*', for: %i[created deleted modified], attach: nil)
|
178
|
+
glob, path = glob_for_path(Pathname.new(path), glob)
|
179
|
+
types = [binding.local_variable_get(:for)].flatten
|
180
|
+
conf = { path: path.to_s, types: types.map(&:to_s), glob: glob.to_s }
|
181
|
+
|
182
|
+
logger.trace("Creating a watch trigger for path(#{path}) with glob(#{glob}) for types(#{types})")
|
183
|
+
append_trigger(OpenHAB::DSL::Rules::Triggers::Watch::WATCH_TRIGGER_MODULE_ID,
|
184
|
+
conf,
|
185
|
+
attach: attach)
|
186
|
+
end
|
187
|
+
|
188
|
+
private
|
189
|
+
|
190
|
+
#
|
191
|
+
# Automatically creates globs for supplied paths if necessary
|
192
|
+
# @param [Pathname] path to check
|
193
|
+
# @param [String] specified glob
|
194
|
+
#
|
195
|
+
# @return [Pathname,String] Pathname to watch and glob to match
|
196
|
+
def glob_for_path(path, glob)
|
197
|
+
# Checks if the supplied pathname last element contains a glob char
|
198
|
+
if OpenHAB::DSL::Rules::Triggers::Watch::GLOB_CHARS.any? { |char| path.basename.to_s.include? char }
|
199
|
+
# Splits the supplied pathname into a glob string and parent path
|
200
|
+
[path.basename.to_s, path.parent]
|
201
|
+
elsif path.file? || !path.exist?
|
202
|
+
# glob string matching end of Pathname and parent path
|
203
|
+
["*/#{path.basename}", path.parent]
|
204
|
+
else
|
205
|
+
[glob, path]
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
211
|
+
end
|
212
|
+
# Add the watch handler to OpenHAB
|
213
|
+
OpenHAB::DSL::Rules::Triggers::Watch.add_watch_handler
|
@@ -108,6 +108,21 @@ module OpenHAB
|
|
108
108
|
class MonthDay
|
109
109
|
include OpenHAB::Log
|
110
110
|
java_import java.time.format.DateTimeFormatter
|
111
|
+
|
112
|
+
#
|
113
|
+
# Constructor
|
114
|
+
#
|
115
|
+
# @param [Integer] m month
|
116
|
+
# @param [Integer] d day of month
|
117
|
+
#
|
118
|
+
# @return [Object] MonthDay object
|
119
|
+
#
|
120
|
+
# rubocop: disable Naming/MethodParameterName
|
121
|
+
def self.new(m:, d:)
|
122
|
+
MonthDay.of(m, d)
|
123
|
+
end
|
124
|
+
# rubocop: enable Naming/MethodParameterName
|
125
|
+
|
111
126
|
# Parse MonthDay string as defined with by Monthday class without leading double dash "--"
|
112
127
|
def self.parse(string)
|
113
128
|
logger.trace("#{self.class}.parse #{string} (#{string.class})")
|
@@ -19,7 +19,7 @@ module OpenHAB
|
|
19
19
|
|
20
20
|
def initialize
|
21
21
|
# Track timer IDs
|
22
|
-
@timer_ids =
|
22
|
+
@timer_ids = {}
|
23
23
|
|
24
24
|
# Reentrant timer lookups
|
25
25
|
@reentrant_timers = {}
|
@@ -39,6 +39,7 @@ module OpenHAB
|
|
39
39
|
|
40
40
|
if timer.respond_to? :id
|
41
41
|
logger.trace("Adding #{timer} with id #{timer.id.inspect} timer ids")
|
42
|
+
@timer_ids[timer.id] = Set.new unless @timer_ids[timer.id]
|
42
43
|
@timer_ids[timer.id] << timer
|
43
44
|
end
|
44
45
|
|
@@ -68,7 +69,10 @@ module OpenHAB
|
|
68
69
|
def delete(timer)
|
69
70
|
logger.trace("Removing #{timer} from timers")
|
70
71
|
@timers.delete(timer)
|
71
|
-
|
72
|
+
if timer.respond_to? :id
|
73
|
+
@timer_ids[timer.id]&.delete(timer)
|
74
|
+
@timer_ids.delete(timer.id) unless @timer_ids[timer.id].any?
|
75
|
+
end
|
72
76
|
@reentrant_timers.delete(timer.reentrant_id) if timer.respond_to? :reentrant_id
|
73
77
|
end
|
74
78
|
|
@@ -2,11 +2,13 @@
|
|
2
2
|
|
3
3
|
require 'forwardable'
|
4
4
|
require 'time'
|
5
|
+
require 'java'
|
5
6
|
|
6
7
|
module OpenHAB
|
7
8
|
module DSL
|
8
9
|
module Types
|
9
10
|
java_import org.openhab.core.library.types.DateTimeType
|
11
|
+
java_import java.time.ZonedDateTime
|
10
12
|
|
11
13
|
# global alias
|
12
14
|
::DateTimeType = DateTimeType
|
@@ -17,6 +17,7 @@ module OpenHAB
|
|
17
17
|
# @param longitude [DecimalType, QuantityType, StringType, Numeric]
|
18
18
|
# @param altitude [DecimalType, QuantityType, StringType, Numeric]
|
19
19
|
def initialize(*args) # rubocop:disable Metrics
|
20
|
+
args = from_hash(args.first.to_hash) if args.first.respond_to? :to_hash
|
20
21
|
if (2..3).cover?(args.length)
|
21
22
|
args = args.each_with_index.map do |value, index|
|
22
23
|
if value.is_a?(DecimalType) || value.is_a?(StringType)
|
@@ -118,6 +119,13 @@ module OpenHAB
|
|
118
119
|
QuantityType.new(raw_altitude.to_big_decimal, Units::METRE)
|
119
120
|
end
|
120
121
|
|
122
|
+
#
|
123
|
+
# Convert the PointType to a hash
|
124
|
+
# @return [Hash] with keys latitude/longitude/altitude
|
125
|
+
def to_h
|
126
|
+
{ latitude: latitude, longitude: longitude, altitude: altitude }
|
127
|
+
end
|
128
|
+
|
121
129
|
#
|
122
130
|
# Calculate the distance in meters from other, ignoring altitude.
|
123
131
|
#
|
@@ -138,7 +146,7 @@ module OpenHAB
|
|
138
146
|
|
139
147
|
# coerce an object to a PointType
|
140
148
|
# @return [PointType]
|
141
|
-
def coerce_single(other)
|
149
|
+
def coerce_single(other) # rubocop:disable Metrics
|
142
150
|
logger.trace("Coercing #{self} as a request from #{other.class}")
|
143
151
|
if other.is_a?(PointType)
|
144
152
|
other
|
@@ -148,7 +156,22 @@ module OpenHAB
|
|
148
156
|
other.state
|
149
157
|
elsif other.respond_to?(:to_str)
|
150
158
|
PointType.new(other.to_str)
|
159
|
+
elsif other.respond_to?(:to_hash)
|
160
|
+
PointType.new(other.to_hash)
|
161
|
+
end
|
162
|
+
end
|
163
|
+
|
164
|
+
#
|
165
|
+
# Convert hash into ordered arguments for constructor
|
166
|
+
#
|
167
|
+
def from_hash(hash)
|
168
|
+
keys = [%i[lat long alt], %i[latitude longitude altitude]]
|
169
|
+
keys.each do |key_set|
|
170
|
+
values = hash.transform_keys(&:to_sym).values_at(*key_set)
|
171
|
+
|
172
|
+
return *values.compact if values[0..1].all?
|
151
173
|
end
|
174
|
+
raise ArgumentError, "Supplied arguments (#{hash}) must contain one of the following sets #{keys}"
|
152
175
|
end
|
153
176
|
end
|
154
177
|
end
|
data/lib/openhab/version.rb
CHANGED
data/lib/openhab.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: openhab-scripting
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 4.
|
4
|
+
version: 4.26.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Brian O'Connell
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-12-
|
11
|
+
date: 2021-12-26 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -51,6 +51,7 @@ files:
|
|
51
51
|
- lib/openhab/core/openhab_setup.rb
|
52
52
|
- lib/openhab/core/osgi.rb
|
53
53
|
- lib/openhab/core/script_handling.rb
|
54
|
+
- lib/openhab/core/services.rb
|
54
55
|
- lib/openhab/core/thread_local.rb
|
55
56
|
- lib/openhab/dsl/actions.rb
|
56
57
|
- lib/openhab/dsl/between.rb
|
@@ -92,6 +93,7 @@ files:
|
|
92
93
|
- lib/openhab/dsl/monkey_patch/ruby/number.rb
|
93
94
|
- lib/openhab/dsl/monkey_patch/ruby/ruby.rb
|
94
95
|
- lib/openhab/dsl/monkey_patch/ruby/string.rb
|
96
|
+
- lib/openhab/dsl/openhab.rb
|
95
97
|
- lib/openhab/dsl/persistence.rb
|
96
98
|
- lib/openhab/dsl/rules/automation_rule.rb
|
97
99
|
- lib/openhab/dsl/rules/cron_trigger_rule.rb
|
@@ -108,6 +110,7 @@ files:
|
|
108
110
|
- lib/openhab/dsl/rules/triggers/generic.rb
|
109
111
|
- lib/openhab/dsl/rules/triggers/trigger.rb
|
110
112
|
- lib/openhab/dsl/rules/triggers/updated.rb
|
113
|
+
- lib/openhab/dsl/rules/triggers/watch.rb
|
111
114
|
- lib/openhab/dsl/states.rb
|
112
115
|
- lib/openhab/dsl/things.rb
|
113
116
|
- lib/openhab/dsl/time/month_day.rb
|