main
vue 105 lines 2.42 KB
Raw
1 <template>
2 <n-spin :show="loading" class="rules-list">
3 <n-scrollbar ref="scrollContent">
4 <div class="list flex min-h-52 flex-col gap-2">
5 <Rule v-for="rule of rules" :key="rule.id" :rule :highlight="highlight === rule.id" embedded />
6 </div>
7 </n-scrollbar>
8 </n-spin>
9 </template>
10
11 <script setup lang="ts">
12 import type { ScrollbarInst } from "naive-ui"
13 import type { PipelineRule } from "@/types/graylog/pipelines.d"
14 import { NScrollbar, NSpin, useMessage } from "naive-ui"
15 import { nextTick, onBeforeMount, ref, toRefs, watch } from "vue"
16 import Api from "@/api"
17 import Rule from "./Rule.vue"
18
19 const props = defineProps<{ highlight: string | null | undefined }>()
20
21 const emit = defineEmits<{
22 (e: "loaded", value: { total: number }): void
23 }>()
24
25 const { highlight } = toRefs(props)
26
27 const message = useMessage()
28 const loading = ref(false)
29 const rules = ref<PipelineRule[]>([])
30 const scrollContent = ref<(ScrollbarInst & { $el: HTMLElement }) | null>(null)
31
32 function scrollToItem(id: string) {
33 const element = document.getElementById(`rule-${id}`)
34 if (element && scrollContent.value) {
35 const wrap = (scrollContent.value.$el.nextSibling || scrollContent.value.$el.nextElementSibling) as HTMLElement
36 const middle = element.offsetTop - wrap.offsetHeight / 2
37 scrollContent.value?.scrollTo({ top: middle, behavior: "smooth" })
38 }
39 }
40
41 function getRules() {
42 loading.value = true
43
44 Api.graylog
45 .getPipelinesRules()
46 .then(res => {
47 if (res.data.success) {
48 rules.value = res.data.pipeline_rules || []
49 emit("loaded", { total: rules.value.length })
50 nextTick(() => {
51 setTimeout(() => {
52 if (highlight.value) {
53 scrollToItem(highlight.value)
54 }
55 }, 300)
56 })
57 } else {
58 message.warning(res.data?.message || "An error occurred. Please try again later.")
59 }
60 })
61 .catch(err => {
62 message.error(err.response?.data?.message || "An error occurred. Please try again later.")
63 })
64 .finally(() => {
65 loading.value = false
66 })
67 }
68
69 watch(highlight, val => {
70 if (val) {
71 nextTick(() => {
72 setTimeout(() => {
73 scrollToItem(val)
74 })
75 })
76 }
77 })
78
79 onBeforeMount(() => {
80 getRules()
81 })
82 </script>
83
84 <style lang="scss" scoped>
85 .rules-list {
86 height: 100%;
87 max-height: 100%;
88 overflow: hidden;
89 box-sizing: border-box;
90
91 :deep() {
92 .n-spin-content {
93 height: 100%;
94 box-sizing: border-box;
95 display: flex;
96 flex-direction: column;
97 }
98 }
99
100 .list {
101 padding: var(--n-body-padding);
102 padding-bottom: 50vh;
103 }
104 }
105 </style>