From 306508856b56a946f3de26f749c5b69509d3d5c5 Mon Sep 17 00:00:00 2001 From: Fine0830 Date: Sat, 13 Jan 2024 11:05:32 +0800 Subject: [PATCH] feat: implement the Service and Instance hierarchy topology. (#360) --- src/assets/icons/hierarchy_topology.svg | 18 + src/assets/img/tools/BROWSER.png | Bin 0 -> 314 bytes src/assets/img/tools/DATABASE.png | Bin 0 -> 150 bytes src/assets/img/tools/ELASTICSEARCH.png | Bin 0 -> 150 bytes src/assets/img/tools/GENERAL.png | Bin 0 -> 211 bytes src/assets/img/tools/K8S.png | Bin 0 -> 471 bytes src/assets/img/tools/K8S_SERVICE.png | Bin 0 -> 471 bytes src/assets/img/tools/MESH.png | Bin 0 -> 262 bytes src/assets/img/tools/MESH_CP.png | Bin 0 -> 262 bytes src/assets/img/tools/MESH_DP.png | Bin 0 -> 262 bytes src/assets/img/tools/MONGODB.png | Bin 0 -> 150 bytes src/assets/img/tools/MQ.png | Bin 0 -> 16222 bytes src/assets/img/tools/NGINX.png | Bin 0 -> 263 bytes src/assets/img/tools/OS_LINUX.png | Bin 0 -> 241 bytes src/assets/img/tools/POSTGRESQL.png | Bin 0 -> 150 bytes src/assets/img/tools/RABBITMQ.png | Bin 0 -> 16222 bytes src/assets/img/tools/VIRTUAL_CACHE.png | Bin 0 -> 211 bytes src/assets/img/tools/VIRTUAL_DATABASE.png | Bin 0 -> 211 bytes src/assets/img/tools/VIRTUAL_GATEWAY.png | Bin 0 -> 211 bytes src/components/SelectSingle.vue | 10 +- src/components/Tags.vue | 2 +- src/graphql/fragments/topology.ts | 53 ++ src/graphql/query/topology.ts | 13 +- src/hooks/useDashboardsSession.ts | 20 +- src/hooks/useExpressionsProcessor.ts | 12 +- src/locales/lang/en.ts | 1 + src/locales/lang/es.ts | 1 + src/locales/lang/zh.ts | 1 + src/store/modules/topology.ts | 210 ++++- src/styles/theme.scss | 14 +- src/types/dashboard.d.ts | 1 + src/types/topology.d.ts | 33 + src/views/dashboard/List.vue | 54 +- src/views/dashboard/data.ts | 4 + src/views/dashboard/panel/Tool.vue | 42 +- .../dashboard/related/topology/Index.vue | 10 +- .../related/topology/components/Graph.vue | 830 +++--------------- .../topology/components/utils/layout.ts | 162 ++++ .../{components => config}/Metrics.vue | 39 +- .../{components => config}/Settings.vue | 21 +- .../related/topology/pod/InstanceMap.vue | 188 ++++ .../PodTopology.vue => pod/PodMap.vue} | 4 +- .../topology/{components => pod}/Sankey.vue | 2 +- .../related/topology/service/HierarchyMap.vue | 196 +++++ .../related/topology/service/ServiceMap.vue | 731 +++++++++++++++ 45 files changed, 1901 insertions(+), 771 deletions(-) create mode 100644 src/assets/icons/hierarchy_topology.svg create mode 100644 src/assets/img/tools/BROWSER.png create mode 100644 src/assets/img/tools/DATABASE.png create mode 100644 src/assets/img/tools/ELASTICSEARCH.png create mode 100644 src/assets/img/tools/GENERAL.png create mode 100644 src/assets/img/tools/K8S.png create mode 100644 src/assets/img/tools/K8S_SERVICE.png create mode 100644 src/assets/img/tools/MESH.png create mode 100644 src/assets/img/tools/MESH_CP.png create mode 100644 src/assets/img/tools/MESH_DP.png create mode 100644 src/assets/img/tools/MONGODB.png create mode 100644 src/assets/img/tools/MQ.png create mode 100644 src/assets/img/tools/NGINX.png create mode 100644 src/assets/img/tools/OS_LINUX.png create mode 100644 src/assets/img/tools/POSTGRESQL.png create mode 100644 src/assets/img/tools/RABBITMQ.png create mode 100644 src/assets/img/tools/VIRTUAL_CACHE.png create mode 100644 src/assets/img/tools/VIRTUAL_DATABASE.png create mode 100644 src/assets/img/tools/VIRTUAL_GATEWAY.png rename src/views/dashboard/related/topology/{components => config}/Metrics.vue (80%) rename src/views/dashboard/related/topology/{components => config}/Settings.vue (97%) create mode 100644 src/views/dashboard/related/topology/pod/InstanceMap.vue rename src/views/dashboard/related/topology/{components/PodTopology.vue => pod/PodMap.vue} (99%) rename src/views/dashboard/related/topology/{components => pod}/Sankey.vue (99%) create mode 100644 src/views/dashboard/related/topology/service/HierarchyMap.vue create mode 100644 src/views/dashboard/related/topology/service/ServiceMap.vue diff --git a/src/assets/icons/hierarchy_topology.svg b/src/assets/icons/hierarchy_topology.svg new file mode 100644 index 00000000..07e0c524 --- /dev/null +++ b/src/assets/icons/hierarchy_topology.svg @@ -0,0 +1,18 @@ + + + + + \ No newline at end of file diff --git a/src/assets/img/tools/BROWSER.png b/src/assets/img/tools/BROWSER.png new file mode 100644 index 0000000000000000000000000000000000000000..c7147ecdb8176cfdf43af785db77986ed8b26ee1 GIT binary patch literal 314 zcmV-A0mc4_P)Px#^hrcPR5(wilWPuyAPj`5w-67bo=iQN>|wxL*v$}zppbpU{j=D#ADwm(^YACF z`r|kz#8q`s)fdjgFs!ZI3gEq8MPz9utLkv439fcyYsp^gb5gCm!Q#u3ethF;Q z$N=6fBJ+8k6S}b03giHWc#;*t>?8w12%4xa{bLU08R7g5VBhyH0t(%&Vx+{Oegllu zhHlC>DFc!~;jEBf1yX{t#j?W^fc0Vy5x^ThXr_!TksbaDs0PYznrq~`D1$TUy3Wxb z)f$W8TucM4@C0D6Hu9QAqO%@Zx%59k$<`yRjWdjMe7)_L*GUr kJ-#j@5oWf{nJ$bB9I~ocj~AvX05vdpy85}Sb4q9e0KT;?0{{R3 literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/ELASTICSEARCH.png b/src/assets/img/tools/ELASTICSEARCH.png new file mode 100644 index 0000000000000000000000000000000000000000..043644b790561cd4ca7802dff288ed119203abe7 GIT binary patch literal 150 zcmeAS@N?(olHy`uVBq!ia0vp^5+KaN3?zjj6;1;w{s5m4S0Mc#44#1j`?H_FfI=)K zL4Lsu%q)KrH!c1E7)_L*GUr kJ-#j@5oWf{nJ$bB9I~ocj~AvX05vdpy85}Sb4q9e0KT;?0{{R3 literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/GENERAL.png b/src/assets/img/tools/GENERAL.png new file mode 100644 index 0000000000000000000000000000000000000000..4f22e976018dec04315b1613995b109dcb46b840 GIT binary patch literal 211 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jP7LeL$-D$|dOcknLoEE4 zPQJ+7pupquR%!#!?3I&O9u7EW5iI1xICaUF_6g7K#bz!@-INiuU%=Q|;hd%L8&QGe zJ1npEo_`)++At-Ep`e4~fL&7wLz-Bj#=2A!Pgj?0?zIfJVvpJ}#wg`2ELzX7_V@KS zR<7J9q$RJKIM{E{JgA-^@^|fjl?@%Mb!RY!C0?9qH^FQ#qx!3|;;Y@<(m;nXc)I$z JtaD0e0szhDOyB?j literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/K8S.png b/src/assets/img/tools/K8S.png new file mode 100644 index 0000000000000000000000000000000000000000..f051f5a624a9518e6121a2ba681f6fdb10c47c46 GIT binary patch literal 471 zcmeAS@N?(olHy`uVBq!ia0vp^5+KaM3?#3wJbMaA%@6PiaRt)19QWfvBemDf#}IBEHcHETC+-oEqp zgNKhEKY9A%^@lIt{$7yzITxs(G0EHAh4DX=?mZx9nWu|mh{pN3ldcOj8Hl);vxrn5 zzIRkg`qjVx+kX~>GVwg-sl2s2U2Qv)Yy8Tsrcv?VneAU*&sW*1CfPgZMi}=e?i0P= znT>BXXn*~<+J}kl(eC9YJEk)-@GfJ#&CsxvW&OsWx$Q3m7z!pNa4|H#FlJDgv|v)E zmH3T#Uzgb>pWa>en-{&V`b?&Q^`v|I6`juJZuqulQufD1ZGJ^t&tAx=z4`U;q3a*n YN_H5Y4iekf1avWjr>mdKI;Vst03z)W#Q*>R literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/K8S_SERVICE.png b/src/assets/img/tools/K8S_SERVICE.png new file mode 100644 index 0000000000000000000000000000000000000000..f051f5a624a9518e6121a2ba681f6fdb10c47c46 GIT binary patch literal 471 zcmeAS@N?(olHy`uVBq!ia0vp^5+KaM3?#3wJbMaA%@6PiaRt)19QWfvBemDf#}IBEHcHETC+-oEqp zgNKhEKY9A%^@lIt{$7yzITxs(G0EHAh4DX=?mZx9nWu|mh{pN3ldcOj8Hl);vxrn5 zzIRkg`qjVx+kX~>GVwg-sl2s2U2Qv)Yy8Tsrcv?VneAU*&sW*1CfPgZMi}=e?i0P= znT>BXXn*~<+J}kl(eC9YJEk)-@GfJ#&CsxvW&OsWx$Q3m7z!pNa4|H#FlJDgv|v)E zmH3T#Uzgb>pWa>en-{&V`b?&Q^`v|I6`juJZuqulQufD1ZGJ^t&tAx=z4`U;q3a*n YN_H5Y4iekf1avWjr>mdKI;Vst03z)W#Q*>R literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/MESH.png b/src/assets/img/tools/MESH.png new file mode 100644 index 0000000000000000000000000000000000000000..fea10bc3a00369bee8d0b36149db02bddf339382 GIT binary patch literal 262 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbL!M}SX=E0Df@`}Y0&_g}tz`TF(i z=g*%%1B0hv0AUj(|NsC0j`>d*&@8c%AirP+b`Eh#v&yROm8%XOI(+2l%{#B&eEv0Q zQ@AWp1!I!8yNfvYwHf_Dj+dv4V~E7%i4swed*&@8c%AirP+b`Eh#v&yROm8%XOI(+2l%{#B&eEv0Q zQ@AWp1!I!8yNfvYwHf_Dj+dv4V~E7%i4swed*&@8c%AirP+b`Eh#v&yROm8%XOI(+2l%{#B&eEv0Q zQ@AWp1!I!8yNfvYwHf_Dj+dv4V~E7%i4swe7)_L*GUr kJ-#j@5oWf{nJ$bB9I~ocj~AvX05vdpy85}Sb4q9e0KT;?0{{R3 literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/MQ.png b/src/assets/img/tools/MQ.png new file mode 100644 index 0000000000000000000000000000000000000000..f2bb56fbebb9d1ebafaddaa937840063d0c4f7e8 GIT binary patch literal 16222 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 LtDnm{r-UW|N)=^J literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/OS_LINUX.png b/src/assets/img/tools/OS_LINUX.png new file mode 100644 index 0000000000000000000000000000000000000000..2cc27c9907077898d47a0f1c763aaadce3bbb8ff GIT binary patch literal 241 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!61|;P_|4#%`jKx9jP7LeL$-D$|R(rZQhFJJ7 zo%B$!S%JrmH(H=g({Gtym=(_k*34q{xUK^yALj3$KE3~d(a(b^b(u^_J<~eOlzvGh zf4jCo>p=B><^$8588&3CjpYquopbrVrGtz6=|wx6HWYO1;9F}D^yX~C*I=)0;d5j@ zuyZJWxHql-#oJicDM$Z0+`YSAeA1R_j{7*bX`juLE%@!FseXU&9&VRCMg4w}vo?M- pXmDPBl$(Js^ZSVf<>Hqc^aD#{1b6Pg=L~c7)_L*GUr kJ-#j@5oWf{nJ$bB9I~ocj~AvX05vdpy85}Sb4q9e0KT;?0{{R3 literal 0 HcmV?d00001 diff --git a/src/assets/img/tools/RABBITMQ.png b/src/assets/img/tools/RABBITMQ.png new file mode 100644 index 0000000000000000000000000000000000000000..f2bb56fbebb9d1ebafaddaa937840063d0c4f7e8 GIT binary patch literal 16222 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 .bar-select { position: relative; justify-content: space-between; - border: 1px solid #ddd; + border: 1px solid var(--el-border-color); background: $theme-background; border-radius: 3px; color: $font-color; @@ -97,8 +97,8 @@ limitations under the License. --> border-radius: 3px; margin: 3px; color: $active-color; - background-color: #fafafa; - border: 1px solid #e8e8e8; + background-color: var(--theme-background); + border: 1px solid var(--el-color-primary); text-align: center; } } @@ -139,7 +139,7 @@ limitations under the License. --> left: 0; background-color: $theme-background; box-shadow: 0 1px 6px rgb(99 99 99 / 20%); - border: 1px solid #ddd; + border: 1px solid var(--el-border-color); width: 100%; border-radius: 0 0 3px 3px; border-right-width: 1px !important; @@ -169,7 +169,7 @@ limitations under the License. --> } &:hover { - background-color: #f5f5f5; + background-color: var(--layout-background); } } diff --git a/src/components/Tags.vue b/src/components/Tags.vue index b854843a..b5af8150 100644 --- a/src/components/Tags.vue +++ b/src/components/Tags.vue @@ -79,7 +79,7 @@ limitations under the License. --> diff --git a/src/views/dashboard/related/topology/Index.vue b/src/views/dashboard/related/topology/Index.vue index 9fff881f..3101ae6c 100644 --- a/src/views/dashboard/related/topology/Index.vue +++ b/src/views/dashboard/related/topology/Index.vue @@ -13,14 +13,14 @@ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. --> - diff --git a/src/views/dashboard/related/topology/components/utils/layout.ts b/src/views/dashboard/related/topology/components/utils/layout.ts index 52b35e5b..689a7ee9 100644 --- a/src/views/dashboard/related/topology/components/utils/layout.ts +++ b/src/views/dashboard/related/topology/components/utils/layout.ts @@ -120,3 +120,165 @@ export function circleIntersection(ax: number, ay: number, ar: number, bx: numbe { x: gx, y: gy }, ]; } +function findMostFrequent(arr: Call[]) { + const count: any = {}; + let maxCount = 0; + let maxItem = null; + + for (let i = 0; i < arr.length; i++) { + const item = arr[i]; + count[item.sourceObj.id] = (count[item.sourceObj.id] || 0) + 1; + if (count[item.sourceObj.id] > maxCount) { + maxCount = count[item.sourceObj.id]; + maxItem = item.sourceObj; + } + count[item.targetObj.id] = (count[item.targetObj.id] || 0) + 1; + if (count[item.targetObj.id] > maxCount) { + maxCount = count[item.targetObj.id]; + maxItem = item.targetObj; + } + } + + return maxItem; +} +export function computeLevels(calls: Call[], nodeList: Node[], levels: any[]) { + const node = findMostFrequent(calls); + const nodes = JSON.parse(JSON.stringify(nodeList)).sort((a: Node, b: Node) => { + if (a.name.toLowerCase() < b.name.toLowerCase()) { + return -1; + } + if (a.name.toLowerCase() > b.name.toLowerCase()) { + return 1; + } + return 0; + }); + const index = nodes.findIndex((n: Node) => n.type === "USER"); + let key = index; + if (index < 0) { + key = nodes.findIndex((n: Node) => n.id === node.id); + } + levels.push([nodes[key]]); + nodes.splice(key, 1); + for (const level of levels) { + const a = []; + for (const l of level) { + for (const n of calls) { + if (n.target === l.id) { + const i = nodes.findIndex((d: Node) => d.id === n.source); + if (i > -1) { + a.push(nodes[i]); + nodes.splice(i, 1); + } + } + if (n.source === l.id) { + const i = nodes.findIndex((d: Node) => d.id === n.target); + if (i > -1) { + a.push(nodes[i]); + nodes.splice(i, 1); + } + } + } + } + if (a.length) { + levels.push(a); + } + } + if (nodes.length) { + const ids = nodes.map((d: Node) => d.id); + const links = calls.filter((item: Call) => ids.includes(item.source) || ids.includes(item.target)); + const list = computeLevels(links, nodes, []); + levels = list.map((subArrayA, index) => subArrayA.concat(levels[index])); + } + return levels; +} +export function changeNode(d: { x: number; y: number }, currentNode: Nullable, layout: any, radius: number) { + if (!currentNode) { + return; + } + for (const node of layout.nodes) { + if (node.id === currentNode.id) { + node.x = d.x; + node.y = d.y; + } + } + for (const call of layout.calls) { + if (call.sourceObj.id === currentNode.id) { + call.sourceObj.x = d.x; + call.sourceObj.y = d.y; + } + if (call.targetObj.id === currentNode.id) { + call.targetObj.x = d.x; + call.targetObj.y = d.y; + } + if (call.targetObj.id === currentNode.id || call.sourceObj.id === currentNode.id) { + const pos: any = circleIntersection( + call.sourceObj.x, + call.sourceObj.y, + radius, + call.targetObj.x, + call.targetObj.y, + radius, + ); + call.sourceX = pos[0].x; + call.sourceY = pos[0].y; + call.targetX = pos[1].x; + call.targetY = pos[1].y; + } + } + return computeCallPos(layout.calls, radius); +} +export function hierarchy(levels: Node[][], calls: Call[], radius: number) { + // precompute level depth + levels.forEach((l: Node[], i: number) => l.forEach((n: any) => n && (n.level = i))); + + const nodes: Node[] = levels.reduce((a, x) => a.concat(x), []); + // layout + const padding = 30; + const node_height = 100; + const node_width = 180; + const bundle_width = 10; + const metro_d = 4; + for (const n of nodes) { + n.width = 5 * metro_d; + } + + let y_offset = padding; + let x_offset = 0; + for (const level of levels) { + x_offset = 0; + y_offset += 3 * bundle_width; + for (const l of level) { + const n: any = l; + for (const call of calls) { + if (call.source === n.id) { + call.sourceObj = n; + } + if (call.target === n.id) { + call.targetObj = n; + } + } + n.x = node_width + x_offset + n.width / 2; + n.y = n.level * node_height + y_offset; + x_offset += node_width + n.width; + } + } + const layout = { + width: d3.max(nodes as any, (n: { x: number }) => n.x) || 0 + node_width + 2 * padding, + height: d3.max(nodes as any, (n: { y: number }) => n.y) || 0 + node_height / 2 + 2 * padding, + }; + + return { nodes, layout, calls: computeCallPos(calls, radius) }; +} +export function computeHierarchyLevels(nodes: Node[]) { + const levelsNum: number[] = nodes.map((d: Node) => d.l || 0); + const list = [...new Set(levelsNum)]; + const sortedArr = list.sort((a, b) => b - a); + const nodesList = []; + + for (const min of sortedArr) { + const arr = nodes.filter((d) => d.l === min); + nodesList.push(arr); + } + + return nodesList; +} diff --git a/src/views/dashboard/related/topology/components/Metrics.vue b/src/views/dashboard/related/topology/config/Metrics.vue similarity index 80% rename from src/views/dashboard/related/topology/components/Metrics.vue rename to src/views/dashboard/related/topology/config/Metrics.vue index 2660d865..12b7263d 100644 --- a/src/views/dashboard/related/topology/components/Metrics.vue +++ b/src/views/dashboard/related/topology/config/Metrics.vue @@ -15,9 +15,12 @@ limitations under the License. -->