main
vue 120 lines 3.33 KB
Raw
1 <template>
2 <div>
3 <CardEntity hoverable :embedded header-box-class="text-default!">
4 <template #headerMain>
5 {{ source.name }}
6 </template>
7 <template #headerExtra>
8 <Badge type="splitted" :color="source.enabled ? 'success' : 'danger'" bright>
9 <template #iconLeft>
10 <Icon :name="source.enabled ? 'carbon:checkmark' : 'carbon:close'" :size="13" />
11 </template>
12 <template #value>{{ source.enabled ? "Enabled" : "Disabled" }}</template>
13 </Badge>
14 </template>
15 <template #default>
16 <div class="flex flex-wrap items-center gap-3">
17 <Badge type="splitted" color="primary">
18 <template #iconLeft>
19 <Icon :name="TypeIcon" :size="13" />
20 </template>
21 <template #label>Type</template>
22 <template #value>{{ source.event_type }}</template>
23 </Badge>
24
25 <Badge type="splitted" color="primary">
26 <template #iconLeft>
27 <Icon :name="IndexIcon" :size="13" />
28 </template>
29 <template #label>Index</template>
30 <template #value>{{ source.index_pattern }}</template>
31 </Badge>
32
33 <Badge type="splitted" color="primary">
34 <template #iconLeft>
35 <Icon :name="TimeIcon" :size="13" />
36 </template>
37 <template #label>Time Field</template>
38 <template #value>{{ source.time_field }}</template>
39 </Badge>
40 </div>
41 </template>
42
43 <template #footerExtra>
44 <div class="flex flex-wrap gap-3">
45 <n-button size="small" @click.stop="emit('edit')">
46 <template #icon>
47 <Icon :name="EditIcon" />
48 </template>
49 Edit
50 </n-button>
51 <n-button size="small" type="error" ghost :loading="loadingDelete" @click.stop="handleDelete">
52 <template #icon>
53 <Icon :name="DeleteIcon" :size="15" />
54 </template>
55 Delete
56 </n-button>
57 </div>
58 </template>
59 </CardEntity>
60 </div>
61 </template>
62
63 <script setup lang="ts">
64 import type { EventSource } from "@/types/eventSources.d"
65 import { NButton, useDialog, useMessage } from "naive-ui"
66 import { ref } from "vue"
67 import Api from "@/api"
68 import Badge from "@/components/common/Badge.vue"
69 import CardEntity from "@/components/common/cards/CardEntity.vue"
70 import Icon from "@/components/common/Icon.vue"
71
72 const { source, embedded } = defineProps<{
73 source: EventSource
74 embedded?: boolean
75 }>()
76
77 const emit = defineEmits<{
78 (e: "edit"): void
79 (e: "deleted"): void
80 }>()
81
82 const TypeIcon = "carbon:category"
83 const IndexIcon = "carbon:catalog"
84 const TimeIcon = "carbon:time"
85 const EditIcon = "carbon:edit"
86 const DeleteIcon = "ph:trash"
87
88 const dialog = useDialog()
89 const message = useMessage()
90 const loadingDelete = ref(false)
91
92 function handleDelete() {
93 dialog.warning({
94 title: "Delete Event Source",
95 content: `Are you sure you want to delete the event source "${source.name}"?`,
96 positiveText: "Delete",
97 negativeText: "Cancel",
98 onPositiveClick: () => {
99 loadingDelete.value = true
100
101 Api.siem
102 .deleteEventSource(source.id)
103 .then(res => {
104 if (res.data.success) {
105 emit("deleted")
106 message.success(res.data?.message || "Event source deleted successfully.")
107 } else {
108 message.warning(res.data?.message || "An error occurred. Please try again later.")
109 }
110 })
111 .catch(err => {
112 message.error(err.response?.data?.message || "An error occurred. Please try again later.")
113 })
114 .finally(() => {
115 loadingDelete.value = false
116 })
117 }
118 })
119 }
120 </script>