Refactor remove device & remove from home assistant

This commit is contained in:
Koenkk 2018-06-09 12:27:04 +02:00
parent 7c53e9bb15
commit 884e3aa475
4 changed files with 66 additions and 33 deletions

View File

@ -162,7 +162,7 @@ class Controller {
getDeviceStartupLogMessage(device) {
let friendlyName = 'unknown';
let type = 'unknown';
let friendlyDevice = { model: 'unkown', description: 'unknown' };
let friendlyDevice = {model: 'unkown', description: 'unknown'};
const mappedModel = zigbeeShepherdConverters.findByZigbeeModel(device.modelId);
if (mappedModel) {
friendlyDevice = mappedModel;
@ -310,20 +310,33 @@ class Controller {
this.mqtt.log('devices', devices);
} else if (option === 'remove') {
if (message.toString() !== null && message.toString() !== '' && message.toString().length > 0) {
const deviceID = Object.keys(settings.get().devices).find((id) =>
settings.getDevice(id).friendly_name === message.toString()
);
if (!deviceID) {
logger.error(`Cannot handle '${topic}' because deviceID of '${message.toString()}' cannot be found`);
return;
}
settings.removeDevice(deviceID);
this.zigbee.removedevice(deviceID);
} else {
logger.error(`Cannot handle MQTT config option '${option}' with Payload is null - we need the friendly_name to proceed`);
message = message.toString();
const deviceID = settings.getIDByFriendlyName(message);
const device = this.zigbee.getDevice(deviceID);
if (!deviceID) {
logger.error(`Cannot handle '${topic}' because device with friendly_name '${message}' cannot be found`);
return;
}
// Remove from zigbee network and settings.
this.zigbee.removeDevice(deviceID, (error) => {
if (!error) {
// Clear Home Assistant MQTT discovery message
const mappedModel = zigbeeShepherdConverters.findByZigbeeModel(device.modelId);
if (settings.get().homeassistant && mappedModel) {
homeassistant.clear(deviceID, mappedModel.model, this.mqtt);
}
// Remove from configuration.yaml
settings.removeDevice(deviceID);
logger.info(`Successfully removed ${deviceID}`);
this.mqtt.log('removed_device', message);
} else {
logger.error(`Failed to remove ${deviceID}`);
}
});
} else {
logger.warn(`Cannot handle MQTT config option '${option}' with message '${message}'`);
}
@ -334,9 +347,7 @@ class Controller {
const topicPrefix = withPrefix ? topic.split('/')[2] : '';
// Map friendlyName to deviceID.
const deviceID = Object.keys(settings.get().devices).find((id) =>
settings.getDevice(id).friendly_name === friendlyName
);
const deviceID = settings.getIDByFriendlyName(friendlyName);
if (!deviceID) {
logger.error(`Cannot handle '${topic}' because deviceID of '${friendlyName}' cannot be found`);
@ -349,7 +360,7 @@ class Controller {
json = JSON.parse(message);
} catch (e) {
// Cannot be parsed to JSON, assume state message.
json = { state: message.toString() };
json = {state: message.toString()};
}
// Find ep for this device
@ -383,7 +394,7 @@ class Controller {
this.zigbee.publish(deviceID, message.cid, message.cmd, message.zclData, ep, callback);
published.push({ message: message, converter: converter });
published.push({message: message, converter: converter});
});
/**

View File

@ -285,7 +285,23 @@ function discover(deviceID, model, mqtt) {
discovered[deviceID] = true;
}
function clear(deviceID, model, mqtt) {
// Check if there are configs.
if (!mapping[model]) {
return;
}
mapping[model].forEach((config) => {
const topic = `${config.type}/${deviceID}/${config.object_id}/config`;
const payload = '';
mqtt.publish(topic, payload, {retain: true, qos: 0}, null, 'homeassistant');
});
discovered[deviceID] = false;
}
module.exports = {
mapping: mapping,
discover: (deviceID, model, mqtt) => discover(deviceID, model, mqtt),
clear: (deviceID, model, mqtt) => clear(deviceID, model, mqtt),
};

View File

@ -34,10 +34,21 @@ function removeDevice(id) {
}
}
function getIDByFriendlyName(friendlyName) {
if (!settings.devices) {
return null;
}
return Object.keys(settings.devices).find((id) =>
settings.devices[id].friendly_name === friendlyName
);
}
module.exports = {
get: () => settings,
write: () => write(),
getDevice: (id) => settings.devices ? settings.devices[id] : false,
addDevice: (id) => addDevice(id),
removeDevice: (id) => removeDevice(id),
getIDByFriendlyName: (friendlyName) => getIDByFriendlyName(friendlyName),
};

View File

@ -108,30 +108,25 @@ class Zigbee {
return this.shepherd.list().filter((device) => device.type !== 'Coordinator');
}
removedevice(deviceID) {
this.shepherd.remove(deviceID, (err) => {
if (err) {
logger.warn(`Failed to remove ${deviceID}`);
this.forceRemove(deviceID);
removeDevice(deviceID, callback) {
this.shepherd.remove(deviceID, (error) => {
if (error) {
logger.warn(`Failed to remove '${deviceID}', trying force remove...`);
this._forceRemove(deviceID, callback);
} else {
logger.info(`Successfully removed ${deviceID}`);
callback(null);
}
});
}
forceRemove(deviceID) {
_forceRemove(deviceID, callback) {
const device = this.shepherd._findDevByAddr(deviceID);
// force
if (device) {
return this.shepherd._unregisterDev(device, (err) => {
if (err) {
logger.warn(`Failed to force remove ${deviceID}`);
} else {
logger.info(`Successfully removed by force ${deviceID}`);
}
});
return this.shepherd._unregisterDev(device, (error) => callback(error));
} else {
logger.warn(`Could not find ${deviceID} for force removal`);
callback(true);
}
}