Midea_dehumi Custom Component (Midea/Inventor Invmate EVA II PRO WiFi dehumidifier)

Hi @barban,
Just dl and i try to install now ;-))

I wonder if the update it include a solution for house with multiple deshumidifier ?
I am in that case with @HVPereira (post 74 & 75 Dec20)

Actually, as per my understanding someone implemented a better solution for the multiple devices.

Credits to gianluca.

in init .py, I pushed into hass.data new client for each appliace:

    if not deviceId:
        if appliances is not None:
            for a in appliances:
                if a["type"] == "0xA1":
                    deviceId = str(a["id"])
                    targetDevice = a
                    client_for_device = MideaClient(username, password, sha256password, cacheTimeInSeconds = 0)
                    res = await hass.async_add_executor_job(client_for_device.login)
                    if res != -1:
                        sessionId = client_for_device.current["sessionId"]
                        _LOGGER.info("midea-dehumi: login success, sessionId=%s", sessionId)
                        hass.data[MIDEA_API_CLIENT + "_" + a["id"]] = client_for_device
                    _LOGGER.info("midea-dehumidifier: loading humidifier entity sub-component...")
                    load_platform(hass, 'humidifier', DOMAIN, {MIDEA_TARGET_DEVICE: targetDevice}, config)
                    _LOGGER.info("midea-dehumidifier: loading sensor entity sub-component...")
                    load_platform(hass, 'sensor', DOMAIN, {MIDEA_TARGET_DEVICE: targetDevice}, config)
                    _LOGGER.info("midea_dehumidifier: platform successfuly initialized.")
    else:
        if appliances is not None:
            for a in appliances:
                if a["type"] == "0xA1" and deviceId == str(a["id"]):
                    targetDevice = a

the key is: hass.data[MIDEA_API_CLIENT + "_" + a["id"]] = client_for_device

In humidifier.py, I changed the way to get client:

self._client = hass.data[MIDEA_API_CLIENT + "_" + targetDevice['id']]

Hope it helps

I belive this is a much better solution I haven’t tested it myself but will try it this weekend.

Best Regards,
HP

Hello again,

For those of you who are trying to have several devices with different humidity sensors. Please find my init.py and humidifier,py in attachment.

All the credits should go to gianluca and barban of course as they were the ones who managed to get here :slight_smile:

I’m very happy to share these files, Hope you find it as useful as I did.

init.py

"""
Custom integation based on humidifer and sensor platforms for EVA II PRO WiFi Smart Dehumidifier appliance by Midea/Inventor.
For more details please refer to the documentation at
https://github.com/barban-dev/midea_inventor_dehumidifier
"""
VERSION = '1.0.0'

DOMAIN = "midea_dehumidifier"
MIDEA_API_CLIENT = "midea_api_client"
MIDEA_TARGET_DEVICE = "midea_target_device"


import logging
import voluptuous as vol
import homeassistant.helpers.config_validation as cv
from homeassistant.helpers.discovery import load_platform
from homeassistant.const import CONF_USERNAME, CONF_PASSWORD

import asyncio
from homeassistant.config_entries import ConfigEntry

_LOGGER = logging.getLogger(__name__)

CONF_SHA256_PASSWORD = 'sha256password'
CONF_DEVICEID = 'deviceId'

CONFIG_SCHEMA = vol.Schema({
    DOMAIN: vol.Schema({
        vol.Required(CONF_USERNAME): cv.string,
        vol.Optional(CONF_PASSWORD): cv.string,
        vol.Optional(CONF_SHA256_PASSWORD): cv.string,
        vol.Optional(CONF_DEVICEID): cv.string
    })
}, extra=vol.ALLOW_EXTRA)


