rspec-openhab-scripting 0.0.15-java → 0.0.18-java

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5d267863174213b2996edf9c92a8704499fb6e4c5136289fb2d2b2aae1a810bf
4
- data.tar.gz: 0cd9ff249e7a045265337bbb8603c0ab7e87d2c7e24145454e08917869202d98
3
+ metadata.gz: 6ea44768dd3bccdfc7276944f329030e21182d161126e433126970f096543f46
4
+ data.tar.gz: 81be4550cd3ab271f43e15616959709bb9e5d1cf14a999dd8565e0b148d3a8d7
5
5
  SHA512:
6
- metadata.gz: 4881e2d5e6cd7149dc15fa518fa6198d189db5177889571db981c204b299b674ac7a8e773fe1b3d14c0c4afeab244ef4653e3c1075a8585188dce465f9acbf5b
7
- data.tar.gz: 7d4f79653bf22e61ea06e19f42efc08544cbf4ad3a3ce3226c28dbd9f54df41f4cfdccec2df8dd6bbdbf4bc42d3d05076fb4217e416ea8f0492ce19b2062c92d
6
+ metadata.gz: 4d70a68375f21fab304d05b620125cf79b5767f3522d5e22a0608301b56e4ed3b2f6baba7942bdfcdb9ffed742378452720b79b7bfc5d7523544087a0bcb15bc
7
+ data.tar.gz: d2ce66901858dc37eb7c76b5f37f82da6147f1b471b8fc70097037099d677eb01c6e4e25d77e12105847e28156a919e059d5420271f9ce5cfcb0c9af933b4383
@@ -4,11 +4,12 @@ require "faraday"
4
4
 
5
5
  module OpenHAB
6
6
  class API
7
- def initialize(url)
7
+ def initialize(url, token = nil)
8
8
  @faraday = Faraday.new(url) do |f|
9
9
  f.response :raise_error
10
10
  f.response :json
11
11
  f.path_prefix = "/rest/"
12
+ f.headers = { "X-OPENHAB-TOKEN" => token } if token
12
13
  end
13
14
  end
14
15
 
@@ -36,6 +37,22 @@ module OpenHAB
36
37
  nil
37
38
  end
38
39
 
40
+ def channel_types
41
+ @faraday.get("channel-types").body
42
+ end
43
+
44
+ def thing_types
45
+ @faraday.get("thing-types").body
46
+ end
47
+
48
+ def things
49
+ @faraday.get("things").body
50
+ end
51
+
52
+ def authenticated?
53
+ @faraday.headers.key?("X-OPENHAB-TOKEN")
54
+ end
55
+
39
56
  private
40
57
 
