waterfurnace_aurora 0.7.4 → 0.8.0

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: f33824465f3bfc29c667d454742a8e25a4ed01a43670d949bba6a47b981ebd1b
4
- data.tar.gz: 3339f23b9eeb86052b6cfe3b9acdbe2c0adfc497b3e8b43dca6fa957958c56d5
3
+ metadata.gz: 288c8dbc14788d26473f14dcfaf388f75c8aee92c2f3b4d388bfa8326cfd2842
4
+ data.tar.gz: c06f92936c81e402d08e01ae6b8c6c573acca46a85c9630914cb3c69f125a56a
5
5
  SHA512:
6
- metadata.gz: 3c73eb53d65545ef60c46976c81d51546e3d11497a13383d7ac1786bc14dcb462b716fd7cddd78958299922095a0314f59cda8f037644cab333f6363278ceadf
7
- data.tar.gz: 43d6f2829a50f71ef586412c918a37c7bb8a8549abac1ddf54c4a2e85a15e0683d1ed1e9d9e82e8e746d9e6168d2b5fe247e4e9cfc1b47457d91978a9b1c5e98
6
+ metadata.gz: 5e64658afee912c8188af6d88bc98e208427b8dc4ef2ce1ea6ff1efcaca15ea2042ed4eef08ccfd764ec59ce0bb82013b0abd82173ec00f9ec61cbde07a66634
7
+ data.tar.gz: 6deff29644f83c329f1727d0a568c87536618ae63c7a27e58e4054eff187496c6f04bf3b63e2c35e649b2a0eb5b6395d81450a68b0096d1cacee9137c2f53c31
data/exe/aurora_fetch CHANGED
@@ -9,11 +9,19 @@ require "uri"
9
9
  require "yaml"
10
10
 
11
11
  debug_modbus = yaml = false
12
+ try_individual = nil
12
13
 
13
14
  options = OptionParser.new do |opts|
14
15
  opts.banner = "Usage: aurora_fetch /path/to/serial/port REGISTERS [options]"
15
16
 
17
+ opts.separator("")
18
+ opts.separator("Use `known` to fetch all identified registers. Use `valid` to fetch all registers that will respond.")
19
+ opts.separator("")
20
+
16
21
  opts.on("--debug-modbus", "Print actual protocol bytes") { debug_modbus = true }
22
+ opts.on("--[no-]try-individual",
23
+ "Query registers one-by-one if a range has an illegal address. " \
24
+ "Defaults to true for `valid` and `known` special registers, false otherwise.") { |v| try_individual = v }
17
25
  opts.on("-y", "--yaml", "Output raw values as YAML") { yaml = true }
18
26
  opts.on("-v", "--version", "Print version") do
19
27
  puts Aurora::VERSION
@@ -32,11 +40,13 @@ unless ARGV.length == 2
32
40
  exit 1
33
41
  end
34
42
 
35
- abc = Aurora::ABCClient.new(ARGV[0])
36
- abc.modbus_slave.logger = Logger.new($stdout)
37
- abc.modbus_slave.logger.level = debug_modbus ? :debug : :warn
43
+ modbus_slave = Aurora::ABCClient.open_modbus_slave(ARGV[0])
44
+ modbus_slave.read_retry_timeout = 15
45
+ modbus_slave.read_retries = 2
46
+ modbus_slave.logger = Logger.new($stdout)
47
+ modbus_slave.logger.level = debug_modbus ? :debug : :warn
38
48
 
39
- registers = abc.query_registers(ARGV[1])
49
+ registers = Aurora::ABCClient.query_registers(modbus_slave, ARGV[1], try_individual: try_individual)
40
50
 
41
51
  if yaml
42
52
  puts YAML.dump(registers)
@@ -155,14 +155,16 @@ class MQTTBridge
155
155
  hass: { sensor: { device_class: :temperature,
156
156
  state_class: :measurement,
157
157
  entity_category: :diagnostic } })
