Skip to content

Commit

Permalink
Support filtered item|thing_added|removed and channel_linked|unlinked…
Browse files Browse the repository at this point in the history
… triggers (#266)
  • Loading branch information
jimtng authored May 14, 2024
1 parent 5cc4acc commit c360146
Show file tree
Hide file tree
Showing 3 changed files with 160 additions and 24 deletions.
5 changes: 5 additions & 0 deletions lib/openhab/core/dto/item_channel_link.rb
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,11 @@ def item
def channel_uid
Things::ChannelUID.new(channelUID)
end

# @return [String]
def to_s
"#{item_name} -> #{channelUID}"
end
end
end
end
Expand Down
76 changes: 52 additions & 24 deletions lib/openhab/dsl/rules/builder.rb
Original file line number Diff line number Diff line change
Expand Up @@ -992,19 +992,25 @@ def channel(*channels, thing: nil, triggered: nil, attach: nil)
#
# Creates a channel linked trigger
#
# @param [Item, String, nil] item The item to create a trigger for. If nil, all items are matched.
# @param [Core::Things::Channel, Core::Things::ChannelUID, String, nil] channel
# The channel to create a trigger for. If nil, all channels are matched.
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for filtering with item and channel was added
#
# @example
# rule "channel linked" do
# channel_linked
# run do |event|
# logger.info("#{event.link.item.name} linked to #{event.link.channel_uid}.")
# end
# end
def channel_linked(attach: nil)
@ruby_triggers << [:channel_linked]
event("openhab/links/*/added", types: "ItemChannelLinkAddedEvent", attach: attach)
def channel_linked(item: nil, channel: nil, attach: nil)
pattern = (item.nil? && channel.nil?) ? "*" : "#{item || "*"}-#{channel || "*"}"
@ruby_triggers << [:channel_linked, pattern]
event("openhab/links/#{pattern}/added", types: "ItemChannelLinkAddedEvent", attach: attach)
end

#
Expand All @@ -1013,19 +1019,25 @@ def channel_linked(attach: nil)
# Note that the item or the thing it's linked to may no longer exist,
# so if you try to access those objects they'll be nil.
#
# @param [Item, String, nil] item The item to create a trigger for. If nil, all items are matched.
# @param [Core::Things::Channel, Core::Things::ChannelUID, String, nil] channel
# The channel to create a trigger for. If nil, all channels are matched.
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for filtering with item and channel was added
#
# @example
# rule "channel unlinked" do
# channel_unlinked
# run do |event|
# logger.info("#{event.link.item_name} unlinked from #{event.link.channel_uid}.")
# end
# end
def channel_unlinked(attach: nil)
@ruby_triggers << [:channel_linked]
event("openhab/links/*/removed", types: "ItemChannelLinkRemovedEvent", attach: attach)
def channel_unlinked(item: nil, channel: nil, attach: nil)
pattern = (item.nil? && channel.nil?) ? "*" : "#{item || "*"}-#{channel || "*"}"
@ruby_triggers << [:channel_unlinked, pattern]
event("openhab/links/#{pattern}/removed", types: "ItemChannelLinkRemovedEvent", attach: attach)
end

#
Expand Down Expand Up @@ -1556,42 +1568,49 @@ def received_command(*items, command: nil, commands: nil, attach: nil)
#
# Creates an item added trigger
#
# @param [String, nil] pattern The pattern to match items against
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for pattern filter was added
#
# @example
# rule "item added" do
# item_added
# run do |event|
# logger.info("#{event.item.name} added.")
# end
# end
def item_added(attach: nil)
@ruby_triggers << [:item_added]
event("openhab/items/*/added", types: "ItemAddedEvent", attach: attach)
def item_added(pattern = "*", attach: nil)
@ruby_triggers << [:item_added, pattern]
event("openhab/items/#{pattern}/added", types: "ItemAddedEvent", attach: attach)
end

#
# Creates an item removed trigger
#
# @param [String, nil] pattern The pattern to match items against
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for pattern filter was added
#
# @example
# rule "item removed" do
# item_removed
# run do |event|
# logger.info("#{event.item.name} removed.")
# end
# end
def item_removed(attach: nil)
@ruby_triggers << [:item_removed]
event("openhab/items/*/removed", types: "ItemRemovedEvent", attach: attach)
def item_removed(pattern = "*", attach: nil)
@ruby_triggers << [:item_removed, pattern]
event("openhab/items/#{pattern}/removed", types: "ItemRemovedEvent", attach: attach)
end

#
# Creates an item updated trigger
#
# @param [String, nil] pattern The pattern to match items against
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
Expand All @@ -1603,53 +1622,62 @@ def item_removed(attach: nil)
# end
# end
#
def item_updated(attach: nil)
@ruby_triggers << [:item_updated]
event("openhab/items/*/updated", types: "ItemUpdatedEvent", attach: attach)
def item_updated(pattern = "*", attach: nil)
@ruby_triggers << [:item_updated, pattern]
event("openhab/items/#{pattern}/updated", types: "ItemUpdatedEvent", attach: attach)
end

#
# Creates a thing added trigger
#
# @param [String, nil] pattern The pattern to match things against
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for pattern filter was added
#
# @example
# rule "thing added" do
# thing_added
# run do |event|
# logger.info("#{event.thing.uid} added.")
# end
# end
def thing_added(attach: nil)
@ruby_triggers << [:thing_added]
event("openhab/things/*/added", types: "ThingAddedEvent", attach: attach)
def thing_added(pattern = "*", attach: nil)
@ruby_triggers << [:thing_added, pattern]
event("openhab/things/#{pattern}/added", types: "ThingAddedEvent", attach: attach)
end

#
# Creates a thing removed trigger
#
# @param [String, nil] pattern The pattern to match things against
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for pattern filter was added
#
# @example
# rule "thing removed" do
# thing_removed
# run do |event|
# logger.info("#{event.thing.uid} removed.")
# end
# end
def thing_removed(attach: nil)
@ruby_triggers << [:thing_removed]
event("openhab/things/*/removed", types: "ThingRemovedEvent", attach: attach)
def thing_removed(pattern = "*", attach: nil)
@ruby_triggers << [:thing_removed, pattern]
event("openhab/things/#{pattern}/removed", types: "ThingRemovedEvent", attach: attach)
end

#
# Creates a thing updated trigger
#
# @param [String, nil] pattern The pattern to match things against
# @param [Object] attach object to be attached to the trigger
# @return [void]
#
# @since openHAB 4.0 Support for pattern filter was added
#
# @example
# rule "thing updated" do
# thing_updated
Expand All @@ -1658,9 +1686,9 @@ def thing_removed(attach: nil)
# end
# end
#
def thing_updated(attach: nil)
@ruby_triggers << [:thing_updated]
event("openhab/things/*/updated", types: "ThingUpdatedEvent", attach: attach)
def thing_updated(pattern = "*", attach: nil)
@ruby_triggers << [:thing_updated, pattern]
event("openhab/things/#{pattern}/updated", types: "ThingUpdatedEvent", attach: attach)
end

#
Expand Down
103 changes: 103 additions & 0 deletions spec/openhab/dsl/rules/builder_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -741,6 +741,49 @@ def self.test_channel_trigger(channel = nil, event: "", &block)
expect(linked_item).to be StringItem1
expect(linked_thing).to be things["astro:sun:home"]
end

context "with filtering", if: OpenHAB::Core.version >= OpenHAB::Core::V4_0 do
it "filters by item" do
linked_item = linked_thing = nil
channel_linked(item: "StringItem1") do |event|
linked_item = event.link.item
linked_thing = event.link.channel_uid.thing
end

items.build { string_item "StringItem1", channel: "astro:sun:home:season#name" }

expect(linked_item).to be StringItem1
expect(linked_thing).to be things["astro:sun:home"]
end

it "filters by channel" do
linked_item = linked_channel = nil
channel_linked(channel: "astro:sun:home:season#name") do |event|
linked_item = event.link.item
linked_channel = event.link.channel_uid
end

items.build { string_item "StringItem1", channel: "astro:sun:home:season#name" }
StringItem1.link("astro:sun:home:zodiac#sign")

expect(linked_item).to be StringItem1
expect(linked_channel).to eq "astro:sun:home:season#name"
end

it "filters by item and channel" do
linked_item = linked_channel = nil
channel_linked(item: "StringItem1", channel: "astro:sun:home:season#name") do |event|
linked_item = event.link.item
linked_channel = event.link.channel_uid
end

items.build { string_item "StringItem1", channel: "astro:sun:home:season#name" }
StringItem1.link("astro:sun:home:zodiac#sign")

expect(linked_item).to be StringItem1
expect(linked_channel).to eq "astro:sun:home:season#name"
end
end
end

describe "#received_command" do
Expand Down Expand Up @@ -847,6 +890,20 @@ def self.test_command_trigger(item, members: false, command: nil, expect_trigger

expect(new_item.name).to eql "Item1"
end

it "supports pattern filter", if: OpenHAB::Core.version >= OpenHAB::Core::V4_0 do
new_item = nil
item_added("Item1") do |event|
new_item = event.item
end

items.build { switch_item Item1 }
expect(new_item.name).to eql "Item1"

new_item = nil
items.build { switch_item Item2 }
expect(new_item).to be_nil
end
end

describe "#item_removed" do
Expand All @@ -861,6 +918,22 @@ def self.test_command_trigger(item, members: false, command: nil, expect_trigger

expect(removed_item.name).to eql "Item1"
end

it "supports pattern filter", if: OpenHAB::Core.version >= OpenHAB::Core::V4_0 do
removed_item = nil
item_removed("Item1") do |event|
removed_item = event.item
end

items.build { switch_item Item1 }
items.remove(Item1)
expect(removed_item.name).to eql "Item1"

removed_item = nil
items.build { switch_item Item2 }
items.remove(Item2)
expect(removed_item).to be_nil
end
end

describe "#thing_added" do
Expand All @@ -874,6 +947,20 @@ def self.test_command_trigger(item, members: false, command: nil, expect_trigger

expect(new_thing.uid).to eql "astro:sun:home"
end

it "supports pattern filter", if: OpenHAB::Core.version >= OpenHAB::Core::V4_0 do
new_thing = nil
thing_added("astro:sun:home") do |event|
new_thing = event.thing
end

things.build { thing "astro:sun:home", config: { "geolocation" => "0,0" } }
expect(new_thing.uid).to eql "astro:sun:home"

new_thing = nil
things.build { thing "astro:sun:home2", config: { "geolocation" => "0,0" } }
expect(new_thing).to be_nil
end
end

describe "#thing_removed" do
Expand All @@ -888,6 +975,22 @@ def self.test_command_trigger(item, members: false, command: nil, expect_trigger

expect(removed_thing.uid).to eql "astro:sun:home"
end

it "supports pattern filter", if: OpenHAB::Core.version >= OpenHAB::Core::V4_0 do
removed_thing = nil
thing_removed("astro:sun:home") do |event|
removed_thing = event.thing
end

things.build { thing "astro:sun:home", config: { "geolocation" => "0,0" } }
things.remove("astro:sun:home")
expect(removed_thing.uid).to eql "astro:sun:home"

removed_thing = nil
things.build { thing "astro:sun:home2", config: { "geolocation" => "0,0" } }
things.remove("astro:sun:home2")
expect(removed_thing).to be_nil
end
end

describe "#updated" do
Expand Down

0 comments on commit c360146

Please sign in to comment.