Improve topology discovery UX with review modals and live search.

Report unmatched/stub neighbors and matched links, move result lists into detail dialogs, deep-link edges to port traffic, and add fuzzy type-ahead canvas/palette NE search.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
oliver 2026-08-01 13:35:52 +08:00
parent 2382cb8269
commit 8cf1696d8c
12 changed files with 1442 additions and 66 deletions

View file

@ -95,6 +95,8 @@ const en = {
concurrency: "Concurrency",
startNow: "Start after create",
neKeywordPh: "Name / IP / vendor",
deepLinkHint: "Opened from topology: NE {{ne}}{{ifname}}. Confirm selection, then continue.",
deepLinkIfname: ", interface {{ifname}}",
selectedNe: "{{count}} NE(s) selected",
selectedPorts: "{{count}} interface(s) selected",
pickNeFirst: "Select NEs in the previous step first",
@ -889,7 +891,7 @@ const en = {
emptyMaps: "No maps yet. Create one to start.",
palette: "NE library",
paletteHint: "Click or drag onto the canvas",
filterPh: "Filter name / IP",
filterPh: "Type to filter: name / IP / vendor",
save: "Save",
saveDirty: "Save *",
unsavedConfirm: "You have unsaved changes. Discard and switch maps?",
@ -985,8 +987,45 @@ const en = {
discoverSummary: "Scanned {{scanned}} · added {{added}} · updated {{updated}} · missing {{stale}} · failed {{failed}}",
discoverNeOk: "neighbors {{neighbors}} · added {{added}} · updated {{updated}}",
discoverNeFail: "Collect failed",
discoverUnmatched: "unmatched {{count}}",
discoverUnmatchedMore: "{{count}} more not listed",
discoverParserStub: "Parser \"{{parser}}\" is still a stub; output was collected but neighbors were not parsed",
discoverNoTargets:
"No scannable NEs on the map. Add managed NEs, or UME NEs with a CLI connect profile.",
discoverFilter: "Result filter",
discoverFilterIssues: "Issues",
discoverFilterFail: "Failed",
discoverFilterWarn: "Warnings",
discoverFilterOk: "OK",
discoverFilterAll: "All",
discoverFilterDetail: "Details",
discoverListTitle: "Discovery details",
discoverListEmpty: "No NEs under the current filter.",
discoverShowLimited: "Showing first {{shown}} / {{total}} (narrow with filters)",
discoverViewDetail: "Detail",
discoverLinkCount: "{{count}} link(s)",
discoverLinksTitle: "Matched links ({{count}})",
discoverLinksEmpty: "No on-map peer links matched in this scan.",
discoverUnmatchedTitle: "Unmatched neighbors ({{count}})",
discoverUnmatchedEmpty: "No unmatched neighbors.",
discoverColPeer: "Peer NE",
discoverColRemote: "Neighbor",
discoverColLocalPort: "Local port",
discoverColRemotePort: "Remote port",
discoverColProtocol: "Protocol",
discoverColAction: "Result",
discoverLinkAdded: "Added",
discoverLinkUpdated: "Updated",
discoverLinkKeptManual: "Kept manual",
discoverLocatePeer: "Locate peer",
discoverLocateNe: "Locate NE",
discoverRawPreview: "Raw output preview (truncated when long; parsing uses full output)",
findNode: "Find",
findNodePh: "Type to search: name / IP / vendor",
findNoMatch: "No matching node on the canvas",
findMore: "{{count}} more matches…",
locateOnCanvas: "Click to locate on canvas",
openPortTraffic: "Open port traffic",
removeStale: "Clear missing ({{count}})",
removeStaleHint: "Delete red-marked missing edges",
staleRemoved: "Removed {{count}} missing edge(s)",

View file

@ -95,6 +95,8 @@ const zh = {
concurrency: "并发",
startNow: "创建后立即启动",
neKeywordPh: "名称 / IP / 厂商",
deepLinkHint: "已从拓扑跳转:网元 {{ne}}{{ifname}}。请确认选中后继续创建监控任务。",
deepLinkIfname: ",接口 {{ifname}}",
selectedNe: "已选 {{count}} 台网元",
selectedPorts: "已选 {{count}} 个接口",
pickNeFirst: "请先在上一步选择网元",
@ -886,7 +888,7 @@ const zh = {
emptyMaps: "还没有拓扑图,先新建一张。",
palette: "网元库",
paletteHint: "点击或拖到画布添加",
filterPh: "筛选名称 / IP",
filterPh: "输入即筛:名称 / IP / 厂商",
save: "保存",
saveDirty: "保存 *",
unsavedConfirm: "有未保存的更改,确定丢弃并切换吗?",
@ -982,7 +984,44 @@ const zh = {
discoverSummary: "扫描 {{scanned}} 台 · 新增 {{added}} · 更新 {{updated}} · 未发现 {{stale}} · 失败 {{failed}}",
discoverNeOk: "邻居 {{neighbors}} · 新增 {{added}} · 更新 {{updated}}",
discoverNeFail: "采集失败",
discoverUnmatched: "未匹配 {{count}}",
discoverUnmatchedMore: "另有 {{count}} 条未列出",
discoverParserStub: "厂商解析器「{{parser}}」仍为 stub,已采集到输出但未能解析邻居",
discoverNoTargets: "画布上没有可扫描网元。请添加托管网元,或添加已配置 CLI 凭据的 UME 网元。",
discoverFilter: "结果筛选",
discoverFilterIssues: "问题",
discoverFilterFail: "失败",
discoverFilterWarn: "警告",
discoverFilterOk: "成功",
discoverFilterAll: "全部",
discoverFilterDetail: "详情",
discoverListTitle: "发现详情",
discoverListEmpty: "当前筛选下没有网元。",
discoverShowLimited: "仅显示前 {{shown}} / {{total}} 条(请用筛选缩小范围)",
discoverViewDetail: "详情",
discoverLinkCount: "链路 {{count}}",
discoverLinksTitle: "匹配链路({{count}})",
discoverLinksEmpty: "本次未匹配到画布上的对端网元链路。",
discoverUnmatchedTitle: "未匹配邻居({{count}})",
discoverUnmatchedEmpty: "无未匹配邻居。",
discoverColPeer: "对端网元",
discoverColRemote: "邻居",
discoverColLocalPort: "本端端口",
discoverColRemotePort: "对端端口",
discoverColProtocol: "协议",
discoverColAction: "结果",
discoverLinkAdded: "新增",
discoverLinkUpdated: "更新",
discoverLinkKeptManual: "保留人工",
discoverLocatePeer: "定位对端",
discoverLocateNe: "定位本端",
discoverRawPreview: "采集原文预览(过长会截断,不影响解析)",
findNode: "定位",
findNodePh: "输入即搜:名称 / IP / 厂商",
findNoMatch: "画布上没有匹配的节点",
findMore: "另有 {{count}} 条匹配…",
locateOnCanvas: "点击定位到画布",
openPortTraffic: "打开端口流量",
removeStale: "清除未发现 ({{count}})",
removeStaleHint: "删除红色标记的未发现链路",
staleRemoved: "已删除 {{count}} 条未发现链路",