41
58
  def root_data
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RSpec
4
+ module OpenHAB
5
+ module Core
6
+ module Mocks
7
+ class ChannelTypeProvider
8
+ include org.openhab.core.thing.type.ChannelTypeProvider
9
+ include Singleton
10
+
11
+ def initialize
12
+ @types = {}
13
+ end
14
+
15
+ def add(type)
16
+ @types[type.uid] = type
17
+ end
18
+
19
+ def get_channel_types(_locale)
20
+ @types.values
21
+ end
22
+
23
+ def get_channel_type(uid, _locale)
24
+ @types[uid]
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RSpec
4
+ module OpenHAB
5
+ module Core
6
+ module Mocks
7
+ class ItemChannelLinkProvider
8
+ include org.openhab.core.thing.link.ItemChannelLinkProvider
9
+ include Singleton
10
+
11
+ def initialize
12
+ @listeners = []
13
+ @links = []
14
+ end
15
+
16
+ def add_provider_change_listener(listener)
17
+ @listeners << listener
18
+ end
19
+
20
+ def remove_provider_change_listener(listener)
21
+ @listeners.delete(listener)
22
+ end
23
+
24
+ def all
25
+ @links
26
+ end
27
+
28
+ def add(link)
29
+ @links << link
30
+ @listeners.each { |l| l.added(self, link) }
31
+ end
32
+ end
33
+ end
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,144 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RSpec
4
+ module OpenHAB
5
+ module Core
6
+ module Mocks
7
+ class PersistenceService
8
+ include org.openhab.core.persistence.ModifiablePersistenceService
9
+ include Singleton
10
+
11
+ class HistoricItem
12
+ include org.openhab.core.persistence.HistoricItem
13
+
14
+ attr_reader :timestamp, :state, :name
15
+
16
+ def initialize(timestamp, state, name)
17
+ @timestamp = timestamp
18
+ @state = state
19
+ @name = name
20
+ end
21
+ end
22
+
23
+ attr_reader :id
24
+
25
+ def initialize
26
+ @id = "default"
27
+ reset
28
+ end
29
+
30
+ def reset
31
+ @data = Hash.new { |h, k| h[k] = [] }
32
+ end
33
+
34
+ def store(item, date = nil, state = nil)
35
+ date = nil if date.is_a?(String) # alias overload
36
+ state ||= item.state
37
+ date ||= ZonedDateTime.now
38
+
39
+ new_item = HistoricItem.new(date, state, item.name)
40
+
41
+ item_history = @data[item.name]
42
+
43
+ insert_index = item_history.bsearch_index do |i|
44
+ i.timestamp.compare_to(date).positive?
45
+ end
46
+
47
+ return item_history << new_item unless insert_index
48
+
49
+ return item_history[insert_index].state = state if item_history[insert_index].timestamp == date
50
+
51
+ item_history.insert(insert_index, new_item)
52
+ end
53
+
54
+ def remove(filter)
55
+ query_internal(filter) do |item_history, index|
56
+ historic_item = item_history.delete_at(index)
57
+ @data.delete(historic_item.name) if item_history.empty?
58
+ end
59
+ end
60
+
61
+ def query(filter)
62
+ result = []
63
+
64
+ query_internal(filter) do |item_history, index|
65
+ result << item_history[index]
66
+
67
+ return result if filter.page_number.zero? && result.length == filter.page_size && filter.item_name
68
+ end
69
+
70
+ result.sort_by! { |hi| hi.timestamp.to_instant.to_epoch_milli } unless filter.item_name
71
+
72
+ unless filter.page_number.zero?
73
+ result = result.slice(filter.page_number * filter.page_size, filter.page_size)
74
+ end
75
+
76
+ result
77
+ end
78
+
79
+ def get_item_info # rubocop:disable Naming/AccessorMethodName must match Java interface
80
+ @data.map do |(n, entries)|
81
+ [n, entries.length, entries.first.timestamp, entries.last.timestamp]
82
+ end.to_set
83
+ end
84
+
85
+ def get_default_strategies # rubocop:disable Naming/AccessorMethodName must match Java interface
86
+ [org.openhab.core.persistence.strategy.PersistenceStrategy::Globals::CHANGE]
87
+ end
88
+
89
+ private
90
+
91
+ def query_internal(filter, &block)
92
+ if filter.item_name
93
+ return unless @data.key?(filter.item_name)
94
+
95
+ query_item_internal(@data[filter.item_name], filter, &block)
96
+ else
97
+ @data.each_value do |item_history|
98
+ query_item_internal(item_history, filter, &block)
99
+ end
100
+ end
101
+ end
102
+
103
+ def query_item_internal(item_history, filter)
104
+ first_index = 0
105
+ last_index = item_history.length
106
+
107
+ if filter.begin_date
108
+ first_index = item_history.bsearch_index do |i|
109
+ i.timestamp.compare_to(filter.begin_date).positive?
110
+ end
111
+ return if first_index.nil?
112
+ end
113
+
114
+ if filter.end_date
115
+ last_index = item_history.bsearch_index do |i|
116
+ i.timestamp.compare_to(filter.end_date).positive?
117
+ end
118
+ return if last_index.zero?
119
+
120
+ last_index ||= item_history.length
121
+ end
122
+
123
+ range = first_index...last_index
124
+
125
+ operator = filter.operator.symbol
126
+ operator = "==" if operator == "="
127
+
128
+ block = lambda do |i|
129
+ next if filter.state && !item_history[i].state.send(operator, filter.state)
130
+
131
+ yield(item_history, i)
132
+ end
133
+
134
+ if filter.ordering == filter.class::Ordering::DESCENDING
135
+ range.reverse_each(&block)
136
+ else
137
+ range.each(&block)
138
+ end
139
+ end
140
+ end
141
+ end
142
+ end
143
+ end
144
+ end
@@ -0,0 +1,48 @@
1
+ # frozen_string_literal: true
2
+
3
+ # rubocop:disable Naming have to follow java interface names
4
+ module RSpec
5
+ module OpenHAB
6
+ module Core
7
+ module Mocks
8
+ class ThingHandler
9
+ include org.openhab.core.thing.binding.BridgeHandler
10
+
11
+ attr_reader :thing, :callback
12
+
13
+ def initialize(thing = nil)
14
+ # have to handle the interface method
15
+ if thing.nil?
16
+ status_info = org.openhab.core.thing.binding.builder.ThingStatusInfoBuilder
17
+ .create(org.openhab.core.thing.ThingStatus::ONLINE).build
18
+ @callback.status_updated(self.thing, status_info)
19
+ return
20
+ end
21
+
22
+ # ruby initializer here
23
+ @thing = thing
24
+ end
25
+
26
+ def handle_command(channel, command); end
27
+
28
+ def set_callback(callback)
29
+ @callback = callback
30
+ end
31
+
32
+ def child_handler_initialized(child_handler, child_thing); end
33
+ end
34
+
35
+ class ThingHandlerFactory < org.openhab.core.thing.binding.BaseThingHandlerFactory
36
+ def supportsThingType(_type)
37
+ true
38
+ end
39
+
40
+ def createHandler(thing)
41
+ ThingHandler.new(thing)
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
47
+ end
48
+ # rubocop:enable Naming
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RSpec
4
+ module OpenHAB
5
+ module Core
6
+ module Mocks
7
+ class ThingTypeProvider
8
+ include org.openhab.core.thing.binding.ThingTypeProvider
9
+ include Singleton
10
+
11
+ def initialize
12
+ @types = {}
13
+ end
14
+
15
+ def add(type)
16
+ @types[type.uid] = type
17
+ end
18
+
19
+ def get_thing_types(_locale)
20
+ @types.values
21
+ end
22
+
23
+ def get_thing_type(uid, _locale)
24
+ @types[uid]
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -4,7 +4,11 @@ module OpenHAB
4
4
  module Core
