diff --git a/src/panels/lovelace/cards/hui-glance-card.js b/src/panels/lovelace/cards/hui-glance-card.js index a43e647762..db8bf7ebf5 100644 --- a/src/panels/lovelace/cards/hui-glance-card.js +++ b/src/panels/lovelace/cards/hui-glance-card.js @@ -3,7 +3,9 @@ import { PolymerElement } from '@polymer/polymer/polymer-element.js'; import computeStateDisplay from '../../../common/entity/compute_state_display.js'; import computeStateName from '../../../common/entity/compute_state_name.js'; +import computeConfigEntities from '../common/compute-config-entities'; import createErrorCardConfig from '../common/create-error-card-config.js'; +import validateEntitiesConfig from '../common/validate-entities-config'; import './hui-error-card.js'; import '../../../components/entity/state-badge.js'; @@ -84,34 +86,36 @@ class HuiGlanceCard extends LocalizeMixin(EventsMixin(PolymerElement)) { } _computeEntities(config) { - if (!config || !config.entities || !Array.isArray(config.entities)) { + const entities = computeConfigEntities(config); + + if (!validateEntitiesConfig(config)) { const error = 'Error in card configuration.'; this._error = createErrorCardConfig(error, config); return []; } this._error = null; - return config.entities; + return entities; } _showEntity(item, states) { - return item in states; + return item.entity in states; } _computeName(item, states) { - return computeStateName(states[item]); + return item.title || computeStateName(states[item.entity]); } _computeStateObj(item, states) { - return states[item]; + return states[item.entity]; } _computeState(item, states) { - return computeStateDisplay(this.localize, states[item]); + return computeStateDisplay(this.localize, states[item.entity]); } _openDialog(ev) { - this.fire('hass-more-info', { entityId: ev.model.item }); + this.fire('hass-more-info', { entityId: ev.model.item.entity }); } } diff --git a/src/panels/lovelace/common/compute-config-entities.js b/src/panels/lovelace/common/compute-config-entities.js new file mode 100644 index 0000000000..6dc76f11df --- /dev/null +++ b/src/panels/lovelace/common/compute-config-entities.js @@ -0,0 +1,17 @@ +// Parse array of entity objects from config +export default function computeConfigEntities(config) { + const entities = config && config.entities; + + if (!entities || !Array.isArray(entities)) { + return null; + } + + return entities.map((entity) => { + if (typeof entity === 'string') { + return { entity }; + } else if (typeof entity === 'object' && !Array.isArray(entity)) { + return entity; + } + return null; + }); +} diff --git a/src/panels/lovelace/common/validate-entities-config.js b/src/panels/lovelace/common/validate-entities-config.js new file mode 100644 index 0000000000..c005a5b276 --- /dev/null +++ b/src/panels/lovelace/common/validate-entities-config.js @@ -0,0 +1,18 @@ +/** + * Check that all items in array are objects with an entity property containing a valid entity_id. + * + * Optionally provide an array of additional keys that must be present in every object + */ + +import validEntityId from '../../../common/entity/valid_entity_id'; + +export default function validateEntitiesConfig(config, additionalKeys = []) { + const entities = config && config.entities; + + if (!entities || !Array.isArray(entities)) { + return false; + } + + return entities.every(entity => entity && typeof entity === 'object' && !Array.isArray(entity) && + 'entity' in entity && validEntityId(entity.entity) && additionalKeys.every(key => key in entity)); +}