async def async_setup(hass, config):
    """Set up client for Midea API based on configuration entries."""
    _LOGGER.info("midea_dehumidifier: initializing platform...")
    _LOGGER.debug("midea_dehumidifier: starting async_setup")

    if DOMAIN not in config:
        _LOGGER.error("midea_dehumi: cannot find midea_dehumi platform on configuration.yaml")
        return False

    from midea_inventor_lib import MideaClient
    	
    username = config[DOMAIN].get(CONF_USERNAME)
    password = config[DOMAIN].get(CONF_PASSWORD)
    sha256password = config[DOMAIN].get(CONF_SHA256_PASSWORD)
    deviceId = config[DOMAIN].get(CONF_DEVICEID)
	
    #_LOGGER.debug("midea_dehumi: CONFIG PARAMS: username=%s, password=%s, sha256password=%s, deviceId=%s", username, password, sha256password, deviceId)

    if not password and not sha256password:
        _LOGGER.error("midea_dehumi: either plain-text password or password's sha256 hash should be specified in config entries.")
        return False

    #Create client
    client = MideaClient(username, password, sha256password, cacheTimeInSeconds = 0)

    #Log-in to the Midea cloud Web Service and get the list of configured Midea/Inventor appliances for the user.
    _LOGGER.info("midea_dehumi: logging into Midea API Web Service...")

    #res = client.login()
    res = await hass.async_add_executor_job(client.login)
    if res == -1:
        _LOGGER.error("midea-dehumi: login error")
        return False
    else:
        sessionId = client.current["sessionId"]
        _LOGGER.info("midea-dehumi: login success, sessionId=%s", sessionId)

    appliances = {}

    #appliances = client.listAppliances()
    appliances = await hass.async_add_executor_job(client.listAppliances)
    
    appliancesStr = ""
    for a in appliances:
        appliancesStr = "[id="+a["id"]+" type="+a["type"]+" name="+a["name"]+"]"
    if a["onlineStatus"] == "1":
        appliancesStr += " is online,"
    else:
        appliancesStr += " is offline,"
    if a["activeStatus"] == "1":
        appliancesStr += " is active.\n"
    else:
        appliancesStr += " is not active.\n"
		
    _LOGGER.info("midea-dehumi: "+appliancesStr)
    
    #The first appliance having type="0xA1" is returned for default (TODO: otherwise, 'deviceId' configuration option can be used)
    hass.data[MIDEA_API_CLIENT] = client
    targetDevice = None
    if not deviceId:
        if appliances is not None:
            for a in appliances:
                if a["type"] == "0xA1":
                    deviceId = str(a["id"])
                    targetDevice = a
                    client_for_device = MideaClient(username, password, sha256password, cacheTimeInSeconds = 0)
                    res = await hass.async_add_executor_job(client_for_device.login)
                    if res != -1:
                        sessionId = client_for_device.current["sessionId"]
                        _LOGGER.info("midea-dehumi: login success, sessionId=%s", sessionId)
                        hass.data[MIDEA_API_CLIENT + "_" + a["id"]] = client_for_device
                    _LOGGER.info("midea-dehumidifier: loading humidifier entity sub-component...")
                    load_platform(hass, 'humidifier', DOMAIN, {MIDEA_TARGET_DEVICE: targetDevice}, config)
                    _LOGGER.info("midea-dehumidifier: loading sensor entity sub-component...")
                    load_platform(hass, 'sensor', DOMAIN, {MIDEA_TARGET_DEVICE: targetDevice}, config)
                    _LOGGER.info("midea_dehumidifier: platform successfuly initialized.")
    else:
        if appliances is not None:
            for a in appliances:
                if a["type"] == "0xA1" and deviceId == str(a["id"]):
                    targetDevice = a


    if targetDevice:
 #       _LOGGER.info("midea-dehumidifier: device type 0xA1 found.")

#        hass.data[MIDEA_API_CLIENT] = client
#        _LOGGER.info("midea-dehumidifier: loading humidifier entity sub-component...")
#        load_platform(hass, 'humidifier', DOMAIN, {MIDEA_TARGET_DEVICE: targetDevice}, config)

#        _LOGGER.info("midea-dehumidifier: loading sensor entity sub-component...")
#        load_platform(hass, 'sensor', DOMAIN, {MIDEA_TARGET_DEVICE: targetDevice}, config)

#        _LOGGER.info("midea_dehumidifier: platform successfuly initialized.")
        return True
    else:
        _LOGGER.error("midea-dehumidifier: device type 0xA1 not found.")
        return False

humidifier.py

"""
Custom integation based on humidifer and sensor platforms for EVA II PRO WiFi Smart Dehumidifier appliance by Midea/Inventor.
For more details please refer to the documentation at
https://github.com/barban-dev/midea_inventor_dehumidifier
"""
VERSION = '1.0.1'

import logging
from midea_inventor_lib import MideaClient
from typing import List, Optional
from custom_components.midea_dehumidifier import DOMAIN, MIDEA_API_CLIENT, MIDEA_TARGET_DEVICE

from homeassistant.components.humidifier import HumidifierEntity
from homeassistant.components.humidifier.const import (
    ATTR_AVAILABLE_MODES,
    ATTR_HUMIDITY,
    ATTR_MAX_HUMIDITY,
    ATTR_MIN_HUMIDITY,
    ATTR_MODE,
    DEFAULT_MAX_HUMIDITY,
    DEFAULT_MIN_HUMIDITY,
    DEVICE_CLASS_DEHUMIDIFIER,
    SERVICE_SET_HUMIDITY,
    SERVICE_SET_MODE,
    SUPPORT_MODES
)

#import asyncio
import voluptuous as vol
import homeassistant.helpers.config_validation as cv
#from homeassistant.helpers import config_validation as cv, entity_platform, service
from homeassistant.helpers import service
from homeassistant.helpers.dispatcher import async_dispatcher_connect, async_dispatcher_send
from homeassistant.core import callback


ATTR_ENTITY_ID = "entity_id"

SERVICE_SET_FAN_SPEED = "set_fan_speed"
ATTR_FAN_SPEED = "fan_speed"
SERVICE_SET_FAN_SPEED_SCHEMA = vol.Schema({
    vol.Required(ATTR_ENTITY_ID): cv.entity_id,
    vol.Required(ATTR_FAN_SPEED): cv.string,
})

SERVICE_SET_ION_STATE = "set_ion_state"
ATTR_ION_STATE = "ion_state"
SERVICE_SET_ION_STATE_SCHEMA = vol.Schema({
    vol.Required(ATTR_ENTITY_ID): cv.entity_id,
    vol.Required(ATTR_ION_STATE): cv.boolean,
})

SERVICE_SET_MODE = "set_mode"
ATTR_MODE = "mode"
SERVICE_SET_MODE_SCHEMA = vol.Schema({
    vol.Required(ATTR_ENTITY_ID): cv.entity_id,
    vol.Required(ATTR_MODE): cv.string,
})


_LOGGER = logging.getLogger(__name__)

#SUPPORT_FLAGS = 0
SUPPORT_FLAGS = SUPPORT_MODES

#TODO: in midea_dehumi python lib the range 30-70 is hard coded (fix it)
MIN_HUMITIDY = 35
MAX_HUMITIDY = 70

DEHUMI_MODES_DICT = { 'TARGET_HUMIDITY' : 1, 'CONTINUOS' : 2, 'SMART' : 3, 'DRYER' : 4}
DEHUMI_MODES_LIST = [ 'Target_humidity', 'Continuos', 'Smart', 'Dryer']

DEHUMI_FAN_SPEED_DICT = { 'SILENT' : 40, 'MEDIUM' : 60, 'HIGH' : 80 }
DEHUMI_FAN_SPEED_LIST = [ 'Silent', 'Medium', 'High' ]


#States Attributes
ATTR_ION_SET_SWITCH = "ion"
#ATTR_MODE = "mode"
ATTR_FAN_SPEED_MODE = "fan_speed_mode"
#ATTR_FAN_SPEED = "fan_speed"
ATTR_CURRRENT_HUMIDITY = "current_humidity"
ATTR_TANK_SHOW = 'tank_show'

PROP_TO_ATTR = {
    "ionSetSwitch": ATTR_ION_SET_SWITCH,
    "mode": ATTR_MODE,
    "windSpeedMode": ATTR_FAN_SPEED_MODE,
    "windSpeed": ATTR_FAN_SPEED,
    "current_humidity": ATTR_CURRRENT_HUMIDITY,
    "tank_show": ATTR_TANK_SHOW,
}


async def async_setup_platform(hass, config, async_add_entities, discovery_info=None):
    """Set up Midea/Inventor dehumidifier platform based on config_entry."""
    _LOGGER.info("midea_dehumidifier: initializing humidifier platform")
    _LOGGER.debug("midea_dehumidifier: starting async_setup_platform")
    _LOGGER.debug("midea_dehumidifier: MIDEA_API_CLIENT="+MIDEA_API_CLIENT)
    _LOGGER.debug("midea_dehumidifier: MIDEA_TARGET_DEVICE="+MIDEA_TARGET_DEVICE)

    #ref: https://developers.home-assistant.io/docs/en/creating_component_generic_discovery.html
    client = hass.data[MIDEA_API_CLIENT]
    targetDevice = discovery_info[MIDEA_TARGET_DEVICE]
    _LOGGER.debug("midea_dehumidifier: targetDevice = %s", targetDevice)

    if targetDevice is not None:
        #Add entity
        async_add_entities([MideaDehumidifierDevice(hass, client, targetDevice)])

        _LOGGER.info("midea_dehumidifier: humidifier entity initialized.")
    else:
        _LOGGER.error("midea_dehumidifier: error initializing humidifier entity.")


    #Register services
    #https://community.home-assistant.io/t/registering-a-service/40327/11

    async def async_service_set_fan_speed(call):
        entity_id = call.data[ATTR_ENTITY_ID]
        speed_mode = call.data[ATTR_FAN_SPEED]
        async_dispatcher_send(hass, SERVICE_SET_FAN_SPEED.format(entity_id), speed_mode)

    async def async_service_set_ion_state(call):
        entity_id = call.data[ATTR_ENTITY_ID]
        ion_state = call.data[ATTR_ION_STATE]
        async_dispatcher_send(hass, SERVICE_SET_ION_STATE.format(entity_id), ion_state)
        
    async def async_service_set_mode(call):
        entity_id = call.data[ATTR_ENTITY_ID]
        mode_name = call.data[ATTR_MODE]
        async_dispatcher_send(hass, SERVICE_SET_MODE.format(entity_id), mode_name)

    hass.services.async_register(DOMAIN, SERVICE_SET_FAN_SPEED, async_service_set_fan_speed, SERVICE_SET_FAN_SPEED_SCHEMA)
    hass.services.async_register(DOMAIN, SERVICE_SET_ION_STATE, async_service_set_ion_state, SERVICE_SET_ION_STATE_SCHEMA)
    hass.services.async_register(DOMAIN, SERVICE_SET_MODE, async_service_set_mode, SERVICE_SET_MODE_SCHEMA)

    return True



async def async_setup_entry(hass, config_entry, async_add_entities):
    """Set up the Dehumidifier device config entry."""
    await async_setup_platform(hass, {}, async_add_entities)


class MideaDehumidifierDevice(HumidifierEntity):
    """Representation of a Midea/Inventor dehumidifier device."""

    def __init__(self, hass, client, targetDevice):
        _LOGGER.debug("midea_dehumidifier: initializing MideaDehumidifierDevice...")

        self._hass = hass
        self._supported_features = SUPPORT_FLAGS

        #Fan modes
        self._fan_dict = DEHUMI_FAN_SPEED_DICT
        self._fan_list = DEHUMI_FAN_SPEED_LIST

        #Device modes
        self._modes_dict = DEHUMI_MODES_DICT
        self._available_modes = DEHUMI_MODES_LIST

        self._client = hass.data[MIDEA_API_CLIENT + "_" + targetDevice['id']]
        self._device = targetDevice
        self._name = "midea_dehumidifier_"+targetDevice['id']
        self._unique_id = 'midea_dehumidifier_' + targetDevice['id']

        #Default values for device state
        self._powerMode = None          # 0:off, 1:on
        self._mode = None               # device's current mode ['Target_humidity', 'Continuos', 'Smart', 'Dryer']
        self._ionSetSwitch = None       # 0:off, 1:on
        self._humidity = None           # current humidity
        self._humidity_set = None       # target hunidity
        self._humidity_dot = None       # current humidity (decimal)
        self._humidity_dot_set = None   # target humidity (decimal)
        self._windSpeed = None          # fan speed [1..99]
        self._windSpeedMode = None      # fan speed mode (Silent:40, Medium:60, High:80)
        self._isDisplay = None
        self._filterShow = False
        self._tankShow = False
        self._dryClothesSetSwitch = None
        self._upanddownSwing = None

        self._device_class = DEVICE_CLASS_DEHUMIDIFIER

        ##Get appliance's status to set initial values for the device
        #_LOGGER.debug("midea-client: querying appliance status via Web API...")
        #res = self._client.get_device_status(self._device['id'])
        #if res == 1:
        #    _LOGGER.debug("midea_dehumidifier: get_device_status suceeded: "+self._client.deviceStatus.toString())
        #    #Set initial values for device's status
        #    self.__refresh_device_status()
        #else:
        #    _LOGGER.error("midea_dehumidifier: get_device_status error")

    @property
    def unique_id(self):
        """Return the unique id."""
        return self._unique_id

    @property
    def name(self):
        """Return the name of the humidity device."""
        return self._name

    @property
    def supported_features(self):
        """Return the list of supported features."""
        return self._supported_features

    @property
    def should_poll(self):
        """Return the polling state."""
        #get device's status by polling it: Midea Web API lacks of notification capability
        return True

    @property
    def target_humidity(self):
        """Return the humidity we try to reach."""
        return self._humidity_set

    @property
    def mode(self):
        """Return current mode."""
        return self._mode

    @property
    def available_modes(self):
        """Return available modes."""
        return self._available_modes

    @property
    def is_on(self):
        """Return true if the device is on."""
        return self._powerMode

    @property
    def device_class(self):
        """Return the device class of the humidifier."""
        return self._device_class

    @property
    def ionSetSwitch(self):
        return self._ionSetSwitch

    @property
    def windSpeed(self):
        return self._windSpeed

    @property
    def windSpeedMode(self):
        return self._windSpeedMode

    @property
    def current_humidity(self):
        """Return the current humidity."""
        return self._humidity

    @property
    def tank_show(self):
        """Return the current Tank Value."""
        return self._tankShow

    @property
    def min_humidity(self):
        """Return the min humidity set."""
        return 40

    @property
    def max_humidity(self):
        """Return the max humidity set."""
        return 85

    @property
    def device_state_attributes(self):
        """Return entity specific state attributes."""
        data = {}

        for prop, attr in PROP_TO_ATTR.items():
            value = getattr(self, prop)
            if value is not None:
                data[attr] = value

        return data


    #####################################################
    #asycn methods 
    #####################################################

    async def async_added_to_hass(self):
        """Run when about to be added to hass."""
        async_dispatcher_connect(self.hass, SERVICE_SET_FAN_SPEED.format(self.entity_id), self.service_set_fan_speed)
        async_dispatcher_connect(self.hass, SERVICE_SET_ION_STATE.format(self.entity_id), self.service_set_ion_state)
        async_dispatcher_connect(self.hass, SERVICE_SET_MODE.format(self.entity_id), self.service_set_mode)