5
5
  class OSGI
6
6
  class << self
7
- def register_service(name, service)
7
+ def register_service(name, service = nil)
8
+ if service.nil?
9
+ service = name
10
+ name = service.java_class.interfaces.first&.name || service.java_class.name
11
+ end
8
12
  (@services ||= {})[name] = service
9
13
  end
10
14
 
@@ -68,6 +68,22 @@ module OpenHAB
68
68
  def add_bundle_listener(listener); end
69
69
  end
70
70
 
71
+ class BundleResolver
72
+ include org.openhab.core.util.BundleResolver
73
+
74
+ def initialize
75
+ @bundles = {}
76
+ end
77
+
78
+ def register(klass, bundle)
79
+ @bundles[klass] = bundle
80
+ end
81
+
82
+ def resolve_bundle(klass)
83
+ @bundles[klass]
84
+ end
85
+ end
86
+
71
87
  # don't depend on org.openhab.core.test
72
88
  class VolatileStorageService
73
89
  include org.openhab.core.storage.StorageService
@@ -98,13 +114,15 @@ module OpenHAB
98
114
  INSTALLED = 2
99
115
 
100
116
  def initialize(*jar_args)
117
+ return if jar_args.empty?
118
+
101
119
  file = Jars.find_jar(*jar_args)
102
120
  @jar = java.util.jar.JarFile.new(file)
103
121
  @symbolic_name = jar_args[1]
104
122
  @version = org.osgi.framework.Version.new(jar_args[2].tr("-", "."))
105
123
  end
106
124
 
107
- attr_reader :symbolic_name, :version
125
+ attr_accessor :symbolic_name, :version
108
126
 
109
127
  def state
110
128
  INSTALLED
@@ -190,7 +208,7 @@ module OpenHAB
190
208
  event_factory.create_event(type, topic, payload, source)
191
209
  rescue Exception => e
192
210
  logger.warn("Creation of event failed, because one of the " \
193
- "registered event factories has thrown an exception: #{e}")
211
+ "registered event factories has thrown an exception: #{e.inspect}")
194
212
  nil
195
213
  end
196
214
 
@@ -201,7 +219,9 @@ module OpenHAB
201
219
  begin
202
220
  event_subscriber.receive(event)
203
221
  rescue Exception => e
204
- logger.warn("Dispatching/filtering event for subscriber '#{event_subscriber.class}' failed: #{e}")
222
+ logger.warn(
223
+ "Dispatching/filtering event for subscriber '#{event_subscriber.class}' failed: #{e.inspect}"
224
+ )
205
225
  end
206
226
  else
207
227
  logger.trace("Skip event subscriber (#{event_subscriber.class}) because of its filter.")
