@wallarm-org/design-system 0.51.0-rc-feature-AS-1026.1 → 0.51.1-rc-fix-table-virtualization-scroll-loop.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/AppShell/story-content/_storyConfigRenderer.d.ts +1 -1
- package/dist/components/AppShell/story-content/_storyConfigRenderer.js +15 -29
- package/dist/components/AppShell/story-content/_storyLib.js +1 -1
- package/dist/components/AppShell/story-content/_storyNavConfigs.d.ts +1 -1
- package/dist/components/AppShell/story-content/_storyNavConfigs.js +5 -0
- package/dist/components/NavPanel/NavPanelHeader.js +1 -1
- package/dist/components/Page/PageContent.js +1 -1
- package/dist/components/Page/PageHeader.js +1 -1
- package/dist/components/ParameterPath/ParameterPath.js +63 -65
- package/dist/components/ParameterPath/ParameterPathRow.d.ts +14 -0
- package/dist/components/ParameterPath/ParameterPathRow.js +67 -0
- package/dist/components/ParameterPath/classes.d.ts +3 -0
- package/dist/components/ParameterPath/classes.js +12 -1
- package/dist/components/ParameterPath/constants.d.ts +11 -0
- package/dist/components/ParameterPath/constants.js +15 -0
- package/dist/components/ParameterPath/types.d.ts +26 -0
- package/dist/components/ParameterPath/useParameterPathTruncation.js +8 -10
- package/dist/components/{ProductNav → RemoteShell}/HeaderActions.d.ts +1 -1
- package/dist/components/{ProductNav → RemoteShell}/NavItemsList.d.ts +1 -1
- package/dist/components/RemoteShell/NavPanelContent.d.ts +6 -0
- package/dist/components/RemoteShell/NavPanelContent.js +65 -0
- package/dist/components/RemoteShell/RemoteShell.d.ts +7 -0
- package/dist/components/RemoteShell/RemoteShell.js +109 -9
- package/dist/components/RemoteShell/RemoteShellBreadcrumb.js +39 -4
- package/dist/components/RemoteShell/RemoteShellContent.d.ts +1 -0
- package/dist/components/RemoteShell/RemoteShellContent.js +7 -3
- package/dist/components/RemoteShell/RemoteShellPanel.d.ts +4 -2
- package/dist/components/RemoteShell/RemoteShellPanel.js +76 -3
- package/dist/components/RemoteShell/index.d.ts +2 -0
- package/dist/components/RemoteShell/index.js +2 -1
- package/dist/components/{ProductNav/ProductNavContext.d.ts → RemoteShell/model/RemoteShellContext.d.ts} +3 -3
- package/dist/components/RemoteShell/model/RemoteShellContext.js +9 -0
- package/dist/components/RemoteShell/model/index.d.ts +5 -0
- package/dist/components/RemoteShell/model/index.js +5 -0
- package/dist/components/{ProductNav → RemoteShell/model}/matchNav.js +1 -1
- package/dist/components/{ProductNav → RemoteShell/model}/types.d.ts +2 -3
- package/dist/components/Table/TableBody/TableBodyVirtualizedContainer.js +3 -5
- package/dist/components/Table/TableBody/TableBodyVirtualizedWindow.js +3 -5
- package/dist/components/Table/TableBody/useResetVirtualizerOnDataChange.d.ts +3 -3
- package/dist/components/Table/TableBody/useResetVirtualizerOnDataChange.js +6 -8
- package/dist/components/Table/TableContext/TableProvider.js +1 -7
- package/dist/components/Table/TableContext/types.d.ts +0 -3
- package/dist/components/Table/TableInner/TableInnerContainer.js +4 -9
- package/dist/components/Table/TableInner/TableInnerWindow.js +4 -9
- package/dist/components/Table/hooks/index.d.ts +1 -1
- package/dist/components/Table/hooks/index.js +2 -2
- package/dist/components/Table/hooks/useEndReached.d.ts +19 -0
- package/dist/components/Table/hooks/{infiniteScroll/useScrollEdge.js → useEndReached.js} +11 -15
- package/dist/components/Table/lib/constants.d.ts +0 -3
- package/dist/components/Table/lib/constants.js +1 -3
- package/dist/components/Table/lib/index.d.ts +1 -3
- package/dist/components/Table/lib/index.js +2 -4
- package/dist/components/Table/mocks.d.ts +0 -13
- package/dist/components/Table/mocks.js +1 -59
- package/dist/components/Table/types.d.ts +1 -11
- package/dist/index.d.ts +1 -2
- package/dist/index.js +2 -3
- package/dist/metadata/components.json +67 -313
- package/dist/utils/hasTextSelection.d.ts +1 -0
- package/dist/utils/hasTextSelection.js +2 -0
- package/dist/utils/range.d.ts +1 -0
- package/dist/utils/range.js +4 -0
- package/package.json +1 -1
- package/dist/components/ProductNav/ProductNav.d.ts +0 -13
- package/dist/components/ProductNav/ProductNav.js +0 -109
- package/dist/components/ProductNav/ProductNavBreadcrumbs.d.ts +0 -2
- package/dist/components/ProductNav/ProductNavBreadcrumbs.js +0 -38
- package/dist/components/ProductNav/ProductNavContext.js +0 -9
- package/dist/components/ProductNav/ProductNavPanel.d.ts +0 -6
- package/dist/components/ProductNav/ProductNavPanel.js +0 -107
- package/dist/components/ProductNav/index.d.ts +0 -11
- package/dist/components/ProductNav/index.js +0 -10
- package/dist/components/ProductNav/useProductNav.d.ts +0 -16
- package/dist/components/ProductNav/useProductNav.js +0 -19
- package/dist/components/Table/hooks/infiniteScroll/index.d.ts +0 -1
- package/dist/components/Table/hooks/infiniteScroll/index.js +0 -2
- package/dist/components/Table/hooks/infiniteScroll/useInfiniteScroll.d.ts +0 -18
- package/dist/components/Table/hooks/infiniteScroll/useInfiniteScroll.js +0 -34
- package/dist/components/Table/hooks/infiniteScroll/useInitialAnchor.d.ts +0 -16
- package/dist/components/Table/hooks/infiniteScroll/useInitialAnchor.js +0 -28
- package/dist/components/Table/hooks/infiniteScroll/usePrependScrollAnchor.d.ts +0 -15
- package/dist/components/Table/hooks/infiniteScroll/usePrependScrollAnchor.js +0 -28
- package/dist/components/Table/hooks/infiniteScroll/useScrollEdge.d.ts +0 -20
- package/dist/components/Table/lib/detectDataChange.d.ts +0 -4
- package/dist/components/Table/lib/detectDataChange.js +0 -7
- package/dist/components/Table/lib/getRowKey.d.ts +0 -4
- package/dist/components/Table/lib/getRowKey.js +0 -2
- /package/dist/components/{ProductNav → RemoteShell}/HeaderActions.js +0 -0
- /package/dist/components/{ProductNav → RemoteShell}/NavItemsList.js +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/matchNav.d.ts +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/navUtils.d.ts +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/navUtils.js +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/types.js +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/useDrillTransition.d.ts +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/useDrillTransition.js +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/useLocationPathname.d.ts +0 -0
- /package/dist/components/{ProductNav → RemoteShell/model}/useLocationPathname.js +0 -0
|
@@ -1,13 +1,11 @@
|
|
|
1
|
-
import { jsx, jsxs } from "react/jsx-runtime";
|
|
1
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { useEffect, useState } from "react";
|
|
3
|
-
import { NavPanel, NavPanelHeader } from "../../NavPanel/index.js";
|
|
4
3
|
import { Page, PageContent, PageHeader, PageTitle } from "../../Page/index.js";
|
|
5
|
-
import {
|
|
6
|
-
import { RemoteShell, RemoteShellBreadcrumb, RemoteShellContent, RemoteShellPanel } from "../../RemoteShell/index.js";
|
|
4
|
+
import { RemoteShell, RemoteShellBreadcrumb, RemoteShellContent, RemoteShellPanel, useRemoteShellContext } from "../../RemoteShell/index.js";
|
|
7
5
|
import { HomeContent } from "./_storyHomeContent.js";
|
|
8
6
|
import { PRODUCT_CONFIGS } from "./_storyLib.js";
|
|
9
7
|
const RemotePageContent = ()=>{
|
|
10
|
-
const { breadcrumbSegments } =
|
|
8
|
+
const { breadcrumbSegments } = useRemoteShellContext();
|
|
11
9
|
const lastSegment = breadcrumbSegments[breadcrumbSegments.length - 1];
|
|
12
10
|
const pageTitle = lastSegment?.label ?? '';
|
|
13
11
|
const fullPath = breadcrumbSegments.map((s)=>s.label).join(' / ');
|
|
@@ -44,36 +42,24 @@ const ConfigRemote = ({ config, basePath })=>{
|
|
|
44
42
|
}, [
|
|
45
43
|
config.productLabel
|
|
46
44
|
]);
|
|
47
|
-
|
|
48
|
-
children: [
|
|
49
|
-
/*#__PURE__*/ jsx(RemoteShellPanel, {
|
|
50
|
-
children: /*#__PURE__*/ jsxs(NavPanel, {
|
|
51
|
-
children: [
|
|
52
|
-
/*#__PURE__*/ jsx(NavPanelHeader, {
|
|
53
|
-
children: config.productLabel
|
|
54
|
-
}),
|
|
55
|
-
/*#__PURE__*/ jsx(NavPanelSkeleton, {
|
|
56
|
-
count: 6
|
|
57
|
-
})
|
|
58
|
-
]
|
|
59
|
-
})
|
|
60
|
-
}),
|
|
61
|
-
/*#__PURE__*/ jsx(RemoteShellContent, {})
|
|
62
|
-
]
|
|
63
|
-
});
|
|
64
|
-
return /*#__PURE__*/ jsx(ProductNav, {
|
|
45
|
+
return /*#__PURE__*/ jsx(RemoteShell, {
|
|
65
46
|
config: config,
|
|
66
47
|
basePath: basePath,
|
|
67
|
-
children: /*#__PURE__*/ jsxs(
|
|
48
|
+
children: loading ? /*#__PURE__*/ jsxs(Fragment, {
|
|
68
49
|
children: [
|
|
69
50
|
/*#__PURE__*/ jsx(RemoteShellPanel, {
|
|
70
|
-
|
|
71
|
-
resizable: true
|
|
72
|
-
})
|
|
51
|
+
isLoading: true
|
|
73
52
|
}),
|
|
74
|
-
/*#__PURE__*/ jsx(
|
|
75
|
-
|
|
53
|
+
/*#__PURE__*/ jsx(RemoteShellContent, {
|
|
54
|
+
isLoading: true
|
|
55
|
+
})
|
|
56
|
+
]
|
|
57
|
+
}) : /*#__PURE__*/ jsxs(Fragment, {
|
|
58
|
+
children: [
|
|
59
|
+
/*#__PURE__*/ jsx(RemoteShellPanel, {
|
|
60
|
+
resizable: true
|
|
76
61
|
}),
|
|
62
|
+
/*#__PURE__*/ jsx(RemoteShellBreadcrumb, {}),
|
|
77
63
|
/*#__PURE__*/ jsx(RemoteShellContent, {
|
|
78
64
|
children: /*#__PURE__*/ jsx(RemotePageContent, {})
|
|
79
65
|
})
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { findFirstLinkPath, pushPathname } from "../../
|
|
1
|
+
import { findFirstLinkPath, pushPathname } from "../../RemoteShell/index.js";
|
|
2
2
|
import { aiHypervisorNavConfig, edgeNavConfig, infraDiscoveryNavConfig, securityTestingNavConfig, settingsNavConfig } from "./_storyNavConfigs.js";
|
|
3
3
|
const KNOWN_PRODUCTS = [
|
|
4
4
|
'home',
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { CircleDashed, Filter, Plus } from "../../../icons/index.js";
|
|
2
2
|
const edgeNavConfig = {
|
|
3
3
|
productLabel: 'Edge',
|
|
4
|
+
productPath: '/edge',
|
|
4
5
|
headerActions: [
|
|
5
6
|
{
|
|
6
7
|
icon: Filter,
|
|
@@ -340,6 +341,7 @@ const edgeNavConfig = {
|
|
|
340
341
|
};
|
|
341
342
|
const aiHypervisorNavConfig = {
|
|
342
343
|
productLabel: 'AI Hypervisor',
|
|
344
|
+
productPath: '/ai-hypervisor',
|
|
343
345
|
items: [
|
|
344
346
|
{
|
|
345
347
|
type: 'link',
|
|
@@ -454,6 +456,7 @@ const aiHypervisorNavConfig = {
|
|
|
454
456
|
};
|
|
455
457
|
const infraDiscoveryNavConfig = {
|
|
456
458
|
productLabel: 'Infra Discovery',
|
|
459
|
+
productPath: '/infra-discovery',
|
|
457
460
|
headerActions: [
|
|
458
461
|
{
|
|
459
462
|
icon: Filter,
|
|
@@ -554,6 +557,7 @@ const infraDiscoveryNavConfig = {
|
|
|
554
557
|
};
|
|
555
558
|
const securityTestingNavConfig = {
|
|
556
559
|
productLabel: 'Security Testing',
|
|
560
|
+
productPath: '/security-testing',
|
|
557
561
|
items: [
|
|
558
562
|
{
|
|
559
563
|
type: 'link',
|
|
@@ -627,6 +631,7 @@ const securityTestingNavConfig = {
|
|
|
627
631
|
};
|
|
628
632
|
const settingsNavConfig = {
|
|
629
633
|
productLabel: 'Settings',
|
|
634
|
+
productPath: '/settings',
|
|
630
635
|
items: [
|
|
631
636
|
{
|
|
632
637
|
type: 'link',
|
|
@@ -9,7 +9,7 @@ const NavPanelHeader = ({ ref, className, children, ...props })=>{
|
|
|
9
9
|
ref: ref,
|
|
10
10
|
"data-slot": "nav-panel-header",
|
|
11
11
|
"data-testid": testId,
|
|
12
|
-
className: cn('sticky top-0 z-10 flex shrink-0 items-center p-4', className),
|
|
12
|
+
className: cn('sticky top-0 z-10 flex shrink-0 items-center p-4 bg-bg-surface-2', className),
|
|
13
13
|
children: /*#__PURE__*/ jsx(Text, {
|
|
14
14
|
size: "sm",
|
|
15
15
|
weight: "medium",
|
|
@@ -8,7 +8,7 @@ const PageContent = ({ ref, children, className, ...props })=>{
|
|
|
8
8
|
ref: ref,
|
|
9
9
|
"data-testid": testId,
|
|
10
10
|
"data-slot": "page-content",
|
|
11
|
-
className: cn('flex-1 min-h-0 overflow-auto px-
|
|
11
|
+
className: cn('flex-1 min-h-0 overflow-auto px-16', className),
|
|
12
12
|
children: children
|
|
13
13
|
});
|
|
14
14
|
};
|
|
@@ -8,7 +8,7 @@ const PageHeader = ({ ref, sticky, children, className, ...props })=>{
|
|
|
8
8
|
ref: ref,
|
|
9
9
|
"data-testid": testId,
|
|
10
10
|
"data-slot": "page-header",
|
|
11
|
-
className: cn('flex items-center px-
|
|
11
|
+
className: cn('flex items-center px-16 pb-16 gap-12', sticky && 'sticky top-0 z-10 bg-bg-surface-2', className),
|
|
12
12
|
children: children
|
|
13
13
|
});
|
|
14
14
|
};
|
|
@@ -1,17 +1,27 @@
|
|
|
1
1
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { useCallback, useRef } from "react";
|
|
3
|
+
import { useControlled } from "../../hooks/index.js";
|
|
3
4
|
import { cn } from "../../utils/cn.js";
|
|
5
|
+
import { hasTextSelection } from "../../utils/hasTextSelection.js";
|
|
4
6
|
import { TestIdProvider } from "../../utils/testId.js";
|
|
5
7
|
import { Tooltip, TooltipContent, TooltipTrigger } from "../Tooltip/index.js";
|
|
6
8
|
import { buildFullPathLabel } from "./buildFullPathLabel.js";
|
|
9
|
+
import { EXPAND_KEYS } from "./constants.js";
|
|
7
10
|
import { formatAsFilter } from "./formatAsFilter.js";
|
|
8
|
-
import {
|
|
9
|
-
import { ParameterPathEncoding } from "./ParameterPathEncoding.js";
|
|
10
|
-
import { ParameterPathJoint } from "./ParameterPathJoint.js";
|
|
11
|
-
import { ParameterPathMethod } from "./ParameterPathMethod.js";
|
|
12
|
-
import { ParameterPathSegment } from "./ParameterPathSegment.js";
|
|
11
|
+
import { ParameterPathRow } from "./ParameterPathRow.js";
|
|
13
12
|
import { useParameterPathTruncation } from "./useParameterPathTruncation.js";
|
|
14
|
-
const ParameterPath = ({ ref, method, segments, encoding, attack = false, copyFormat = formatAsFilter, className, 'data-testid': testId, ...rest })=>{
|
|
13
|
+
const ParameterPath = ({ ref, method, segments, encoding, attack = false, expandable = false, expanded, defaultExpanded = false, onExpandedChange, copyFormat = formatAsFilter, className, 'data-testid': testId, ...rest })=>{
|
|
14
|
+
const [expandedState, setExpandedUncontrolled] = useControlled({
|
|
15
|
+
controlled: expanded,
|
|
16
|
+
default: defaultExpanded
|
|
17
|
+
});
|
|
18
|
+
const setExpanded = useCallback((next)=>{
|
|
19
|
+
setExpandedUncontrolled(next);
|
|
20
|
+
onExpandedChange?.(next);
|
|
21
|
+
}, [
|
|
22
|
+
setExpandedUncontrolled,
|
|
23
|
+
onExpandedChange
|
|
24
|
+
]);
|
|
15
25
|
const handleCopy = useCallback((event)=>{
|
|
16
26
|
const text = copyFormat({
|
|
17
27
|
method,
|
|
@@ -36,63 +46,28 @@ const ParameterPath = ({ ref, method, segments, encoding, attack = false, copyFo
|
|
|
36
46
|
hasMethod: Boolean(method),
|
|
37
47
|
hasEncoding: Boolean(encoding)
|
|
38
48
|
});
|
|
39
|
-
const
|
|
40
|
-
const
|
|
41
|
-
const
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
}, `j-${segIndex}-pre`));
|
|
60
|
-
const isCollapsedBoundary = !forMeasurement && null !== indices && 0 === position && 2 === visibleIdx.length;
|
|
61
|
-
items.push(/*#__PURE__*/ jsx(ParameterPathSegment, {
|
|
62
|
-
index: segIndex,
|
|
63
|
-
variant: isLast ? 'highlighted' : 'default',
|
|
64
|
-
withZap: isLast && attack,
|
|
65
|
-
"data-measure": measure('segment'),
|
|
66
|
-
children: value
|
|
67
|
-
}, `s-${segIndex}`));
|
|
68
|
-
if (isCollapsedBoundary) items.push(/*#__PURE__*/ jsx(ParameterPathJoint, {}, "ellipsis-joint-pre"), /*#__PURE__*/ jsx(ParameterPathEllipsis, {}, "ellipsis"));
|
|
69
|
-
});
|
|
70
|
-
if (encoding) items.push(/*#__PURE__*/ jsx(ParameterPathJoint, {
|
|
71
|
-
"data-measure": measure('joint')
|
|
72
|
-
}, "enc-joint"), /*#__PURE__*/ jsx(ParameterPathEncoding, {
|
|
73
|
-
"data-measure": measure('encoding'),
|
|
74
|
-
children: encoding
|
|
75
|
-
}, "enc"));
|
|
76
|
-
return items;
|
|
77
|
-
};
|
|
78
|
-
const visibleRow = /*#__PURE__*/ jsx("div", {
|
|
79
|
-
ref: containerRef,
|
|
80
|
-
"data-row": "visible",
|
|
81
|
-
className: "flex items-center gap-0 min-w-0 overflow-hidden",
|
|
82
|
-
children: renderRow(false)
|
|
83
|
-
});
|
|
84
|
-
const measurementRow = /*#__PURE__*/ jsx("div", {
|
|
85
|
-
ref: measurementRef,
|
|
86
|
-
"data-row": "measure",
|
|
87
|
-
"aria-hidden": "true",
|
|
88
|
-
className: "flex items-center gap-0 absolute left-[-9999px] top-0 invisible pointer-events-none",
|
|
89
|
-
children: /*#__PURE__*/ jsx(TestIdProvider, {
|
|
90
|
-
value: void 0,
|
|
91
|
-
children: renderRow(true)
|
|
92
|
-
})
|
|
93
|
-
});
|
|
49
|
+
const collapsible = isTruncated && segments.length > 2;
|
|
50
|
+
const isExpanded = Boolean(expandedState) && collapsible;
|
|
51
|
+
const interactive = expandable && collapsible;
|
|
52
|
+
const indices = collapsible && !isExpanded ? visibleSegmentIndices : null;
|
|
53
|
+
const toggleExpanded = useCallback(()=>{
|
|
54
|
+
if (hasTextSelection()) return;
|
|
55
|
+
setExpanded(!isExpanded);
|
|
56
|
+
}, [
|
|
57
|
+
isExpanded,
|
|
58
|
+
setExpanded
|
|
59
|
+
]);
|
|
60
|
+
const handleKeyDown = useCallback((event)=>{
|
|
61
|
+
if (EXPAND_KEYS.includes(event.key)) {
|
|
62
|
+
event.preventDefault();
|
|
63
|
+
setExpanded(!isExpanded);
|
|
64
|
+
}
|
|
65
|
+
}, [
|
|
66
|
+
isExpanded,
|
|
67
|
+
setExpanded
|
|
68
|
+
]);
|
|
94
69
|
return /*#__PURE__*/ jsxs(Tooltip, {
|
|
95
|
-
disabled: !isTruncated,
|
|
70
|
+
disabled: !isTruncated || isExpanded,
|
|
96
71
|
children: [
|
|
97
72
|
/*#__PURE__*/ jsx(TooltipTrigger, {
|
|
98
73
|
asChild: true,
|
|
@@ -101,14 +76,37 @@ const ParameterPath = ({ ref, method, segments, encoding, attack = false, copyFo
|
|
|
101
76
|
"data-testid": testId,
|
|
102
77
|
"data-slot": "parameter-path",
|
|
103
78
|
"data-truncated": isTruncated || void 0,
|
|
79
|
+
"data-expanded": isExpanded || void 0,
|
|
104
80
|
ref: ref,
|
|
105
81
|
onCopy: handleCopy,
|
|
106
|
-
|
|
82
|
+
role: interactive ? 'button' : void 0,
|
|
83
|
+
tabIndex: interactive ? 0 : void 0,
|
|
84
|
+
"aria-expanded": interactive ? isExpanded : void 0,
|
|
85
|
+
onClick: interactive ? toggleExpanded : void 0,
|
|
86
|
+
onKeyDown: interactive ? handleKeyDown : void 0,
|
|
87
|
+
className: cn('relative flex items-center min-w-0', interactive && 'cursor-pointer', className),
|
|
107
88
|
children: /*#__PURE__*/ jsxs(TestIdProvider, {
|
|
108
89
|
value: testId,
|
|
109
90
|
children: [
|
|
110
|
-
|
|
111
|
-
|
|
91
|
+
/*#__PURE__*/ jsx(ParameterPathRow, {
|
|
92
|
+
ref: containerRef,
|
|
93
|
+
forMeasurement: false,
|
|
94
|
+
isExpanded: isExpanded,
|
|
95
|
+
indices: indices,
|
|
96
|
+
method: method,
|
|
97
|
+
segments: segments,
|
|
98
|
+
encoding: encoding,
|
|
99
|
+
attack: attack
|
|
100
|
+
}),
|
|
101
|
+
/*#__PURE__*/ jsx(ParameterPathRow, {
|
|
102
|
+
ref: measurementRef,
|
|
103
|
+
forMeasurement: true,
|
|
104
|
+
indices: null,
|
|
105
|
+
method: method,
|
|
106
|
+
segments: segments,
|
|
107
|
+
encoding: encoding,
|
|
108
|
+
attack: attack
|
|
109
|
+
})
|
|
112
110
|
]
|
|
113
111
|
})
|
|
114
112
|
})
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { FC, Ref } from 'react';
|
|
2
|
+
import type { HttpMethodName } from '../HttpMethod';
|
|
3
|
+
interface ParameterPathRowProps {
|
|
4
|
+
ref?: Ref<HTMLDivElement>;
|
|
5
|
+
method?: HttpMethodName;
|
|
6
|
+
segments: string[];
|
|
7
|
+
encoding?: string;
|
|
8
|
+
attack: boolean;
|
|
9
|
+
forMeasurement: boolean;
|
|
10
|
+
indices: number[] | null;
|
|
11
|
+
isExpanded?: boolean;
|
|
12
|
+
}
|
|
13
|
+
export declare const ParameterPathRow: FC<ParameterPathRowProps>;
|
|
14
|
+
export {};
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
import { jsx } from "react/jsx-runtime";
|
|
2
|
+
import { range } from "../../utils/range.js";
|
|
3
|
+
import { TestIdProvider } from "../../utils/testId.js";
|
|
4
|
+
import { rowVariants } from "./classes.js";
|
|
5
|
+
import { MEASURE, ROW } from "./constants.js";
|
|
6
|
+
import { ParameterPathEllipsis } from "./ParameterPathEllipsis.js";
|
|
7
|
+
import { ParameterPathEncoding } from "./ParameterPathEncoding.js";
|
|
8
|
+
import { ParameterPathJoint } from "./ParameterPathJoint.js";
|
|
9
|
+
import { ParameterPathMethod } from "./ParameterPathMethod.js";
|
|
10
|
+
import { ParameterPathSegment } from "./ParameterPathSegment.js";
|
|
11
|
+
const ParameterPathRow = ({ ref, method, segments, encoding, attack, forMeasurement, indices, isExpanded = false })=>{
|
|
12
|
+
const lastIndex = segments.length - 1;
|
|
13
|
+
const visibleIdx = forMeasurement || null === indices ? range(segments.length) : indices;
|
|
14
|
+
const measure = (slot)=>forMeasurement ? slot : void 0;
|
|
15
|
+
const items = [];
|
|
16
|
+
if (method) items.push(/*#__PURE__*/ jsx(ParameterPathMethod, {
|
|
17
|
+
method: method,
|
|
18
|
+
"data-measure": measure(MEASURE.method)
|
|
19
|
+
}, "method"));
|
|
20
|
+
visibleIdx.forEach((segIndex, position)=>{
|
|
21
|
+
const value = segments[segIndex];
|
|
22
|
+
if (void 0 === value) return;
|
|
23
|
+
const isLast = segIndex === lastIndex;
|
|
24
|
+
const isFirstShown = 0 === position;
|
|
25
|
+
const showJointBefore = !(isFirstShown && !method);
|
|
26
|
+
if (showJointBefore) items.push(/*#__PURE__*/ jsx(ParameterPathJoint, {
|
|
27
|
+
"data-measure": measure(MEASURE.joint)
|
|
28
|
+
}, `j-${segIndex}-pre`));
|
|
29
|
+
const isCollapsedBoundary = !forMeasurement && null !== indices && 0 === position && 2 === visibleIdx.length;
|
|
30
|
+
items.push(/*#__PURE__*/ jsx(ParameterPathSegment, {
|
|
31
|
+
index: segIndex,
|
|
32
|
+
variant: isLast ? 'highlighted' : 'default',
|
|
33
|
+
withZap: isLast && attack,
|
|
34
|
+
"data-measure": measure(MEASURE.segment),
|
|
35
|
+
children: value
|
|
36
|
+
}, `s-${segIndex}`));
|
|
37
|
+
if (isCollapsedBoundary) items.push(/*#__PURE__*/ jsx(ParameterPathJoint, {}, "ellipsis-joint-pre"), /*#__PURE__*/ jsx(ParameterPathEllipsis, {}, "ellipsis"));
|
|
38
|
+
});
|
|
39
|
+
if (encoding) items.push(/*#__PURE__*/ jsx(ParameterPathJoint, {
|
|
40
|
+
"data-measure": measure(MEASURE.joint)
|
|
41
|
+
}, "enc-joint"), /*#__PURE__*/ jsx(ParameterPathEncoding, {
|
|
42
|
+
"data-measure": measure(MEASURE.encoding),
|
|
43
|
+
children: encoding
|
|
44
|
+
}, "enc"));
|
|
45
|
+
if (forMeasurement) return /*#__PURE__*/ jsx("div", {
|
|
46
|
+
ref: ref,
|
|
47
|
+
"data-slot": "parameter-path-row",
|
|
48
|
+
"data-row": ROW.measure,
|
|
49
|
+
"aria-hidden": "true",
|
|
50
|
+
className: "flex items-center gap-0 absolute left-[-9999px] top-0 invisible pointer-events-none",
|
|
51
|
+
children: /*#__PURE__*/ jsx(TestIdProvider, {
|
|
52
|
+
value: void 0,
|
|
53
|
+
children: items
|
|
54
|
+
})
|
|
55
|
+
});
|
|
56
|
+
return /*#__PURE__*/ jsx("div", {
|
|
57
|
+
ref: ref,
|
|
58
|
+
"data-slot": "parameter-path-row",
|
|
59
|
+
"data-row": ROW.visible,
|
|
60
|
+
className: rowVariants({
|
|
61
|
+
expanded: isExpanded
|
|
62
|
+
}),
|
|
63
|
+
children: items
|
|
64
|
+
});
|
|
65
|
+
};
|
|
66
|
+
ParameterPathRow.displayName = 'ParameterPathRow';
|
|
67
|
+
export { ParameterPathRow };
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
export declare const rowVariants: (props?: ({
|
|
2
|
+
expanded?: boolean | null | undefined;
|
|
3
|
+
} & import("class-variance-authority/types").ClassProp) | undefined) => string;
|
|
1
4
|
export declare const segmentVariants: (props?: ({
|
|
2
5
|
variant?: "default" | "highlighted" | null | undefined;
|
|
3
6
|
} & import("class-variance-authority/types").ClassProp) | undefined) => string;
|
|
@@ -1,4 +1,15 @@
|
|
|
1
1
|
import { cva } from "class-variance-authority";
|
|
2
|
+
const rowVariants = cva('flex items-center gap-0 min-w-0', {
|
|
3
|
+
variants: {
|
|
4
|
+
expanded: {
|
|
5
|
+
true: 'flex-wrap',
|
|
6
|
+
false: 'overflow-hidden'
|
|
7
|
+
}
|
|
8
|
+
},
|
|
9
|
+
defaultVariants: {
|
|
10
|
+
expanded: false
|
|
11
|
+
}
|
|
12
|
+
});
|
|
2
13
|
const segmentVariants = cva('flex items-center justify-center gap-2 shrink-0 text-sm leading-5 whitespace-nowrap font-sans', {
|
|
3
14
|
variants: {
|
|
4
15
|
variant: {
|
|
@@ -22,4 +33,4 @@ const ellipsisVariants = cva([
|
|
|
22
33
|
'h-20 px-2 gap-2',
|
|
23
34
|
'text-text-secondary'
|
|
24
35
|
]);
|
|
25
|
-
export { ellipsisVariants, encodingVariants, jointVariants, segmentVariants };
|
|
36
|
+
export { ellipsisVariants, encodingVariants, jointVariants, rowVariants, segmentVariants };
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export declare const MEASURE: {
|
|
2
|
+
readonly method: "method";
|
|
3
|
+
readonly joint: "joint";
|
|
4
|
+
readonly segment: "segment";
|
|
5
|
+
readonly encoding: "encoding";
|
|
6
|
+
};
|
|
7
|
+
export declare const ROW: {
|
|
8
|
+
readonly visible: "visible";
|
|
9
|
+
readonly measure: "measure";
|
|
10
|
+
};
|
|
11
|
+
export declare const EXPAND_KEYS: readonly string[];
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
const MEASURE = {
|
|
2
|
+
method: 'method',
|
|
3
|
+
joint: 'joint',
|
|
4
|
+
segment: 'segment',
|
|
5
|
+
encoding: 'encoding'
|
|
6
|
+
};
|
|
7
|
+
const ROW = {
|
|
8
|
+
visible: 'visible',
|
|
9
|
+
measure: 'measure'
|
|
10
|
+
};
|
|
11
|
+
const EXPAND_KEYS = [
|
|
12
|
+
'Enter',
|
|
13
|
+
' '
|
|
14
|
+
];
|
|
15
|
+
export { EXPAND_KEYS, MEASURE, ROW };
|
|
@@ -12,5 +12,31 @@ export interface ParameterPathProps extends Omit<HTMLAttributes<HTMLDivElement>,
|
|
|
12
12
|
segments: string[];
|
|
13
13
|
encoding?: string;
|
|
14
14
|
attack?: boolean;
|
|
15
|
+
/**
|
|
16
|
+
* Opt in to click-to-expand. When `true`, a *truncated* path becomes
|
|
17
|
+
* interactive: clicking the `…` collapse indicator (or the path) expands it
|
|
18
|
+
* inline to show every segment, and clicking again collapses it back to
|
|
19
|
+
* `first … last`. No effect when the path already fits without truncation.
|
|
20
|
+
*
|
|
21
|
+
* `expandable` only controls the affordance (whether the user can toggle);
|
|
22
|
+
* the open/closed state is owned by `expanded` / `defaultExpanded`.
|
|
23
|
+
*/
|
|
24
|
+
expandable?: boolean;
|
|
25
|
+
/**
|
|
26
|
+
* Controlled expanded state. When provided, the component does not manage its
|
|
27
|
+
* own state — pair it with {@link onExpandedChange}.
|
|
28
|
+
*/
|
|
29
|
+
expanded?: boolean;
|
|
30
|
+
/**
|
|
31
|
+
* Initial expanded state for the uncontrolled case. Ignored when `expanded`
|
|
32
|
+
* is provided. Defaults to `false`.
|
|
33
|
+
*/
|
|
34
|
+
defaultExpanded?: boolean;
|
|
35
|
+
/**
|
|
36
|
+
* Called with the next expanded state whenever the user toggles the path.
|
|
37
|
+
* Required for controlled usage; also useful for analytics in the
|
|
38
|
+
* uncontrolled case.
|
|
39
|
+
*/
|
|
40
|
+
onExpandedChange?: (expanded: boolean) => void;
|
|
15
41
|
copyFormat?: (data: CopyFormatData) => string;
|
|
16
42
|
}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { useLayoutEffect, useState } from "react";
|
|
2
|
+
import { range } from "../../utils/range.js";
|
|
2
3
|
import { useContainerWidth } from "../Table/lib/useContainerWidth.js";
|
|
4
|
+
import { MEASURE } from "./constants.js";
|
|
3
5
|
const computeTruncation = ({ containerWidth, methodWidth, encodingWidth, segmentWidths, jointsWidth })=>{
|
|
4
6
|
const segCount = segmentWidths.length;
|
|
5
|
-
const allIndices =
|
|
6
|
-
length: segCount
|
|
7
|
-
}, (_, i)=>i);
|
|
7
|
+
const allIndices = range(segCount);
|
|
8
8
|
if (segCount <= 2 || containerWidth <= 0) return {
|
|
9
9
|
isTruncated: false,
|
|
10
10
|
visibleSegmentIndices: allIndices
|
|
@@ -27,17 +27,15 @@ const useParameterPathTruncation = ({ containerRef, measurementRef, segmentCount
|
|
|
27
27
|
const containerWidth = useContainerWidth(containerRef);
|
|
28
28
|
const [result, setResult] = useState({
|
|
29
29
|
isTruncated: false,
|
|
30
|
-
visibleSegmentIndices:
|
|
31
|
-
length: segmentCount
|
|
32
|
-
}, (_, i)=>i)
|
|
30
|
+
visibleSegmentIndices: range(segmentCount)
|
|
33
31
|
});
|
|
34
32
|
useLayoutEffect(()=>{
|
|
35
33
|
const root = measurementRef.current;
|
|
36
34
|
if (!root) return;
|
|
37
|
-
const methodEl = root.querySelector(
|
|
38
|
-
const encodingEl = root.querySelector(
|
|
39
|
-
const jointEls = Array.from(root.querySelectorAll(
|
|
40
|
-
const segmentEls = Array.from(root.querySelectorAll(
|
|
35
|
+
const methodEl = root.querySelector(`[data-measure="${MEASURE.method}"]`);
|
|
36
|
+
const encodingEl = root.querySelector(`[data-measure="${MEASURE.encoding}"]`);
|
|
37
|
+
const jointEls = Array.from(root.querySelectorAll(`[data-measure="${MEASURE.joint}"]`));
|
|
38
|
+
const segmentEls = Array.from(root.querySelectorAll(`[data-measure="${MEASURE.segment}"]`));
|
|
41
39
|
const segmentWidths = segmentEls.map((el)=>el.getBoundingClientRect().width);
|
|
42
40
|
const methodWidth = hasMethod && methodEl ? methodEl.getBoundingClientRect().width : 0;
|
|
43
41
|
const encodingWidth = hasEncoding && encodingEl ? encodingEl.getBoundingClientRect().width : 0;
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { NavPanelBack, NavPanelDivider, NavPanelHeader } from "../NavPanel/index.js";
|
|
3
|
+
import { Text } from "../Text/index.js";
|
|
4
|
+
import { HeaderActions } from "./HeaderActions.js";
|
|
5
|
+
import { findDrillNode, useRemoteShellContext } from "./model/index.js";
|
|
6
|
+
import { NavItemsList } from "./NavItemsList.js";
|
|
7
|
+
const NavPanelContent = ({ level: rawLevel })=>{
|
|
8
|
+
const { config, navStack, effectiveActiveItemId, navigate, drillInto, goBack } = useRemoteShellContext();
|
|
9
|
+
const level = Math.min(rawLevel, navStack.length - 1);
|
|
10
|
+
const entry = navStack[level];
|
|
11
|
+
const hasHeaderActions = !!config.headerActions?.length;
|
|
12
|
+
if (0 === level) return /*#__PURE__*/ jsxs(Fragment, {
|
|
13
|
+
children: [
|
|
14
|
+
hasHeaderActions ? /*#__PURE__*/ jsxs("div", {
|
|
15
|
+
className: "sticky top-0 z-10 flex shrink-0 items-center justify-between p-4 bg-bg-surface-2",
|
|
16
|
+
children: [
|
|
17
|
+
/*#__PURE__*/ jsx(Text, {
|
|
18
|
+
size: "sm",
|
|
19
|
+
weight: "medium",
|
|
20
|
+
children: config.productLabel
|
|
21
|
+
}),
|
|
22
|
+
/*#__PURE__*/ jsx(HeaderActions, {
|
|
23
|
+
actions: config.headerActions
|
|
24
|
+
})
|
|
25
|
+
]
|
|
26
|
+
}) : /*#__PURE__*/ jsx(NavPanelHeader, {
|
|
27
|
+
children: config.productLabel
|
|
28
|
+
}),
|
|
29
|
+
/*#__PURE__*/ jsx(NavItemsList, {
|
|
30
|
+
items: config.items,
|
|
31
|
+
activeItemId: effectiveActiveItemId,
|
|
32
|
+
onNavigate: navigate,
|
|
33
|
+
onDrillClick: drillInto
|
|
34
|
+
})
|
|
35
|
+
]
|
|
36
|
+
});
|
|
37
|
+
const parentEntry = navStack[level - 1];
|
|
38
|
+
const drillNode = findDrillNode(parentEntry.items, parentEntry.activeItemId);
|
|
39
|
+
const backLabel = drillNode?.label ?? 'Back';
|
|
40
|
+
return /*#__PURE__*/ jsxs(Fragment, {
|
|
41
|
+
children: [
|
|
42
|
+
/*#__PURE__*/ jsxs("div", {
|
|
43
|
+
className: "sticky top-0 z-10 flex flex-col gap-2 bg-bg-surface-1",
|
|
44
|
+
children: [
|
|
45
|
+
/*#__PURE__*/ jsx(NavPanelHeader, {
|
|
46
|
+
children: entry.title
|
|
47
|
+
}),
|
|
48
|
+
/*#__PURE__*/ jsx(NavPanelBack, {
|
|
49
|
+
onClick: goBack,
|
|
50
|
+
children: backLabel
|
|
51
|
+
}),
|
|
52
|
+
/*#__PURE__*/ jsx(NavPanelDivider, {})
|
|
53
|
+
]
|
|
54
|
+
}),
|
|
55
|
+
/*#__PURE__*/ jsx(NavItemsList, {
|
|
56
|
+
items: entry.items,
|
|
57
|
+
activeItemId: effectiveActiveItemId,
|
|
58
|
+
onNavigate: navigate,
|
|
59
|
+
onDrillClick: drillInto
|
|
60
|
+
})
|
|
61
|
+
]
|
|
62
|
+
});
|
|
63
|
+
};
|
|
64
|
+
NavPanelContent.displayName = 'NavPanelContent';
|
|
65
|
+
export { NavPanelContent };
|
|
@@ -1,7 +1,14 @@
|
|
|
1
1
|
import type { FC, HTMLAttributes, ReactNode, Ref } from 'react';
|
|
2
2
|
import { type TestableProps } from '../../utils/testId';
|
|
3
|
+
import type { NavConfig } from './model';
|
|
3
4
|
export interface RemoteShellProps extends HTMLAttributes<HTMLDivElement>, TestableProps {
|
|
4
5
|
ref?: Ref<HTMLDivElement>;
|
|
5
6
|
children?: ReactNode;
|
|
7
|
+
/** Navigation config used to build nav state for sub-components. */
|
|
8
|
+
config: NavConfig;
|
|
9
|
+
/** URL prefix stripped before matching and prepended when navigating (e.g. `"/edge"`). */
|
|
10
|
+
basePath?: string;
|
|
11
|
+
/** Custom navigation handler for router integration (React Router, Next.js, etc.). */
|
|
12
|
+
onNavigate?: (pathname: string) => void;
|
|
6
13
|
}
|
|
7
14
|
export declare const RemoteShell: FC<RemoteShellProps>;
|