rzwaveway 0.0.11 → 0.0.13

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
  SHA1:
3
- metadata.gz: 01e99f245086e41fbeca9e16d6c0c6867324906d
4
- data.tar.gz: adc57ec22b54fb1f084b2adc44bbcde9835fb3c8
3
+ metadata.gz: 6f5e0b677ce1728466c714be10191c2fea92bc97
4
+ data.tar.gz: b07f33865fb9ac752453ef12efcccfa3f206d120
5
5
  SHA512:
6
- metadata.gz: 54c2f9b32d733c49a8e5022e452cc8d16c828f9b7eab5da5436db7dab2c15b73f7391378895f163b17bc6558a46dd13c3330e033a255d9b8fc23d0a973264687
7
- data.tar.gz: 7c1b8a78ebd3e5942b86e576b9e2323089b865c73dff680c7edd031c0c096e50afed5aa469db3853523b8911e640a53567e2ad8affbee8b55f10652f934e6486
6
+ metadata.gz: e0043ffd5ae35ceaaea940771f828e1662256d9a145ae9440dcd7d53a03f4ce604ec5a7ebdfc7ec09855062bdbb24729865638f95f7c56d665a56341aec8dba5
7
+ data.tar.gz: b9d79401b008fe87b9ba484602fe4c7c7f3027d7dcc7ae210c328cb7fa6ebca8e29f632b27ec0dce053cc909283116652920c231230436e8ae8d0b23f34427c5
data/README.md CHANGED
@@ -10,7 +10,7 @@ A Ruby library for communicating with the ZWave protocol stack from ZWay, runnin
10
10
  require 'rzwaveway'
11
11
 
12
12
  z_way = RZWaveWay::ZWay.instance
13
- z_way.setup('192.168.1.123')
13
+ z_way.setup(hostname: '192.168.1.123', port: 8083)
14
14
  z_way.start
15
15
  ```
16
16
 
@@ -27,7 +27,7 @@ z_way.on_event(RZWaveWay::AliveEvent) {|event| puts "A device woke up" }
27
27
  z_way.on_event(RZWaveWay::LevelEvent) {|event| puts "A device got triggered" }
28
28
  while true do
29
29
  sleep 5
30
- z_way.process_events
30
+ z_way.process
31
31
  end
32
32
  ```
33
33
 
@@ -40,6 +40,6 @@ or
40
40
 
41
41
  ```
42
42
  switch = z_way.devices[4]
43
- switch.SwitchBinary.set(1)
44
- switch.SwitchBinary.set(0)
43
+ switch.SwitchBinary.level = 1
44
+ switch.SwitchBinary.level = 0
45
45
  ```
@@ -1,6 +1,8 @@
1
+ require_relative 'rzwaveway/logger'
2
+ require_relative 'rzwaveway/property'
3
+ require_relative 'rzwaveway/properties_cache'
1
4
  require_relative 'rzwaveway/command_classes'
2
5
  require_relative 'rzwaveway/events'
3
- require_relative 'rzwaveway/logger'
4
6
  require_relative 'rzwaveway/zwave_device'
5
7
  require_relative 'rzwaveway/zway'
6
8
  require_relative 'rzwaveway/extensions'
@@ -1,29 +1,40 @@
1
1
  module RZWaveWay
2
- module CommandClass
2
+ class CommandClass
3
+ include Logger
4
+ include PropertiesCache
5
+
3
6
  BASIC = 32
4
7
  SWITCH_BINARY = 37
5
8
  SWITCH_MULTI_LEVEL = 38
6
9
  SENSOR_BINARY = 48
7
10
  SENSOR_MULTI_LEVEL = 49
11
+ METER = 50
8
12
  CONFIGURATION = 112
9
13
  ALARM = 113
14
+ NOTIFICATION = ALARM
10
15
  MANUFACTURER_SPECIFIC = 114
11
16
  BATTERY = 128
12
17
  WAKEUP = 132
13
18
  ASSOCIATION = 133
14
19
  VERSION = 134
20
+ SECURITY = 152
15
21
  ALARM_SENSOR = 156
16
22
 
17
- private
23
+ attr_reader :device
24
+
25
+ def initialize(device)
26
+ @device = device
27
+ end
28
+
29
+ def build_from(data)
30
+ end
18
31
 
19
- def find(name, data)
20
- parts = name.split '.'
21
- result = data
22
- parts.each do | part |
23
- raise "Could not find part '#{part}' in '#{name}'" unless result.has_key? part
24
- result = result[part]
25
- end
26
- result
32
+ def name
33
+ self.class.name.split('::').last
34
+ end
35
+
36
+ def to_s
37
+ name
27
38
  end