@@ -217,7 +237,7 @@ module OpenHAB
217
237
  include Singleton
218
238
 
219
239
  def submit(runnable)
220
- runnable.run
240
+ runnable.respond_to?(:run) ? runnable.run : runnable.call
221
241
 
222
242
  java.util.concurrent.CompletableFuture.completed_future(nil)
223
243
  end
@@ -233,6 +253,40 @@ module OpenHAB
233
253
  end
234
254
  end
235
255
 
256
+ class SafeCaller
257
+ include org.openhab.core.common.SafeCaller
258
+ include org.openhab.core.common.SafeCallerBuilder
259
+
260
+ def create(target, _interface_type)
261
+ @target = target
262
+ self
263
+ end
264
+
265
+ def build
266
+ @target
267
+ end
268
+
269
+ def with_timeout(_timeout)
270
+ self
271
+ end
272
+
273
+ def with_identifier(_identifier)
274
+ self
275
+ end
276
+
277
+ def on_exception(_handler)
278
+ self
279
+ end
280
+
281
+ def on_timeout(_handler)
282
+ self
283
+ end
284
+
285
+ def with_async
286
+ self
287
+ end
288
+ end
289
+
236
290
  class CallbacksMap < java.util.HashMap
237
291
  def put(_rule_uid, trigger_handler)
238
292
  trigger_handler.executor.shutdown_now
@@ -271,11 +325,12 @@ module OpenHAB
271
325
  bc = BundleContext.new(em)
272
326
  cc = ComponentContext.new(bc)
273
327
  cc.properties["measurementSystem"] = api.measurement_system if api
328
+ resolver = BundleResolver.new
274
329
 
275
330
  # the registries!
276
331
  ss = VolatileStorageService.new
277
332
  mr = org.openhab.core.internal.items.MetadataRegistryImpl.new
278
- OpenHAB::Core::OSGI.register_service("org.openhab.core.items.MetadataRegistry", mr)
333
+ OpenHAB::Core::OSGI.register_service(mr)
279
334
  mr.managed_provider = mmp = org.openhab.core.internal.items.ManagedMetadataProviderImpl.new(ss)
280
335
  mr.add_provider(mmp)
281
336
  gmp = org.openhab.core.model.item.internal.GenericMetadataProvider.new
@@ -286,16 +341,25 @@ module OpenHAB
286
341
  ir.event_publisher = ep
287
342
  up = org.openhab.core.internal.i18n.I18nProviderImpl.new(cc)
288
343
  ir.unit_provider = up
289
- ir.item_state_converter = org.openhab.core.internal.items.ItemStateConverterImpl.new(up)
344
+ ir.item_state_converter = isc = org.openhab.core.internal.items.ItemStateConverterImpl.new(up)
290
345
  tr = org.openhab.core.thing.internal.ThingRegistryImpl.new
346
+ tr.managed_provider = mtp = org.openhab.core.thing.ManagedThingProvider.new(ss)
347
+ tr.add_provider(mtp)
291
348
  mtr = org.openhab.core.automation.internal.type.ModuleTypeRegistryImpl.new
292
349
  rr = org.openhab.core.automation.internal.RuleRegistryImpl.new
293
350
  rr.module_type_registry = mtr
294
351
  rr.managed_provider = mrp = org.openhab.core.automation.ManagedRuleProvider.new(ss)
295
352
  rr.add_provider(mrp)
296
353
  iclr = org.openhab.core.thing.link.ItemChannelLinkRegistry.new(tr, ir)
354
+ iclr.add_provider(RSpec::OpenHAB::Core::Mocks::ItemChannelLinkProvider.instance)
355
+ OpenHAB::Core::OSGI.register_service(iclr)
297
356
  ctr = org.openhab.core.thing.type.ChannelTypeRegistry.new
357
+ OpenHAB::Core::OSGI.register_service(ctr)
358
+ ctr.add_channel_type_provider(RSpec::OpenHAB::Core::Mocks::ChannelTypeProvider.instance)
298
359
  ttr = org.openhab.core.thing.type.ThingTypeRegistry.new(ctr)
360
+ OpenHAB::Core::OSGI.register_service(ttr)
361
+ ttr.add_thing_type_provider(RSpec::OpenHAB::Core::Mocks::ThingTypeProvider.instance)
362
+ cgtr = org.openhab.core.thing.type.ChannelGroupTypeRegistry.new
299
363
 