158
- node.property("leaving-air-temperature",
159
- "Leaving Air Temperature",
160
- :float,
161
- @abc.leaving_air_temperature,
162
- unit: "°F",
163
- hass: { sensor: { device_class: :temperature,
164
- state_class: :measurement,
165
- entity_category: :diagnostic } })
158
+ if @abc.awl_communicating?
159
+ node.property("leaving-air-temperature",
160
+ "Leaving Air Temperature",
161
+ :float,
162
+ @abc.leaving_air_temperature,
163
+ unit: "°F",
164
+ hass: { sensor: { device_class: :temperature,
165
+ state_class: :measurement,
166
+ entity_category: :diagnostic } })
167
+ end
166
168
  node.property("leaving-water-temperature",
167
169
  "Leaving Water Temperature",
168
170
  :float,
@@ -171,7 +173,8 @@ class MQTTBridge
171
173
  hass: { sensor: { device_class: :temperature,
172
174
  state_class: :measurement,
173
175
  entity_category: :diagnostic } })
174
- unless @abc.outdoor_temperature.zero? # TODO: figure out the config if this actually exists
176
+ # TODO: figure out the config if this actually exists
177
+ if @abc.awl_communicating? && !@abc.outdoor_temperature.zero?
175
178
  node.property("outdoor-temperature",
176
179
  "Outdoor Temperature",
177
180
  :float,
@@ -181,6 +184,14 @@ class MQTTBridge
181
184
  state_class: :measurement } })
182
185
  end
183
186
 
187
+ node.property("line-voltage",
188
+ "Line Voltage Setting",
189
+ :integer,
190
+ @abc.line_voltage,
191
+ format: 90..635,
192
+ unit: "V") do |value, property|
193
+ @mutex.synchronize { property.value = @abc.line_voltage = value }
194
+ end
184
195
  node.property("fp1",
185
196
  "FP1 Sensor",
186
197
  :float,
@@ -325,15 +336,6 @@ class MQTTBridge
325
336
  :boolean,
326
337
  @abc.pump.running,
327
338
  hass: { binary_sensor: { device_class: :running } })
328
- node.property("speed",
329
- "Speed",
330
- :integer,
331
- @abc.pump.speed,
332
- format: 0..100,
333
- unit: "%",
334
- hass: { number: { entity_category: :diagnostic } }) do |value, property|
335
- @mutex.synchronize { property.value = @abc.pump.speed = value }
336
- end
337
339
  node.property("manual-control",
338
340
  "Manual Control",
339
341
  :boolean,
@@ -359,6 +361,17 @@ class MQTTBridge
359
361
  hass: { number: { entity_category: :config } }) do |value, property|
360
362
  @mutex.synchronize { property.value = @abc.pump.maximum_speed = value }
361
363
  end
364
+ next unless @abc.awl_axb?
365
+
366
+ node.property("speed",
367
+ "Speed",
368
+ :integer,
369
+ @abc.pump.speed,
370
+ format: 0..100,
371
+ unit: "%",
372
+ hass: { number: { entity_category: :diagnostic } }) do |value, property|
373
+ @mutex.synchronize { property.value = @abc.pump.speed = value }
374
+ end
362
375
  end
363
376
 
364
377
  if @abc.dhw
@@ -388,47 +401,41 @@ class MQTTBridge
388
401
  @abc.dhw.set_point,
389
402
  format: 100..140,
390
403
  unit: "°F",
391
- hass: :number) do |value, property|
404
+ hass: { number: { step: 5 } }) do |value, property|
392
405
  @mutex.synchronize { property.value = @abc.dhw.set_point = value }
393
406
  end
394
407
  end
395
408
  end
396
409
 
397
410
  @humidistat = @homie.node("humidistat", "Humidistat", "Humidistat") do |node|
398
- node.property("relative-humidity",
399
- "Relative Humidity",
400
- :integer,
401
- @abc.humidistat.relative_humidity,
402
- unit: "%",
403
- format: 0..100,
404
- hass: { sensor: { device_class: :humidity,
405
- state_class: :measurement } })
406
411
  if @abc.humidistat.humidifier?
407
412
  node.property("humidifier-running",
408
413
  "Humidifier Running",
409
414
  :boolean,
410
415
  @abc.humidistat.humidifier_running?)