#
#    def __hass_update_state_attribute(self, _state, _attr, _value):
#        """Update attribute on state obtained via hass.states.get() and return dict containing all the state attributes."""
#        data = {}
#        for attr, value in _state.attributes.items():
#            #_LOGGER.info("(attr, value) = (%s,%s)", attr, value)
#            if attr == _attr:
#                data[attr] = _value
#            else:
#                data[attr] = value
#
#        return data
#

    @callback
    async def service_set_fan_speed(self, speed_mode):
        """service_set_fan_speed"""
        _LOGGER.info("service_set_fan_speed called, speed_mode = %s", speed_mode)
        speed = self._fan_dict.get(speed_mode.upper(), 0)
        _LOGGER.info("speed = %s", speed)
        if self.is_on and self._windSpeed != speed and self._client.deviceStatus.setMode != 4:
            _LOGGER.debug("midea-dehumidifier: sending send_fan_speed_command via Web API...")
            res = await self.hass.async_add_executor_job(self._client.send_fan_speed_command, self._device["id"], speed)
            if res is not None:
                _LOGGER.debug("midea-dehumidifier: send_fan_speed_command suceeded: "+self._client.deviceStatus.toString())
                self._windSpeed = speed
                self._windSpeedMode = speed_mode
                
                #Update state attribute
                state = self._hass.states.get('humidifier.'+self._unique_id)
                if state:
                    #attrs = self.__hass_update_state_attribute(state, ATTR_FAN_SPEED_MODE, speed)
                    attrs = state.attributes.copy()
                    attrs[ATTR_FAN_SPEED_MODE] = speed_mode
                    attrs[ATTR_FAN_SPEED] = speed
                    
                    self._hass.states.async_set('humidifier.'+self._unique_id, state.state, attrs, force_update = True)

            else:
                _LOGGER.error("midea-dehumidifier: send_fan_speed_command ERROR.")

    @callback
    async def service_set_ion_state(self, ion_state):
        """service_set_ion_state"""
        _LOGGER.info("service_set_ion_state called, ion_state = %s", ion_state)
        if self.is_on and self._ionSetSwitch != ion_state:
            if ion_state:
                _LOGGER.debug("midea-dehumidifier: sending send_ion_on_command via Web API...")
                res = await self.hass.async_add_executor_job(self._client.send_ion_on_command, self._device["id"])
            else:
                _LOGGER.debug("midea-dehumidifier: sending send_ion_off_command via Web API...")
                res = await self.hass.async_add_executor_job(self._client.send_ion_off_command, self._device["id"])
            if res is not None:
                _LOGGER.debug("midea-dehumidifier: send_ion_(on/off)_command suceeded: "+self._client.deviceStatus.toString())
                self._ionSetSwitch = ion_state
                #Update state attribute
                state = self._hass.states.get('humidifier.'+self._unique_id)
                if state:
                    #attrs = self.__hass_update_state_attribute(state, ATTR_ION_SET_SWITCH, ion_state)
                    attrs = state.attributes.copy()
                    attrs[ATTR_ION_SET_SWITCH] = ion_state                  
                    self._hass.states.async_set('humidifier.'+self._unique_id, state.state, attrs, force_update = True)

            else:
                _LOGGER.error("midea-dehumidifier: send_fan_speed_command ERROR.")

    @callback
    async def service_set_mode(self, mode_name):
        """service_set_mode"""
        _LOGGER.info("service_set_mode called, mode_name = %s", mode_name)
        mode = self._modes_dict.get(mode_name.upper(), 0)
        _LOGGER.info("mode = %s", mode)
        if self.is_on and self._mode != mode:
            _LOGGER.debug("midea-dehumidifier: sending send_mode_command via Web API...")
            res = await self.hass.async_add_executor_job(self._client.send_mode_command, self._device["id"], mode)
            if res is not None:
                _LOGGER.debug("midea-dehumidifier: send_mode_command suceeded: "+self._client.deviceStatus.toString())
                self._mode = mode_name
                #Dryer mode set speed_mode to High too
                if mode == 4:    
                    self._windSpeedMode = 'High'
                    self._windSpeed = self._fan_dict.get('HIGH', 0)
                
                #Update state attribute
                state = self._hass.states.get('humidifier.'+self._unique_id)
                if state:
                    attrs = state.attributes.copy()
                    attrs[ATTR_MODE] = mode_name
                    #Dryer mode set speed_mode to High too
                    if mode == 4:
                        attrs[ATTR_FAN_SPEED_MODE] = 'High'
                        attrs[ATTR_FAN_SPEED] = self._fan_dict.get('HIGH', 0)
                    
                    #attrs = self.__hass_update_state_attribute(state, ATTR_MODE, mode)
                    self._hass.states.async_set('humidifier.'+self._unique_id, state.state, attrs, force_update = True)

            else:
                _LOGGER.error("midea-dehumidifier: send_mode_command ERROR.")


    async def async_update(self):
        """Retrieve latest state from the appliance and keep UI updated with respect to the updated status."""
        _LOGGER.info("midea-dehumidifier: async_update called.")
        
        if self._client.security.access_token:
            _LOGGER.debug("midea-dehumidifier: sending get_device_status via Web API...")
            #res = self._client.get_device_status(self._device['id'])
            res = await self.hass.async_add_executor_job(self._client.get_device_status, self._device['id'])
            if res == 1:
                _LOGGER.info(self._device['id']+" - "+self._client.deviceStatus.toString())
                #Refresh device status
                self.__refresh_device_status()
            else:
                _LOGGER.error("midea-dehumidifier: get_device_status ERROR.")


    def __refresh_device_status(self):
        """Called by async_update(self): keep UI updated with respect to the updated status."""
        if self._client.deviceStatus is not None:
            self._powerMode = self._client.deviceStatus.powerMode
            self._ionSetSwitch = self._client.deviceStatus.ionSetSwitch

            #Current mode
            #self._mode = self._client.deviceStatus.setMode
            self._mode = self._available_modes[self._client.deviceStatus.setMode - 1]

            self._windSpeed = self._client.deviceStatus.windSpeed
            if self._windSpeed == 40:
                self._windSpeedMode = self._fan_list[0]
            elif self._windSpeed == 60:
                self._windSpeedMode = self._fan_list[1]
            elif self._windSpeed == 80:
                self._windSpeedMode = self._fan_list[2]
            else:
                self._windSpeedMode = "unknown"

            self._humidity = self._client.deviceStatus.humidity
            self._humidity_set = self._client.deviceStatus.humidity_set
            self._humidity_dot = self._client.deviceStatus.humidity_dot
            self._humidity_dot_set = self._client.deviceStatus.humidity_dot_set
            self._isDisplay = self._client.deviceStatus.isDisplay
            self._filterShow = self._client.deviceStatus.filterShow
            self._tankShow = self._client.deviceStatus.tankShow
            self._dryClothesSetSwitch = self._client.deviceStatus.dryClothesSetSwitch
            self._upAndDownSwing = self._client.deviceStatus.upAndDownSwing

            #Useful or useless ?
            #self.async_update_ha_state()
            #self.async_schedule_update_ha_state()

            #PROVE
            #async_update_entity(self._hass, self._name)
            #async_update_entity(self._hass, 'humidifier.midea_dehumidifier_17592186063322')
            #ALTERNATIVA DA PROVARE: self.async_update_entity(self._hass, self._unique_id)