300
364
  safe_emf = org.openhab.core.model.core.internal.SafeEMFImpl.new
301
365
  model_repository = org.openhab.core.model.core.internal.ModelRepositoryImpl.new(safe_emf)
@@ -360,15 +424,18 @@ module OpenHAB
360
424
 
361
425
  # link up event bus infrastructure
362
426
  iu = org.openhab.core.internal.items.ItemUpdater.new(ir)
363
- ief = org.openhab.core.items.events.ItemEventFactory.new
364
427
 
365
- sc = org.openhab.core.internal.common.SafeCallerImpl.new({})
366
- aum = org.openhab.core.thing.internal.AutoUpdateManager.new({ "enabled" => "true" }, nil, ep, iclr, mr, tr)
367
- cm = org.openhab.core.thing.internal.CommunicationManager.new(aum, nil, nil, iclr, ir, nil, ep, sc, tr)
428
+ sc = SafeCaller.new
429
+ aum = org.openhab.core.thing.internal.AutoUpdateManager.new(
430
+ { "enabled" => true, "sendOptimisticUpdates" => true }, ctr, ep, iclr, mr, tr
431
+ )
432
+ spf = org.openhab.core.thing.internal.profiles.SystemProfileFactory.new(ctr, nil, resolver)
433
+ cm = org.openhab.core.thing.internal.CommunicationManager.new(aum, ctr, spf, iclr, ir, isc, ep, sc, tr)
368
434
 
369
435
  em.add_event_subscriber(iu)
370
436
  em.add_event_subscriber(cm)
371
- em.add_event_factory(ief)
437
+ em.add_event_factory(org.openhab.core.items.events.ItemEventFactory.new)
438
+ em.add_event_factory(org.openhab.core.thing.events.ThingEventFactory.new)
372
439
 
373
440
  # set up the rules engine part 2
374
441
  k = org.openhab.core.automation.internal.module.factory.CoreModuleHandlerFactory
@@ -400,6 +467,42 @@ module OpenHAB
400
467
  el = org.openhab.core.io.monitor.internal.EventLogger.new(rs)
401
468
  em.add_event_subscriber(el)
402
469
  el.on_ready_marker_added(nil)
470
+
471
+ # set up persistence
472
+ psr = org.openhab.core.persistence.internal.PersistenceServiceRegistryImpl.new
473
+ org.openhab.core.persistence.extensions.PersistenceExtensions.new(psr)
474
+ psr.activate("default" => "default")
475
+ ps = RSpec::OpenHAB::Core::Mocks::PersistenceService.instance
476
+ psr.add_persistence_service(ps)
477
+
478
+ pm = org.openhab.core.persistence.internal.PersistenceManagerImpl.new(nil, ir, sc, rs)
479
+ pm.add_persistence_service(ps)
480
+ pm.on_ready_marker_added(nil)
481
+
482
+ # set up ThingManager so we can trigger channels
483
+ localizer = org.openhab.core.thing.i18n.ThingStatusInfoI18nLocalizationService.new
484
+ tm = org.openhab.core.thing.internal.ThingManagerImpl.new(
485
+ resolver,
486
+ cgtr,
487
+ ctr,
488
+ cm,
489
+ nil,
490
+ nil,
491
+ ep,
492
+ iclr,
493
+ rs,
494
+ sc,
495
+ ss,
496
+ tr,
497
+ localizer,
498
+ ttr
499
+ )
500
+ thf = RSpec::OpenHAB::Core::Mocks::ThingHandlerFactory.new
501
+ this_bundle = Bundle.new
502
+ this_bundle.symbolic_name = "org.openhab.automation.jrubyscripting.rspec"
503
+ resolver.register(thf.class.java_class, this_bundle)
504
+ tm.add_thing_handler_factory(thf)
505
+ tm.on_ready_marker_added(org.openhab.core.service.ReadyMarker.new(nil, this_bundle.symbolic_name))
403
506
  end
404
507
  end
405
508
  end
@@ -24,6 +24,13 @@ module RSpec
24
24
  @rules.fetch(rule_name).execute(nil, { "event" => event })
25
25
  end
26
26
 
27
+ def trigger_channel(channel, event)
28
+ channel = org.openhab.core.thing.ChannelUID.new(channel) if channel.is_a?(String)
29
+ channel = channel.uid if channel.is_a?(org.openhab.core.thing.Channel)
30
+ thing = channel.thing
31
+ thing.handler.callback.channel_triggered(nil, channel, event)
32
+ end
33
+
27
34
  private