411
- node.property("humidifier-mode",
412
- "Humidifier Mode",
413
- :enum,
414
- @abc.humidistat.humidifier_mode,
415
- format: %i[auto manual]) do |value, property|
416
- @mutex.synchronize { property.value = @abc.humidistat.humidifier_mode = value.to_sym }
417
- end
418
- node.property("humidification-target",
419
- "Humidification Target Relative Humidity",
420
- :integer,
421
- @abc.humidistat.humidification_target,
422
- unit: "%",
423
- format: 15..50) do |value, property|
424
- @mutex.synchronize { property.value = @abc.humidistat.humidification_target = value }
416
+ if @abc.awl_communicating?
417
+ node.property("humidifier-mode",
418
+ "Humidifier Mode",
419
+ :enum,
420
+ @abc.humidistat.humidifier_mode,
421
+ format: %i[auto manual]) do |value, property|
422
+ @mutex.synchronize { property.value = @abc.humidistat.humidifier_mode = value.to_sym }
423
+ end
424
+ node.property("humidification-target",
425
+ "Humidification Target Relative Humidity",
426
+ :integer,
427
+ @abc.humidistat.humidification_target,
428
+ unit: "%",
429
+ format: 15..50) do |value, property|
430
+ @mutex.synchronize { property.value = @abc.humidistat.humidification_target = value }
431
+ end
432
+ node.hass_humidifier("humidifier-running",
433
+ target_property: "humidification-target",
434
+ mode_property: "humidifier-mode",
435
+ id: "humidifier",
436
+ name: "Humidifier",
437
+ device_class: :humidifier)
425
438
  end
426
- node.hass_humidifier("humidifier-running",
427
- target_property: "humidification-target",
428
- mode_property: "humidifier-mode",
429
- id: "humidifier",
430
- name: "Humidifier",
431
- device_class: :humidifier)
432
439
  end
433
440
 
434
441
  # VSDrive can perform active dehumidification, even without a dedicated dehumidifier
@@ -438,28 +445,40 @@ class MQTTBridge
438
445
  "Dehumidifier Running",
439
446
  :boolean,
440
447
  @abc.humidistat.dehumidifier_running?)
441
- node.property("dehumidifier-mode",
442
- "Dehumidifier Mode",
443
- :enum,
444
- @abc.humidistat.dehumidifier_mode,
445
- format: %i[auto manual]) do |value, property|
446
- @mutex.synchronize { property.value = @abc.humidistat.dehumidifier_mode = value.to_sym }
447
- end
448
- node.property("dehumidification-target",
449
- "Dehumidification Target Relative Humidity",
450
- :integer,
451
- @abc.humidistat.dehumidification_target,
452
- unit: "%",
453
- format: 35..65) do |value, property|
454
- @mutex.synchronize { property.value = @abc.humidistat.dehumidification_target = value }
448
+ if @abc.awl_communicating?
449
+ node.property("dehumidifier-mode",
450
+ "Dehumidifier Mode",
451
+ :enum,
452
+ @abc.humidistat.dehumidifier_mode,
453
+ format: %i[auto manual]) do |value, property|
454
+ @mutex.synchronize { property.value = @abc.humidistat.dehumidifier_mode = value.to_sym }
455
+ end
456
+ node.property("dehumidification-target",
457
+ "Dehumidification Target Relative Humidity",
458
+ :integer,
459
+ @abc.humidistat.dehumidification_target,
460
+ unit: "%",
461
+ format: 35..65) do |value, property|
462
+ @mutex.synchronize { property.value = @abc.humidistat.dehumidification_target = value }
463
+ end
464
+ node.hass_humidifier("dehumidifier-running",
465
+ target_property: "dehumidification-target",
466
+ mode_property: "dehumidifier-mode",
467
+ id: "dehumidifier",
468
+ name: "Dehumidifier",
469
+ device_class: :dehumidifier)
455
470
  end
456
- node.hass_humidifier("dehumidifier-running",
457
- target_property: "dehumidification-target",
458
- mode_property: "dehumidifier-mode",
459
- id: "dehumidifier",
460
- name: "Dehumidifier",
461
- device_class: :dehumidifier)
462
471
  end
472
+ next unless @abc.awl_communicating?
473
+
474
+ node.property("relative-humidity",
475
+ "Relative Humidity",
476
+ :integer,
477
+ @abc.humidistat.relative_humidity,
478
+ unit: "%",
479
+ format: 0..100,
480
+ hass: { sensor: { device_class: :humidity,
481
+ state_class: :measurement } })
463
482
  end
464
483
 
465
484
  @faults = @homie.node("faults", "Fault History", "ABC") do |node|
