From 0c1bacee2295f8b0594416296425a599c1639a04 Mon Sep 17 00:00:00 2001 From: Steven Rollason <2099542+gadgetchnnel@users.noreply.github.com> Date: Fri, 25 Jun 2021 21:27:22 +0100 Subject: [PATCH] Updated UTC timezone conversion Updated UTC timezone conversion to be after application of history_days_back and calendar_days_back and calendar_days_forward. --- lovelace-home-feed-card.js | 2 +- src/main.js | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/lovelace-home-feed-card.js b/lovelace-home-feed-card.js index 309434e..a59efb9 100644 --- a/lovelace-home-feed-card.js +++ b/lovelace-home-feed-card.js @@ -346,7 +346,7 @@ const Q=window.ShadowRoot&&(void 0===window.ShadyCSS||window.ShadyCSS.nativeShad
${this.feedContent.map(e=>this._renderItem(e))}
${this._config.footer?this.renderHeaderFooter(this._config.footer,"footer"):""} - `):(this.style.display="none",A``):A``}get cacheId(){return this._config.card_id?this._config.card_id:this.pageId+this._config.title}get inEditMode(){return"HUI-CARD-PREVIEW"==(this.parentElement&&this.parentElement.nodeName)}clearCache(){localStorage.removeItem("home-feed-card-events"+this.cacheId),localStorage.removeItem("home-feed-card-eventsLastUpdate"+this.cacheId),localStorage.removeItem("home-feed-card-notifications"+this.cacheId),localStorage.removeItem("home-feed-card-notificationsLastUpdate"+this.cacheId),localStorage.removeItem("home-feed-card-history"+this.cacheId)}setConfig(e){if(!e)throw new Error("Invalid configuration");this._config=e,this.entities=this.processConfigEntities(this._config.entities),this.calendars=this._config.calendars,this.oldStates={},this.inEditMode||(console.log("Clearing Cache"),this.clearCache()),this.preloadElementsIfNeeded(),setTimeout(()=>this.buildIfReady(),10)}preloadElementsIfNeeded(){customElements.get("ha-markdown")&&customElements.get("hui-markdown-card")||(console.log("Preloading elements"),_e({type:"markdown",content:"**dummy Markdown card**"}))}processConfigEntities(e){if(!e)return[];if(!Array.isArray(e))throw new Error("Entities need to be an array");return e.map((e,t)=>{if("string"==typeof e)e={entity:e,exclude_states:["unknown"]};else{if("object"!=typeof e||Array.isArray(e))throw new Error(`Invalid entity specified at position ${t}.`);if(!e.entity)throw new Error(`Entity object at position ${t} is missing entity field.`);e.exclude_states||(e={...e,exclude_states:["unknown",null]})}return e})}computeStateDisplay(e,t){let a=t.entity.split(".")[0];if(t.attribute)return e.attributes[t.attribute];if("automation"==a)return"Triggered";var n,s,i=t.state_map&&t.state_map[e.state]?t.state_map[e.state]:null;return i||(n=this.hass_version,s="0.109.0",i=n.split(".").map(e=>String(parseInt(e)).padStart(3,"0")).join(".")>=s.split(".").map(e=>String(parseInt(e)).padStart(3,"0")).join(".")?function(e,t,a){if("unknown"===t.state||"unavailable"===t.state)return e("state.default."+t.state);if("timestamp"==t.attributes.device_class)return""+t.state;if(t.attributes.unit_of_measurement)return`${t.state} ${t.attributes.unit_of_measurement}`;const n=function(e){return(t=e.entity_id).substr(0,t.indexOf("."));var t}(t);if("input_datetime"===n){let e;if(!t.attributes.has_time)return e=new Date(t.attributes.year,t.attributes.month-1,t.attributes.day),Ne(e,a);if(!t.attributes.has_date){const n=new Date;return e=new Date(n.getFullYear(),n.getMonth(),n.getDay(),t.attributes.hour,t.attributes.minute),Fe(e,a)}return e=new Date(t.attributes.year,t.attributes.month-1,t.attributes.day,t.attributes.hour,t.attributes.minute),Ce(e,a)}return t.attributes.device_class&&e(`component.${n}.state.${t.attributes.device_class}.${t.state}`)||e(`component.${n}.state._.${t.state}`)||t.state}(this._hass.localize,e):$e(this._hass.localize,e)),i}getIcon(e,t){return t||(e&&e.attributes&&e.attributes.icon?e.attributes.icon:t)}getEntities(){return this.entities.filter(e=>!0!==e.multiple_items&&!0!==e.include_history).map(e=>{let t=this._hass.states[e.entity];if(null==t)return{entity_id:e.entity,icon:null,entity:e.entity,display_name:this._hass.localize("ui.panel.lovelace.warning.entity_not_found","entity",e.entity),more_info_on_tap:!1,content_template:null,state:"unavailable",stateObj:null,item_type:"unavailable"};let a=e.entity.split(".")[0];return e.exclude_states.includes(t.state)||"automation"==a&&!t.attributes.last_triggered?null:{...t,icon:this.getIcon(t,e.icon),entity:e.entity,display_name:e.name?e.name:t.attributes.friendly_name,format:null!=e.format?e.format:"relative",more_info_on_tap:e.more_info_on_tap,content_template:e.content_template,state:this.computeStateDisplay(t,e),stateObj:t,item_type:"entity"}}).filter(e=>null!=e)}applyTemplate(e,t,a=!1){var n=t;return"string"==typeof e&&(e={value:e}),Object.keys(e).forEach(t=>{n=n.replace("{{"+t+"}}",a?"{{ config.item."+t+" }}":e[t])}),e.attributes&&Object.keys(e.attributes).forEach(t=>{n=n.replace("{{"+t+"}}",e.attributes[t])}),n}getMultiItemEntities(){let e=this.entities.filter(e=>!0===e.multiple_items&&e.list_attribute&&e.content_template).map(e=>{let t=this._hass.states[e.entity];if(!t)return[];let a=this.getIcon(t,e.icon);return(t.attributes[e.list_attribute]?t.attributes[e.list_attribute]:[]).map(n=>{let s=e.timestamp_property&&n[e.timestamp_property]?n[e.timestamp_property]:t.last_changed,i=isNaN(s)?s:new Date(1e3*s);return{...t,icon:a,format:null!=e.format?e.format:"relative",entity:e.entity,display_name:this.applyTemplate(n,e.content_template),last_changed:i,stateObj:t,more_info_on_tap:e.more_info_on_tap,item_data:n,detail:e.detail_template?this.applyTemplate(n,e.detail_template,!1):null,item_type:"multi_entity"}}).sort((e,t)=>e.last_changed1==e.include_history).map(e=>e.entity).join();if(!e||0==e.length)return[];let t=this._config.history_days_back?this._config.history_days_back:0;const a=this.moment.utc().startOf("day").add(-t,"days").format("YYYY-MM-DDTHH:mm:ss"),n=this.moment.utc().format("YYYY-MM-DDTHH:mm:ss");try{let t=(await this._hass.callApi("get",`history/period/${a}Z?end_time=${n}Z&filter_entity_id=${e}`)).map(e=>{let t=this.entities.find(t=>t.entity==e[0].entity_id),a=this._hass.states[t.entity];if(!a)return[];let n=!1!==t.remove_repeats;return e.filter(e=>!t.exclude_states.includes(e.state)).filter((e,a,s)=>this.repeatFilter(e,a,s,n,t.keep_latest)).reverse().slice(0,t.max_history?t.max_history:3).map(e=>({...e,icon:this.getIcon(e,t.icon),display_name:t.name?t.name:e.attributes.friendly_name,format:null!=t.format?t.format:"relative",more_info_on_tap:t.more_info_on_tap,content_template:t.content_template,state:this.computeStateDisplay(e,t),latestStateObj:a,stateObj:this.getHistoryState(a,e),item_type:"entity_history"}))});return[].concat.apply([],t)}catch(e){return[]}}haveHistoryEntitiesChanged(){var e=this.entities.filter(e=>1==e.include_history).map(e=>e.entity);if(!e)return!1;for(const t of e){let e=this.oldStates[t];null==e&&(e={state:"undefined"});let a=this._hass.states[t];if(null==a&&(a={state:"undefined"}),a.state!=e.state)return!0}return!1}async refreshEntityHistory(){if(!this._config.entities||0==this._config.entities.length)return void(JSON.parse(localStorage.getItem("home-feed-card-history"+this.cacheId))&&localStorage.removeItem("home-feed-card-history"+this.cacheId));let e=await this.getLiveEntityHistory();localStorage.setItem("home-feed-card-history"+this.cacheId,JSON.stringify(e)),this.buildIfReady()}eventTime(e){return e.date?e.date:e.dateTime?e.dateTime:e}eventAllDay(e){var t=!1;if(e.start.date)t=!0;else if(e.start.dateTime)t=!1;else{let a=this.moment(e.start);t=this.moment(e.end).diff(a,"hours")>=24}return t}async getEvents(){if(!this.calendars||0==this.calendars.length)return[];let e=JSON.parse(localStorage.getItem("home-feed-card-eventsLastUpdate"+this.cacheId));if(!e||this.moment&&this.moment().diff(e,"minutes")>15){let e=void 0!==this._config.calendar_days_back?this._config.calendar_days_back:0,n=void 0!==this._config.calendar_days_forward?this._config.calendar_days_forward:1;const s=this.moment.utc().startOf("day").add(-e,"days").format("YYYY-MM-DDTHH:mm:ss"),i=this.moment.utc().startOf("day").add(n+1,"days").format("YYYY-MM-DDTHH:mm:ss");try{var t=await Promise.all(this.calendars.map(async e=>{let t=`calendars/${e}?start=${s}Z&end=${i}Z`;return(await this._hass.callApi("get",t)).map(t=>({...t,calendar:e}))}))}catch(e){console.error("Error getting calendar events");t=[]}var a=[].concat.apply([],t).map(e=>{let t=this._hass.states[e.calendar];if(!t)return[];let a={...e,display_name:e.summary?e.summary:e.title,start_time:this.eventTime(e.start),end_time:this.eventTime(e.end),all_day:this.eventAllDay(e),format:this._config.calendar_time_format?this._config.calendar_time_format:"relative",item_type:"calendar_event"},n=this.moment(new Date(a.start_time)),s=this.moment(new Date(a.end_time)),i="";return a.all_day?(s=s.startOf("day").add(-1,"hours"),i=n.clone().startOf("day").isSame(s.clone().startOf("day"))?""+n.format("dddd, D MMMM"):n.month()==s.month()?`${n.format("D")} - ${s.format("D MMMM YYYY")}`:n.year()==s.year()?`${n.format("D MMMM")} - ${s.format("D MMMM YYYY")}`:`${n.format("D MMMM YYYY")} - ${s.format("D MMMM YYYY")}`):i=n.clone().startOf("day").isSame(s.clone().startOf("day"))?n.format("a")==s.format("a")?`${n.format("dddd, D MMMM")} ⋅ ${n.format("h:mm")} - ${s.format("h:mm a")}`:`${n.format("dddd, D MMMM")} ⋅ ${n.format("h:mm a")} - ${s.format("h:mm a")}`:`${n.format("D MMMM YYYY, h:mm a")} - ${s.format("D MMMM YYYY, h:mm a")}`,a.detail=` ${i}\n\t \t\t\n ${t.attributes.friendly_name}\n\t \t\t`,a});return localStorage.setItem("home-feed-card-events"+this.cacheId,JSON.stringify(a)),localStorage.setItem("home-feed-card-eventsLastUpdate"+this.cacheId,JSON.stringify(this.moment())),a}return JSON.parse(localStorage.getItem("home-feed-card-events"+this.cacheId))}notificationIdToTitle(e){return e.replace(/[^a-zA-Z0-9]/g," ").toLowerCase().replace(/\b(\w)/g,e=>e.toUpperCase())}async refreshNotifications(){if(!this._hass)return;if(this.refreshingNotifications)return;this.refreshingNotifications=!0;var e=await this._hass.callWS({type:"persistent_notification/get"});this._config.id_filter&&(e=e.filter(e=>e.notification_id.match(this._config.id_filter)));let t=e.map(e=>({...e,title:e.title?e.title:this.notificationIdToTitle(e.notification_id),format:"relative",item_type:"notification",original_notification:e}));localStorage.setItem("home-feed-card-notifications"+this.cacheId,JSON.stringify(t)),this.moment&&localStorage.setItem("home-feed-card-notificationsLastUpdate"+this.cacheId,JSON.stringify(this.moment())),this.refreshingNotifications=!1,this.loadedNotifications=!0,this.buildIfReady()}getNotifications(){return JSON.parse(localStorage.getItem("home-feed-card-notifications"+this.cacheId))?JSON.parse(localStorage.getItem("home-feed-card-notifications"+this.cacheId)):[]}async getEntityHistoryItems(){return JSON.parse(localStorage.getItem("home-feed-card-history"+this.cacheId))?JSON.parse(localStorage.getItem("home-feed-card-history"+this.cacheId)):[]}getItemTimestamp(e){switch(e.item_type){case"notification":return e.created_at;case"calendar_event":return e.start_time;case"entity":case"entity_history":case"multi_entity":if("timestamp"===e.attributes.device_class)return e.state;return"automation"==e.entity_id.split(".")[0]?e.attributes.last_triggered:e.attributes.last_changed?e.attributes.last_changed:e.last_changed;default:return(new Date).toISOString()}}debugItem(){if(!this._config.debug)return[];let e=localStorage.getItem("home-feed-card-history"+this.cacheId),t="## Debug Information\n\n**Cache Id:** "+this.cacheId+"\n\n**Cache Status:** "+(e?"From Cache":"Live")+"\n\n**Language (Home Assistant):** "+(this._hass?this._hass.language:"unknown")+"\n\n**Language (Browser):** "+(this.browser_language?this.browser_language:"unknown");return[{state:"on",attributes:{device_class:"debug"},icon:"mdi:bug",format:"relative",entity_id:"home_feed.debug_info",entity:"home_feed.debug_info",display_name:t,last_changed:new Date,stateObj:null,more_info_on_tap:!0,item_data:null,detail:t,content_template:"{{display_name}}",item_type:"entity"}]}async getFeedItems(){var e=[].concat.apply([],await Promise.all([this.debugItem(),this.getNotifications(),this.getEvents(),this.getEntities(),this.getMultiItemEntities(),this.getEntityHistoryItems()])),t=new Date;return(e=e.map(e=>{let a=this.getItemTimestamp(e),n=new Date(a),s=(t-n)/1e3;return{...e,timestamp:a,timeDifference:{value:s,abs:Math.abs(s),sign:Math.sign(s)}}})).sort((e,t)=>e.timeDifference.abst.timeDifference.abs?1:0)}_handleDismiss(e){var t=e.target.notificationId;this._hass.callService("persistent_notification","dismiss",{notification_id:t})}_moreInfoHeaderClick(e){let t=document.querySelector("home-assistant")._moreInfoEl;t.large=!t.large}provideHass(e){return document.querySelector("hc-main")?document.querySelector("hc-main").provideHass(e):document.querySelector("home-assistant")?document.querySelector("home-assistant").provideHass(e):void 0}fireEvent(e,t,a=null){if((e=new Event(e,{bubbles:!0,cancelable:!1,composed:!0})).detail=t||{},a)a.dispatchEvent(e);else{var n=document.querySelector("home-assistant");(n=(n=(n=(n=(n=(n=(n=(n=(n=(n=(n=n&&n.shadowRoot)&&n.querySelector("home-assistant-main"))&&n.shadowRoot)&&n.querySelector("app-drawer-layout partial-panel-resolver"))&&n.shadowRoot||n)&&n.querySelector("ha-panel-lovelace"))&&n.shadowRoot)&&n.querySelector("hui-root"))&&n.shadowRoot)&&n.querySelector("ha-app-layout #view"))&&n.firstElementChild)&&n.dispatchEvent(e)}}moreInfo(e){this.fireEvent("hass-more-info",{entityId:e})}findPopUpCard(e){let t=document.querySelector("home-assistant");return t=t&&t.shadowRoot,t=t&&t.querySelector("card-tools-popup"),t=t&&t.shadowRoot,t=t&&t.querySelector("ha-dialog"),t.querySelector(e)}_handleClick(e){let t=e.currentTarget.item;if("entity_history"==t.item_type){let e={};Object.assign(e,this._hass),e.states=[],e.states[t.entity_id]=t.stateObj;let a={type:"custom:hui-entities-card",entities:[{entity:t.entity_id,secondary_info:"last-changed"},{type:"custom:hui-history-graph-card",entities:[t.entity_id]},{type:"custom:hui-logbook-card",entities:[t.entity_id]}]};_e({type:"logbook",entities:[t.entity_id]}),ce(t.display_name,a,!1,{"box-shadow":"none!important"}),setTimeout(()=>{let t=this.findPopUpCard("hui-entities-card");if(t){t.hass=e;let a=t.shadowRoot&&t.shadowRoot.querySelector("ha-card");a&&(a.style.borderRadius="0");let n=a&&a.querySelector("#states");if(n){n.querySelector("div hui-history-graph-card").shadowRoot.querySelector("ha-card").style.boxShadow="none",n.querySelector("div hui-logbook-card").shadowRoot.querySelector("ha-card").style.boxShadow="none"}}},100)}else if("multi_entity"==t.item_type||"calendar_event"==t.item_type){let e={};Object.assign(e,this._hass);let a={type:"custom:hui-markdown-card",content:t.detail,item:t.item_data},n=80,s=t.display_name;s.length>n&&(s=s.substring(0,n-3)+"..."),ce(s,a,!1),setTimeout(()=>{let e=this.findPopUpCard("hui-markdown-card"),t=e.parentElement.parentElement.querySelector("app-toolbar").getBoundingClientRect(),a=Math.trunc(t.width),n=e&&e.shadowRoot&&e.shadowRoot.querySelector("ha-card");if(n){n.style.background="rgba(0,0,0,0)",n.style.boxShadow="none",n.style.borderRadius=0,n.style.maxHeight="75vh",n.style.minWidth=a+"px",n.style.overflow="auto";let e=n.querySelector("ha-markdown").shadowRoot.querySelector("ha-markdown-element");e&&e.querySelectorAll("a").forEach(e=>{e.addEventListener("click",me)})}},100)}else if("notification"==t.item_type){let e=t.original_notification;e.title||(e.title=this.notificationIdToTitle(e.notification_id));let a={type:"custom:home-feed-notification-popup",notification:e};ce(e.title,a,!1)}else!function(e,t,a,n,s){var i;if(s&&a.double_tap_action?i=a.double_tap_action:n&&a.hold_action?i=a.hold_action:!n&&a.tap_action&&(i=a.tap_action),i||(i={action:"more-info"}),!i.confirmation||i.confirmation.exemptions&&i.confirmation.exemptions.some((function(e){return e.user===t.user.id}))||confirm(i.confirmation.text||"Are you sure you want to "+i.action+"?"))switch(i.action){case"more-info":(i.entity||a.entity||a.camera_image)&&(Je(e,"hass-more-info",{entityId:i.entity?i.entity:a.entity?a.entity:a.camera_image}),i.haptic&&Ve(i.haptic));break;case"navigate":i.navigation_path&&(qe(0,i.navigation_path),i.haptic&&Ve(i.haptic));break;case"url":i.url_path&&window.open(i.url_path),i.haptic&&Ve(i.haptic);break;case"toggle":a.entity&&(Ge(t,a.entity),i.haptic&&Ve(i.haptic));break;case"call-service":if(!i.service)return;var r=i.service.split(".",2),o=r[0],d=r[1],u=Object.assign({},i.service_data);"entity"===u.entity_id&&(u.entity_id=a.entity),t.callService(o,d,u),i.haptic&&Ve(i.haptic)}}(this,this._hass,{entity:t.entity_id,tap_action:{action:"more-info"}},!1,!1)}_computeTooltip(e,t){if(!e||!t)return;return new Date(t.created_at).toLocaleDateString(this._hass.language,{year:"numeric",month:"short",day:"numeric",minute:"numeric",hour:"numeric"})}_buildFeed(){this._hass&&this.getFeedItems().then(e=>{this._config.max_item_count&&e.splice(this._config.max_item_count),this.feedContent=e,this.requestUpdate()})}_renderItem(e){let t=!0===this._config.compact_mode,a=!1!==this._config.show_icons;switch(e.item_type){case"notification":var n="mdi:bell";if(this._config.show_notification_title)var s=""+e.title+"\n\n"+e.message;else s=e.message;break;case"calendar_event":n="mdi:calendar",s=e.display_name;break;case"entity":case"entity_history":n=e.icon;e.entity_id.split(".")[0];if("timestamp"===e.attributes.device_class){s=""+e.display_name;if(!n)n="mdi:clock-outline"}else if(e.content_template)s=this.applyTemplate(e,e.content_template);else s=`${e.display_name} @ ${e.state}`;break;case"multi_entity":n=e.icon,s=""+e.display_name;break;case"unavailable":n="mdi:alert-circle",s=""+e.display_name;break;default:n="mdi:bell",s="Unknown Item Type"}e.stateObj||n||(n="mdi:bell");var i=!1,r="";if(void 0!==e.more_info_on_tap?e.more_info_on_tap:this._config.more_info_on_tap)switch(e.item_type){case"entity":case"entity_history":case"notification":i=!0;break;case"multi_entity":case"calendar_event":i=!!e.detail}var o;if(t&&"notification"==e.item_type&&(i=!0),i&&(r="state-card-dialog"),"calendar_event"==e.item_type&&e.all_day){let a=e.start.date?this.moment(e.start.date).startOf("day"):this.moment(e.start).startOf("day"),n=e.end.date?this.moment(e.end.date).startOf("day"):this.moment(e.end).startOf("day");if(n=n.add(-1,"hours").startOf("day"),Math.abs(a.diff(this.moment().startOf("day"),"days"))<=7){var d=Ze(a);if(n>a){let e=Ze(n);e==n.format("L")&&(e=n.toDate().toLocaleDateString(this._hass.language,{year:"numeric",month:"long",day:"numeric"})),d=d+" - "+e}o=A`
${d}
`}else{d=a.toDate().toLocaleDateString(this._language,{year:"numeric",month:"long",day:"numeric"});n>a&&(d=d+" - "+n.toDate().toLocaleDateString(this._hass.language,{year:"numeric",month:"long",day:"numeric"})),o=A`
${d}
`}}else{let a=!0===this._config.exact_durations;if(isNaN(e.timeDifference.value))o=A`
${e.timestamp}
`;else if(e.timeDifference.abs<60&&"relative"==e.format&&!a)if("en"!=this._language){let a=this._hass.localize("ui.components.relative_time.duration.minute","count",1).replace("1","<1"),n=e.timeDifference.sign>=0?"past":"future",s=this._hass.localize("ui.components.relative_time."+n,"time",a);o=A`
${s}
`}else{let a=0==e.timeDifference.sign?"now":1==e.timeDifference.sign?"<1 minute ago":"in <1 minute";o=A`
${a}
`}else o=A`this.buildIfReady(),10)}preloadElementsIfNeeded(){customElements.get("ha-markdown")&&customElements.get("hui-markdown-card")||(console.log("Preloading elements"),_e({type:"markdown",content:"**dummy Markdown card**"}))}processConfigEntities(e){if(!e)return[];if(!Array.isArray(e))throw new Error("Entities need to be an array");return e.map((e,t)=>{if("string"==typeof e)e={entity:e,exclude_states:["unknown"]};else{if("object"!=typeof e||Array.isArray(e))throw new Error(`Invalid entity specified at position ${t}.`);if(!e.entity)throw new Error(`Entity object at position ${t} is missing entity field.`);e.exclude_states||(e={...e,exclude_states:["unknown",null]})}return e})}computeStateDisplay(e,t){let a=t.entity.split(".")[0];if(t.attribute)return e.attributes[t.attribute];if("automation"==a)return"Triggered";var n,s,i=t.state_map&&t.state_map[e.state]?t.state_map[e.state]:null;return i||(n=this.hass_version,s="0.109.0",i=n.split(".").map(e=>String(parseInt(e)).padStart(3,"0")).join(".")>=s.split(".").map(e=>String(parseInt(e)).padStart(3,"0")).join(".")?function(e,t,a){if("unknown"===t.state||"unavailable"===t.state)return e("state.default."+t.state);if("timestamp"==t.attributes.device_class)return""+t.state;if(t.attributes.unit_of_measurement)return`${t.state} ${t.attributes.unit_of_measurement}`;const n=function(e){return(t=e.entity_id).substr(0,t.indexOf("."));var t}(t);if("input_datetime"===n){let e;if(!t.attributes.has_time)return e=new Date(t.attributes.year,t.attributes.month-1,t.attributes.day),Ne(e,a);if(!t.attributes.has_date){const n=new Date;return e=new Date(n.getFullYear(),n.getMonth(),n.getDay(),t.attributes.hour,t.attributes.minute),Fe(e,a)}return e=new Date(t.attributes.year,t.attributes.month-1,t.attributes.day,t.attributes.hour,t.attributes.minute),Ce(e,a)}return t.attributes.device_class&&e(`component.${n}.state.${t.attributes.device_class}.${t.state}`)||e(`component.${n}.state._.${t.state}`)||t.state}(this._hass.localize,e):$e(this._hass.localize,e)),i}getIcon(e,t){return t||(e&&e.attributes&&e.attributes.icon?e.attributes.icon:t)}getEntities(){return this.entities.filter(e=>!0!==e.multiple_items&&!0!==e.include_history).map(e=>{let t=this._hass.states[e.entity];if(null==t)return{entity_id:e.entity,icon:null,entity:e.entity,display_name:this._hass.localize("ui.panel.lovelace.warning.entity_not_found","entity",e.entity),more_info_on_tap:!1,content_template:null,state:"unavailable",stateObj:null,item_type:"unavailable"};let a=e.entity.split(".")[0];return e.exclude_states.includes(t.state)||"automation"==a&&!t.attributes.last_triggered?null:{...t,icon:this.getIcon(t,e.icon),entity:e.entity,display_name:e.name?e.name:t.attributes.friendly_name,format:null!=e.format?e.format:"relative",more_info_on_tap:e.more_info_on_tap,content_template:e.content_template,state:this.computeStateDisplay(t,e),stateObj:t,item_type:"entity"}}).filter(e=>null!=e)}applyTemplate(e,t,a=!1){var n=t;return"string"==typeof e&&(e={value:e}),Object.keys(e).forEach(t=>{n=n.replace("{{"+t+"}}",a?"{{ config.item."+t+" }}":e[t])}),e.attributes&&Object.keys(e.attributes).forEach(t=>{n=n.replace("{{"+t+"}}",e.attributes[t])}),n}getMultiItemEntities(){let e=this.entities.filter(e=>!0===e.multiple_items&&e.list_attribute&&e.content_template).map(e=>{let t=this._hass.states[e.entity];if(!t)return[];let a=this.getIcon(t,e.icon);return(t.attributes[e.list_attribute]?t.attributes[e.list_attribute]:[]).map(n=>{let s=e.timestamp_property&&n[e.timestamp_property]?n[e.timestamp_property]:t.last_changed,i=isNaN(s)?s:new Date(1e3*s);return{...t,icon:a,format:null!=e.format?e.format:"relative",entity:e.entity,display_name:this.applyTemplate(n,e.content_template),last_changed:i,stateObj:t,more_info_on_tap:e.more_info_on_tap,item_data:n,detail:e.detail_template?this.applyTemplate(n,e.detail_template,!1):null,item_type:"multi_entity"}}).sort((e,t)=>e.last_changed1==e.include_history).map(e=>e.entity).join();if(!e||0==e.length)return[];let t=this._config.history_days_back?this._config.history_days_back:0;const a=this.moment().startOf("day").add(-t,"days").utc().format("YYYY-MM-DDTHH:mm:ss"),n=this.moment.utc().format("YYYY-MM-DDTHH:mm:ss");try{let t=(await this._hass.callApi("get",`history/period/${a}Z?end_time=${n}Z&filter_entity_id=${e}`)).map(e=>{let t=this.entities.find(t=>t.entity==e[0].entity_id),a=this._hass.states[t.entity];if(!a)return[];let n=!1!==t.remove_repeats;return e.filter(e=>!t.exclude_states.includes(e.state)).filter((e,a,s)=>this.repeatFilter(e,a,s,n,t.keep_latest)).reverse().slice(0,t.max_history?t.max_history:3).map(e=>({...e,icon:this.getIcon(e,t.icon),display_name:t.name?t.name:e.attributes.friendly_name,format:null!=t.format?t.format:"relative",more_info_on_tap:t.more_info_on_tap,content_template:t.content_template,state:this.computeStateDisplay(e,t),latestStateObj:a,stateObj:this.getHistoryState(a,e),item_type:"entity_history"}))});return[].concat.apply([],t)}catch(e){return[]}}haveHistoryEntitiesChanged(){var e=this.entities.filter(e=>1==e.include_history).map(e=>e.entity);if(!e)return!1;for(const t of e){let e=this.oldStates[t];null==e&&(e={state:"undefined"});let a=this._hass.states[t];if(null==a&&(a={state:"undefined"}),a.state!=e.state)return!0}return!1}async refreshEntityHistory(){if(!this._config.entities||0==this._config.entities.length)return void(JSON.parse(localStorage.getItem("home-feed-card-history"+this.cacheId))&&localStorage.removeItem("home-feed-card-history"+this.cacheId));let e=await this.getLiveEntityHistory();localStorage.setItem("home-feed-card-history"+this.cacheId,JSON.stringify(e)),this.buildIfReady()}eventTime(e){return e.date?e.date:e.dateTime?e.dateTime:e}eventAllDay(e){var t=!1;if(e.start.date)t=!0;else if(e.start.dateTime)t=!1;else{let a=this.moment(e.start);t=this.moment(e.end).diff(a,"hours")>=24}return t}async getEvents(){if(!this.calendars||0==this.calendars.length)return[];let e=JSON.parse(localStorage.getItem("home-feed-card-eventsLastUpdate"+this.cacheId));if(!e||this.moment&&this.moment().diff(e,"minutes")>15){let e=void 0!==this._config.calendar_days_back?this._config.calendar_days_back:0,n=void 0!==this._config.calendar_days_forward?this._config.calendar_days_forward:1;const s=this.moment().startOf("day").add(-e,"days").utc().format("YYYY-MM-DDTHH:mm:ss"),i=this.moment().startOf("day").add(n+1,"days").utc().format("YYYY-MM-DDTHH:mm:ss");try{var t=await Promise.all(this.calendars.map(async e=>{let t=`calendars/${e}?start=${s}Z&end=${i}Z`;return(await this._hass.callApi("get",t)).map(t=>({...t,calendar:e}))}))}catch(e){console.error("Error getting calendar events");t=[]}var a=[].concat.apply([],t).map(e=>{let t=this._hass.states[e.calendar];if(!t)return[];let a={...e,display_name:e.summary?e.summary:e.title,start_time:this.eventTime(e.start),end_time:this.eventTime(e.end),all_day:this.eventAllDay(e),format:this._config.calendar_time_format?this._config.calendar_time_format:"relative",item_type:"calendar_event"},n=this.moment(new Date(a.start_time)),s=this.moment(new Date(a.end_time)),i="";return a.all_day?(s=s.startOf("day").add(-1,"hours"),i=n.clone().startOf("day").isSame(s.clone().startOf("day"))?""+n.format("dddd, D MMMM"):n.month()==s.month()?`${n.format("D")} - ${s.format("D MMMM YYYY")}`:n.year()==s.year()?`${n.format("D MMMM")} - ${s.format("D MMMM YYYY")}`:`${n.format("D MMMM YYYY")} - ${s.format("D MMMM YYYY")}`):i=n.clone().startOf("day").isSame(s.clone().startOf("day"))?n.format("a")==s.format("a")?`${n.format("dddd, D MMMM")} ⋅ ${n.format("h:mm")} - ${s.format("h:mm a")}`:`${n.format("dddd, D MMMM")} ⋅ ${n.format("h:mm a")} - ${s.format("h:mm a")}`:`${n.format("D MMMM YYYY, h:mm a")} - ${s.format("D MMMM YYYY, h:mm a")}`,a.detail=` ${i}\n\t \t\t\n ${t.attributes.friendly_name}\n\t \t\t`,a});return localStorage.setItem("home-feed-card-events"+this.cacheId,JSON.stringify(a)),localStorage.setItem("home-feed-card-eventsLastUpdate"+this.cacheId,JSON.stringify(this.moment())),a}return JSON.parse(localStorage.getItem("home-feed-card-events"+this.cacheId))}notificationIdToTitle(e){return e.replace(/[^a-zA-Z0-9]/g," ").toLowerCase().replace(/\b(\w)/g,e=>e.toUpperCase())}async refreshNotifications(){if(!this._hass)return;if(this.refreshingNotifications)return;this.refreshingNotifications=!0;var e=await this._hass.callWS({type:"persistent_notification/get"});this._config.id_filter&&(e=e.filter(e=>e.notification_id.match(this._config.id_filter)));let t=e.map(e=>({...e,title:e.title?e.title:this.notificationIdToTitle(e.notification_id),format:"relative",item_type:"notification",original_notification:e}));localStorage.setItem("home-feed-card-notifications"+this.cacheId,JSON.stringify(t)),this.moment&&localStorage.setItem("home-feed-card-notificationsLastUpdate"+this.cacheId,JSON.stringify(this.moment())),this.refreshingNotifications=!1,this.loadedNotifications=!0,this.buildIfReady()}getNotifications(){return JSON.parse(localStorage.getItem("home-feed-card-notifications"+this.cacheId))?JSON.parse(localStorage.getItem("home-feed-card-notifications"+this.cacheId)):[]}async getEntityHistoryItems(){return JSON.parse(localStorage.getItem("home-feed-card-history"+this.cacheId))?JSON.parse(localStorage.getItem("home-feed-card-history"+this.cacheId)):[]}getItemTimestamp(e){switch(e.item_type){case"notification":return e.created_at;case"calendar_event":return e.start_time;case"entity":case"entity_history":case"multi_entity":if("timestamp"===e.attributes.device_class)return e.state;return"automation"==e.entity_id.split(".")[0]?e.attributes.last_triggered:e.attributes.last_changed?e.attributes.last_changed:e.last_changed;default:return(new Date).toISOString()}}debugItem(){if(!this._config.debug)return[];let e=localStorage.getItem("home-feed-card-history"+this.cacheId),t="## Debug Information\n\n**Cache Id:** "+this.cacheId+"\n\n**Cache Status:** "+(e?"From Cache":"Live")+"\n\n**Language (Home Assistant):** "+(this._hass?this._hass.language:"unknown")+"\n\n**Language (Browser):** "+(this.browser_language?this.browser_language:"unknown");return[{state:"on",attributes:{device_class:"debug"},icon:"mdi:bug",format:"relative",entity_id:"home_feed.debug_info",entity:"home_feed.debug_info",display_name:t,last_changed:new Date,stateObj:null,more_info_on_tap:!0,item_data:null,detail:t,content_template:"{{display_name}}",item_type:"entity"}]}async getFeedItems(){var e=[].concat.apply([],await Promise.all([this.debugItem(),this.getNotifications(),this.getEvents(),this.getEntities(),this.getMultiItemEntities(),this.getEntityHistoryItems()])),t=new Date;return(e=e.map(e=>{let a=this.getItemTimestamp(e),n=new Date(a),s=(t-n)/1e3;return{...e,timestamp:a,timeDifference:{value:s,abs:Math.abs(s),sign:Math.sign(s)}}})).sort((e,t)=>e.timeDifference.abst.timeDifference.abs?1:0)}_handleDismiss(e){var t=e.target.notificationId;this._hass.callService("persistent_notification","dismiss",{notification_id:t})}_moreInfoHeaderClick(e){let t=document.querySelector("home-assistant")._moreInfoEl;t.large=!t.large}provideHass(e){return document.querySelector("hc-main")?document.querySelector("hc-main").provideHass(e):document.querySelector("home-assistant")?document.querySelector("home-assistant").provideHass(e):void 0}fireEvent(e,t,a=null){if((e=new Event(e,{bubbles:!0,cancelable:!1,composed:!0})).detail=t||{},a)a.dispatchEvent(e);else{var n=document.querySelector("home-assistant");(n=(n=(n=(n=(n=(n=(n=(n=(n=(n=(n=n&&n.shadowRoot)&&n.querySelector("home-assistant-main"))&&n.shadowRoot)&&n.querySelector("app-drawer-layout partial-panel-resolver"))&&n.shadowRoot||n)&&n.querySelector("ha-panel-lovelace"))&&n.shadowRoot)&&n.querySelector("hui-root"))&&n.shadowRoot)&&n.querySelector("ha-app-layout #view"))&&n.firstElementChild)&&n.dispatchEvent(e)}}moreInfo(e){this.fireEvent("hass-more-info",{entityId:e})}findPopUpCard(e){let t=document.querySelector("home-assistant");return t=t&&t.shadowRoot,t=t&&t.querySelector("card-tools-popup"),t=t&&t.shadowRoot,t=t&&t.querySelector("ha-dialog"),t.querySelector(e)}_handleClick(e){let t=e.currentTarget.item;if("entity_history"==t.item_type){let e={};Object.assign(e,this._hass),e.states=[],e.states[t.entity_id]=t.stateObj;let a={type:"custom:hui-entities-card",entities:[{entity:t.entity_id,secondary_info:"last-changed"},{type:"custom:hui-history-graph-card",entities:[t.entity_id]},{type:"custom:hui-logbook-card",entities:[t.entity_id]}]};_e({type:"logbook",entities:[t.entity_id]}),ce(t.display_name,a,!1,{"box-shadow":"none!important"}),setTimeout(()=>{let t=this.findPopUpCard("hui-entities-card");if(t){t.hass=e;let a=t.shadowRoot&&t.shadowRoot.querySelector("ha-card");a&&(a.style.borderRadius="0");let n=a&&a.querySelector("#states");if(n){n.querySelector("div hui-history-graph-card").shadowRoot.querySelector("ha-card").style.boxShadow="none",n.querySelector("div hui-logbook-card").shadowRoot.querySelector("ha-card").style.boxShadow="none"}}},100)}else if("multi_entity"==t.item_type||"calendar_event"==t.item_type){let e={};Object.assign(e,this._hass);let a={type:"custom:hui-markdown-card",content:t.detail,item:t.item_data},n=80,s=t.display_name;s.length>n&&(s=s.substring(0,n-3)+"..."),ce(s,a,!1),setTimeout(()=>{let e=this.findPopUpCard("hui-markdown-card"),t=e.parentElement.parentElement.querySelector("app-toolbar").getBoundingClientRect(),a=Math.trunc(t.width),n=e&&e.shadowRoot&&e.shadowRoot.querySelector("ha-card");if(n){n.style.background="rgba(0,0,0,0)",n.style.boxShadow="none",n.style.borderRadius=0,n.style.maxHeight="75vh",n.style.minWidth=a+"px",n.style.overflow="auto";let e=n.querySelector("ha-markdown").shadowRoot.querySelector("ha-markdown-element");e&&e.querySelectorAll("a").forEach(e=>{e.addEventListener("click",me)})}},100)}else if("notification"==t.item_type){let e=t.original_notification;e.title||(e.title=this.notificationIdToTitle(e.notification_id));let a={type:"custom:home-feed-notification-popup",notification:e};ce(e.title,a,!1)}else!function(e,t,a,n,s){var i;if(s&&a.double_tap_action?i=a.double_tap_action:n&&a.hold_action?i=a.hold_action:!n&&a.tap_action&&(i=a.tap_action),i||(i={action:"more-info"}),!i.confirmation||i.confirmation.exemptions&&i.confirmation.exemptions.some((function(e){return e.user===t.user.id}))||confirm(i.confirmation.text||"Are you sure you want to "+i.action+"?"))switch(i.action){case"more-info":(i.entity||a.entity||a.camera_image)&&(Je(e,"hass-more-info",{entityId:i.entity?i.entity:a.entity?a.entity:a.camera_image}),i.haptic&&Ve(i.haptic));break;case"navigate":i.navigation_path&&(qe(0,i.navigation_path),i.haptic&&Ve(i.haptic));break;case"url":i.url_path&&window.open(i.url_path),i.haptic&&Ve(i.haptic);break;case"toggle":a.entity&&(Ge(t,a.entity),i.haptic&&Ve(i.haptic));break;case"call-service":if(!i.service)return;var r=i.service.split(".",2),o=r[0],d=r[1],u=Object.assign({},i.service_data);"entity"===u.entity_id&&(u.entity_id=a.entity),t.callService(o,d,u),i.haptic&&Ve(i.haptic)}}(this,this._hass,{entity:t.entity_id,tap_action:{action:"more-info"}},!1,!1)}_computeTooltip(e,t){if(!e||!t)return;return new Date(t.created_at).toLocaleDateString(this._hass.language,{year:"numeric",month:"short",day:"numeric",minute:"numeric",hour:"numeric"})}_buildFeed(){this._hass&&this.getFeedItems().then(e=>{this._config.max_item_count&&e.splice(this._config.max_item_count),this.feedContent=e,this.requestUpdate()})}_renderItem(e){let t=!0===this._config.compact_mode,a=!1!==this._config.show_icons;switch(e.item_type){case"notification":var n="mdi:bell";if(this._config.show_notification_title)var s=""+e.title+"\n\n"+e.message;else s=e.message;break;case"calendar_event":n="mdi:calendar",s=e.display_name;break;case"entity":case"entity_history":n=e.icon;e.entity_id.split(".")[0];if("timestamp"===e.attributes.device_class){s=""+e.display_name;if(!n)n="mdi:clock-outline"}else if(e.content_template)s=this.applyTemplate(e,e.content_template);else s=`${e.display_name} @ ${e.state}`;break;case"multi_entity":n=e.icon,s=""+e.display_name;break;case"unavailable":n="mdi:alert-circle",s=""+e.display_name;break;default:n="mdi:bell",s="Unknown Item Type"}e.stateObj||n||(n="mdi:bell");var i=!1,r="";if(void 0!==e.more_info_on_tap?e.more_info_on_tap:this._config.more_info_on_tap)switch(e.item_type){case"entity":case"entity_history":case"notification":i=!0;break;case"multi_entity":case"calendar_event":i=!!e.detail}var o;if(t&&"notification"==e.item_type&&(i=!0),i&&(r="state-card-dialog"),"calendar_event"==e.item_type&&e.all_day){let a=e.start.date?this.moment(e.start.date).startOf("day"):this.moment(e.start).startOf("day"),n=e.end.date?this.moment(e.end.date).startOf("day"):this.moment(e.end).startOf("day");if(n=n.add(-1,"hours").startOf("day"),Math.abs(a.diff(this.moment().startOf("day"),"days"))<=7){var d=Ze(a);if(n>a){let e=Ze(n);e==n.format("L")&&(e=n.toDate().toLocaleDateString(this._hass.language,{year:"numeric",month:"long",day:"numeric"})),d=d+" - "+e}o=A`
${d}
`}else{d=a.toDate().toLocaleDateString(this._language,{year:"numeric",month:"long",day:"numeric"});n>a&&(d=d+" - "+n.toDate().toLocaleDateString(this._hass.language,{year:"numeric",month:"long",day:"numeric"})),o=A`
${d}
`}}else{let a=!0===this._config.exact_durations;if(isNaN(e.timeDifference.value))o=A`
${e.timestamp}
`;else if(e.timeDifference.abs<60&&"relative"==e.format&&!a)if("en"!=this._language){let a=this._hass.localize("ui.components.relative_time.duration.minute","count",1).replace("1","<1"),n=e.timeDifference.sign>=0?"past":"future",s=this._hass.localize("ui.components.relative_time."+n,"time",a);o=A`
${s}
`}else{let a=0==e.timeDifference.sign?"now":1==e.timeDifference.sign?"<1 minute ago":"in <1 minute";o=A`
${a}
`}else o=A` 15)) { let calendarDaysBack = (typeof this._config.calendar_days_back !== 'undefined' ? this._config.calendar_days_back : 0); let calendarDaysForward = (typeof this._config.calendar_days_forward !== 'undefined' ? this._config.calendar_days_forward : 1); - const start = this.moment.utc().startOf('day').add(-calendarDaysBack, 'days').format("YYYY-MM-DDTHH:mm:ss"); - const end = this.moment.utc().startOf('day').add(calendarDaysForward + 1, 'days').format("YYYY-MM-DDTHH:mm:ss"); + const start = this.moment().startOf('day').add(-calendarDaysBack, 'days').utc().format("YYYY-MM-DDTHH:mm:ss"); + const end = this.moment().startOf('day').add(calendarDaysForward + 1, 'days').utc().format("YYYY-MM-DDTHH:mm:ss"); try{ var calendars = await Promise.all( this.calendars.map(