#            state = hass.states.get(entity_id)
#            if state:
#                attrs = state.attributes
#            self._hass.states.set(self._unique_id, state, state.attributes, force_update=True)


    async def async_turn_on(self, **kwargs):
        """Turn the device on."""
        _LOGGER.info("midea-dehumidifier:async_turn_on called.")
        if not self.is_on:
            _LOGGER.debug("midea-dehumi: sending power-on command via Web API...")
            #res = self._client.send_poweron_command(self._device["id"])
            res = await self.hass.async_add_executor_job(self._client.send_poweron_command, self._device["id"])
            if res is not None:
                _LOGGER.debug("midea-dehumidifier: send_poweron_command suceeded: "+self._client.deviceStatus.toString())
                #Refresh device status
                self.__refresh_device_status()
            else:
                _LOGGER.error("midea-dehumidifier: send_poweron_command ERROR.")


    async def async_turn_off(self, **kwargs):
        """Turn the device off."""
        _LOGGER.info("midea-dehumidifier: async_turn_off called.")
        if self.is_on:
            _LOGGER.debug("midea-dehumi: sending power-off command via Web API...")
            #res = self._client.send_poweroff_command(self._device["id"])
            res = await self.hass.async_add_executor_job(self._client.send_poweroff_command, self._device["id"])
            if res is not None:
                _LOGGER.debug("midea-dehumidifier: send_poweroff_command suceeded: "+self._client.deviceStatus.toString())
                #Refresh device status
                self.__refresh_device_status()
            else:
                _LOGGER.error("climate.midea-dehumi: send_poweroff_command ERROR.")


    async def async_set_humidity(self, humidity):
        """Set new humidity level."""
        _LOGGER.info("midea-dehumidifier: async_set_humidity called.")
        if self.is_on:
            if self._humidity_set != humidity:
                _LOGGER.debug("midea-dehumidifier: setting new target hunidity value via Web API...")
                #res = self._client.send_target_humidity_command(self._device["id"], humidity)
                res = await self.hass.async_add_executor_job(self._client.send_target_humidity_command, self._device["id"], humidity)
                if res is not None:
                    _LOGGER.info("midea-dehumidifier: send_target_humidity_command succeeded: "+self._client.deviceStatus.toString())
                    #Refresh device status
                    self.__refresh_device_status()
                else:
                    _LOGGER.error("midea-dehumidifier: send_target_humidity_command ERROR")


    async def async_set_mode(self, mode):
        """Update mode."""
        _LOGGER.info("midea-dehumidifier: async_set_mode called; current_mode=%s, new mode=%s", self._mode, mode)
        if self.is_on:
            mode_num = self._modes_dict.get(mode.upper(), 0)            
            _LOGGER.debug("midea-dehumi: sending update status command via Web API...")
            #res = self._client.send_mode_command(self._device["id"], mode_num)
            res = await self.hass.async_add_executor_job(self._client.send_mode_command, self._device["id"], mode_num)
            if res is not None:
                _LOGGER.debug("midea-dehumidifier: send_mode_command suceeded: "+self._client.deviceStatus.toString())
                self._client.deviceStatus._setMode = mode_num
                #Refresh device status
                self.__refresh_device_status()
            else:
                _LOGGER.error("climate.midea-dehumi: send_mode_command ERROR.")