28
39
  end
29
40
  end
@@ -1,6 +1,8 @@
1
1
  require 'singleton'
2
2
 
3
3
  require_relative 'command_class'
4
+ require_relative 'command_classes/alarm'
5
+ require_relative 'command_classes/alarm_sensor'
4
6
  require_relative 'command_classes/battery'
5
7
  require_relative 'command_classes/switch_binary'
6
8
  require_relative 'command_classes/switch_multi_level'
@@ -9,36 +11,48 @@ require_relative 'command_classes/wake_up'
9
11
 
10
12
  module RZWaveWay
11
13
  module CommandClasses
12
- class Dummy
14
+ class Unsupported
13
15
  include Singleton
14
16
 
15
- def initialize
17
+ def build_from(data)
16
18
  end
17
19
 
18
20
  def process(updates)
19
21
  end
22
+
23
+ def save_properties
24
+ end
25
+
26
+ def to_hash
27
+ {}
28
+ end
29
+
30
+ def to_s
31
+ 'Unsupported'
32
+ end
20
33
  end
21
34
 
22
35
  class Factory
23
36
  include Singleton
24
- include CommandClass
25
37
 
26
- def instantiate(id, data, device)
38
+ def instantiate(id, device)
27
39
  if CLASSES.has_key? id
28
- return CLASSES[id].new(data, device)
40
+ CLASSES[id].new(device)
29
41
  else
30
- return CommandClasses::Dummy.instance
42
+ CommandClasses::Unsupported.instance
31
43
  end
32
44
  end
33
45
 
34
46
  private
35
47
 
36
48
  CLASSES = {
37
- SWITCH_BINARY => CommandClasses::SwitchBinary,
38
- SWITCH_MULTI_LEVEL => CommandClasses::SwitchMultiLevel,
39
- SENSOR_BINARY => CommandClasses::SensorBinary,
40
- WAKEUP => CommandClasses::WakeUp,
41
- BATTERY => CommandClasses::Battery
49
+ CommandClass::SWITCH_BINARY => CommandClasses::SwitchBinary,
50
+ CommandClass::SWITCH_MULTI_LEVEL => CommandClasses::SwitchMultiLevel,
51
+ CommandClass::SENSOR_BINARY => CommandClasses::SensorBinary,
52
+ CommandClass::WAKEUP => CommandClasses::WakeUp,
53
+ CommandClass::ALARM => CommandClasses::Alarm,
54
+ CommandClass::ALARM_SENSOR => CommandClasses::AlarmSensor,
55
+ CommandClass::BATTERY => CommandClasses::Battery
42
56
  }
43
57
  end
44
58
  end
@@ -0,0 +1,43 @@
1
+ module RZWaveWay
2
+ module CommandClasses
3
+ class Alarm < CommandClass
4
+
5
+ def process(updates)
6
+ updates.each do |key, value|
7
+ if key == 'data.V1event'
8
+ alarm_type = value['alarmType']['value']
9
+ yield AlarmEvent.new(device_id: device.id,
10
+ time: value['updateTime'],
11
+ alarm_type: ALARM_TYPES[alarm_type],
12
+ level: value['level']['value'])
13
+ else
14
+ match_data = key.match(/^data.(\d+)/)
15
+ if match_data
16
+ alarm_type = match_data[1].to_i
17
+ yield AlarmEvent.new(device_id: device.id,
18
+ time: value['updateTime'],
19
+ alarm_type: ALARM_TYPES[alarm_type],
20
+ level: value['event']['value'])
21
+ end
22
+ end
23
+ end
24
+ end
25
+
26
+ private
27
+
28
+ ALARM_TYPES = {
29
+ 0x01 => :smoke,
30
+ 0x02 => :co,
31
+ 0x03 => :co2,
32
+ 0x04 => :heat,
33
+ 0x05 => :water,
34
+ 0x06 => :access_control,
35
+ 0x07 => :burglar,
36
+ 0x08 => :power_management,
37
+ 0x09 => :system,
38
+ 0x0a => :emergency,
39
+ 0x0b => :clock
40
+ }
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,17 @@
1
+ module RZWaveWay
2
+ module CommandClasses
3
+ class AlarmSensor < CommandClass
4
+ GENERAL_PURPOSE = 0x00
5
+ SMOKE = 0x01
6
+ CO = 0x02
7
+ CO2 = 0x03
8
+ HEAT = 0x04
9
+ WATER_LEAK = 0x05
10
+
11
+ def process(updates)
12
+ log.info updates
13
+ nil
14
+ end
15
+ end
16
+ end
17
+ end
@@ -1,28 +1,24 @@
1
1
  module RZWaveWay
