Skip to content

Commit 81e4156

Browse files
authored
feat(sidebar): active connections toggle COMPASS-8114 (#6458)
* Add ConnectedPlugs and DisconnectedPlug icons * Show icon button to the right of NavigationItemsFilter * Add "exclude inactive" to connections filtering * Turn IconButton active when filtering is active * fixup! Show icon button to the right of NavigationItemsFilter Use default align for the Tooltip * Fix existing tests * Add a new test * fixup! Add a new test Use queryByTestId to fix test * fixup! fixup! Add a new test Move asserts into a shared expectElementByTestId * Add useFilteredConnections tests * fixup! fixup! fixup! Add a new test Revert the shared helper * fixup! fixup! fixup! fixup! Add a new test Remove unused import
1 parent 421c06d commit 81e4156

File tree

9 files changed

+288
-26
lines changed

9 files changed

+288
-26
lines changed
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
import { palette } from '@leafygreen-ui/palette';
2+
import React, { useMemo } from 'react';
3+
4+
import { useDarkMode } from '../../hooks/use-theme';
5+
6+
const ConnectedPlugsIcon: React.FunctionComponent = () => {
7+
const darkMode = useDarkMode();
8+
9+
const fillColor = useMemo(
10+
() => (darkMode ? palette.white : palette.black),
11+
[darkMode]
12+
);
13+
14+
const sparkColor = palette.green.dark1;
15+
16+
return (
17+
<svg
18+
width="14"
19+
height="14"
20+
viewBox="0 0 14 14"
21+
fill={fillColor}
22+
xmlns="http://www.w3.org/2000/svg"
23+
>
24+
<path d="M13.8694 0.157499C13.8235 0.108563 13.7683 0.0693554 13.7069 0.0422086C13.6456 0.0150618 13.5794 0.000531054 13.5124 -0.000518593C13.4453 -0.00156824 13.3787 0.0108846 13.3166 0.0360987C13.2544 0.0613128 13.198 0.0987728 13.1506 0.146249L9.87498 3.42187L9.53873 3.08562C9.35298 2.89967 9.13241 2.75215 8.88961 2.6515C8.64682 2.55086 8.38656 2.49905 8.12373 2.49905C7.8609 2.49905 7.60065 2.55086 7.35785 2.6515C7.11505 2.75215 6.89448 2.89967 6.70873 3.08562L5.63373 4.15875C5.61049 4.18197 5.59205 4.20954 5.57947 4.23989C5.56688 4.27024 5.56041 4.30277 5.56041 4.33562C5.56041 4.36848 5.56688 4.40101 5.57947 4.43136C5.59205 4.46171 5.61049 4.48928 5.63373 4.5125L9.48998 8.36625C9.5132 8.38949 9.54077 8.40793 9.57112 8.42051C9.60147 8.43309 9.634 8.43957 9.66686 8.43957C9.69971 8.43957 9.73224 8.43309 9.76259 8.42051C9.79294 8.40793 9.82051 8.38949 9.84373 8.36625L10.89 7.32C11.2692 6.94811 11.489 6.44343 11.5031 5.9125C11.5083 5.64409 11.4591 5.37741 11.3584 5.12853C11.2578 4.87965 11.1078 4.65373 10.9175 4.46437L10.5812 4.12875L13.8437 0.868124C13.9388 0.77584 13.9946 0.650384 13.9994 0.517961C14.0041 0.385539 13.9576 0.256392 13.8694 0.157499ZM4.35248 4.64625C4.30512 4.59887 4.24872 4.56149 4.18663 4.53633C4.12453 4.51118 4.05802 4.49875 3.99104 4.4998C3.92405 4.50085 3.85796 4.51535 3.79669 4.54244C3.73542 4.56953 3.68021 4.60866 3.63436 4.6575C3.54616 4.75639 3.49958 4.88554 3.50436 5.01796C3.50913 5.15038 3.56489 5.27584 3.65998 5.36812L4.04186 5.75L3.08373 6.70687C2.89384 6.89631 2.74424 7.12221 2.64392 7.37097C2.5436 7.61972 2.49464 7.8862 2.49998 8.15437C2.51318 8.68518 2.73213 9.19009 3.11061 9.5625L3.42311 9.87125L0.155606 13.1331C0.0634122 13.2229 0.00832355 13.3441 0.00126193 13.4726C-0.00579969 13.6011 0.0356812 13.7275 0.117481 13.8269C0.162402 13.879 0.217595 13.9213 0.279606 13.9511C0.341618 13.9809 0.409113 13.9976 0.477869 14.0001C0.546624 14.0026 0.615161 13.9909 0.67919 13.9657C0.743219 13.9406 0.801362 13.9024 0.849981 13.8537L4.12498 10.5781L4.46061 10.9144C4.83658 11.2886 5.34545 11.4987 5.87592 11.4987C6.40638 11.4987 6.91526 11.2886 7.29123 10.9144L8.24998 9.95687L8.64623 10.3537C8.69269 10.4002 8.74784 10.4371 8.80853 10.4622C8.86923 10.4873 8.93428 10.5003 8.99998 10.5003C9.06568 10.5003 9.13073 10.4873 9.19143 10.4622C9.25213 10.4371 9.30728 10.4002 9.35373 10.3537C9.40019 10.3073 9.43704 10.2521 9.46218 10.1914C9.48732 10.1307 9.50026 10.0657 9.50026 10C9.50026 9.9343 9.48732 9.86925 9.46218 9.80855C9.43704 9.74785 9.40019 9.6927 9.35373 9.64625L4.35248 4.64625Z" />
25+
26+
<path
27+
d="M4.539 0.804287C4.48708 0.926537 4.48584 1.06441 4.53557 1.18757L5.03557 2.43757C5.06019 2.49855 5.09659 2.55409 5.14267 2.601C5.18876 2.64792 5.24363 2.6853 5.30417 2.71101C5.3647 2.73672 5.4297 2.75026 5.49546 2.75085C5.56123 2.75144 5.62646 2.73907 5.68745 2.71444C5.74843 2.68982 5.80396 2.65343 5.85088 2.60734C5.8978 2.56125 5.93518 2.50638 5.96089 2.44585C5.9866 2.38532 6.00014 2.32031 6.00073 2.25455C6.00131 2.18879 5.98894 2.12355 5.96432 2.06257L5.46432 0.812567C5.41459 0.689407 5.31798 0.591046 5.19573 0.539122C5.07348 0.487198 4.93561 0.485964 4.81245 0.535692C4.68929 0.58542 4.59092 0.682037 4.539 0.804287Z"
28+
fill={sparkColor}
29+
/>
30+
<path
31+
d="M2.06245 5.96444L0.812445 5.46444C0.689285 5.41471 0.590924 5.3181 0.539 5.19585C0.487076 5.0736 0.485842 4.93573 0.53557 4.81257C0.585298 4.68941 0.681915 4.59105 0.804165 4.53912C0.926415 4.4872 1.06429 4.48596 1.18745 4.53569L2.43745 5.03569C2.49843 5.06032 2.55396 5.09671 2.60088 5.14279C2.6478 5.18888 2.68518 5.24375 2.71089 5.30429C2.7366 5.36482 2.75014 5.42982 2.75072 5.49559C2.75131 5.56135 2.73894 5.62658 2.71432 5.68757C2.6897 5.74855 2.6533 5.80409 2.60722 5.851C2.56113 5.89792 2.50626 5.9353 2.44573 5.96101C2.38519 5.98672 2.32019 6.00026 2.25443 6.00085C2.18866 6.00144 2.12343 5.98907 2.06245 5.96444Z"
32+
fill={sparkColor}
33+
/>
34+
<path
35+
d="M11.9374 8.03569L13.1874 8.53569C13.3106 8.58542 13.409 8.68204 13.4609 8.80429C13.5128 8.92654 13.514 9.06441 13.4643 9.18757C13.4146 9.31073 13.318 9.40909 13.1957 9.46101C13.0735 9.51294 12.9356 9.51417 12.8124 9.46444L11.5624 8.96444C11.4393 8.91471 11.3409 8.8181 11.289 8.69585C11.2371 8.5736 11.2358 8.43573 11.2856 8.31257C11.3353 8.18941 11.4319 8.09105 11.5542 8.03912C11.6764 7.9872 11.8143 7.98596 11.9374 8.03569Z"
36+
fill={sparkColor}
37+
/>
38+
<path
39+
d="M8.69573 11.2891C8.81798 11.341 8.91459 11.4394 8.96432 11.5626L9.46432 12.8126C9.51405 12.9357 9.51281 13.0736 9.46089 13.1958C9.40897 13.3181 9.31061 13.4147 9.18745 13.4644C9.06429 13.5142 8.92642 13.5129 8.80417 13.461C8.68192 13.4091 8.5853 13.3107 8.53557 13.1876L8.03557 11.9376C7.98584 11.8144 7.98708 11.6765 8.039 11.5543C8.09092 11.432 8.18929 11.3354 8.31245 11.2857C8.43561 11.236 8.57347 11.2372 8.69573 11.2891Z"
40+
fill={sparkColor}
41+
/>
42+
</svg>
43+
);
44+
};
45+
46+
export { ConnectedPlugsIcon };
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import { palette } from '@leafygreen-ui/palette';
2+
import React, { useMemo } from 'react';
3+
4+
import { useDarkMode } from '../../hooks/use-theme';
5+
6+
const DisconnectedPlugIcon: React.FunctionComponent = () => {
7+
const darkMode = useDarkMode();
8+
9+
const fillColor = useMemo(
10+
() => (darkMode ? palette.white : palette.black),
11+
[darkMode]
12+
);
13+
14+
return (
15+
<svg
16+
width="15"
17+
height="15"
18+
viewBox="0 0 15 15"
19+
fill={fillColor}
20+
xmlns="http://www.w3.org/2000/svg"
21+
>
22+
<path d="M14.0306 3.96938C13.961 3.89946 13.8782 3.84398 13.787 3.80613C13.6958 3.76827 13.5981 3.74879 13.4994 3.74879C13.4007 3.74879 13.3029 3.76827 13.2118 3.80613C13.1206 3.84398 13.0378 3.89946 12.9681 3.96938L11 5.9375L9.0625 4L11.0325 2.03063C11.1734 1.88973 11.2526 1.69864 11.2526 1.49938C11.2526 1.30012 11.1734 1.10902 11.0325 0.968128C10.8916 0.827232 10.7005 0.748077 10.5013 0.748077C10.302 0.748077 10.1109 0.827232 9.97001 0.968128L8 2.9375L6.53063 1.46938C6.46086 1.39961 6.37804 1.34427 6.28689 1.30652C6.19574 1.26876 6.09804 1.24933 5.99938 1.24933C5.80012 1.24933 5.60903 1.32848 5.46813 1.46938C5.32723 1.61027 5.24808 1.80137 5.24808 2.00063C5.24808 2.19989 5.32723 2.39098 5.46813 2.53188L5.6875 2.75L2.55563 5.88375C2.30023 6.13912 2.09763 6.4423 1.9594 6.77597C1.82117 7.10964 1.75003 7.46727 1.75003 7.82844C1.75003 8.18961 1.82117 8.54724 1.9594 8.88091C2.09763 9.21459 2.30023 9.51776 2.55563 9.77313L3.36063 10.5781L0.46938 13.4694C0.399615 13.5391 0.344274 13.622 0.306518 13.7131C0.268762 13.8043 0.249329 13.902 0.249329 14.0006C0.249329 14.0993 0.268762 14.197 0.306518 14.2881C0.344274 14.3793 0.399615 14.4621 0.46938 14.5319C0.610276 14.6728 0.801372 14.7519 1.00063 14.7519C1.09929 14.7519 1.19699 14.7325 1.28814 14.6947C1.37929 14.657 1.46211 14.6016 1.53188 14.5319L4.42313 11.6406L5.22813 12.4456C5.4835 12.701 5.78667 12.9036 6.12034 13.0419C6.45402 13.1801 6.81165 13.2512 7.17282 13.2512C7.53399 13.2512 7.89162 13.1801 8.22529 13.0419C8.55896 12.9036 8.86214 12.701 9.11751 12.4456L12.25 9.3125L12.4694 9.5325C12.5391 9.60227 12.622 9.65761 12.7131 9.69536C12.8043 9.73312 12.902 9.75255 13.0006 9.75255C13.0993 9.75255 13.197 9.73312 13.2881 9.69536C13.3793 9.65761 13.4621 9.60227 13.5319 9.5325C13.6016 9.46274 13.657 9.37992 13.6947 9.28876C13.7325 9.19761 13.7519 9.09992 13.7519 9.00125C13.7519 8.90259 13.7325 8.80489 13.6947 8.71374C13.657 8.62259 13.6016 8.53977 13.5319 8.47L12.0625 7L14.0325 5.03063C14.1021 4.96085 14.1573 4.87804 14.1949 4.78692C14.2325 4.69581 14.2517 4.59818 14.2515 4.49961C14.2514 4.40105 14.2318 4.30349 14.1939 4.21251C14.156 4.12153 14.1005 4.03891 14.0306 3.96938ZM8.05563 11.3838C7.93955 11.4999 7.80173 11.592 7.65004 11.6549C7.49835 11.7177 7.33576 11.75 7.17157 11.75C7.00737 11.75 6.84479 11.7177 6.6931 11.6549C6.54141 11.592 6.40358 11.4999 6.2875 11.3838L3.61625 8.7125C3.50013 8.59642 3.40801 8.4586 3.34516 8.30691C3.28231 8.15522 3.24996 7.99264 3.24996 7.82844C3.24996 7.66425 3.28231 7.50166 3.34516 7.34997C3.40801 7.19828 3.50013 7.06046 3.61625 6.94438L6.75 3.8125L11.1875 8.25L8.05563 11.3838Z" />
23+
</svg>
24+
);
25+
};
26+
27+
export { DisconnectedPlugIcon };

packages/compass-components/src/index.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,8 @@ export { DocumentIcon } from './components/icons/document-icon';
5959
export { FavoriteIcon } from './components/icons/favorite-icon';
6060
export { ServerIcon } from './components/icons/server-icon';
6161
export { NoSavedItemsIcon } from './components/icons/no-saved-items-icon';
62+
export { ConnectedPlugsIcon } from './components/icons/connected-plugs';
63+
export { DisconnectedPlugIcon } from './components/icons/disconnected-plug';
6264
export { GuideCue as LGGuideCue } from '@leafygreen-ui/guide-cue';
6365
export { Variant as BadgeVariant } from '@leafygreen-ui/badge';
6466
export { Variant as BannerVariant } from '@leafygreen-ui/banner';

packages/compass-sidebar/src/components/multiple-connections/connections-navigation.tsx

Lines changed: 49 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,10 @@ import {
1212
Button,
1313
Icon,
1414
ButtonVariant,
15+
IconButton,
16+
ConnectedPlugsIcon,
17+
DisconnectedPlugIcon,
18+
Tooltip,
1519
} from '@mongodb-js/compass-components';
1620
import { ConnectionsNavigationTree } from '@mongodb-js/compass-connections-navigation';
1721
import type { MapDispatchToProps, MapStateToProps } from 'react-redux';
@@ -80,11 +84,19 @@ const connectionCountStyles = css({
8084
marginLeft: spacing[100],
8185
});
8286

83-
const searchStyles = css({
87+
const filterContainerStyles = css({
88+
display: 'flex',
89+
flexDirection: 'row',
90+
alignItems: 'center',
91+
gap: spacing[200],
8492
paddingLeft: spacing[400],
8593
paddingRight: spacing[400],
8694
});
8795

96+
const searchFormStyles = css({
97+
flexGrow: 1,
98+
});
99+
88100
const noDeploymentStyles = css({
89101
paddingLeft: spacing[400],
90102
paddingRight: spacing[400],
@@ -112,7 +124,9 @@ type ConnectionsNavigationComponentProps = {
112124
connectionsWithStatus: ReturnType<typeof useConnectionsWithStatus>;
113125
activeWorkspace: WorkspaceTab | null;
114126
filterRegex: RegExp | null;
127+
excludeInactive: boolean;
115128
onFilterChange(regex: RegExp | null): void;
129+
onToggleExcludeInactive(): void;
116130
onConnect(info: ConnectionInfo): void;
117131
onNewConnection(): void;
118132
onEditConnection(info: ConnectionInfo): void;
@@ -154,10 +168,12 @@ const ConnectionsNavigation: React.FC<ConnectionsNavigationProps> = ({
154168
connectionsWithStatus,
155169
activeWorkspace,
156170
filterRegex,
171+
excludeInactive,
157172
instances,
158173
databases,
159174
isPerformanceTabSupported,
160175
onFilterChange,
176+
onToggleExcludeInactive,
161177
onConnect,
162178
onNewConnection,
163179
onEditConnection,
@@ -257,6 +273,7 @@ const ConnectionsNavigation: React.FC<ConnectionsNavigationProps> = ({
257273
filterRegex,
258274
fetchAllCollections,
259275
onDatabaseExpand,
276+
excludeInactive,
260277
});
261278

262279
const connectionListTitleActions =
@@ -502,11 +519,37 @@ const ConnectionsNavigation: React.FC<ConnectionsNavigationProps> = ({
502519
</div>
503520
{connections.length > 0 && (
504521
<>
505-
<NavigationItemsFilter
506-
searchInputClassName={searchStyles}
507-
placeholder="Search connections"
508-
onFilterChange={onFilterChange}
509-
/>
522+
<div className={filterContainerStyles}>
523+
<NavigationItemsFilter
524+
className={searchFormStyles}
525+
placeholder="Search connections"
526+
onFilterChange={onFilterChange}
527+
/>
528+
<Tooltip
529+
justify="middle"
530+
trigger={
531+
<IconButton
532+
onClick={onToggleExcludeInactive}
533+
active={excludeInactive}
534+
aria-label={
535+
excludeInactive
536+
? 'Showing active connections'
537+
: 'Showing all connections'
538+
}
539+
>
540+
{excludeInactive ? (
541+
<ConnectedPlugsIcon />
542+
) : (
543+
<DisconnectedPlugIcon />
544+
)}
545+
</IconButton>
546+
}
547+
>
548+
{excludeInactive
549+
? 'Showing active connections'
550+
: 'Showing all connections'}
551+
</Tooltip>
552+
</div>
510553
<ConnectionsNavigationTree
511554
connections={filtered || connections}
512555
activeWorkspace={activeWorkspace}

packages/compass-sidebar/src/components/multiple-connections/sidebar.spec.tsx

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -357,6 +357,36 @@ describe('Multiple Connections Sidebar Component', function () {
357357
expect(screen.getByText('Remove')).to.be.visible;
358358
});
359359

360+
it('should render the only connected connections when toggled', async () => {
361+
await renderAndWaitForNavigationTree();
362+
363+
const favoriteConnectionId = savedFavoriteConnection.id;
364+
const recentConnectionId = savedRecentConnection.id;
365+
366+
const activeConnectionsToggleButton = screen.getByLabelText(
367+
'Showing all connections'
368+
);
369+
370+
expect(screen.queryByTestId(favoriteConnectionId)).to.be.visible;
371+
expect(screen.queryByTestId(recentConnectionId)).to.be.visible;
372+
373+
userEvent.click(activeConnectionsToggleButton);
374+
expect(activeConnectionsToggleButton.ariaLabel).equals(
375+
'Showing active connections'
376+
);
377+
378+
expect(screen.queryByTestId(favoriteConnectionId)).to.be.null;
379+
expect(screen.queryByTestId(recentConnectionId)).to.be.null;
380+
381+
await connectAndNotifyInstanceManager(savedFavoriteConnection);
382+
expect(screen.queryByTestId(favoriteConnectionId)).to.be.visible;
383+
expect(screen.queryByTestId(recentConnectionId)).to.be.null;
384+
385+
await connectAndNotifyInstanceManager(savedRecentConnection);
386+
expect(screen.queryByTestId(favoriteConnectionId)).to.be.visible;
387+
expect(screen.queryByTestId(recentConnectionId)).to.be.visible;
388+
});
389+
360390
context('and performing actions', function () {
361391
beforeEach(async function () {
362392
await renderAndWaitForNavigationTree({

packages/compass-sidebar/src/components/multiple-connections/sidebar.tsx

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,10 @@ export function MultipleConnectionSidebar({
103103
useState<RegExp | null>(null);
104104
const [connectionInfoModalConnectionId, setConnectionInfoModalConnectionId] =
105105
useState<string | undefined>();
106+
const [excludeInactive, setExcludeInactiveConnections] = useState(false);
107+
const toggleExcludeInactiveConnections = useCallback(() => {
108+
setExcludeInactiveConnections((previous) => !previous);
109+
}, []);
106110

107111
const formPreferences = useConnectionFormPreferences();
108112
const maybeProtectConnectionString = useMaybeProtectConnectionString();
@@ -204,7 +208,9 @@ export function MultipleConnectionSidebar({
204208
connectionsWithStatus={connectionsWithStatus}
205209
activeWorkspace={activeWorkspace}
206210
filterRegex={activeConnectionsFilterRegex}
211+
excludeInactive={excludeInactive}
207212
onFilterChange={onActiveConnectionFilterChange}
213+
onToggleExcludeInactive={toggleExcludeInactiveConnections}
208214
onConnect={(connectionInfo) => {
209215
void connect(connectionInfo);
210216
}}

packages/compass-sidebar/src/components/navigation-items-filter.tsx

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,13 @@ export default function NavigationItemsFilter({
66
ariaLabel = 'Search',
77
title = 'Search',
88
onFilterChange,
9-
searchInputClassName,
9+
className,
1010
}: {
1111
placeholder?: string;
1212
ariaLabel?: string;
1313
title?: string;
14-
searchInputClassName?: string;
1514
onFilterChange(regex: RegExp | null): void;
15+
className?: string;
1616
}): React.ReactElement {
1717
const onChange = useCallback(
1818
(event) => {
@@ -37,15 +37,14 @@ export default function NavigationItemsFilter({
3737
}, []);
3838

3939
return (
40-
<form noValidate onSubmit={onSubmit}>
40+
<form noValidate className={className} onSubmit={onSubmit}>
4141
<TextInput
4242
data-testid="sidebar-filter-input"
4343
placeholder={placeholder}
4444
type="search"
4545
aria-label={ariaLabel}
4646
title={title}
4747
onChange={onChange}
48-
className={searchInputClassName}
4948
/>
5049
</form>
5150
);

0 commit comments

Comments
 (0)