summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorDixsie Wolmers <dixsie@ibm.com>2021-05-03 02:20:27 +0300
committerDerick Montague <derick.montague@ibm.com>2021-06-09 15:04:53 +0300
commit27d68affdeaba25f011aef52ccbe56506e63d92c (patch)
tree66ed00b677c37df41bf484110c0fb1182b116d4c /src
parentdca9b0a5baddfec7ea0ea5e4bdb63c2dd0be27b2 (diff)
downloadwebui-vue-27d68affdeaba25f011aef52ccbe56506e63d92c.tar.xz
Add event log resolve and unresolve log functionality
Displays resolved or unresolved status, adds ability to filter by resolved or unresolved, and adds ability to resolve or unresolve one or more logs. Move event type table field to expanded row. Signed-off-by: Dixsie Wolmers <dixsie@ibm.com> Change-Id: Ie5761753a7660a714f98c238d8d89aa018719dcf
Diffstat (limited to 'src')
-rw-r--r--src/components/Global/TableToolbar.vue2
-rw-r--r--src/locales/en-US.json14
-rw-r--r--src/store/modules/Health/EventLogStore.js92
-rw-r--r--src/views/Health/EventLogs/EventLogs.vue85
-rw-r--r--src/views/Health/Sensors/Sensors.vue2
5 files changed, 185 insertions, 10 deletions
diff --git a/src/components/Global/TableToolbar.vue b/src/components/Global/TableToolbar.vue
index a9281748..5235feae 100644
--- a/src/components/Global/TableToolbar.vue
+++ b/src/components/Global/TableToolbar.vue
@@ -6,6 +6,7 @@
{{ selectedItemsCount }} {{ $t('global.action.selected') }}
</p>
<div class="toolbar-actions d-flex">
+ <slot name="toolbar-buttons"></slot>
<b-button
v-for="(action, index) in actions"
:key="index"
@@ -16,7 +17,6 @@
>
{{ action.label }}
</b-button>
- <slot name="export"></slot>
<b-button
variant="secondary"
class="d-block"
diff --git a/src/locales/en-US.json b/src/locales/en-US.json
index c6a87459..34efa621 100644
--- a/src/locales/en-US.json
+++ b/src/locales/en-US.json
@@ -246,6 +246,10 @@
},
"pageEventLogs": {
"exportFilePrefix": "event_logs_",
+ "resolve": "Resolve",
+ "resolved": "Resolved",
+ "unresolve": "Unresolve",
+ "unresolved": "Unresolved",
"modal": {
"deleteTitle": "Delete log | Delete logs",
"deleteMessage": "Are you sure you want to delete %{count} log? This action cannot be undone. | Are you sure you want to delete %{count} logs? This action cannot be undone."
@@ -258,11 +262,19 @@
"name": "Name",
"searchLogs": "Search logs",
"severity": "Severity",
+ "status": "Status",
"type": "Type"
},
"toast": {
"errorDelete": "Error deleting %{count} log. | Error deleting %{count} logs.",
- "successDelete": "Successfully deleted %{count} log. | Successfully deleted %{count} logs."
+ "successDelete": "Successfully deleted %{count} log. | Successfully deleted %{count} logs.",
+ "errorLogStatusUpdate": "Error updating log status.",
+ "errorResolveLogs": "Error resolving %{count} log. | Error resolving %{count} logs.",
+ "errorUnresolveLogs": "Error unresolving %{count} log. | Error unresolving %{count} logs.",
+ "successResolveLog": "Successfully resolved log.",
+ "successResolveLogs": "Successfully resolved %{count} log. | Successfully resolved %{count} logs.",
+ "successUnresolveLog": "Successfully unresolved log.",
+ "successUnresolveLogs": "Successfully unresolved %{count} log. | Successfully unresolved %{count} logs."
}
},
"pageFactoryReset": {
diff --git a/src/store/modules/Health/EventLogStore.js b/src/store/modules/Health/EventLogStore.js
index eaec7490..2b6d5f94 100644
--- a/src/store/modules/Health/EventLogStore.js
+++ b/src/store/modules/Health/EventLogStore.js
@@ -51,6 +51,7 @@ const EventLogStore = {
Message,
Name,
Modified,
+ Resolved,
} = log;
return {
id: Id,
@@ -61,6 +62,8 @@ const EventLogStore = {
name: Name,
modifiedDate: new Date(Modified),
uri: log['@odata.id'],
+ filterByStatus: Resolved ? 'Resolved' : 'Unresolved',
+ status: Resolved, //true or false
};
});
commit('setAllEvents', eventLogs);
@@ -119,6 +122,95 @@ const EventLogStore = {
})
);
},
+ async resolveEventLogs({ dispatch }, logs) {
+ const promises = logs.map((log) =>
+ api.patch(log.uri, { Resolved: true }).catch((error) => {
+ console.log(error);
+ return error;
+ })
+ );
+ return await api
+ .all(promises)
+ .then((response) => {
+ dispatch('getEventLogData');
+ return response;
+ })
+ .then(
+ api.spread((...responses) => {
+ const { successCount, errorCount } = getResponseCount(responses);
+ const toastMessages = [];
+ if (successCount) {
+ const message = i18n.tc(
+ 'pageEventLogs.toast.successResolveLogs',
+ successCount
+ );
+ toastMessages.push({ type: 'success', message });
+ }
+ if (errorCount) {
+ const message = i18n.tc(
+ 'pageEventLogs.toast.errorResolveLogs',
+ errorCount
+ );
+ toastMessages.push({ type: 'error', message });
+ }
+ return toastMessages;
+ })
+ );
+ },
+ async unresolveEventLogs({ dispatch }, logs) {
+ const promises = logs.map((log) =>
+ api.patch(log.uri, { Resolved: false }).catch((error) => {
+ console.log(error);
+ return error;
+ })
+ );
+ return await api
+ .all(promises)
+ .then((response) => {
+ dispatch('getEventLogData');
+ return response;
+ })
+ .then(
+ api.spread((...responses) => {
+ const { successCount, errorCount } = getResponseCount(responses);
+ const toastMessages = [];
+ if (successCount) {
+ const message = i18n.tc(
+ 'pageEventLogs.toast.successUnresolveLogs',
+ successCount
+ );
+ toastMessages.push({ type: 'success', message });
+ }
+ if (errorCount) {
+ const message = i18n.tc(
+ 'pageEventLogs.toast.errorUnresolveLogs',
+ errorCount
+ );
+ toastMessages.push({ type: 'error', message });
+ }
+ return toastMessages;
+ })
+ );
+ },
+ async updateEventLogStatus({ dispatch }, log) {
+ const updatedEventLogStatus = log.status;
+ return await api
+ .patch(log.uri, { Resolved: updatedEventLogStatus })
+ .then(() => {
+ dispatch('getEventLogData');
+ })
+ .then(() => {
+ if (log.status) {
+ return i18n.t('pageEventLogs.toast.successResolveLog');
+ } else {
+ return i18n.t('pageEventLogs.toast.successUnresolveLog');
+ }
+ })
+ .catch((error) => {
+ console.log(error);
+ throw new Error(i18n.t('pageEventLogs.toast.errorLogStatusUpdate'));
+ });
+ },
},
};
diff --git a/src/views/Health/EventLogs/EventLogs.vue b/src/views/Health/EventLogs/EventLogs.vue
index 69545a57..64e2adb9 100644
--- a/src/views/Health/EventLogs/EventLogs.vue
+++ b/src/views/Health/EventLogs/EventLogs.vue
@@ -34,7 +34,13 @@
@clear-selected="clearSelectedRows($refs.table)"
@batch-action="onBatchAction"
>
- <template #export>
+ <template #toolbar-buttons>
+ <b-button variant="primary" @click="resolveLogs">
+ {{ $t('pageEventLogs.resolve') }}
+ </b-button>
+ <b-button variant="primary" @click="unresolveLogs">
+ {{ $t('pageEventLogs.unresolve') }}
+ </b-button>
<table-toolbar-export
:data="batchExportData"
:file-name="exportFileNameByDate()"
@@ -107,6 +113,11 @@
<dt>{{ $t('pageEventLogs.table.name') }}:</dt>
<dd>{{ tableFormatter(item.name) }}</dd>
</dl>
+ <dl>
+ <!-- Type -->
+ <dt>{{ $t('pageEventLogs.table.type') }}:</dt>
+ <dd>{{ tableFormatter(item.type) }}</dd>
+ </dl>
</b-col>
<b-col sm="6" xl="4">
<dl>
@@ -128,13 +139,30 @@
<status-icon v-if="value" :status="statusIcon(value)" />
{{ value }}
</template>
-
<!-- Date column -->
<template #cell(date)="{ value }">
<p class="mb-0">{{ value | formatDate }}</p>
<p class="mb-0">{{ value | formatTime }}</p>
</template>
+ <!-- Status column -->
+ <template #cell(status)="row">
+ <b-form-checkbox
+ v-model="row.item.status"
+ name="switch"
+ switch
+ @change="changelogStatus(row.item)"
+ >
+ <span v-if="row.item.status">
+ {{ $t('pageEventLogs.resolved') }}
+ </span>
+ <span v-else> {{ $t('pageEventLogs.unresolved') }} </span>
+ </b-form-checkbox>
+ </template>
+ <template #cell(filterByStatus)="{ value }">
+ {{ value }}
+ </template>
+
<!-- Actions column -->
<template #cell(actions)="row">
<table-row-action
@@ -280,18 +308,19 @@ export default {
tdClass: 'text-nowrap',
},
{
- key: 'type',
- label: this.$t('pageEventLogs.table.type'),
- sortable: true,
- },
- {
key: 'date',
label: this.$t('pageEventLogs.table.date'),
sortable: true,
+ tdClass: 'text-nowrap',
},
{
key: 'description',
label: this.$t('pageEventLogs.table.description'),
+ tdClass: 'text-break',
+ },
+ {
+ key: 'status',
+ label: this.$t('pageEventLogs.table.status'),
},
{
key: 'actions',
@@ -306,6 +335,11 @@ export default {
label: this.$t('pageEventLogs.table.severity'),
values: ['OK', 'Warning', 'Critical'],
},
+ {
+ key: 'filterByStatus',
+ label: this.$t('pageEventLogs.table.status'),
+ values: ['Resolved', 'Unresolved'],
+ },
],
expandRowLabel,
activeFilters: [],
@@ -374,6 +408,17 @@ export default {
.finally(() => this.endLoader());
},
methods: {
+ changelogStatus(row) {
+ this.$store
+ .dispatch('eventLog/updateEventLogStatus', {
+ uri: row.uri,
+ status: row.status,
+ })
+ .then((success) => {
+ this.successToast(success);
+ })
+ .catch(({ message }) => this.errorToast(message));
+ },
deleteLogs(uris) {
this.$store
.dispatch('eventLog/deleteEventLogs', uris)
@@ -459,6 +504,32 @@ export default {
date.toString().split(':').join('-').split(' ')[4];
return this.$t('pageEventLogs.exportFilePrefix') + date;
},
+ resolveLogs() {
+ this.$store
+ .dispatch('eventLog/resolveEventLogs', this.selectedRows)
+ .then((messages) => {
+ messages.forEach(({ type, message }) => {
+ if (type === 'success') {
+ this.successToast(message);
+ } else if (type === 'error') {
+ this.errorToast(message);
+ }
+ });
+ });
+ },
+ unresolveLogs() {
+ this.$store
+ .dispatch('eventLog/unresolveEventLogs', this.selectedRows)
+ .then((messages) => {
+ messages.forEach(({ type, message }) => {
+ if (type === 'success') {
+ this.successToast(message);
+ } else if (type === 'error') {
+ this.errorToast(message);
+ }
+ });
+ });
+ },
},
};
</script>
diff --git a/src/views/Health/Sensors/Sensors.vue b/src/views/Health/Sensors/Sensors.vue
index 8bc4e22e..c69532a6 100644
--- a/src/views/Health/Sensors/Sensors.vue
+++ b/src/views/Health/Sensors/Sensors.vue
@@ -27,7 +27,7 @@
:selected-items-count="selectedRows.length"
@clear-selected="clearSelectedRows($refs.table)"
>
- <template #export>
+ <template #toolbar-buttons>
<table-toolbar-export
:data="selectedRows"
:file-name="exportFileNameByDate()"