diff --git a/src/components/Discover/Map/Filter/Trace.vue b/src/components/Discover/Map/Filter/Trace.vue index 5b71096..00cbc16 100644 --- a/src/components/Discover/Map/Filter/Trace.vue +++ b/src/components/Discover/Map/Filter/Trace.vue @@ -72,10 +72,10 @@ export default { setup() { const allMapDataStore = AllMapDataStore(); const loadingStore = LoadingStore(); - const { infinit404, infiniteStart, traces, traceTaskSeq, cases } = storeToRefs(allMapDataStore); + const { infinit404, baseInfiniteStart, baseTraces, baseTraceTaskSeq, baseCases } = storeToRefs(allMapDataStore); const { isLoading } = storeToRefs(loadingStore); - return {allMapDataStore, infinit404, infiniteStart, traces, traceTaskSeq, cases, isLoading} + return {allMapDataStore, infinit404, baseInfiniteStart, baseTraces, baseTraceTaskSeq, baseCases, isLoading} }, data() { return { @@ -92,13 +92,13 @@ export default { }, computed: { traceTotal: function() { - return this.traces.length; + return this.baseTraces.length; }, traceCountTotal: function() { - return this.traces.map(trace => trace.count).reduce((acc, cur) => acc + cur, 0); + return this.baseTraces.map(trace => trace.count).reduce((acc, cur) => acc + cur, 0); }, traceList: function() { - return this.traces.map(trace => { + return this.baseTraces.map(trace => { return { id: trace.id, value: this.progressWidth(Number(((trace.count / this.traceCountTotal) * 100).toFixed(1))), @@ -116,9 +116,9 @@ export default { chartData: function() { const start = this.selectArea[0]; const end = this.selectArea[1] - 1; - const labels = this.traces.map(trace => `#${trace.id}`); - const data = this.traces.map(trace => this.getPercentLabel(trace.count / this.traceCountTotal)); - const selectAreaData = this.traces.map((trace, index) => index >= start && index <= end ? 'rgba(0,153,255)' : 'rgba(203, 213, 225)'); + const labels = this.baseTraces.map(trace => `#${trace.id}`); + const data = this.baseTraces.map(trace => this.getPercentLabel(trace.count / this.traceCountTotal)); + const selectAreaData = this.baseTraces.map((trace, index) => index >= start && index <= end ? 'rgba(0,153,255)' : 'rgba(203, 213, 225)'); return { // 要呈現的資料 labels, @@ -223,9 +223,9 @@ export default { this.infinit404 = null; this.infinitMaxItems = false; this.showTraceId = id; - this.infiniteStart = 0; - this.allMapDataStore.traceId = id; - this.infiniteData = await this.allMapDataStore.getTraceDetail(); + this.baseInfiniteStart = 0; + this.allMapDataStore.baseTraceId = id; + this.infiniteData = await this.allMapDataStore.getBaseTraceDetail(); this.createCy(); this.isLoading = false; }, @@ -236,7 +236,7 @@ export default { // 避免每次渲染都重複累加 this.processMap.nodes = []; // 將 api call 回來的資料帶進 node - this.traceTaskSeq.forEach((node, index) => { + this.baseTraceTaskSeq.forEach((node, index) => { this.processMap.nodes.push({ data: { id: index, @@ -255,7 +255,7 @@ export default { */ setEdgesData(){ this.processMap.edges = []; - this.traceTaskSeq.forEach((edge, index) => { + this.baseTraceTaskSeq.forEach((edge, index) => { this.processMap.edges.push({ data: { source: `${index}`, @@ -283,7 +283,7 @@ export default { * @param {element} event */ handleScroll(event) { - if(this.infinitMaxItems || this.cases.length < 20) return; + if(this.infinitMaxItems || this.baseCases.length < 20) return; const container = event.target; const overScrollHeight = container.scrollTop + container.clientHeight >= container.scrollHeight; @@ -295,9 +295,9 @@ export default { */ async fetchData() { try { - this.infiniteStart += 20; - await this.allMapDataStore.getTraceDetail(); - this.infiniteData = [...this.infiniteData, ...this.cases]; + this.baseInfiniteStart += 20; + await this.allMapDataStore.getBaseTraceDetail(); + this.infiniteData = [...this.infiniteData, ...this.baseCases]; } catch(error) { console.error('Failed to load data:', error); } diff --git a/src/module/apiError.js b/src/module/apiError.js index e61bc8c..cca8b1f 100644 --- a/src/module/apiError.js +++ b/src/module/apiError.js @@ -17,7 +17,7 @@ const delay = (s = 0) => new Promise((resolve, reject) => setTimeout(resolve, s * @returns {string} Error HTTP Status */ export default async function apiError(error, toastMessage) { - if(error?.request.status === 401) { + if(error.request?.status === 401) { delete axios.defaults.headers.common["Authorization"]; document.cookie = 'luciaToken=; expires=Thu, 01 Jan 1970 00:00:00 UTC;'; return router.push('/login'); diff --git a/src/stores/allMapData.js b/src/stores/allMapData.js index 74f2bd7..4322199 100644 --- a/src/stores/allMapData.js +++ b/src/stores/allMapData.js @@ -4,8 +4,10 @@ import apiError from '@/module/apiError.js'; export default defineStore('allMapDataStore', { state: () => ({ + baseLogId: null, logId: null, traceId: 1, + baseTraceId: 1, tempFilterId: null, createFilterId: null, filterName: null, @@ -14,8 +16,11 @@ export default defineStore('allMapDataStore', { allStats: {}, allInsights: {}, allTrace: [], + allBaseTrace: [], allCase: [], + allBaseCase: [], allTraceTaskSeq: [], + allBaseTraceTaskSeq: [], allFilterTask: [], allFilterStartToEnd: [], allFilterEndToStart: [], @@ -31,6 +36,7 @@ export default defineStore('allMapDataStore', { selectTimeFrame: [], // user select time start and end infinite404: null, // 無限滾動式是否到底要換頁 infiniteStart: 0, // 無限滾動 case 開始的數字 + baseInfiniteStart: 0, // 無限滾動 case 開始的數字 }), getters: { processMap: state => { @@ -48,15 +54,27 @@ export default defineStore('allMapDataStore', { traces: state => { return state.allTrace; }, + baseTraces: state => { + return state.allBaseTrace; + }, cases: state => { return state.allCase; }, + baseCases: state => { + return state.allBaseCase; + }, infiniteFirstCases: state => { if(state.infiniteStart === 0) return state.allCase; }, + BaseInfiniteFirstCases: state => { + if(state.BaseInfiniteStart === 0) return state.allBaseCase; + }, traceTaskSeq: state => { return state.allTraceTaskSeq; }, + baseTraceTaskSeq: state => { + return state.allBaseTraceTaskSeq; + }, // All tasks filterTasks: state => { return state.allFilterTask; @@ -111,6 +129,8 @@ export default defineStore('allMapDataStore', { let logId = this.logId; let tempFilterId = this.tempFilterId; let createfilterId = this.createFilterId; + let baseLogId = this.baseLogId; + let baseApi = `/api/logs/${baseLogId}/traces`; let api = ''; // 先判斷暫存 再判斷 filter 最後 log @@ -119,9 +139,11 @@ export default defineStore('allMapDataStore', { else api = `/api/logs/${logId}/traces`; try { + let baseResponse; const response = await this.$axios.get(api); this.allTrace = response.data; - + if(baseLogId) baseResponse = await this.$axios.get(baseApi); + this.allBaseTrace = baseResponse.data; } catch(error) { apiError(error, 'Failed to load the Trace.'); } @@ -137,7 +159,6 @@ export default defineStore('allMapDataStore', { let start = this.infiniteStart; let api = ''; - // 先判斷暫存 再判斷 filter 最後 log if(tempFilterId != null) api = `/api/temp-filters/${tempFilterId}/traces/${traceId}?start=${start}&page_size=20`; else if(createfilterId!= null) api = `/api/filters/${createfilterId}/traces/${traceId}?start=${start}&page_size=20`; @@ -158,6 +179,30 @@ export default defineStore('allMapDataStore', { apiError(error, 'Failed to load the Trace Detail.'); }; }, + /** + * fetch base log trace detail api. + */ + async getBaseTraceDetail() { + let logId = this.baseLogId; + let traceId = this.baseTraceId; + let start = this.baseInfiniteStart; + let api = `/api/logs/${logId}/traces/${traceId}?start=${start}&page_size=20`; + + try { + const response = await this.$axios.get(api); + this.allBaseTraceTaskSeq = response.data.task_seq; + this.allBaseCase = response.data.cases; + this.allBaseCase.map(c => { + c.started_at = moment(c.started_at).format('YYYY-MM-DD HH:MM'); + c.completed_at = moment(c.completed_at).format('YYYY-MM-DD HH:MM'); + return this.allBaseCase; + }); + return this.allBaseCase; + } catch(error) { + if(error.response.status === 404) return this.infinite404 = 404; + apiError(error, 'Failed to load the Trace Detail.'); + }; + }, /** * fetch Filter Parameters api. */ diff --git a/src/views/Discover/Map/index.vue b/src/views/Discover/Map/index.vue index 657a1aa..bd7bf54 100644 --- a/src/views/Discover/Map/index.vue +++ b/src/views/Discover/Map/index.vue @@ -68,9 +68,9 @@ export default { const loadingStore = LoadingStore(); const allMapDataStore = AllMapDataStore(); const { isLoading } = storeToRefs(loadingStore); - const { processMap, bpmn, stats, insights, traceId, traces, filterTasks, filterStartToEnd, filterEndToStart, filterTimeframe, filterTrace, temporaryData, isRuleData, ruleData, logId, createFilterId } = storeToRefs(allMapDataStore); + const { processMap, bpmn, stats, insights, traceId, traces, baseTraces, baseTraceId, filterTasks, filterStartToEnd, filterEndToStart, filterTimeframe, filterTrace, temporaryData, isRuleData, ruleData, logId, createFilterId } = storeToRefs(allMapDataStore); - return { isLoading, processMap, bpmn, stats, insights, traceId, traces, filterTasks, filterStartToEnd, filterEndToStart, filterTimeframe, filterTrace, logId, createFilterId, temporaryData, isRuleData, ruleData, allMapDataStore} + return { isLoading, processMap, bpmn, stats, insights, traceId, traces, baseTraces, baseTraceId, filterTasks, filterStartToEnd, filterEndToStart, filterTimeframe, filterTrace, logId, createFilterId, temporaryData, isRuleData, ruleData, allMapDataStore} }, components: { SidebarView, @@ -311,7 +311,9 @@ export default { // 取得 logId 後才 call api await this.allMapDataStore.getAllMapData(); await this.allMapDataStore.getAllTrace(); - this.traceId = await this.traces[0]?.id; // log、filter 檔切換過程中, trace id 不同,將初始 trace id 設定為該檔案的 trace 幣一筆資料的 id。 + // log、filter 檔切換過程中, trace id 不同,將初始 trace id 設定為該檔案的 trace 幣一筆資料的 id。 + this.traceId = await this.traces[0]?.id; + this.baseTraceId = await this.baseTraces[0]?.id; this.createCy(this.mapType); await this.allMapDataStore.getFilterParams(); diff --git a/src/views/Files/index.vue b/src/views/Files/index.vue index a13f42d..2539fa3 100644 --- a/src/views/Files/index.vue +++ b/src/views/Files/index.vue @@ -92,9 +92,9 @@ setup() { const store = filesStore(); const allMapDataStore = AllMapDataStore(); - const { createFilterId } = storeToRefs(allMapDataStore); + const { createFilterId, baseLogId } = storeToRefs(allMapDataStore); - return { store, allMapDataStore, createFilterId } + return { store, allMapDataStore, createFilterId, baseLogId } }, components: { IconDataFormat, @@ -139,6 +139,7 @@ switch (file.fileType) { case 'Log': this.createFilterId = null; + this.baseLogId = file.id; fileId = file.id; type = 'log'; params = { type: type, fileId: fileId }; @@ -146,6 +147,7 @@ break; case 'Filter': this.createFilterId = file.id; + this.baseLogId = file.log.id; fileId = file.id; type = 'filter'; params = { type: type, fileId: fileId };