Add LG RH90V9_WW heat pump dryer device class#55
Conversation
|
Thank you for the PR. It seems quite complex, so I'll ask you for a clarification on a few points before doing a proper review.
It's quite obvious that the PR message was written by a LLM. I have nothing against that, but I'd like the responses to be authored by an actual person who understands the code :) |
|
It's more comprehensive than complex. I gained access to the schema from the LG API so I was able to build out the full set of features. I will document this process shortly so others may be able to add in other types of LG appliances. And yes LLM is great for documenting and summarising the whole build but can miss the human aspect at times. As for your questions, LG prevent "power on" in their apps for all their dryers. So in the app you can turn it off but you can't turn it back on. However the machine does respond to this command regardless. So I added the ability to turn the machine on, but it's hidden behind the "safety lock". There's a situation where someone might turn on the dryer and not be aware, say if they had the button on a dashboard etc. This could be a fire risk etc. So just being overly cautious here. To turn it on you'd need to first turn off the safety lock, and it resets each power cycle, so it's always considered safe. Re selector lock / this is purely a UX debounce, nothing safety related. The dryer sends state packets every few seconds. If a user changes a selector in HA (e.g. switches cycle from Cotton to Mixed Fabric), the next incoming state packet would immediately overwrite their selection before they hit Start. The selector lock suppresses state packet overwrites for 10 seconds after a user edit, giving them time to configure and start. It’s internal to the device class, no HA entity, not user-facing at all. I’ll write some documentation shortly on this module and pop it in the PR. Including the statement around safety. I think the long term question is - how much of this can be reused in a base dryer class. Right now it’s hard to answer, without some packets from other machines. If we spot similar packets on other machines than I’ll look to move some of this logic into a base class. Any other questions let me know. And must say a huge thanks for getting this repo up and running in the first place. |
Great! This could be really useful. |
You mean, you can't turn the device on via the app, ever? Or is there a time window during which it is allowed?
Hmm, tell me if I understand this correctly. The device sends its state periodically. Is it (a), (b), or something else? |
|
Hi!
|
…N payload - Remove Safety Lock entity, selector lock machinery, and all selectedXxx state - cycle/dry_level/eco_hybrid/reservation become read-only sensors; anti_crease keeps its switch (state reflects Bd, toggle updates start fallback) - processAABB publishes Bd values directly without schema correction or lock checks - start button accepts optional JSON payload with cycle/dry_level/eco_hybrid/ reservation/anti_crease; missing fields fall back to last known Bd values - buildStartCommand still validates against CYCLE_SCHEMA and silently corrects invalid combos with a warning - Power ON no longer requires Safety Lock; wake sequence (F0 25 + F0 2A) unchanged - Update tests to match: remove selector/lock tests, add JSON payload tests Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Just to add. I'm not sure about bypassing the 'safety lock' as @alexw23 stated but the whole idea is, on the front of the dryer you can enable "remote start", which then gives you access to all the remote functions of starting the dryer or pausing the dryer to change a mode or setting. Once the dryer is paused, you have a limited time to start the dryer again from the app before it auto turns off the dryer to power save. Once this happens the remote start feature is disabled again and you have to be physically in front of the dryer to enable it again. As far as I'm aware, with the remote start feature enabled, the dryer will stay on until you start a program but once paused will auto timeout and turn off. Another thing to add is, my dryer is the slightly newer version of this with touch buttons instead of push buttons for the power and start/pause. All of the options @alexw23 has found seem to be the same for the updated version too. So rather than maybe having duplicate code for all the different models of dryer (I think LG has a lot based on country and slight variations in colours), maybe multiple models could be grouped together? |
I think this is more built into LG dryers than a a feature @alexw23 is coding. Once remote start, is enabled on these machines, the door locks. The idea is that if you were to start the machine remotely, then the door has been locked since you enabled it whilst at the machine, so nothing could have opened or climbed inside in the mean time (I used to have a dog that liked opening our old dryer door). Obviously turning the dryer on remotely, you would have no idea what had happened. |
|
I'm not sure what @Drafteed had meant, but in my opinion, we should neither fight against the lockout built into the device, nor implement our own on top of that. |
That’s exactly what I meant :) |
What is the Thinq model name of your dryer? If it's RH90V9_WW, then we will assume that the protocol is bit-identical (until proven otherwise). If it's different, then .. we can still get lucky and reuse the same implementation if the protocol matches. Otherwise we can reuse some parts (see fridge_common for an example) |
So my model is FDV1110B. I've no idea how LG model numbers work but they seem to change based on country and then slight appearance changes/updates. I've yet to test any of this code, but was brought here after the latest LG debacle with account banning. I'm a great believe in having more control over IOT and stopping things 'calling home' |
This is the customer-visible model. The "techhnical" model name is visible in rethink logs, both during provisioning & normal operation. I guess it's also available through the official API but I haven't checked. |
I think we could accumulate a certain number of devices first, and then consolidate them into a common builder/base class where model-specific features/capabilities are selected for each device. |
Ah in that case I'll have to do a little more digging. The official app doesn't give any other information that the visible model number and some software version. |
|
Ok so I checked the home assistant SmartThinQ LGE Sensors integration and it is indeed the same model number: RH90V9_WW-Dryer (DRYER) by LG Maybe we do have the same dryer? Or maybe they do use the same technical model across different dryers. Maybe @alexw23 can enlighten us with what his customer model of dryer he has. |
|
@alexw23 I see that you've pushed some changes. It would be helpful if you answered my previous questions and what's the rationale behind these changes. That is - if you're still interested in merging this. |
|
I own the same type of tumble dryer. So I tried Alex' code as a simple new file to |
|
Thanks for the feedback Oiled. Glad it’s all working.
I’m maintaining my own fork of this repo as I found the questioning was a
little overzealous. For a commit of a high attention to detail it was
framed as being “complex” rather than comprehensive. Spent a whole weekend
and more on this including the home assistant additions.
If you want to use my fork feel free (github.com/alexw23/rethink) I’ll be
merging in this repo here and there.
Either way glad it’s all working for you 👍
…On Sat, 13 Jun 2026 at 11:47 pm, OiledAmoeba ***@***.***> wrote:
*OiledAmoeba* left a comment (anszom/rethink#55)
<#55 (comment)>
I own the same type of tumble dryer. So I tried Alex' code as a simple new
file to cloud/devices and referred the new file in cloud/ha_bridge.ts.
(Short npm run build is required, because of the design by the
precompiled project)
For me, the dryer works perfectly well in HomeAssistant (and since it'uses
MQTT, also in FHEM).
For example, my last used "Downloaded Program" was "Rainy Day". Alex' code
showed exactly that program over MQTT.
From my perspective, the PR should be accepted/approved, or at least Alex'
.ts for the device class to use it for the build process.
The use of Alex' standalone device class file within your flattened new
folder structure causes no problems in my installation. By accepting only
the device class file, your project would be able to support this type of
dryer. And later you can discuss Alex' extra edits ;-)
—
Reply to this email directly, view it on GitHub
<#55?email_source=notifications&email_token=AALPRWHFCBZ6I5XBRCB46SD47XKX5A5CNFSNUABFM5UWIORPF5TWS5BNNB2WEL2JONZXKZKDN5WW2ZLOOQXTINZQGAYDEMJRG432M4TFMFZW63VHNVSW45DJN5XKKZLWMVXHJLDGN5XXIZLSL5RWY2LDNM#issuecomment-4700021177>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AALPRWAGTQUQXXOSS6XLICT47XKX5AVCNFSNUABFKJSXA33TNF2G64TZHM3TEMBYGMYDONZZHNEXG43VMU5TINJRGI4TGMZSGEZKC5QC>
.
You are receiving this because you were mentioned.Message ID:
***@***.***>
|
Add LG RH90V9_WW heat pump dryer device class
Adds a full device class for the LG RH90V9_WW heat pump dryer, reverse engineered from wire captures against the AABB packet protocol.
Entities
Controls
Sensors
Protocol
Full field map confirmed from wire captures and official modelJson:
Bd[0]Bd[1-2]Bd[3-4]Bd[5]Bd[6]Bd[7]Bd[8]Bd[9]Bd[10]Bd[14]0x02=anti-creaseBd[15]0x01=remote start armedBd[20]Start command inner layout (
F0 26opcode, 16 bytes):[2][3][4][8]0=off,3-19=delayed end)[11]0x00=off,0x02=on)[12]0x03=start,0x01=resume/update)[14]0x00for base courses)Features
Per-cycle schema — dry level and eco hybrid options filter dynamically when cycle changes, with defaults applied from modelJson. Covers all 15 base courses.
Stale value correction — packet values validated against schema on every state update. Invalid or stale values (e.g. dry level carrying over from a previous cycle) are corrected to schema defaults rather than published to HA.
Downloaded cycles —
DOWNLOADED_CYCLEStable maps SmartCourse wire IDs to friendly names and schema defaults. Two IDs confirmed from captures (GYMCLOTHES=0x66,DEODORIZATION=0x6b), fourteen others commented out awaiting capture. Adownloaded_cycle_iddiagnostic sensor shows the raw hex ID to help users identify new cycles.Selector debounce — 10s lock prevents incoming state packets from overwriting in-progress HA selector edits.
Safety Lock — gates Power On (wire-level confirmed working via
F02A0100, rejected by LG cloud) and Remote Start per session. Resets to locked on every restart.Confirmed captures
All field mappings verified against real packet captures from an RH90V9_WW unit running firmware
2.10.123.