1. Fix International Language. (#166)
2. Optimize code structure.
3. Fix illegal code.
diff --git a/src/assets/lang/en.ts b/src/assets/lang/en.ts
index 682991b..b24325f 100644
--- a/src/assets/lang/en.ts
+++ b/src/assets/lang/en.ts
@@ -96,7 +96,7 @@
monthCutTip: 'Last 1 month',
serverZone: 'Server Zone',
percentResponse: 'Percent Response',
- download: 'Dowanload',
+ exportImage: 'Export image',
};
export default m;
diff --git a/src/assets/lang/zh.ts b/src/assets/lang/zh.ts
index 71de156..b751014 100644
--- a/src/assets/lang/zh.ts
+++ b/src/assets/lang/zh.ts
@@ -96,7 +96,7 @@
monthCutTip: '最近1月',
serverZone: '服务器时区',
percentResponse: '百分比响应',
- download: '导出为图片',
+ exportImage: '导出为图片',
};
export default m;
diff --git a/src/views/components/trace/trace-detail-chart-list.vue b/src/views/components/trace/trace-detail-chart-list.vue
index c005a25..05f09e6 100644
--- a/src/views/components/trace/trace-detail-chart-list.vue
+++ b/src/views/components/trace/trace-detail-chart-list.vue
@@ -30,7 +30,7 @@
<span>{{i}}</span>
</span>
</transition-group>
- <a class="rk-btn r vm tc" @click="downloadTrace">{{$t('download')}}</a>
+ <a class="rk-btn r vm tc" @click="downloadTrace">{{$t('exportImage')}}</a>
<rk-sidebox :width="'50%'" :show.sync="showDetail" :title="$t('spanInfo')">
<div class="rk-trace-detail">
<h5 class="mb-15">{{$t('tags')}}.</h5>
@@ -73,13 +73,11 @@
import * as d3 from 'd3';
import Trace from './d3-trace';
import _ from 'lodash';
-/* eslint-disable */
-/* tslint:disable */
export default {
props: ['data', 'traceId'],
- data(){
+ data() {
return {
- segmentId:[],
+ segmentId: [],
showDetail: false,
list: [],
currentSpan: [],
@@ -88,27 +86,27 @@
},
watch: {
data() {
- if(!this.data.length) {return;}
+ if (!this.data.length) { return; }
this.loading = true;
this.changeTree();
- this.tree.init({label:`TRACE_ROOT`, children: this.segmentId}, this.data);
+ this.tree.init({label: 'TRACE_ROOT', children: this.segmentId}, this.data);
this.tree.draw(() => {
setTimeout(() => {
- this.loading = false
+ this.loading = false;
}, 200);
- })
- }
+ });
+ },
},
beforeDestroy() {
d3.selectAll('.d3-tip').remove();
},
mounted() {
- this.$eventBus.$on('TRACE-LIST-LOADING', this, ()=>{ this.loading = true });
+ this.$eventBus.$on('TRACE-LIST-LOADING', this, () => { this.loading = true; });
// this.loading = true;
this.changeTree();
- this.tree = new Trace(this.$refs.traceList, this)
- this.tree.init({label:`TRACE_ROOT`, children: this.segmentId}, this.data);
- this.tree.draw()
+ this.tree = new Trace(this.$refs.traceList, this);
+ this.tree.init({label: 'TRACE_ROOT', children: this.segmentId}, this.data);
+ this.tree.draw();
this.loading = false;
// this.computedScale();
},
@@ -118,13 +116,16 @@
this.currentSpan = i.data;
this.showDetail = true;
},
- traverseTree(node, spanId, segmentId, data){
- if (!node) return;
- if(node.spanId == spanId && node.segmentId == segmentId) {node.children.push(data);return;}
+ traverseTree(node, spanId, segmentId, data) {
+ if (!node) { return; }
+ if (node.spanId === spanId && node.segmentId === segmentId) {
+ node.children.push(data);
+ return;
+ }
if (node.children && node.children.length > 0) {
- for (let i = 0; i < node.children.length; i++) {
- this.traverseTree(node.children[i],spanId,segmentId,data);
- }
+ node.children.forEach((nodeItem) => {
+ this.traverseTree(nodeItem, spanId, segmentId, data);
+ });
}
},
computedScale(i) {
@@ -134,133 +135,164 @@
.interpolator(d3.interpolateCool);
return sequentialScale(i);
},
- changeTree(){
- if (this.data.length === 0) return [];
- this.list = Array.from(new Set(this.data.map(i => i.serviceCode)));
+ changeTree() {
+ if (this.data.length === 0) {
+ return [];
+ }
+ this.list = Array.from(new Set(this.data.map((i) => i.serviceCode)));
this.segmentId = [];
const segmentGroup = {};
const segmentIdGroup = [];
const fixSpans = [];
const segmentHeaders = [];
- this.data.forEach((span) => {
- if (span.parentSpanId === -1) {
- segmentHeaders.push(span);
- } else {
- const index = this.data.findIndex(i => (i.segmentId === span.segmentId && i.spanId === (span.spanId - 1)));
- const fixSpanKeyContent = {
- traceId: span.traceId,
- segmentId: span.segmentId,
- spanId: span.spanId - 1,
- parentSpanId: span.spanId - 2,
- };
- if (index === -1 && !_.find(fixSpans, fixSpanKeyContent)) {
- fixSpans.push(
- {
- ...fixSpanKeyContent, refs: [], endpointName: `VNode: ${span.segmentId}`, serviceCode: 'VirtualNode', type: `[Broken] ${span.type}`, peer: '', component: `VirtualNode: #${span.spanId - 1}`, isError: true, isBroken: true, layer: 'Broken', tags: [], logs: [],
- },
- );
- }
+ this.data.forEach((span) => {
+ if (span.parentSpanId === -1) {
+ segmentHeaders.push(span);
+ } else {
+ const index = this.data.findIndex((i) => (
+ i.segmentId === span.segmentId
+ &&
+ i.spanId === (span.spanId - 1)
+ ));
+ const fixSpanKeyContent = {
+ traceId: span.traceId,
+ segmentId: span.segmentId,
+ spanId: span.spanId - 1,
+ parentSpanId: span.spanId - 2,
+ };
+ if (index === -1 && !_.find(fixSpans, fixSpanKeyContent)) {
+ fixSpans.push(
+ {
+ ...fixSpanKeyContent,
+ refs: [],
+ endpointName: `VNode: ${span.segmentId}`,
+ serviceCode: 'VirtualNode',
+ type: `[Broken] ${span.type}`,
+ peer: '',
+ component: `VirtualNode: #${span.spanId - 1}`,
+ isError: true,
+ isBroken: true,
+ layer: 'Broken',
+ tags: [],
+ logs: [],
+ },
+ );
}
- });
- segmentHeaders.forEach((span) => {
- if (span.refs.length) {
- span.refs.forEach((ref) => {
- const index = this.data.findIndex(i => (ref.parentSegmentId === i.segmentId && ref.parentSpanId === i.spanId));
- if (index === -1) {
- // create a known broken node.
- const i = ref.parentSpanId;
- const fixSpanKeyContent = {
+ }
+ });
+ segmentHeaders.forEach((span) => {
+ if (span.refs.length) {
+ span.refs.forEach((ref) => {
+ const index = this.data.findIndex((i) => (
+ ref.parentSegmentId === i.segmentId
+ &&
+ ref.parentSpanId === i.spanId
+ ));
+ if (index === -1) {
+ // create a known broken node.
+ const i = ref.parentSpanId;
+ const fixSpanKeyContent = {
+ traceId: ref.traceId,
+ segmentId: ref.parentSegmentId,
+ spanId: i,
+ parentSpanId: i > -1 ? 0 : -1,
+ };
+ if (!_.find(fixSpans, fixSpanKeyContent)) {
+ fixSpans.push({
+ ...fixSpanKeyContent, refs: [], endpointName: `VNode: ${ref.parentSegmentId}`, serviceCode: 'VirtualNode', type: `[Broken] ${ref.type}`, peer: '', component: `VirtualNode: #${i}`, isError: true, isBroken: true, layer: 'Broken', tags: [], logs: [],
+ });
+ }
+ // if root broken node is not exist, create a root broken node.
+ if (fixSpanKeyContent.parentSpanId > -1) {
+ const fixRootSpanKeyContent = {
traceId: ref.traceId,
segmentId: ref.parentSegmentId,
- spanId: i,
- parentSpanId: i > -1 ? 0 : -1,
+ spanId: 0,
+ parentSpanId: -1,
};
- !_.find(fixSpans, fixSpanKeyContent) && fixSpans.push(
- {
- ...fixSpanKeyContent, refs: [], endpointName: `VNode: ${ref.parentSegmentId}`, serviceCode: 'VirtualNode', type: `[Broken] ${ref.type}`, peer: '', component: `VirtualNode: #${i}`, isError: true, isBroken: true, layer: 'Broken', tags: [], logs: [],
- },
- );
- // if root broken node is not exist, create a root broken node.
- if (fixSpanKeyContent.parentSpanId > -1) {
- const fixRootSpanKeyContent = {
- traceId: ref.traceId,
- segmentId: ref.parentSegmentId,
- spanId: 0,
- parentSpanId: -1,
- };
- !_.find(fixSpans, fixRootSpanKeyContent) && fixSpans.push(
- {
- ...fixRootSpanKeyContent,
- refs: [],
- endpointName: `VNode: ${ref.parentSegmentId}`,
- serviceCode: 'VirtualNode',
- type: `[Broken] ${ref.type}`,
- peer: '',
- component: `VirtualNode: #0`,
- isError: true,
- isBroken: true,
- layer: 'Broken',
- tags: [],
- logs: [],
- },
- );
+ if (!_.find(fixSpans, fixRootSpanKeyContent)) {
+ fixSpans.push({
+ ...fixRootSpanKeyContent,
+ refs: [],
+ endpointName: `VNode: ${ref.parentSegmentId}`,
+ serviceCode: 'VirtualNode',
+ type: `[Broken] ${ref.type}`,
+ peer: '',
+ component: `VirtualNode: #0`,
+ isError: true,
+ isBroken: true,
+ layer: 'Broken',
+ tags: [],
+ logs: [],
+ });
}
}
+ }
+ });
+ }
+ });
+ [...fixSpans, ...this.data].forEach((i) => {
+ i.label = i.endpointName || 'no operation name';
+ i.children = [];
+ if (segmentGroup[i.segmentId] === undefined) {
+ segmentIdGroup.push(i.segmentId);
+ segmentGroup[i.segmentId] = [];
+ segmentGroup[i.segmentId].push(i);
+ } else {
+ segmentGroup[i.segmentId].push(i);
+ }
+ });
+ segmentIdGroup.forEach((id) => {
+ const currentSegment = segmentGroup[id].sort((a, b) => b.parentSpanId - a.parentSpanId);
+ currentSegment.forEach((s) => {
+ const index = currentSegment.findIndex((i) => i.spanId === s.parentSpanId);
+ if (index !== -1) {
+ if (
+ (currentSegment[index].isBroken && currentSegment[index].parentSpanId === -1)
+ ||
+ !currentSegment[index].isBroken
+ ) {
+ currentSegment[index].children.push(s);
+ currentSegment[index].children.sort((a, b) => a.spanId - b.spanId);
+ }
+ }
+ if (s.isBroken) {
+ const children = _.filter(this.data, (span) => {
+ return _.find(span.refs, {traceId: s.traceId, parentSegmentId: s.segmentId, parentSpanId: s.spanId});
});
+ if (children.length > 0) {
+ s.children.push(...children);
+ }
}
});
- [...fixSpans, ...this.data].forEach(i => {
- i.label=i.endpointName || 'no operation name';
- i.children = [];
- if(segmentGroup[i.segmentId] === undefined){
- segmentIdGroup.push(i.segmentId);
- segmentGroup[i.segmentId] = [];
- segmentGroup[i.segmentId].push(i);
- }else{
- segmentGroup[i.segmentId].push(i);
+ segmentGroup[id] = currentSegment[currentSegment.length - 1];
+ });
+ segmentIdGroup.forEach((id) => {
+ segmentGroup[id].refs.forEach((ref) => {
+ if (ref.traceId === this.traceId) {
+ this.traverseTree(
+ segmentGroup[ref.parentSegmentId],
+ ref.parentSpanId,
+ ref.parentSegmentId,
+ segmentGroup[id]);
}
});
- segmentIdGroup.forEach(id => {
- let currentSegment = segmentGroup[id].sort((a,b) => b.parentSpanId-a.parentSpanId);
- currentSegment.forEach(s =>{
- let index = currentSegment.findIndex(i => i.spanId === s.parentSpanId);
- if (index !== -1) {
- if ((currentSegment[index].isBroken && currentSegment[index].parentSpanId === -1) || !currentSegment[index].isBroken) {
- currentSegment[index].children.push(s);
- currentSegment[index].children.sort((a, b) => a.spanId - b.spanId);
- }
- }
- if (s.isBroken) {
- const children = _.filter(this.data, (span) => {
- return _.find(span.refs, {traceId: s.traceId, parentSegmentId: s.segmentId, parentSpanId: s.spanId});
- });
- children.length > 0 && s.children.push(...children);
- }
- })
- segmentGroup[id] = currentSegment[currentSegment.length-1]
- })
- segmentIdGroup.forEach(id => {
- segmentGroup[id].refs.forEach(ref => {
- if(ref.traceId === this.traceId) {
- this.traverseTree(segmentGroup[ref.parentSegmentId],ref.parentSpanId,ref.parentSegmentId,segmentGroup[id])
- };
- })
- // if(segmentGroup[id].refs.length !==0 ) delete segmentGroup[id];
- })
- for (let i in segmentGroup) {
- if(segmentGroup[i].refs.length ===0 )
- this.segmentId.push(segmentGroup[i]);
+ });
+ for (const i in segmentGroup) {
+ if (segmentGroup[i].refs.length === 0 ) {
+ this.segmentId.push(segmentGroup[i]);
+ }
}
- this.segmentId.forEach((_, i) => {
- this.collapse(this.segmentId[i]);
- })
+ this.segmentId.forEach((i) => {
+ this.collapse(i);
+ });
},
collapse(d) {
- if(d.children){
+ if (d.children) {
let dur = d.endTime - d.startTime;
- d.children.forEach(i => {
+ d.children.forEach((i) => {
dur -= (i.endTime - i.startTime);
- })
+ });
d.dur = dur < 0 ? 0 : dur;
d.children.forEach((i) => this.collapse(i));
}
@@ -268,7 +300,7 @@
showCurrentSpanDetail(title, text) {
const textLineNumber = text.split('\n').length;
let textHeight = textLineNumber * 20.2 + 10;
- const tmpHeight = window.innerHeight * 0.9
+ const tmpHeight = window.innerHeight * 0.9;
textHeight = textHeight >= tmpHeight ? tmpHeight : textHeight;
this.$modal.show('dialog', {
title,
@@ -284,31 +316,29 @@
title: 'Close',
},
],
- })
+ });
},
downloadTrace() {
- let serializer = new XMLSerializer();
- let svgNode = d3.select('.trace-list-dowanload').node();
- let width = d3.select('.trace-list-dowanload')._groups[0][0].clientWidth;
- let height = d3.select('.trace-list-dowanload')._groups[0][0].clientHeight;
- let source = serializer.serializeToString(svgNode);
- source = '<?xml version="1.0" standalone="no"?>\r\n' + source;
- let url = "data:image/svg+xml;charset=utf-8," + encodeURIComponent(source);
- let canvas = document.createElement("canvas");
- canvas.width = width;
- canvas.height = height;
- let context = canvas.getContext("2d");
- let image = new Image;
- image.src = url;
- image.onload = function() {
- context.drawImage(image, 0, 0);
- var a = document.createElement("a");
- a.download = "trace-list.png";
- a.href = canvas.toDataURL("image/png");
- a.click();
- }
- }
- }
+ const serializer = new XMLSerializer();
+ const svgNode = d3.select('.trace-list-dowanload').node();
+ const source = `<?xml version="1.0" standalone="no"?>\r\n${serializer.serializeToString(svgNode)}`;
+ const canvas = document.createElement('canvas');
+ const context = canvas.getContext('2d');
+ canvas.width = d3.select('.trace-list-dowanload')._groups[0][0].clientWidth;
+ canvas.height = d3.select('.trace-list-dowanload')._groups[0][0].clientHeight;
+ context.fillStyle = '#fff';
+ context.fillRect(0, 0, canvas.width, canvas.height);
+ const image = new Image();
+ image.src = `data:image/svg+xml;charset=utf-8,${encodeURIComponent(source)}`;
+ image.onload = () => {
+ context.drawImage(image, 0, 0);
+ const tagA = document.createElement('a');
+ tagA.download = 'trace-list.png';
+ tagA.href = canvas.toDataURL('image/png');
+ tagA.click();
+ };
+ },
+ },
};
</script>
<style lang="scss">
diff --git a/src/views/components/trace/trace-search.vue b/src/views/components/trace/trace-search.vue
index 02fc4ff..3fe1149 100644
--- a/src/views/components/trace/trace-search.vue
+++ b/src/views/components/trace/trace-search.vue
@@ -30,7 +30,7 @@
</svg>
<span class="vm">{{this.$t('search')}}</span>
</a>
- <a class="rk-trace-clear-btn bg-warning r mr-10" @click="clearSearch">
+ <a class="rk-trace-clear-btn r mr-10" @click="clearSearch">
<svg class="icon mr-5 vm">
<use xlink:href="#clear"></use>
</svg>