Skip to content

[Aqara] add Aqara Bath Heater T1#2942

Open
seojune79 wants to merge 6 commits into
SmartThingsCommunity:mainfrom
seojune79:Aqara-Bath-Heater
Open

[Aqara] add Aqara Bath Heater T1#2942
seojune79 wants to merge 6 commits into
SmartThingsCommunity:mainfrom
seojune79:Aqara-Bath-Heater

Conversation

@seojune79
Copy link
Copy Markdown
Contributor

@seojune79 seojune79 commented May 4, 2026

Check all that apply

Type of Change

  • WWST Certification Request
    • If this is your first time contributing code:
      • I have reviewed the README.md file
      • I have reviewed the CODE_OF_CONDUCT.md file
      • I have signed the CLA
    • I plan on entering a WWST Certification Request or have entered a request through the WWST Certification console at developer.smartthings.com
  • Bug fix
  • New feature
  • Refactor

Checklist

  • I have performed a self-review of my code
  • I have commented my code in hard-to-understand areas
  • I have verified my changes by testing with a device or have communicated a plan for testing
  • I am adding new behavior, such as adding a sub-driver, and have added and run new unit tests to cover the new behavior

Description of Change

Summary of Completed Tests

@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 4, 2026

Duplicate profile check: Passed - no duplicate profiles detected.

@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 4, 2026

@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 4, 2026

Test Results

   73 files    512 suites   0s ⏱️
2 900 tests 2 900 ✅ 0 💤 0 ❌
4 773 runs  4 773 ✅ 0 💤 0 ❌

Results for commit fefff4b.

♻️ This comment has been updated with latest results.

@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 4, 2026

File Coverage
All files 93%
/home/runner/work/SmartThingsEdgeDrivers/SmartThingsEdgeDrivers/drivers/Aqara/aqara-bath-heater/src/init.lua 93%

Minimum allowed coverage is 90%

Generated by 🐒 cobertura-action against fefff4b

HIGH = "high",
}
local MODE_TO_FAN = { [SPEED.LOW] = FAN_LOW, [SPEED.MEDIUM] = FAN_MID, [SPEED.HIGH] = FAN_HIGH }
local FAN_TO_MODE = { [0] = SPEED.LOW, [1] = SPEED.MEDIUM, [2] = SPEED.HIGH }
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
local FAN_TO_MODE = { [0] = SPEED.LOW, [1] = SPEED.MEDIUM, [2] = SPEED.HIGH }
local FAN_TO_MODE = { [FAN_LOW] = SPEED.LOW, [FAN_MID] = SPEED.MEDIUM, [FAN_HIGH] = SPEED.HIGH }

nit: Keep them interlocked

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I have made the requested changes.


if params.setpoint ~= nil then
local sp_raw = math.floor(clamp(params.setpoint, 16, 45) * 100) & 0xFFFF
hi32 = (sp_raw << 16) | (hi32 & 0xFFFF)
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
hi32 = (sp_raw << 16) | (hi32 & 0xFFFF)
hi32 = (sp_raw << 16) | 0xFFFF

Since hi32 is unmodified from being set to 0xFFFFFFFF and (hi32 & 0xFFFF) will always evaluate to 0xFFFF

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The unnecessary computations have been removed.

…ition since hi32 remains 0xFFFFFFFF, making (hi32 & 0xFFFF) always 0xFFFF.
Copy link
Copy Markdown
Contributor

@cjswedes cjswedes left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I dont see a reason to not use the defaults, so I would prefer those are used.

Comment thread drivers/Aqara/aqara-bath-heater/src/init.lua Outdated
Comment thread drivers/Aqara/aqara-bath-heater/src/init.lua Outdated
Comment on lines +580 to +588
[OnOff.ID] = {
[OnOff.attributes.OnOff.ID] = on_off_attr_handler,
},
[Level.ID] = {
[Level.attributes.CurrentLevel.ID] = current_level_handler,
},
[ColorControl.ID] = {
[ColorControl.attributes.ColorTemperatureMireds.ID] = color_temp_handler,
},
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These handlers are also covered by the defaults

[ColorControl.attributes.ColorTemperatureMireds.ID] = color_temp_handler,
},
[aqara.CLUSTER_ID] = {
[aqara.ATTR_AC_CODE] = ac_code_attr_handler,
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I dont see any reporting configuration setup for this attribute. Does Aqara just automatically do the reporting?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, the aqara.ATTR_AC_CODE attribute under the aqara.CLUSTER_ID cluster is automatically reported by the device whenever there is a change in the device status. No additional reporting configuration is required for this specific attribute.

device:emit_event(capabilities.fanOscillationMode.fanOscillationMode(st_fan))
end

local function handle_fan_mode(driver, device, cmd)
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Other handlers emit the event after the ac_code has been sent. Why not do that here? Should the other command handlers be following this pattern to ensure we are emitting events that match the reported device state (i.e. handle_fan_oscillation_mode, handle_heating_setpoint, handler_thermostat_mode) ?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch. I've adjusted the event emission timing to execute after the ac_code is sent, ensuring consistency across all command handlers as suggested.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is the reason for emitting the even prior to receiving the updated state from the device? If there is a failure on the device, the platform will show the wrong state.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's a valid point, and I was already aware of this trade-off — I understood the risk of showing an inconsistent state if the device reports a failure.

The reason I added this optimistic emit was twofold:

  1. Improved UX responsiveness — emitting early gives users immediate visual feedback, reducing perceived latency.
  2. Consistency with thermostat mode changes — the same pattern was already being used there, so I followed the same approach for uniformity.

That said, your concern is well-founded, and I've updated the code to wait for the confirmed state from the device before emitting. One exception: I've kept the optimistic emit for thermostat mode changes, as that behavior is intentional to match the UX of the Aqara app. Please take note of that when reviewing.

- Add register_for_default_handlers and call handle_refresh to eliminate duplicated code.
- Update event emission to trigger after ac_code is sent for consistency across all command handlers.
Copy link
Copy Markdown
Contributor

@nand-nor nand-nor left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks good to me with all the added fixes addressing others comments

- Remove optimistic emit to prevent temporary inconsistent states.
- Exception: Keep optimistic emit for thermostat mode changes to match Aqara app UX.
Comment on lines +487 to +491
supported_capabilities = {
capabilities.switch,
capabilities.switchLevel,
capabilities.colorTemperature
},
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These should be updated to include thermostatMode, thermostatHeatingSetpoint, fanOscilalationMode, and fanMode. Its not super critical since you are not relying on any default functionality, but it also affects the default driver switch behavior (which is a rarely used path)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants