mirror of
https://github.com/home-assistant/frontend.git
synced 2025-07-26 18:56:39 +00:00
Highlight if log comes from custom component (#8912)
Co-authored-by: Joakim Sørensen <joasoe@gmail.com>
This commit is contained in:
parent
dc79fc2919
commit
b8bb0c038d
@ -16,9 +16,27 @@ export interface LoggedError {
|
|||||||
export const fetchSystemLog = (hass: HomeAssistant) =>
|
export const fetchSystemLog = (hass: HomeAssistant) =>
|
||||||
hass.callApi<LoggedError[]>("GET", "error/all");
|
hass.callApi<LoggedError[]>("GET", "error/all");
|
||||||
|
|
||||||
export const getLoggedErrorIntegration = (item: LoggedError) =>
|
export const getLoggedErrorIntegration = (item: LoggedError) => {
|
||||||
item.name.startsWith("homeassistant.components.")
|
// Try to derive from logger name
|
||||||
? item.name.split(".")[2]
|
if (item.name.startsWith("homeassistant.components.")) {
|
||||||
: item.name.startsWith("custom_components.")
|
return item.name.split(".")[2];
|
||||||
? item.name.split(".")[1]
|
}
|
||||||
: undefined;
|
if (item.name.startsWith("custom_components.")) {
|
||||||
|
return item.name.split(".")[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try to derive from logged location
|
||||||
|
if (item.source[0].startsWith("custom_components/")) {
|
||||||
|
return item.source[0].split("/")[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (item.source[0].startsWith("homeassistant/components/")) {
|
||||||
|
return item.source[0].split("/")[2];
|
||||||
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
|
};
|
||||||
|
|
||||||
|
export const isCustomIntegrationError = (item: LoggedError) =>
|
||||||
|
item.name.startsWith("custom_components.") ||
|
||||||
|
item.source[0].startsWith("custom_components/");
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import "@material/mwc-icon-button/mwc-icon-button";
|
import "@material/mwc-icon-button/mwc-icon-button";
|
||||||
import { mdiClose, mdiContentCopy } from "@mdi/js";
|
import { mdiClose, mdiContentCopy, mdiPackageVariant } from "@mdi/js";
|
||||||
import "@polymer/paper-tooltip/paper-tooltip";
|
import "@polymer/paper-tooltip/paper-tooltip";
|
||||||
import {
|
import {
|
||||||
css,
|
css,
|
||||||
@ -21,7 +21,10 @@ import {
|
|||||||
integrationIssuesUrl,
|
integrationIssuesUrl,
|
||||||
IntegrationManifest,
|
IntegrationManifest,
|
||||||
} from "../../../data/integration";
|
} from "../../../data/integration";
|
||||||
import { getLoggedErrorIntegration } from "../../../data/system_log";
|
import {
|
||||||
|
getLoggedErrorIntegration,
|
||||||
|
isCustomIntegrationError,
|
||||||
|
} from "../../../data/system_log";
|
||||||
import { haStyleDialog } from "../../../resources/styles";
|
import { haStyleDialog } from "../../../resources/styles";
|
||||||
import type { HomeAssistant } from "../../../types";
|
import type { HomeAssistant } from "../../../types";
|
||||||
import { showToast } from "../../../util/toast";
|
import { showToast } from "../../../util/toast";
|
||||||
@ -65,6 +68,12 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
|
|
||||||
const integration = getLoggedErrorIntegration(item);
|
const integration = getLoggedErrorIntegration(item);
|
||||||
|
|
||||||
|
const showDocumentation =
|
||||||
|
this._manifest &&
|
||||||
|
(this._manifest.is_built_in ||
|
||||||
|
// Custom components with our offical docs should not link to our docs
|
||||||
|
!this._manifest.documentation.includes("www.home-assistant.io"));
|
||||||
|
|
||||||
return html`
|
return html`
|
||||||
<ha-dialog open @closed=${this.closeDialog} hideActions heading=${true}>
|
<ha-dialog open @closed=${this.closeDialog} hideActions heading=${true}>
|
||||||
<ha-header-bar slot="heading">
|
<ha-header-bar slot="heading">
|
||||||
@ -86,6 +95,14 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
<ha-svg-icon .path=${mdiContentCopy}></ha-svg-icon>
|
<ha-svg-icon .path=${mdiContentCopy}></ha-svg-icon>
|
||||||
</mwc-icon-button>
|
</mwc-icon-button>
|
||||||
</ha-header-bar>
|
</ha-header-bar>
|
||||||
|
${this.isCustomIntegration
|
||||||
|
? html`<div class="custom">
|
||||||
|
<ha-svg-icon .path=${mdiPackageVariant}></ha-svg-icon>
|
||||||
|
${this.hass.localize(
|
||||||
|
"ui.panel.config.logs.error_from_custom_integration"
|
||||||
|
)}
|
||||||
|
</div>`
|
||||||
|
: ""}
|
||||||
<div class="contents">
|
<div class="contents">
|
||||||
<p>
|
<p>
|
||||||
Logger: ${item.name}<br />
|
Logger: ${item.name}<br />
|
||||||
@ -96,7 +113,7 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
Integration: ${domainToName(this.hass.localize, integration)}
|
Integration: ${domainToName(this.hass.localize, integration)}
|
||||||
${!this._manifest ||
|
${!this._manifest ||
|
||||||
// Can happen with custom integrations
|
// Can happen with custom integrations
|
||||||
!this._manifest.documentation
|
!showDocumentation
|
||||||
? ""
|
? ""
|
||||||
: html`
|
: html`
|
||||||
(<a
|
(<a
|
||||||
@ -144,6 +161,12 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private get isCustomIntegration(): boolean {
|
||||||
|
return this._manifest
|
||||||
|
? !this._manifest.is_built_in
|
||||||
|
: isCustomIntegrationError(this._params!.item);
|
||||||
|
}
|
||||||
|
|
||||||
private async _fetchManifest(integration: string) {
|
private async _fetchManifest(integration: string) {
|
||||||
try {
|
try {
|
||||||
this._manifest = await fetchIntegrationManifest(this.hass, integration);
|
this._manifest = await fetchIntegrationManifest(this.hass, integration);
|
||||||
@ -157,7 +180,18 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
".contents"
|
".contents"
|
||||||
) as HTMLElement;
|
) as HTMLElement;
|
||||||
|
|
||||||
await copyToClipboard(copyElement.innerText);
|
let text = copyElement.innerText;
|
||||||
|
|
||||||
|
if (this.isCustomIntegration) {
|
||||||
|
text =
|
||||||
|
this.hass.localize(
|
||||||
|
"ui.panel.config.logs.error_from_custom_integration"
|
||||||
|
) +
|
||||||
|
"\n\n" +
|
||||||
|
text;
|
||||||
|
}
|
||||||
|
|
||||||
|
await copyToClipboard(text);
|
||||||
showToast(this, {
|
showToast(this, {
|
||||||
message: this.hass.localize("ui.common.copied_clipboard"),
|
message: this.hass.localize("ui.common.copied_clipboard"),
|
||||||
});
|
});
|
||||||
@ -167,6 +201,10 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
return [
|
return [
|
||||||
haStyleDialog,
|
haStyleDialog,
|
||||||
css`
|
css`
|
||||||
|
ha-dialog {
|
||||||
|
--dialog-content-padding: 0px;
|
||||||
|
}
|
||||||
|
|
||||||
a {
|
a {
|
||||||
color: var(--primary-color);
|
color: var(--primary-color);
|
||||||
}
|
}
|
||||||
@ -177,6 +215,13 @@ class DialogSystemLogDetail extends LitElement {
|
|||||||
margin-bottom: 0;
|
margin-bottom: 0;
|
||||||
font-family: var(--code-font-family, monospace);
|
font-family: var(--code-font-family, monospace);
|
||||||
}
|
}
|
||||||
|
.custom {
|
||||||
|
padding: 8px 16px;
|
||||||
|
background-color: var(--warning-color);
|
||||||
|
}
|
||||||
|
.contents {
|
||||||
|
padding: 16px;
|
||||||
|
}
|
||||||
.error {
|
.error {
|
||||||
color: var(--error-color);
|
color: var(--error-color);
|
||||||
}
|
}
|
||||||
|
@ -19,6 +19,7 @@ import { domainToName } from "../../../data/integration";
|
|||||||
import {
|
import {
|
||||||
fetchSystemLog,
|
fetchSystemLog,
|
||||||
getLoggedErrorIntegration,
|
getLoggedErrorIntegration,
|
||||||
|
isCustomIntegrationError,
|
||||||
LoggedError,
|
LoggedError,
|
||||||
} from "../../../data/system_log";
|
} from "../../../data/system_log";
|
||||||
import { HomeAssistant } from "../../../types";
|
import { HomeAssistant } from "../../../types";
|
||||||
@ -78,10 +79,16 @@ export class SystemLogCard extends LitElement {
|
|||||||
)}</span
|
)}</span
|
||||||
>) `}
|
>) `}
|
||||||
${integrations[idx]
|
${integrations[idx]
|
||||||
? domainToName(
|
? `${domainToName(
|
||||||
this.hass!.localize,
|
this.hass!.localize,
|
||||||
integrations[idx]!
|
integrations[idx]!
|
||||||
)
|
)}${
|
||||||
|
isCustomIntegrationError(item)
|
||||||
|
? ` (${this.hass.localize(
|
||||||
|
"ui.panel.config.logs.custom_integration"
|
||||||
|
)})`
|
||||||
|
: ""
|
||||||
|
}`
|
||||||
: item.source[0]}
|
: item.source[0]}
|
||||||
${item.count > 1
|
${item.count > 1
|
||||||
? html`
|
? html`
|
||||||
|
@ -1067,7 +1067,9 @@
|
|||||||
"warning": "WARNING",
|
"warning": "WARNING",
|
||||||
"info": "INFO",
|
"info": "INFO",
|
||||||
"debug": "DEBUG"
|
"debug": "DEBUG"
|
||||||
}
|
},
|
||||||
|
"custom_integration": "custom integration",
|
||||||
|
"error_from_custom_integration": "This error originated from a custom integration."
|
||||||
},
|
},
|
||||||
"lovelace": {
|
"lovelace": {
|
||||||
"caption": "Lovelace Dashboards",
|
"caption": "Lovelace Dashboards",
|
||||||
|
Loading…
x
Reference in New Issue
Block a user