From eb2ba5ae07c1a4dfb9712f1b8fa9e0d6f7fa27e0 Mon Sep 17 00:00:00 2001 From: Alexander Zobnin Date: Fri, 28 Dec 2018 19:24:57 +0300 Subject: [PATCH] problems: show status icon --- src/panel-triggers/components/GFHeartIcon.tsx | 19 ++++++++ src/panel-triggers/components/Problems.tsx | 32 ++++++++++++-- src/panel-triggers/partials/options_tab.html | 6 +++ src/panel-triggers/triggers_panel_ctrl.js | 43 +++++++++++++++++++ src/panel-triggers/types.ts | 1 + src/sass/_panel-problems.scss | 21 +++++++++ src/sass/_variables.dark.scss | 3 ++ src/sass/_variables.light.scss | 3 ++ 8 files changed, 124 insertions(+), 4 deletions(-) create mode 100644 src/panel-triggers/components/GFHeartIcon.tsx diff --git a/src/panel-triggers/components/GFHeartIcon.tsx b/src/panel-triggers/components/GFHeartIcon.tsx new file mode 100644 index 0000000..24bcc86 --- /dev/null +++ b/src/panel-triggers/components/GFHeartIcon.tsx @@ -0,0 +1,19 @@ +import React from 'react'; +import classNames from 'classnames'; + +interface GFHeartIconProps { + status: 'critical' | 'warning' | 'online' | 'ok' | 'problem'; + className?: string; +} + +export default function GFHeartIcon(props: GFHeartIconProps) { + const status = props.status; + const className = classNames("icon-gf", props.className, + { "icon-gf-critical": status === 'critical' || status === 'problem' }, + { "icon-gf-warning": status === 'warning' }, + { "icon-gf-online": status === 'online' || status === 'ok' }, + ); + return ( + + ); +} diff --git a/src/panel-triggers/components/Problems.tsx b/src/panel-triggers/components/Problems.tsx index 4cc733b..4835cdd 100644 --- a/src/panel-triggers/components/Problems.tsx +++ b/src/panel-triggers/components/Problems.tsx @@ -7,6 +7,7 @@ import { ProblemsPanelOptions, Trigger, ZBXEvent, GFTimeRange, RTCell, ZBXTag, T import EventTag from './EventTag'; import ProblemDetails from './ProblemDetails'; import { AckProblemData } from './Modal'; +import GFHeartIcon from './GFHeartIcon'; export interface ProblemListProps { problems: Trigger[]; @@ -84,22 +85,32 @@ export class ProblemList extends PureComponent StatusCell(props, options.okEventColor, DEFAULT_PROBLEM_COLOR, highlightNewerThan); + const statusIconCell = props => StatusIconCell(props, highlightNewerThan); + const columns = [ { Header: 'Host', accessor: 'host', show: options.hostField }, { Header: 'Host (Technical Name)', accessor: 'hostTechName', show: options.hostTechNameField }, { Header: 'Host Groups', accessor: 'groups', show: options.hostGroups, Cell: GroupCell }, { Header: 'Proxy', accessor: 'proxy', show: options.hostProxy }, - { Header: 'Severity', show: options.severityField, className: 'problem-severity', width: 120, + { + Header: 'Severity', show: options.severityField, className: 'problem-severity', width: 120, accessor: problem => problem.priority, id: 'severity', Cell: props => SeverityCell(props, options.triggerSeverity), }, + { + Header: '', id: 'statusIcon', show: options.statusIcon, className: 'problem-status-icon', width: 50, + accessor: 'value', + Cell: statusIconCell, + }, { Header: 'Status', accessor: 'value', show: options.statusField, width: 100, Cell: statusCell }, { Header: 'Problem', accessor: 'description', minWidth: 200, Cell: ProblemCell}, - { Header: 'Tags', accessor: 'tags', show: options.showTags, className: 'problem-tags', + { + Header: 'Tags', accessor: 'tags', show: options.showTags, className: 'problem-tags', Cell: props => }, - { Header: 'Time', className: 'last-change', width: timeColWidth, + { + Header: 'Time', className: 'last-change', width: timeColWidth, accessor: 'lastchangeUnix', id: 'lastchange', Cell: row => row.original.lastchange, @@ -171,7 +182,6 @@ const DEFAULT_OK_COLOR = 'rgb(56, 189, 113)'; const DEFAULT_PROBLEM_COLOR = 'rgb(215, 0, 0)'; function StatusCell(props: RTCell, okColor = DEFAULT_OK_COLOR, problemColor = DEFAULT_PROBLEM_COLOR, highlightNewerThan?: string) { - // console.log(props); const status = props.value === '0' ? 'RESOLVED' : 'PROBLEM'; const color = props.value === '0' ? okColor : problemColor; let newProblem = false; @@ -183,6 +193,20 @@ function StatusCell(props: RTCell, okColor = DEFAULT_OK_COLOR, problemC ); } +function StatusIconCell(props: RTCell, highlightNewerThan?: string) { + const status = props.value === '0' ? 'ok' : 'problem'; + let newProblem = false; + if (highlightNewerThan) { + newProblem = isNewProblem(props.original, highlightNewerThan); + } + const className = classNames('zbx-problem-status-icon', + { 'problem-status--new': newProblem }, + { 'zbx-problem': props.value === '1' }, + { 'zbx-ok': props.value === '0' }, + ); + return ; +} + function GroupCell(props: RTCell) { let groups = ""; if (props.value && props.value.length) { diff --git a/src/panel-triggers/partials/options_tab.html b/src/panel-triggers/partials/options_tab.html index 0727ccb..7ff1efd 100644 --- a/src/panel-triggers/partials/options_tab.html +++ b/src/panel-triggers/partials/options_tab.html @@ -37,6 +37,12 @@ checked="ctrl.panel.statusField" on-change="ctrl.render()"> + + = 3) { + iconClass = 'icon-gf-critical'; + } else { + iconClass = 'icon-gf-warning'; + } + } else { + iconClass = 'icon-gf-online'; + } + + if (this.panel.highlightNewEvents && this.isNewTrigger(trigger)) { + iconClass += ' zabbix-trigger--blinked'; + } + return iconClass; + } + + getAlertIconClassBySeverity(triggerSeverity) { + let iconClass = 'icon-gf-warning'; + if (triggerSeverity.priority >= 3) { + iconClass = 'icon-gf-critical'; + } + return iconClass; + } + + getAlertStateClass(trigger) { + let statusClass = ''; + + if (trigger.value === '1') { + statusClass = 'alert-state-critical'; + } else { + statusClass = 'alert-state-ok'; + } + + if (this.panel.highlightNewEvents && this.isNewTrigger(trigger)) { + statusClass += ' zabbix-trigger--blinked'; + } + + return statusClass; + } + resetResizedColumns() { this.panel.resizedColumns = []; this.render(); diff --git a/src/panel-triggers/types.ts b/src/panel-triggers/types.ts index c7d7474..500d772 100644 --- a/src/panel-triggers/types.ts +++ b/src/panel-triggers/types.ts @@ -9,6 +9,7 @@ export interface ProblemsPanelOptions { hostProxy?: boolean; showTags?: boolean; statusField?: boolean; + statusIcon?: boolean; severityField?: boolean; descriptionField?: boolean; descriptionAtNewLine?: boolean; diff --git a/src/sass/_panel-problems.scss b/src/sass/_panel-problems.scss index 219ad53..b41f2d7 100644 --- a/src/sass/_panel-problems.scss +++ b/src/sass/_panel-problems.scss @@ -66,6 +66,7 @@ .rt-tr { .rt-td { border: 0; + transition: 0s; } // &:hover { @@ -171,6 +172,26 @@ &.last-change { text-align: left; } + + &.problem-status-icon { + padding: 0; + margin-top: 0; + font-size: 1.5em; + + i { + // margin: 0 1.2em; + width: 100%; + padding-left: 0.6em; + text-align: center; + + &.zbx-problem { + color: $problem-icon-problem-color; + } + &.zbx-ok { + color: $problem-icon-ok-color; + } + } + } } .comments-icon { diff --git a/src/sass/_variables.dark.scss b/src/sass/_variables.dark.scss index 7885f91..451c500 100644 --- a/src/sass/_variables.dark.scss +++ b/src/sass/_variables.dark.scss @@ -29,4 +29,7 @@ $problem-event-core: #000000; $problem-event-ok-color: #38bd71; $problem-event-problem-color: #d70000; +$problem-icon-problem-color: rgb(163, 16, 0); +$problem-icon-ok-color: #629e51; + $problem-container-shadow: rgba($gray-2, 0.2) diff --git a/src/sass/_variables.light.scss b/src/sass/_variables.light.scss index f707632..d6cd90d 100644 --- a/src/sass/_variables.light.scss +++ b/src/sass/_variables.light.scss @@ -29,4 +29,7 @@ $problem-event-core: $gray-6; $problem-event-ok-color: #2baf63; $problem-event-problem-color: #d70000; +$problem-icon-problem-color: rgb(163, 16, 0); +$problem-icon-ok-color: #629e51; + $problem-container-shadow: rgba($gray-2, 0.5)