1<template> 2 <b-container fluid="xl"> 3 <page-title :description="$t('pageSnmpAlerts.pageDescription')" /> 4 <b-row> 5 <b-col xl="9" class="text-right"> 6 <b-button variant="primary" @click="initModalAddDestination"> 7 <icon-add /> 8 {{ $t('pageSnmpAlerts.addDestination') }} 9 </b-button> 10 </b-col> 11 </b-row> 12 <b-row> 13 <b-col xl="9"> 14 <table-toolbar 15 ref="toolbar" 16 :selected-items-count="selectedRows.length" 17 :actions="tableToolbarActions" 18 @clear-selected="clearSelectedRows($refs.table)" 19 @batch-action="onBatchAction" 20 /> 21 <b-table 22 ref="table" 23 responsive="md" 24 selectable 25 show-empty 26 no-select-on-click 27 hover 28 :fields="fields" 29 :items="tableItems" 30 :empty-text="$t('global.table.emptyMessage')" 31 @row-selected="onRowSelected($event, tableItems.length)" 32 > 33 <!-- Checkbox column --> 34 <template #head(checkbox)> 35 <b-form-checkbox 36 v-model="tableHeaderCheckboxModel" 37 data-test-id="snmpAlerts-checkbox-selectAll" 38 :indeterminate="tableHeaderCheckboxIndeterminate" 39 @change="onChangeHeaderCheckbox($refs.table)" 40 > 41 <span class="sr-only">{{ $t('global.table.selectAll') }}</span> 42 </b-form-checkbox> 43 </template> 44 <template #cell(checkbox)="row"> 45 <b-form-checkbox 46 v-model="row.rowSelected" 47 :data-test-id="`snmpAlerts-checkbox-selectRow-${row.index}`" 48 @change="toggleSelectRow($refs.table, row.index)" 49 > 50 <span class="sr-only">{{ $t('global.table.selectItem') }}</span> 51 </b-form-checkbox> 52 </template> 53 54 <!-- table actions column --> 55 <template #cell(actions)="{ item }"> 56 <table-row-action 57 v-for="(action, index) in item.actions" 58 :key="index" 59 :value="action.value" 60 :enabled="action.enabled" 61 :title="action.title" 62 :data-test-id="`snmpAlerts-button-deleteRow-${item.index}`" 63 @click-table-action="onTableRowAction($event, item)" 64 > 65 <template #icon> 66 <icon-trashcan v-if="action.value === 'delete'" /> 67 </template> 68 </table-row-action> 69 </template> 70 </b-table> 71 </b-col> 72 </b-row> 73 <!-- Modals --> 74 <modal-add-destination @ok="onModalOk" /> 75 </b-container> 76</template> 77 78<script> 79import IconTrashcan from '@carbon/icons-vue/es/trash-can/20'; 80import ModalAddDestination from './ModalAddDestination'; 81import PageTitle from '@/components/Global/PageTitle'; 82import IconAdd from '@carbon/icons-vue/es/add--alt/20'; 83import TableToolbar from '@/components/Global/TableToolbar'; 84import TableRowAction from '@/components/Global/TableRowAction'; 85import LoadingBarMixin from '@/components/Mixins/LoadingBarMixin'; 86import BVToastMixin from '@/components/Mixins/BVToastMixin'; 87 88import BVTableSelectableMixin, { 89 selectedRows, 90 tableHeaderCheckboxModel, 91 tableHeaderCheckboxIndeterminate, 92} from '@/components/Mixins/BVTableSelectableMixin'; 93import { useI18n } from 'vue-i18n'; 94import i18n from '@/i18n'; 95 96export default { 97 name: 'SnmpAlerts', 98 components: { 99 PageTitle, 100 IconAdd, 101 TableToolbar, 102 IconTrashcan, 103 ModalAddDestination, 104 TableRowAction, 105 }, 106 mixins: [BVTableSelectableMixin, BVToastMixin, LoadingBarMixin], 107 beforeRouteLeave(to, from, next) { 108 this.hideLoader(); 109 next(); 110 }, 111 data() { 112 return { 113 $t: useI18n().t, 114 fields: [ 115 { 116 key: 'checkbox', 117 }, 118 { 119 key: 'IP', 120 label: i18n.global.t('pageSnmpAlerts.table.ipaddress'), 121 }, 122 { 123 key: 'Port', 124 label: i18n.global.t('pageSnmpAlerts.table.port'), 125 }, 126 { 127 key: 'actions', 128 label: '', 129 tdClass: 'text-right text-nowrap', 130 }, 131 ], 132 tableToolbarActions: [ 133 { 134 value: 'delete', 135 label: i18n.global.t('global.action.delete'), 136 }, 137 ], 138 selectedRows: selectedRows, 139 tableHeaderCheckboxModel: tableHeaderCheckboxModel, 140 tableHeaderCheckboxIndeterminate: tableHeaderCheckboxIndeterminate, 141 }; 142 }, 143 computed: { 144 allSnmpDetails() { 145 return this.$store.getters['snmpAlerts/allSnmpDetails']; 146 }, 147 tableItems() { 148 // transform destination data to table data 149 return this.allSnmpDetails.map((subscriptions) => { 150 const [destination, dataWithProtocol, dataWithoutProtocol] = [ 151 subscriptions.Destination, 152 subscriptions.Destination.split('/')[2].split(':'), 153 subscriptions.Destination.split(':'), 154 ]; 155 //condition to check if destination comes with protocol or not 156 const conditionForProtocolCheck = destination.includes('://'); 157 const ip = conditionForProtocolCheck 158 ? dataWithProtocol[0] 159 : dataWithoutProtocol[0]; 160 const port = conditionForProtocolCheck 161 ? dataWithProtocol[1] 162 : dataWithoutProtocol[1]; 163 return { 164 IP: ip, 165 Port: port, 166 id: subscriptions.Id, 167 actions: [ 168 { 169 value: 'delete', 170 enabled: true, 171 title: i18n.global.t('pageSnmpAlerts.deleteDestination'), 172 }, 173 ], 174 ...subscriptions, 175 }; 176 }); 177 }, 178 }, 179 created() { 180 this.startLoader(); 181 this.$store 182 .dispatch('snmpAlerts/getSnmpDetails') 183 .finally(() => this.endLoader()); 184 }, 185 methods: { 186 onModalOk({ ipAddress, port }) { 187 const protocolIpAddress = 'snmp://' + ipAddress; 188 const destination = port 189 ? protocolIpAddress + ':' + port 190 : protocolIpAddress; 191 const data = { 192 Destination: destination, 193 SubscriptionType: 'SNMPTrap', 194 Protocol: 'SNMPv2c', 195 }; 196 this.startLoader(); 197 this.$store 198 .dispatch('snmpAlerts/addDestination', { data }) 199 .then((success) => this.successToast(success)) 200 .catch(({ message }) => this.errorToast(message)) 201 .finally(() => this.endLoader()); 202 }, 203 initModalAddDestination() { 204 this.$bvModal.show('add-destination'); 205 }, 206 initModalDeleteDestination(destination) { 207 this.$bvModal 208 .msgBoxConfirm( 209 i18n.global.t('pageSnmpAlerts.modal.deleteConfirmMessage', { 210 destination: destination.id, 211 }), 212 { 213 title: i18n.global.t( 214 'pageSnmpAlerts.modal.deleteSnmpDestinationTitle', 215 ), 216 okTitle: i18n.global.t('pageSnmpAlerts.deleteDestination'), 217 cancelTitle: i18n.global.t('global.action.cancel'), 218 autoFocusButton: 'ok', 219 }, 220 ) 221 .then((deleteConfirmed) => { 222 if (deleteConfirmed) { 223 this.deleteDestination(destination); 224 } 225 }); 226 }, 227 deleteDestination({ id }) { 228 this.startLoader(); 229 this.$store 230 .dispatch('snmpAlerts/deleteDestination', id) 231 .then((success) => this.successToast(success)) 232 .catch(({ message }) => this.errorToast(message)) 233 .finally(() => this.endLoader()); 234 }, 235 onBatchAction(action) { 236 if (action === 'delete') { 237 this.$bvModal 238 .msgBoxConfirm( 239 i18n.global.t( 240 'pageSnmpAlerts.modal.batchDeleteConfirmMessage', 241 this.selectedRows.length, 242 ), 243 { 244 title: i18n.global.t( 245 'pageSnmpAlerts.modal.deleteSnmpDestinationTitle', 246 this.selectedRows.length, 247 ), 248 okTitle: i18n.global.t( 249 'pageSnmpAlerts.deleteDestination', 250 this.selectedRows.length, 251 ), 252 cancelTitle: i18n.global.t('global.action.cancel'), 253 autoFocusButton: 'ok', 254 }, 255 ) 256 .then((deleteConfirmed) => { 257 if (deleteConfirmed) { 258 this.startLoader(); 259 this.$store 260 .dispatch( 261 'snmpAlerts/deleteMultipleDestinations', 262 this.selectedRows, 263 ) 264 .then((messages) => { 265 messages.forEach(({ type, message }) => { 266 if (type === 'success') this.successToast(message); 267 if (type === 'error') this.errorToast(message); 268 }); 269 }) 270 .finally(() => this.endLoader()); 271 } 272 }); 273 } 274 }, 275 onTableRowAction(action, row) { 276 if (action === 'delete') { 277 this.initModalDeleteDestination(row); 278 } 279 }, 280 }, 281}; 282</script> 283