@@ -487,6 +506,14 @@ class MQTTBridge
487
506
  @abc.zones.each_with_index do |zone, i|
488
507
  type = zone.is_a?(Aurora::IZ2Zone) ? "IntelliZone 2 Zone" : "Thermostat"
489
508
  @homie.node("zone#{i + 1}", "Zone #{i + 1}", type) do |node|
509
+ node.property("current-mode",
510
+ "Current Heating/Cooling Mode Requested",
511
+ :enum,
512
+ zone.current_mode,
513
+ format: %w[standby h1 h2 h3 c1 c2])
514
+
515
+ next unless @abc.awl_communicating?
516
+
490
517
  allowed_modes = %w[off auto cool heat]
491
518
  allowed_modes << "eheat" if i.zero?
492
519
  node.property("target-mode",
@@ -496,11 +523,6 @@ class MQTTBridge
496
523
  format: allowed_modes) do |value, property|
497
524
  @mutex.synchronize { property.value = zone.target_mode = value.to_sym }
498
525
  end
499
- node.property("current-mode",
500
- "Current Heating/Cooling Mode Requested",
501
- :enum,
502
- zone.current_mode,
503
- format: %w[standby h1 h2 h3 c1 c2])
504
526
  node.property("target-fan-mode",
505
527
  "Target Fan Mode",
506
528
  :enum,
@@ -40,9 +40,53 @@ module Aurora
40
40
  client = ::ModBus::RTUClient.new(io)
41
41
  client.with_slave(1)
42
42
  end
43
+
44
+ def query_registers(modbus_slave, query, try_individual: false)
45
+ implicit = try_individual
46
+ ranges = query.split(",").map do |addr|
47
+ case addr
48
+ when "known"
49
+ implicit = true
50
+ try_individual = true if try_individual.nil?
51
+ Aurora::REGISTER_NAMES.keys
52
+ when "valid"
53
+ implicit = true
54
+ try_individual = true if try_individual.nil?
55
+ break Aurora::REGISTER_RANGES
56
+ when /^(\d+)(?:\.\.|-)(\d+)$/
57
+ $1.to_i..$2.to_i
58
+ else
59
+ addr.to_i
60
+ end
61
+ end
62
+ queries = Aurora.normalize_ranges(ranges)
63
+ registers = {}
64
+ queries.each do |subquery|
65
+ registers.merge!(modbus_slave.read_multiple_holding_registers(*subquery))
66
+ rescue ::ModBus::Errors::IllegalDataAddress, ::ModBus::Errors::IllegalFunction
67
+ # maybe this unit doesn't respond to all the addresses we want?
68
+ raise unless implicit
69
+
70
+ # try each query individually
71
+ subquery.each do |subsubquery|
72
+ registers.merge!(modbus_slave.read_multiple_holding_registers(subsubquery))
73
+ rescue ::ModBus::Errors::IllegalDataAddress, ::ModBus::Errors::IllegalFunction
74
+ next unless try_individual
75
+
76
+ # seriously?? try each register individually
77
+ subsubquery.each do |i|
78
+ registers[i] = modbus_slave.holding_registers[i]
79
+ rescue ::ModBus::Errors::IllegalDataAddress, ::ModBus::Errors::IllegalFunction
80
+ next
81
+ end
82
+ end
83
+ end
84
+ registers
85
+ end
43
86
  end
44
87
 
45
88
  attr_reader :modbus_slave,
89
+ :abc_version,
46
90
  :model,
47
91
  :serial_number,
48
92
  :zones,
@@ -60,6 +104,7 @@ module Aurora
60
104
  :outdoor_temperature,
61
105
  :fp1,
62
106
  :fp2,
107
+ :line_voltage,
63
108
  :aux_heat_watts,
64
109
  :total_watts
65
110
 
@@ -67,14 +112,15 @@ module Aurora
67
112
  @modbus_slave = self.class.open_modbus_slave(uri)
68
113
  @modbus_slave.read_retry_timeout = 15
69
114
  @modbus_slave.read_retries = 2
70
- raw_registers = @modbus_slave.holding_registers[33, 88...110, 404, 412..413, 1103, 1114]
115
+ raw_registers = @modbus_slave.holding_registers[2, 33, 88...110, 404, 412..413, 813, 1103, 1114]
71
116
  registers = Aurora.transform_registers(raw_registers.dup)
117
+ @abc_version = registers[2]
72
118
  @program = registers[88]
73
119
  @model = registers[92]
74
120
  @serial_number = registers[105]
75
121
  @energy_monitor = raw_registers[412]
76
122
 
77
- @zones = if iz2?
123
+ @zones = if iz2? && iz2_version >= 2.0
78
124
  iz2_zone_count = @modbus_slave.holding_registers[483]
79
125
  (0...iz2_zone_count).map { |i| IZ2Zone.new(self, i + 1) }
80
126
  else
@@ -108,8 +154,9 @@ module Aurora
108
154
 
109
155
  @faults = []
110
156
 
111
- @registers_to_read = [6, 19..20, 25, 30, 344, 740..741, 900, 1104, 1110..1111, 1114, 1150..1153, 1165,
112
- 31_003]
157
+ @registers_to_read = [6, 19..20, 25, 30, 112, 344, 567, 1104, 1110..1111, 1114, 1150..1153, 1165]
158
+ @registers_to_read.concat([741, 31_003]) if awl_communicating?
159
+ @registers_to_read << 900 if awl_axb?
113
160
  zones.each do |z|
114
161
  @registers_to_read.concat(z.registers_to_read)
115
162
  end
@@ -122,37 +169,7 @@ module Aurora
122
169
  end
123
170
 
124
171
  def query_registers(query)
125
- implicit = false
126
- ranges = query.split(",").map do |addr|
127
- case addr
128
- when "known"
129
- implicit = true
130
- Aurora::REGISTER_NAMES.keys
131
- when "valid"
132
- implicit = true
133
- break Aurora::REGISTER_RANGES
134
- when /^(\d+)(?:\.\.|-)(\d+)$/
135
- $1.to_i..$2.to_i
136
- else
137
- addr.to_i
138
- end
139
- end
140
- queries = Aurora.normalize_ranges(ranges)
141
- registers = {}
142
- queries.each do |subquery|
143
- registers.merge!(@modbus_slave.read_multiple_holding_registers(*subquery))
144
- rescue ::ModBus::Errors::IllegalDataAddress
145
- # maybe this unit doesn't respond to all the addresses we want?
146
- raise unless implicit
147
-
148
- # try each query individually
149
- subquery.each do |subsubquery|
150
- registers.merge!(@modbus_slave.read_multiple_holding_registers(subsubquery))
151
- rescue ::ModBus::Errors::IllegalDataAddress
152
- next
153
- end
154
- end
155
- registers
172
+ self.class.query_registers(@modbus_slave, query)
156
173
  end
157
174
 
158
175
  def refresh
@@ -164,8 +181,8 @@ module Aurora
164
181
 
165
182
  outputs = registers[30]
166
183
 
167
- @entering_air_temperature = registers[740]
168
- @leaving_air_temperature = registers[900]
184
+ @entering_air_temperature = registers[567]
185
+ @leaving_air_temperature = registers[900] if awl_axb?
169
186
  @leaving_water_temperature = registers[1110]
170
187
  @entering_water_temperature = registers[1111]
171
188
  @outdoor_temperature = registers[31_003]
@@ -175,6 +192,7 @@ module Aurora
175
192
  @error = registers[25] & 0x7fff
176
193
  @derated = (41..46).cover?(@error)
177
194
  @safe_mode = [47, 48, 49, 72, 74].include?(@error)
195
+ @line_voltage = registers[112]
178
196
  @aux_heat_watts = registers[1151]
179
197
  @total_watts = registers[1153]
180
198
 
@@ -255,13 +273,18 @@ module Aurora
255
273
  end
256
274
 
257
275
  # config aurora system
258
- { thermostat: 800, axb: 806, iz2: 812, aoc: 815, moc: 818, eev2: 824 }.each do |(component, register)|
276
+ { thermostat: 800, axb: 806, iz2: 812, aoc: 815, moc: 818, eev2: 824, awl: 827 }.each do |(component, register)|
259
277
  class_eval <<-RUBY, __FILE__, __LINE__ + 1
260
278
  def #{component}?
261
279
  return @#{component} if instance_variable_defined?(:@#{component})
262
280
  @#{component} = @modbus_slave.holding_registers[#{register}] != 3
263
281
  end
264
282
 
283
+ def #{component}_version
284
+ return @#{component}_version if instance_variable_defined?(:@#{component}_version)
285
+ @#{component}_version = @modbus_slave.holding_registers[#{register + 1}].to_f / 100
286
+ end
287
+
265
288
  def add_#{component}
266
289
  @modbus_slave.holding_registers[#{register}] = 2
267
290
  end
@@ -272,6 +295,27 @@ module Aurora
272
295
  RUBY
273
296
  end
274
297
 
298
+ # see https://www.waterfurnace.com/literature/symphony/ig2001ew.pdf
299
+ # is there a communicating system compliant with AWL?
300
+ def awl_communicating?
301
+ awl_thermostat? || awl_iz2?
302
+ end
303
+
304
+ # is the thermostat AWL compliant?
305
+ def awl_thermostat?
306
+ thermostat? && thermostat_version >= 3.0
307
+ end
308
+
309
+ # is the IZ2 AWL compliant?
310
+ def awl_iz2?
311
+ iz2? && iz2_version >= 2.0
312
+ end
313
+
314
+ # is the AXB AWL compliant?
315
+ def awl_axb?
316
+ axb? && axb_version >= 2.0
317
+ end
318
+
275
319
  def inspect
276
320
  "#<Aurora::ABCClient #{(instance_variables - [:@modbus_slave]).map do |iv|
277
321
  "#{iv}=#{instance_variable_get(iv).inspect}"
@@ -29,6 +29,8 @@ module Aurora
29
29
  alias_method :dehumidifier_running?, :dehumidifier_running
30
30
 
31
31
  def registers_to_read
32
+ return [] unless @abc.awl_communicating?
33
+
32
34
  result = [741]
33
35
  if humidifier? || dehumidifier? || abc.compressor.is_a?(Compressor::VSDrive)
34
36
  result.concat(abc.iz2? ? [21_114, 31_109..31_110] : [12_309..12_310])
@@ -20,9 +20,14 @@ module Aurora
20
20
  if register.length == 1
21
21
  case register.first
22
22
  when Integer
23
+ missing_register(register.first) unless @registers.key?(register.first)
23
24
  @registers[register.first]
24
25
  when Range
25
- @registers.values_at(*register.first.to_a)
26
+ registers = register.first.to_a
27
+ registers.each do |i|
28
+ missing_register(i) unless @registers.key?(i)
29
+ end
30
+ @registers.values_at(*registers)
26
31
  else
27
32
  raise ArgumentError, "Not implemented yet #{register.inspect}"
28
33
  end
@@ -35,6 +40,11 @@ module Aurora
35
40
  result = {}
36
41
  queries.each do |query|
37
42
  Array(query).each do |i|
43
+ unless @registers.key?(i)
44
+ missing_register(i)
45
+ next
46
+ end
47
+
38
48
  result[i] = @registers[i]
39
49
  end
40
50
  end
@@ -45,5 +55,11 @@ module Aurora
45
55
  @registers[addr] = value
46
56
  end
47
57
  alias_method :[]=, :write_holding_register
58
+
59
+ private
60
+
61
+ def missing_register(idx)
62
+ logger.warn("missing register #{idx}")
63
+ end
48
64
  end
49
65
  end
data/lib/aurora/pump.rb CHANGED
@@ -31,7 +31,7 @@ module Aurora
31
31
  alias_method :manual_control?, :manual_control
32
32
 
33
33
  def registers_to_read
34
- super + [321..325]
34
+ super + (@abc.awl_axb? ? [321..325] : [321..324])
35
35
  end
36
36
 
37
37
  def refresh(registers)
@@ -39,7 +39,7 @@ module Aurora
39
39
  @minimum_speed = registers[321]
40
40
  @maximum_speed = registers[322]
41
41
  @manual_control = registers[323] != :off
42
- @speed = registers[325]
42
+ @speed = registers[325] if @abc.awl_axb?
43
43
  end
44
44
 
45
45
  def manual_control=(value)
@@ -65,7 +65,7 @@ module Aurora
65
65
 
66
66
  def to_string(registers, idx, length)
67
67
  (idx...(idx + length)).map do |i|
68
- raise ArgumentError, "Missing register #{i} for string starting at #{idx}" unless registers[i]
68
+ next "\ufffd" unless registers[i] # missing data? add unicode invalid character
69
69
 
70
70
  (registers[i] >> 8).chr + (registers[i] & 0xff).chr
71
71
  end.join.sub(/[ \0]+$/, "")
@@ -112,7 +112,7 @@ module Aurora
112
112
  53 => "Condensing Pressure Sensor", # Low condensing pressure (PD) or invalid (0 to 870 psi) Retry 10x.
113
113
  54 => "Low Supply Voltage", # Supply Voltage is <180 V (190V to reset) or powered off/on too quickly (<30 sec.).
114
114
  55 => "Out of Envelope", # Comp Operating out of envelope (P0) more than 90 sec. Retry 10x.
115
- 56 => "Drive Over Currnet", # Over current tripped by phase loss, earth fault, short circuit, low water flow, low air flow, or major drive fault. # rubocop:disable Layout/LineLength
115
+ 56 => "Drive Over Current", # Over current tripped by phase loss, earth fault, short circuit, low water flow, low air flow, or major drive fault. # rubocop:disable Layout/LineLength
116
116
  57 => "Drive Over/Under Voltage", # DC Link Voltage to compressor is >450vdc or at minimum voltage (<185vdc).
117
117
  58 => "High Drive Temp", # Drive Temp has reached critical High Temp >239 F
118
118
  59 => "Internal Drive Error", # The MOC has encountered an internal fault or an internal error. Probably fatal.
@@ -15,19 +15,23 @@ module Aurora
15
15
  :fan_intermittent_off
16
16
 
17
17
  def registers_to_read
18
+ return [31] unless @abc.awl_thermostat?
19
+
18
20
  [31, 502, 745..746, 12_005..12_006]
19
21
  end
20
22
 
21
23
  def refresh(registers)
22
- @ambient_temperature = registers[502]
23
- @heating_target_temperature = registers[745]
24
- @cooling_target_temperature = registers[746]
25
- config1 = registers[12_005]
26
- config2 = registers[12_006]
27
- @target_fan_mode = config1[:fan]
28
- @fan_intermittent_on = config1[:on_time]
29
- @fan_intermittent_off = config1[:off_time]
30
- @target_mode = config2[:mode]
24
+ if @abc.awl_thermostat?
25
+ @ambient_temperature = registers[502]
26
+ @heating_target_temperature = registers[745]
27
+ @cooling_target_temperature = registers[746]
28
+ config1 = registers[12_005]
29
+ config2 = registers[12_006]
30
+ @target_fan_mode = config1[:fan]
31
+ @fan_intermittent_on = config1[:on_time]
32
+ @fan_intermittent_off = config1[:off_time]
33
+ @target_mode = config2[:mode]
34
+ end
31
35
 
32
36
  inputs = registers[31]
33
37
  @current_fan_mode = inputs.include?(:g)
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Aurora
4
- VERSION = "0.7.4"
4
+ VERSION = "0.8.0"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: waterfurnace_aurora
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.7.4
4
+ version: 0.8.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Cody Cutrer
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-12-10 00:00:00.000000000 Z
11
+ date: 2022-01-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: ccutrer-serialport
@@ -16,14 +16,14 @@ dependencies:
16
16
  requirements:
17
17
  - - "~>"
18
18
  - !ruby/object:Gem::Version
19
- version: 1.0.0
19
+ version: '1.0'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - "~>"
25
25
  - !ruby/object:Gem::Version
26
- version: 1.0.0
26
+ version: '1.0'
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: mqtt-homeassistant
29
29
  requirement: !ruby/object:Gem::Requirement
@@ -33,7 +33,7 @@ dependencies:
33
33
  version: '0.1'
34
34
  - - ">="
35
35
  - !ruby/object:Gem::Version
36
- version: 0.1.2
36
+ version: 0.1.3
37
37
  type: :runtime
38
38
  prerelease: false
39
39
  version_requirements: !ruby/object:Gem::Requirement
@@ -43,7 +43,7 @@ dependencies:
43
43
  version: '0.1'
44
44
  - - ">="
45
45
  - !ruby/object:Gem::Version
46
- version: 0.1.2
46
+ version: 0.1.3
47
47
  - !ruby/object:Gem::Dependency
48
48
  name: net-telnet-rfc2217
49
49
  requirement: !ruby/object:Gem::Requirement