2
2
  module CommandClasses
3
- class Battery
4
- include CommandClass
3
+ class Battery < CommandClass
5
4
 
6
- def initialize(data, device)
7
- @device = device
8
- @device.add_property(name: :battery_level,
9
- value: find('data.last.value', data),
10
- update_time: find('data.last.updateTime', data))
5
+ def build_from(data)
6
+ define_property(:battery_level, 'data.last', true, data)
11
7
  end
12
8
 
13
9
  def process(updates)
14
10
  if updates.keys.include?('data.last')
15
11
  data = updates['data.last']
16
12
  value = data['value']
17
- updateTime = data['updateTime']
18
- if @device.update_property(:battery_level, value, updateTime)
19
- return BatteryValueEvent.new(@device.id, updateTime, value)
13
+ update_time = data['updateTime']
14
+ if @properties[:battery_level].update(value, update_time)
15
+ yield BatteryValueEvent.new(device_id: device.id, time: update_time, value: value)
20
16
  end
21
17
  end
22
18
  end
23
19
 
24
- def get
25
- RZWaveWay::ZWay.instance.execute(@device.id, BATTERY, :Get)
20
+ def refresh
21
+ RZWaveWay::ZWay.instance.execute(device.id, BATTERY, :Get)
26
22
  end
27
23
  end
28
24
  end
@@ -1,32 +1,24 @@
1
1
  module RZWaveWay
2
2
  module CommandClasses
3
- class SensorBinary
4
- include CommandClass
3
+ class SensorBinary < CommandClass
5
4
 
6
- def initialize(data, device)
7
- @device = device
8
- @device.add_property(name: :level,
9
- value: find('data.1.level.value', data),
10
- update_time: find('data.1.level.updateTime', data))
5
+ def build_from(data)
6
+ define_property(:level, 'data.1.level', true, data)
11
7
  end
12
8
 
13
9
  def process(updates)
14
10
  if updates.keys.include?('data.1')
15
11
  data = updates['data.1']['level']
16
12
  value = data['value']
17
- updateTime = data['updateTime']
18
- if @device.update_property(:level, value, updateTime)
19
- return LevelEvent.new(@device.id, updateTime, value)
13
+ update_time = data['updateTime']
14
+ if @properties[:level].update(value, update_time)
15
+ yield LevelEvent.new(device_id: device.id, time: update_time, level: value)
20
16
  end
21
17
  end
22
18
  end
23
19
 
24
- def level
25
- @device.get_property(:level)[0]
26
- end
27
-
28
- def get
29
- RZWaveWay::ZWay.instance.execute(@device.id, SENSOR_BINARY, :Get)
20
+ def refresh
21
+ RZWaveWay::ZWay.instance.execute(device.id, SENSOR_BINARY, :Get)
30
22
  end
31
23
  end
32
24
  end
@@ -1,37 +1,28 @@
1
1
  module RZWaveWay
2
2
  module CommandClasses
3
- class SwitchBinary
4
- include CommandClass
3
+ class SwitchBinary < CommandClass
5
4
 
6
- def initialize(data, device)
7
- @device = device
8
- @device.add_property(name: :level,
9
- value: find('data.level.value', data),
10
- update_time: find('data.level.updateTime', data),
11
- read_only: false)
5
+ def build_from(data)
6
+ define_property(:level, 'data.level', false, data)
12
7
  end
13
8
 
14
9
  def process(updates)
15
10
  if updates.keys.include?('data.level')
16
11
  data = updates['data.level']
17
12
  value = data['value']
18
- updateTime = data['updateTime']
19
- if @device.update_property(:level, value, updateTime)
20
- return LevelEvent.new(@device.id, updateTime, value)
13
+ update_time = data['updateTime']
14
+ if @properties[:level].update(value, update_time)
15
+ yield LevelEvent.new(device_id: device.id, time: update_time, level: value)
21
16
  end
22
17
  end
23
18
  end
24
19
 
25
- def level
26
- @device.get_property(:level)[0]
20
+ def level=(value)
21
+ RZWaveWay::ZWay.instance.execute(device.id, SWITCH_BINARY, :Set, value)
27
22
  end
28
23
 
29
- def get
30
- RZWaveWay::ZWay.instance.execute(@device.id, SWITCH_BINARY, :Get)
31
- end
32
-
33
- def set(value)
34
- RZWaveWay::ZWay.instance.execute(@device.id, SWITCH_BINARY, :Set, value)
24
+ def refresh
25
+ RZWaveWay::ZWay.instance.execute(device.id, SWITCH_BINARY, :Get)
35
26
  end
36
27
  end
37
28
  end