28
35
 
29
36
  def restore_autoupdate_items
@@ -10,9 +10,11 @@ RSpec.configure do |config|
10
10
  end
11
11
  end
12
12
  end
13
+
13
14
  config.after do
14
15
  OpenHAB::DSL::Timers.timer_manager.cancel_all
15
16
  Timecop.return
16
17
  restore_autoupdate_items
18
+ RSpec::OpenHAB::Core::Mocks::PersistenceService.instance.reset
17
19
  end
18
20
  end
@@ -39,6 +39,15 @@ module RSpec
39
39
  item.category = item_json["category"] if item_json["category"]
40
40
 
41
41
  $ir.add(item)
42
+
43
+ next unless item.meta["channel"]&.value
44
+
45
+ channel_uid = org.openhab.core.thing.ChannelUID.new(item.meta["channel"].value)
46
+ channel = $things.get_channel(channel_uid)
47
+ next unless channel
48
+
49
+ link = org.openhab.core.thing.link.ItemChannelLink.new(item.name, channel_uid)
50
+ Core::Mocks::ItemChannelLinkProvider.instance.add(link)
42
51
  end
43
52
  all_items.each do |item_json| # rubocop:disable Style/CombinableLoops
44
53
  item_json["groupNames"].each do |group_name|
@@ -48,6 +57,163 @@ module RSpec
48
57
  end
49
58
  end
50
59
  end
