diff --git a/src/views/dashboard/related/trace/components/D3Graph/Index.vue b/src/views/dashboard/related/trace/components/D3Graph/Index.vue
index 66770f09..11d9d6b0 100644
--- a/src/views/dashboard/related/trace/components/D3Graph/Index.vue
+++ b/src/views/dashboard/related/trace/components/D3Graph/Index.vue
@@ -17,7 +17,9 @@ limitations under the License. -->
Span Details
-
{{ `Parent Span: ${span.parentSegmentId}` }}
+
{{
+ `Parent Span: ${span.parentSegmentId}`
+ }}
@@ -97,16 +99,26 @@ limitations under the License. -->
}
}
function handleSelectSpan(i: Recordable) {
+ parentSpans.value = [];
currentSpan.value = i.data;
- parentSpans.value = currentSpan.value?.refs?.filter((d) => d) || [];
- if (currentSpan.value?.parentSpanId !== -1) {
+ parentSpans.value = [];
+ if (!currentSpan.value) {
+ return;
+ }
+ for (const ref of currentSpan.value.refs || []) {
+ parentSpans.value.push(ref);
+ }
+ if ((currentSpan.value.parentSpanId ?? -1) > -1) {
parentSpans.value.push({
- parentSegmentId: currentSpan.value?.segmentId || "",
- parentSpanId: currentSpan.value?.parentSpanId || NaN,
- traceId: currentSpan.value?.traceId || "",
+ parentSegmentId: currentSpan.value.segmentId,
+ parentSpanId: currentSpan.value.parentSpanId,
+ traceId: currentSpan.value.traceId,
});
}
}
+ function viewParentSpan() {
+ tree.value.highlightParents();
+ }
function traverseTree(node: Recordable, spanId: string, segmentId: string, data: Recordable) {
if (!node || node.isBroken) {
return;
@@ -409,6 +421,11 @@ limitations under the License. -->
fill: #409eff;
}
+ .trace-node.highlightedParent .node-text {
+ font-weight: bold;
+ fill: #4caf50;
+ }
+
#action-box {
position: absolute;
color: $font-color;
diff --git a/src/views/dashboard/related/trace/utils/d3-trace-list.ts b/src/views/dashboard/related/trace/utils/d3-trace-list.ts
index 1e13f735..f266c866 100644
--- a/src/views/dashboard/related/trace/utils/d3-trace-list.ts
+++ b/src/views/dashboard/related/trace/utils/d3-trace-list.ts
@@ -87,6 +87,7 @@ export default class ListGraph {
}
init(data: Recordable, row: Recordable[], fixSpansSize: number) {
d3.select(`.${this.el?.className} .trace-xaxis`).remove();
+ d3.select("#action-box").style("display", "none");
this.row = row;
this.data = data;
this.min = d3.min(this.row.map((i) => i.startTime));
@@ -117,10 +118,10 @@ export default class ListGraph {
}
draw(callback: Function) {
this.update(this.root, callback);
- d3.select("body").on("click", function (event) {
- if (event.target.closest("#action-box")) return;
- d3.select("#action-box").style("display", "none");
- });
+ // d3.select("body").on("click", function (event) {
+ // if (event.target.closest("#action-box")) return;
+ // d3.select("#action-box").style("display", "none");
+ // });
}
click(d: Recordable, scope: Recordable) {
if (!d.data.type) return;
@@ -147,6 +148,7 @@ export default class ListGraph {
.enter()
.append("g")
.attr("transform", `translate(${source.y0},${source.x0})`)
+ .attr("id", (d: Recordable) => `list-node-${d.id}`)
.attr("class", "trace-node")
.attr("style", "cursor: pointer")
.on("mouseover", function (event: MouseEvent, d: Trace) {
@@ -175,6 +177,10 @@ export default class ListGraph {
if (t.handleSelectSpan) {
t.handleSelectSpan(d);
}
+ t.root.descendants().map((node: { id: number }) => {
+ d3.select(`#list-node-${node.id}`).classed("highlightedParent", false);
+ return node;
+ });
});
nodeEnter
.append("rect")
@@ -401,6 +407,39 @@ export default class ListGraph {
callback();
}
}
+ highlightParents() {
+ if (!this.selectedNode) {
+ return;
+ }
+ const nodes = this.root.descendants().map((node: { id: number }) => {
+ d3.select(`#list-node-${node.id}`).classed("highlightedParent", false);
+ return node;
+ });
+ const selectedNode = this.selectedNode.datum();
+ const parentSpans = selectedNode.data.refs.map((d: Recordable) => d);
+ if (selectedNode.data?.parentSpanId !== -1) {
+ parentSpans.push({
+ parentSegmentId: selectedNode.data.segmentId,
+ parentSpanId: selectedNode.data.parentSpanId,
+ traceId: selectedNode.data.traceId,
+ });
+ }
+ const parents = parentSpans.map((d: Recordable) => {
+ return nodes.find(
+ (node: Recordable) =>
+ d.parentSpanId === node.data.spanId &&
+ d.parentSegmentId === node.data.segmentId &&
+ d.traceId === node.data.traceId,
+ );
+ });
+ for (const node of parents) {
+ if (node) {
+ d3.select(`#list-node-${node.id}`).classed("highlightedParent", true);
+ }
+ }
+ d3.select("#action-box").style("display", "none");
+ this.selectedNode.classed("highlighted", false);
+ }
visDate(date: number, pattern = "YYYY-MM-DD HH:mm:ss:SSS") {
return dayjs(date).format(pattern);
}