@@ -1,37 +1,28 @@
1
1
  module RZWaveWay
2
2
  module CommandClasses
3
- class SwitchMultiLevel
4
- include CommandClass
3
+ class SwitchMultiLevel < CommandClass
5
4
 
6
- def initialize(data, device)
7
- @device = device
8
- @device.add_property(name: :level,
9
- value: find('data.level.value', data),
10
- update_time: find('data.level.updateTime', data),
11
- read_only: false)
5
+ def build_from(data)
6
+ define_property(:level, 'data.level', false, data)
12
7
  end
13
8
 
14
9
  def process(updates)
15
10
  if updates.keys.include?('data.level')
16
11
  data = updates['data.level']
17
12
  value = data['value']
18
- updateTime = data['updateTime']
19
- if @device.update_property(:level, value, updateTime)
20
- return MultiLevelEvent.new(@device.id, updateTime, value)
13
+ update_time = data['updateTime']
14
+ if @properties[:level].update(value, update_time)
15
+ yield MultiLevelEvent.new(device_id: device.id, time: update_time, level: value)
21
16
  end
22
17
  end
23
18
  end
24
19
 
25
- def level
26
- @device.get_property(:level)[0]
20
+ def level=(value)
21
+ RZWaveWay::ZWay.instance.execute(device.id, SWITCH_MULTI_LEVEL, :Set, value)
27
22
  end
28
23
 
29
- def get
30
- RZWaveWay::ZWay.instance.execute(@device.id, SWITCH_MULTI_LEVEL, :Get)
31
- end
32
-
33
- def set(value)
34
- RZWaveWay::ZWay.instance.execute(@device.id, SWITCH_MULTI_LEVEL, :Set, value)
24
+ def refresh
25
+ RZWaveWay::ZWay.instance.execute(device.id, SWITCH_MULTI_LEVEL, :Get)
35
26
  end
36
27
  end
37
28
  end
@@ -1,44 +1,41 @@
1
1
  module RZWaveWay
2
2
  module CommandClasses
3
- class WakeUp
4
- include CommandClass
3
+ class WakeUp < CommandClass
5
4
 
6
- def initialize(data, device)
7
- @device = device
8
- wakeup_interval = find('data.interval.value', data)
9
- last_wakeup_time = find('data.lastWakeup.value', data)
10
- last_sleep_time = find('data.lastSleep.value', data)
5
+ def build_from(data)
6
+ define_property(:contact_frequency, 'data.interval', true, data)
7
+ define_property(:last_sleep_time, 'data.lastSleep', true, data)
8
+ define_property(:last_wakeup_time, 'data.lastWakeup', true, data)
11
9
 
12
- @device.add_property(name: :wakeup_interval,
13
- value: wakeup_interval,
14
- update_time: find('data.interval.updateTime', data),
15
- internal: true)
16
- @device.add_property(name: :wakeup_last_sleep_time,
17
- value: last_sleep_time,
18
- update_time: find('data.lastSleep.updateTime', data),
19
- internal: true)
20
- @device.add_property(name: :wakeup_last_wakeup_time,
21
- value: last_wakeup_time,
22
- update_time: find('data.lastWakeup.updateTime', data),
23
- internal: true)
10
+ device.notify_contacted(find('data.lastWakeup.value', data))
11
+ end
12
+
13
+ def missed_contact_count(time = Time.now)
14
+ (elapsed_seconds_since_last_contact(time) / contact_frequency).to_i
15
+ end
24
16
 
25
- @device.contact_frequency = wakeup_interval
26
- @device.notify_contacted(last_wakeup_time)
17
+ def on_time?(time = Time.now)
18
+ elapsed_seconds_since_last_contact(time) < (contact_frequency * 1.2)
27
19
  end
28
20
 
29
21
  def process(updates)
30
22
  if updates.keys.include?('data.lastWakeup')
31
23
  data = updates['data.lastWakeup']
32
24
  value = data['value']
33
- updateTime = data['updateTime']
34
- if @device.update_property(:wakeup_last_wakeup_time, value, updateTime)
35
- @device.notify_contacted(value)
36
- return AliveEvent.new(@device.id, value)
25
+ update_time = data['updateTime']
26
+ if @properties[:last_wakeup_time].update(value, update_time)
27
+ device.notify_contacted(value)
37
28
  end
38
29
  end
39
-
30
+ nil
40
31
  # TODO handle change of wake up interval value?
41
32
  end
33
+
34
+ private
35
+
36
+ def elapsed_seconds_since_last_contact(time)
37
+ time.to_i - device.last_contact_time
38
+ end
42
39
  end
43
40
  end
44
41
  end