60
+
61
+ def populate_things_from_api(api)
62
+ populate_channel_types_from_api(api)
63
+ populate_thing_types_from_api(api)
64
+
65
+ thing_type_registry = ::OpenHAB::Core::OSGI.service("org.openhab.core.thing.type.ThingTypeRegistry")
66
+
67
+ api.things.each do |thing_json|
68
+ uid = org.openhab.core.thing.ThingUID.new(thing_json["UID"])
69
+ type_uid = org.openhab.core.thing.ThingTypeUID.new(thing_json["thingTypeUID"])
70
+ bridge_uid = org.openhab.core.thing.ThingUID.new(thing_json["bridgeUID"]) if thing_json["bridgeUID"]
71
+
72
+ type = thing_type_registry.get_thing_type(type_uid)
73
+ klass = if type.is_a?(org.openhab.core.thing.type.BridgeType)
74
+ org.openhab.core.thing.binding.builder.BridgeBuilder
75
+ else
76
+ org.openhab.core.thing.binding.builder.ThingBuilder
77
+ end
78
+ builder = klass.create(type_uid, uid)
79
+ builder.with_bridge(bridge_uid) if bridge_uid
80
+
81
+ thing_json.each do |(k, v)|
82
+ case k
83
+ when "UID", "thingTypeUID", "bridgeUID", "statusInfo", "editable"
84
+ nil
85
+ when "channels"
86
+ builder.with_channels(v.map { |c| build_channel(c) })
87
+ when "configuration"
88
+ builder.with_configuration(org.openhab.core.config.core.Configuration.new(v))
89
+ else
90
+ builder.send(:"with_#{k}", v)
91
+ end
92
+ end
93
+
94
+ $things.add(builder.build)
95
+ end
96
+ end
97
+
98
+ private
99
+
100
+ def populate_channel_types_from_api(api)
101
+ api.channel_types.each do |ct_json|
102
+ uid = org.openhab.core.thing.type.ChannelTypeUID.new(ct_json["UID"])
103
+ builder = case ct_json["kind"]
104
+ when "STATE"
105
+ org.openhab.core.thing.type.ChannelTypeBuilder.state(uid, ct_json["label"], ct_json["itemType"])
106
+ when "TRIGGER"
107
+ org.openhab.core.thing.type.ChannelTypeBuilder.trigger(uid, ct_json["label"])
108
+ else
109
+ raise ArgumentError, "Unrecognized channel type kind #{ct_json["kind"]} for #{uid}"
110
+ end
111
+
112
+ ct_json.each do |(k, v)|
113
+ case k
114
+ when "parameters", "parameterGroups", "label", "kind", "UID", "itemType"
115
+ nil
116
+ when "commandDescription"
117
+ builder.with_command_description(build_command_description(v))
118
+ when "stateDescription"
119
+ builder.with_state_description_fragment(build_state_description_fragment(v))
120
+ when "advanced"
121
+ builder.is_advanced(v)
122
+ else
123
+ builder.send(:"with_#{k}", v)
124
+ end
125
+ end
126
+
127
+ ct = builder.build
128
+ Core::Mocks::ChannelTypeProvider.instance.add(ct)
129
+ end
130
+ end
131
+
132
+ def build_command_description(json)
133
+ org.openhab.core.types.CommandDescriptionBuilder.create
134
+ .with_command_options(json["commandOptions"].map do |o|
135
+ org.openhab.core.types.CommandOption.new(o["command"], o["label"])
136
+ end)
137
+ .build
138
+ end
139
+
140
+ def build_state_description_fragment(json)
141
+ org.openhab.core.types.StateDescriptionFragmentBuilder.create
142
+ .with_minimum(json["minimum"]&.to_d)
143
+ .with_maximum(json["maximum"]&.to_d)
144
+ .with_step(json["step"&.to_d])
145
+ .with_pattern(json["pattern"])
146
+ .with_read_only(json["readOnly"])
147
+ .with_options(json["options"].map { |o| org.openhab.core.types.StateOption.new(o["value"], o["label"]) })
148
+ .build
149
+ end
150
+
151
+ def populate_thing_types_from_api(api)
152
+ api.thing_types.each do |tt_json|
153
+ uid = org.openhab.core.thing.ThingTypeUID.new(tt_json["UID"])
154
+ builder = org.openhab.core.thing.type.ThingTypeBuilder.instance(uid, tt_json["label"])
155
+ tt_json.each do |(k, v)|
156
+ case k
157
+ when "UID", "label", "bridge"
158
+ nil
159
+ when "listed"
160
+ builder.is_listed(v)
161
+ when "channels"
162
+ builder.with_channels(v.map { |c| build_channel_definition(c) })
163
+ when "channelGroups"
164
+ builder.with_channel_groups(v.map { |cg| build_channel_group_definition(cg) })
165
+ else
166
+ builder.send(:"with#{k[0].upcase}#{k[1..]}", v)
167
+ end
168
+ end
169
+
170
+ tt = tt_json["bridge"] ? builder.build_bridge : builder.build
171
+ Core::Mocks::ThingTypeProvider.instance.add(tt)
172
+ end
173
+ end
174
+
175
+ def build_channel_definition(json)
176
+ org.openhab.core.thing.type.ChannelDefinition.new(
177
+ json["uid"],
178
+ org.openhab.core.thing.type.ChannelTypeUID.new(json["typeUID"]),
179
+ json["description"],
180
+ json["properties"],
181
+ nil
182
+ )
183
+ end
184
+
185
+ def build_channel_group_definition(json)
186
+ org.openhab.core.thing.type.ChannelGroupDefinition.new(
187
+ json["uid"],
188
+ org.openhab.core.thing.type.ChannelGroupTypeUID.new(json["typeUID"]),
189
+ json["label"],
190
+ json["description"]
191
+ )
192
+ end
193
+
194
+ def build_channel(json)
195
+ uid = org.openhab.core.thing.ChannelUID.new(json["uid"])
196
+ builder = org.openhab.core.thing.binding.builder.ChannelBuilder.create(uid)
197
+
198
+ json.each do |(k, v)|
199
+ case k
200
+ when "uid", "id", "linkedItems", "itemType"
201
+ nil
202
+ when "channelTypeUID"
203
+ builder.with_type(org.openhab.core.thing.type.ChannelTypeUID.new((v)))
204
+ when "configuration"
205
+ builder.with_configuration(org.openhab.core.config.core.Configuration.new(v))
206
+ when "kind"
207
+ builder.with_kind(org.openhab.core.thing.type.ChannelKind.const_get(v, false))
208
+ when "defaultTags"
209
+ builder.with_default_tags(v.to_set)
210
+ else
211
+ builder.send("with_#{k}", v)
212
+ end
213
+ end
214
+
215
+ builder.build
216
+ end
51
217
  end
52
218
  end
53
219
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module RSpec
4
4
  module OpenHAB
5
- VERSION = "0.0.15"
5
+ VERSION = "0.0.18"
6
6
  end
7
7
  end
@@ -5,7 +5,8 @@
5
5
  $LOAD_PATH.unshift(File.expand_path("../vendor/gems/jar-dependencies-1.0.0/lib", __dir__))
6
6
 
7
7
  require "rspec/openhab/api"