Hello, do you get any info about compatibility of Atmosphere with this component?

Update: Inventor Atmosphere use Tuya as communication, so you can use TuyaSmart app instead
Inventor Control. Even Tuya has a native support in HA, the Tuya dehumidifier’s doesn’t supported yet, so you can just have scenes defined in Tuya which you can trigger from HA but this is one way communication. I hope HA will get support for Tuya dehumidifier’s in the near feature.

1 Like

Hello fellow home-assistant enthusiasts!
I have a quick question, did anybody (or is it even possible?) used a Wemos Mini (Esp8266) and Tasmota to controll the device cloud-free?
I have found projects for ESP8266 but not with the Wemos version or Tasmota

Update:
I got the cloud-free control through https://github.com/Hypfer/esp8266-midea-dehumidifier
I also didn’t use a USB Adapter since I cut the USB female connector and connected direct the cables on ESP-01

1 Like

Hello! A couple of days now the integration stopped working. I believe something changed to the midea API.

Problem resolved without any changes.

Problem integation log pase:

Logger: homeassistant.setup
Source: setup.py:308
First occurred: 20:52:44 (2 occurrences)
Last logged: 20:52:45

  • Unable to prepare setup for platform midea_dehumidifier.sensor: Platform not found (cannot import name ‘ATTR_MODE’ from ‘homeassistant.components.humidifier.const’ (/usr/src/homeassistant/homeassistant/components/humidifier/const.py)).
  • Unable to prepare setup for platform midea_dehumidifier.humidifier: Platform not found (cannot import name ‘ATTR_MODE’ from ‘homeassistant.components.humidifier.const’ (/usr/src/homeassistant/homeassistant/components/humidifier/const.py)).

My product Inventor Eva II PRO WiFi, everything was working so far with HACS

Help, please…

My sistem:

Versión core-2021.4.3
Tipo de instalación Home Assistant OS
Desarrollo false
Supervisor true
Docker true
Entorno virtual false
Versión de Python 3.8.7
Nombre del Sistema Operativo Linux
Versión del Sistema Operativo 5.4.83-v7l
Arquitectura de CPU armv7l
Zona horaria Europe/Madrid

Try to update your integration. There were some recent changes in the repository which do fix the issue.
I had the same problem using it as a manual added custom component and after installing the new files it is working perfectly again.

https://github.com/barban-dev/homeassistant-midea-dehumidifier/commits/master/custom_components/midea_dehumidifier

I have a question. Is possible have a sensor, to know when the tank is water full ?

Hello Barban,

please do you think this integration would work with the new “ion” version? seems same and I dont care about automating the ioniser… just dehumidifying.

BR,
Dusan

1 Like

It seems that there is compatibility, based on this issue.
Although, it would be great if we had an official response approving its full compatibility.

Hope to have a response as well.

1 Like

thank you, i noted that eva 2 pro too had Ioniser on UK Amazon so I figured it could just be different markets naming. I ordered to Slovakia from German Amazon, as only one seller here offered it, and that for 350 eur, so ordering from Germany with 50 eur postage still saved me 100 eur :man_facepalming: :).

now let’s hope it works :D, as it’s the main reason I got this model :slight_smile:

Please inform us about its compatibility with the integration, as soon as it arrives.

Thank you

Anyone know if this works with the Media 50 Pint Cube dehumidifier?
MAD50S1QWT

So, does anyone know if the Eva ION Pro is compatible with this integration?

It works! I can set target humidity and modes and so on!

1 Like

Thank you barban,

I confirm this custom component works also with “Eva ION Pro Wi-Fi“

2 Likes

I can confirm that it works for “50 Pint Cube Smart Dehumidifier” : MC50MSWBA3RCM

The only function that has a quirk is ‘Fan Mode’. The Cube model mentioned only has two fan speeds - Low and High. Using the the ‘Medium’ input_select changes the Fan Mode to ‘Low’ - so no real issue there just have to remember.

All other functions work as expected.

2 Likes

Hello, so I tried out quite a bit of what I’ve read here.
First that works with the integration of several devices.
Now to the problems it depends on which card is used. If you use the recommended card, you can’t change Fan Made at all.


But if you use a different card you can change the Fan Mod and the mode, but with me it happens on all devices at the same time. Sometimes all devices turn on.