8
- api = OpenHAB::API.new("http://#{ENV.fetch("OPENHAB_HOST", "localhost")}:#{ENV.fetch("OPENHAB_HTTP_PORT", "8080")}/")
8
+ api = OpenHAB::API.new("http://#{ENV.fetch("OPENHAB_HOST", "localhost")}:#{ENV.fetch("OPENHAB_HTTP_PORT", "8080")}/",
9
+ ENV.fetch("OPENHAB_TOKEN", nil))
9
10
 
10
11
  module OpenHAB
11
12
  module Core
@@ -42,9 +43,11 @@ maven_require do
42
43
  require "jar org.openhab.core.bundles, org.openhab.core.model.core, #{openhab_version}"
43
44
  require "jar org.openhab.core.bundles, org.openhab.core.model.item, #{openhab_version}"
44
45
  require "jar org.openhab.core.bundles, org.openhab.core.model.script, #{openhab_version}"
46
+ require "jar org.openhab.core.bundles, org.openhab.core.persistence, #{openhab_version}"
45
47
  require "jar org.openhab.core.bundles, org.openhab.core.semantics, #{openhab_version}"
46
48
  require "jar org.openhab.core.bundles, org.openhab.core.thing, #{openhab_version}"
47
49
  end
50
+ java_import org.openhab.core.persistence.extensions.PersistenceExtensions
48
51
 
49
52
  require "openhab/version"
50
53
 
@@ -64,6 +67,11 @@ require "rspec/openhab/core/logger"
64
67
  # during testing, we don't want "regular" output from rules
65
68
  OpenHAB::Log.logger("org.openhab.automation.jruby.runtime").level = :warn
66
69
  OpenHAB::Log.logger("org.openhab.automation.jruby.logger").level = :warn
70
+ require "rspec/openhab/core/mocks/channel_type_provider"
71
+ require "rspec/openhab/core/mocks/item_channel_link_provider"
72
+ require "rspec/openhab/core/mocks/persistence_service"
73
+ require "rspec/openhab/core/mocks/thing_handler"
74
+ require "rspec/openhab/core/mocks/thing_type_provider"
67
75
  require "openhab/dsl/imports"
68
76
  OpenHAB::DSL::Imports.api = api
69
77
  OpenHAB::DSL::Imports.import_presets
@@ -90,6 +98,7 @@ RSpec.configure do |config|
90
98
  end
91
99
 
92
100
  RSpec::OpenHAB::SuspendRules.suspend_rules do
101
+ RSpec::OpenHAB::Items.populate_things_from_api(api) if api.authenticated?
93
102
  RSpec::OpenHAB::Items.populate_items_from_api(api)
94
103
  end
95
104
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rspec-openhab-scripting
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.15
4
+ version: 0.0.18
5
5
  platform: java
6
6
  authors:
7
7
  - Cody Cutrer
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-07-05 00:00:00.000000000 Z
11
+ date: 2022-07-20 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  requirement: !ruby/object:Gem::Requirement
@@ -192,6 +192,11 @@ files:
192
192
  - lib/rspec/openhab/core/item_proxy.rb
193
193
  - lib/rspec/openhab/core/load_path.rb
194
194
  - lib/rspec/openhab/core/logger.rb
195
+ - lib/rspec/openhab/core/mocks/channel_type_provider.rb
196
+ - lib/rspec/openhab/core/mocks/item_channel_link_provider.rb
197
+ - lib/rspec/openhab/core/mocks/persistence_service.rb
198
+ - lib/rspec/openhab/core/mocks/thing_handler.rb
199
+ - lib/rspec/openhab/core/mocks/thing_type_provider.rb
195
200
  - lib/rspec/openhab/core/openhab_setup.rb
196
201
  - lib/rspec/openhab/core/osgi.rb
197
202
  - lib/rspec/openhab/core/script_handling.rb
@@ -236,7 +241,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
236
241
  requirements:
237
242
  - - ">="
238
243
  - !ruby/object:Gem::Version
239
- version: '2.5'
244
+ version: '2.6'
240
245
  required_rubygems_version: !ruby/object:Gem::Requirement
241
246
  requirements:
242
247
  - - ">="
@@ -244,7 +249,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
244
249
  version: '0'
245
250
  requirements:
246
251
  - jar ch.qos.logback, logback-classic, 1.2.9
247
- rubygems_version: 3.3.17
252
+ rubygems_version: 3.2.29
248
253
  signing_key:
249
254
  specification_version: 4
250
255
  summary: Library testing OpenHAB ruby rules with rspec.