@datalayer/core 1.2.18 → 1.2.19
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/lib/cli-login.js +5 -51
- package/lib/components/anonymous/AnonymousKeyExpired.js +1 -15
- package/lib/components/anonymous/AnonymousKeyTimer.js +5 -15
- package/lib/components/auth/SignIn.js +2 -2
- package/lib/components/avatars/UserAvatar.js +3 -27
- package/lib/components/billing/BillingEntitySelect.js +6 -48
- package/lib/components/checkout/StripeCheckout.js +33 -217
- package/lib/components/contents/ContentSourceCard.js +2 -11
- package/lib/components/contents/HomeFolderObjectsBrowser.d.ts +1 -1
- package/lib/components/contents/HomeFolderObjectsBrowser.js +11 -35
- package/lib/components/display/CenteredSpinner.js +1 -6
- package/lib/components/display/DatalayerBox.js +2 -14
- package/lib/components/flashes/FlashClosable.js +2 -17
- package/lib/components/mcp/ClientBadge.js +1 -1
- package/lib/components/mcp/McpErrorBlankslate.js +1 -1
- package/lib/components/mcp/ScopeList.js +1 -1
- package/lib/components/notebooks/JupyterNotebook.js +1 -2
- package/lib/components/principal/Principal.js +2 -10
- package/lib/components/principal/PrincipalAppearance.js +19 -63
- package/lib/components/principal/PrincipalAvatar.js +5 -25
- package/lib/components/principal/PrincipalBadge.js +3 -13
- package/lib/components/principal/PrincipalBanner.js +4 -32
- package/lib/components/principal/PrincipalDetailsOverlay.js +7 -23
- package/lib/components/principal/PrincipalHoverCard.js +15 -18
- package/lib/components/principal/PrincipalSwitcherMenu.js +15 -83
- package/lib/components/progress/ConsumptionBar.js +1 -1
- package/lib/components/sharing/ShareAccessComponent.js +21 -229
- package/lib/components/sharing/SharingEditor.js +1 -1
- package/lib/components/spaces/SpaceDetailsOverlay.js +4 -35
- package/lib/components/spaces/SpaceDisplay.js +1 -8
- package/lib/components/storage/ContentsBrowser.js +3 -26
- package/lib/components/storage/ContentsTable.js +4 -23
- package/lib/components/students/StudentResultCircle.js +7 -29
- package/lib/components/timeline/Timeline.js +4 -36
- package/lib/hooks/layouts/LayoutBackdrop.js +2 -1
- package/lib/hooks/layouts/LayoutScreencapture.js +1 -1
- package/lib/hooks/libraryApp.d.ts +6 -1
- package/lib/hooks/libraryApp.js +10 -1
- package/lib/hooks/useAuthorization.js +6 -1
- package/lib/mocks/components/FlashMock.js +3 -8
- package/lib/mocks/views/DashboardMock.js +6 -72
- package/lib/mocks/views/FormMock.js +3 -2
- package/lib/mocks/views/TableMock.js +3 -2
- package/lib/mocks/views/WipMock.js +2 -1
- package/lib/models/Person.d.ts +9 -0
- package/lib/models/Person.js +23 -0
- package/lib/otel/views/OtelLive.js +4 -62
- package/lib/otel/views/OtelLiveSpans.js +4 -29
- package/lib/otel/views/OtelLogsList.js +13 -64
- package/lib/otel/views/OtelMetricsChart.js +4 -19
- package/lib/otel/views/OtelMetricsList.js +8 -77
- package/lib/otel/views/OtelSearchBar.js +3 -12
- package/lib/otel/views/OtelSpanDetail.js +9 -79
- package/lib/otel/views/OtelSpanTree.js +7 -57
- package/lib/otel/views/OtelSqlView.js +5 -99
- package/lib/otel/views/OtelSystemView.js +4 -34
- package/lib/otel/views/OtelTimeline.js +7 -37
- package/lib/otel/views/OtelTimelineRangeSlider.js +7 -140
- package/lib/otel/views/OtelTracesList.js +12 -76
- package/lib/portable/index.d.ts +8 -0
- package/lib/portable/index.js +12 -0
- package/lib/state/substates/NavigationState.d.ts +6 -4
- package/lib/state/substates/NavigationState.js +6 -5
- package/lib/views/api-keys/APIKeyEdit.js +2 -11
- package/lib/views/api-keys/APIKeyNew.js +3 -19
- package/lib/views/api-keys/APIKeys.js +6 -11
- package/lib/views/api-keys/APIKeysStandalone.js +1 -1
- package/lib/views/datasources/DatasourceDetail.d.ts +1 -1
- package/lib/views/datasources/DatasourceDetail.js +24 -17
- package/lib/views/datasources/DatasourceNew.js +2 -6
- package/lib/views/datasources/Datasources.js +2 -14
- package/lib/views/iam/SignInSimple.js +8 -64
- package/lib/views/mcp/AdmittedClients.js +3 -16
- package/lib/views/mcp/AlertDestinations.js +2 -10
- package/lib/views/mcp/AlertRules.js +4 -9
- package/lib/views/mcp/ApprovalQueue.js +4 -21
- package/lib/views/mcp/AuditLog.js +7 -44
- package/lib/views/mcp/ConnectedAgents.js +1 -6
- package/lib/views/mcp/EnterpriseConsole.js +10 -23
- package/lib/views/mcp/IdentityProviders.js +7 -31
- package/lib/views/mcp/McpDashboard.js +14 -30
- package/lib/views/mcp/McpHome.js +7 -54
- package/lib/views/mcp/McpObservability.js +13 -85
- package/lib/views/mcp/NotebookRuns.js +5 -12
- package/lib/views/mcp/OrganizationPolicy.js +3 -9
- package/lib/views/mcp/OrganizationUsage.js +4 -11
- package/lib/views/mcp/PersonalPolicy.js +3 -3
- package/lib/views/mcp/Policies.js +5 -46
- package/lib/views/mcp/PolicyForm.js +1 -9
- package/lib/views/mcp/PolicyHistory.js +2 -8
- package/lib/views/mcp/RunDetail.js +3 -25
- package/lib/views/mcp/ScimProvisioning.js +3 -15
- package/lib/views/mcp/ServiceAgents.js +4 -17
- package/lib/views/mcp/TeamPolicies.js +7 -19
- package/lib/views/mcp/ToolAccess.js +15 -22
- package/lib/views/mcp/TraceTimeline.js +8 -23
- package/lib/views/otel/DashboardView.js +2 -2
- package/lib/views/otel/LogsView.js +2 -2
- package/lib/views/otel/MetricsView.js +2 -2
- package/lib/views/otel/OtelHeader.js +6 -40
- package/lib/views/otel/SqlView.js +2 -2
- package/lib/views/otel/SystemView.js +2 -2
- package/lib/views/otel/TracesView.js +2 -2
- package/lib/views/profile/UserBadge.js +6 -98
- package/lib/views/secrets/SecretEdit.js +2 -11
- package/lib/views/secrets/SecretNew.js +1 -1
- package/package.json +1 -1
|
@@ -15,7 +15,7 @@ export const ClientBadge = ({ clientId, clientName, registration, clientHostname
|
|
|
15
15
|
const byDocument = (registration ?? (isCimdClientId(clientId) ? 'cimd' : 'dcr')) === 'cimd';
|
|
16
16
|
const hostname = clientHostname || (byDocument ? clientHostnameOf(clientId) : '');
|
|
17
17
|
const name = clientName || (byDocument ? hostname : '') || clientId || 'Unknown client';
|
|
18
|
-
return (_jsxs(Box, {
|
|
18
|
+
return (_jsxs(Box, { display: "grid", gap: "2px", minWidth: 0, children: [_jsxs(Box, { display: "flex", alignItems: "center", gap: 2, minWidth: 0, children: [_jsx(Text, { sx: {
|
|
19
19
|
fontSize: 1,
|
|
20
20
|
fontWeight: 'semibold',
|
|
21
21
|
overflow: 'hidden',
|
|
@@ -12,6 +12,6 @@ const VISUAL = {
|
|
|
12
12
|
};
|
|
13
13
|
export const McpErrorBlankslate = ({ state, onRetry, border = true, }) => {
|
|
14
14
|
const Icon = VISUAL[state.reason];
|
|
15
|
-
return (_jsx(Box, {
|
|
15
|
+
return (_jsx(Box, { width: "100%", minWidth: 0, children: _jsxs(Blankslate, { border: border, spacious: true, children: [_jsx(Blankslate.Visual, { children: _jsx(Icon, { size: "medium" }) }), _jsx(Blankslate.Heading, { children: state.heading }), _jsx(Blankslate.Description, { children: _jsx(Text, { sx: { textAlign: 'center' }, children: state.description }) }), state.retryable && onRetry && (_jsx(Button, { size: "small", onClick: onRetry, children: "Try again" }))] }) }));
|
|
16
16
|
};
|
|
17
17
|
export default McpErrorBlankslate;
|
|
@@ -9,6 +9,6 @@ export const ScopeList = ({ scopes, max = 3 }) => {
|
|
|
9
9
|
}
|
|
10
10
|
const shown = scopes.slice(0, max);
|
|
11
11
|
const rest = scopes.length - shown.length;
|
|
12
|
-
return (_jsxs(Box, {
|
|
12
|
+
return (_jsxs(Box, { display: "flex", gap: 1, flexWrap: "wrap", alignItems: "center", children: [shown.map(scope => (_jsx(Label, { size: "small", variant: "secondary", children: scope }, scope))), rest > 0 && (_jsxs(Text, { as: "span", title: scopes.join('\n'), "aria-label": `and ${rest} more: ${scopes.slice(max).join(', ')}`, sx: { fontSize: 0, color: 'fg.muted' }, children: ["+", rest] }))] }));
|
|
13
13
|
};
|
|
14
14
|
export default ScopeList;
|
|
@@ -6,8 +6,7 @@ import { jsx as _jsx } from "react/jsx-runtime";
|
|
|
6
6
|
import { Box } from '@datalayer/primer-addons';
|
|
7
7
|
import { Lumino } from '@datalayer/jupyter-react';
|
|
8
8
|
export const JupyterNotebook = ({ boxPanel, height = '100%', }) => {
|
|
9
|
-
return (_jsx("div", { style: { position: 'relative' }, children: _jsx(Box, { className: "jp-LabShell", sx: {
|
|
10
|
-
position: 'relative',
|
|
9
|
+
return (_jsx("div", { style: { position: 'relative' }, children: _jsx(Box, { className: "jp-LabShell", position: "relative", sx: {
|
|
11
10
|
'& .dla-Jupyter-Notebook': {
|
|
12
11
|
height,
|
|
13
12
|
maxHeight: 1000,
|
|
@@ -226,9 +226,7 @@ export const Principal = ({ principal, isAdmin = false, avatarSize = 20, gap = 2
|
|
|
226
226
|
hydratedEntity?.avatarUrl ||
|
|
227
227
|
cachedPrincipal?.avatarUrl ||
|
|
228
228
|
undefined,
|
|
229
|
-
avatarIcon: principal.avatarIcon ||
|
|
230
|
-
hydratedEntity?.avatarIcon ||
|
|
231
|
-
undefined,
|
|
229
|
+
avatarIcon: principal.avatarIcon || hydratedEntity?.avatarIcon || undefined,
|
|
232
230
|
banner: principal.banner || hydratedEntity?.banner || undefined,
|
|
233
231
|
firstName: principal.firstName ||
|
|
234
232
|
hydratedEntity?.firstName ||
|
|
@@ -290,12 +288,6 @@ export const Principal = ({ principal, isAdmin = false, avatarSize = 20, gap = 2
|
|
|
290
288
|
resolvedIsPublic,
|
|
291
289
|
upsertCachedPrincipal,
|
|
292
290
|
]);
|
|
293
|
-
return (_jsxs(Box, { sx: {
|
|
294
|
-
display: 'inline-flex',
|
|
295
|
-
alignItems: 'center',
|
|
296
|
-
gap,
|
|
297
|
-
minWidth: 0,
|
|
298
|
-
...sx,
|
|
299
|
-
}, children: [_jsx(PrincipalAvatar, { kind: resolvedPrincipal.kind, avatarUrl: resolvedPrincipal.avatarUrl, avatarIcon: resolvedPrincipal.avatarIcon, alt: resolvedPrincipal.displayName, size: avatarSize, square: square }), _jsx(PrincipalDetailsOverlay, { kind: resolvedPrincipal.kind, uid: resolvedPrincipal.uid, displayName: resolvedPrincipal.displayName, name: resolvedPrincipal.name, description: resolvedPrincipal.description, handle: resolvedPrincipal.handle, accountHandle: resolvedPrincipal.accountHandle, firstName: resolvedPrincipal.firstName, lastName: resolvedPrincipal.lastName, email: resolvedPrincipal.email, origin: resolvedPrincipal.origin, avatarUrl: resolvedPrincipal.avatarUrl, avatarIcon: resolvedPrincipal.avatarIcon, organizationName: teamOrganizationNameResolved, memberCount: teamMemberCount, isPublic: resolvedIsPublic, isAdmin: isAdmin })] }));
|
|
291
|
+
return (_jsxs(Box, { display: "inline-flex", alignItems: "center", gap: gap, minWidth: 0, sx: sx, children: [_jsx(PrincipalAvatar, { kind: resolvedPrincipal.kind, avatarUrl: resolvedPrincipal.avatarUrl, avatarIcon: resolvedPrincipal.avatarIcon, alt: resolvedPrincipal.displayName, size: avatarSize, square: square }), _jsx(PrincipalDetailsOverlay, { kind: resolvedPrincipal.kind, uid: resolvedPrincipal.uid, displayName: resolvedPrincipal.displayName, name: resolvedPrincipal.name, description: resolvedPrincipal.description, handle: resolvedPrincipal.handle, accountHandle: resolvedPrincipal.accountHandle, firstName: resolvedPrincipal.firstName, lastName: resolvedPrincipal.lastName, email: resolvedPrincipal.email, origin: resolvedPrincipal.origin, avatarUrl: resolvedPrincipal.avatarUrl, avatarIcon: resolvedPrincipal.avatarIcon, organizationName: teamOrganizationNameResolved, memberCount: teamMemberCount, isPublic: resolvedIsPublic, isAdmin: isAdmin })] }));
|
|
300
292
|
};
|
|
301
293
|
export default Principal;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
2
|
import { Suspense, lazy, useEffect, useState, } from 'react';
|
|
3
|
-
import { Box
|
|
3
|
+
import { Box } from '@datalayer/primer-addons';
|
|
4
|
+
import { Button, Text, Tooltip } from '@primer/react';
|
|
4
5
|
import { Dialog } from '@primer/react/experimental';
|
|
5
6
|
/**
|
|
6
7
|
* An avatar icon, fetched the first time it is drawn.
|
|
@@ -583,13 +584,10 @@ export function PrincipalBannerImage({ banner, height = 180, }) {
|
|
|
583
584
|
const Banner = PRINCIPAL_BANNERS.find(option => option.name === banner)?.Component;
|
|
584
585
|
if (!Banner)
|
|
585
586
|
return null;
|
|
586
|
-
return (_jsx(Box, { sx: {
|
|
587
|
+
return (_jsx(Box, { overflow: "hidden", borderRadius: 2, bg: "canvas.subtle", sx: {
|
|
587
588
|
position: 'relative',
|
|
588
589
|
width: '100%',
|
|
589
590
|
height,
|
|
590
|
-
overflow: 'hidden',
|
|
591
|
-
borderRadius: 2,
|
|
592
|
-
bg: 'canvas.subtle',
|
|
593
591
|
'& > svg': {
|
|
594
592
|
position: 'absolute',
|
|
595
593
|
inset: 0,
|
|
@@ -624,17 +622,14 @@ export function PrincipalAvatarPicker({ value, onChange, disabled = false, }) {
|
|
|
624
622
|
width: 'min(1080px, calc(100vw - 32px))',
|
|
625
623
|
maxWidth: 'none',
|
|
626
624
|
},
|
|
627
|
-
}, children: _jsx(Box, {
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
],
|
|
636
|
-
gap: 2,
|
|
637
|
-
}, children: PRINCIPAL_AVATAR_ICONS.map(({ name, label, description, Icon }) => (
|
|
625
|
+
}, children: _jsx(Box, { display: "grid",
|
|
626
|
+
// Twelve to a line, whatever the dialog is wide: the columns
|
|
627
|
+
// share it evenly and `minmax(0, …)` lets them shrink under
|
|
628
|
+
// their content, which a long name would otherwise widen.
|
|
629
|
+
gridTemplateColumns: [
|
|
630
|
+
'repeat(6, minmax(0, 1fr))',
|
|
631
|
+
'repeat(12, minmax(0, 1fr))',
|
|
632
|
+
], gap: 2, children: PRINCIPAL_AVATAR_ICONS.map(({ name, label, description, Icon }) => (
|
|
638
633
|
// A button drawn as a card rather than a Primer `Button`: the
|
|
639
634
|
// avatar is named under it, as the banners are under theirs.
|
|
640
635
|
// The name under a card is clipped when it is long, and a
|
|
@@ -643,25 +638,7 @@ export function PrincipalAvatarPicker({ value, onChange, disabled = false, }) {
|
|
|
643
638
|
_jsx(Tooltip, { text: description ? `${label} — ${description}` : label, direction: "n", children: _jsxs(Box, { as: "button", type: "button", "aria-label": description ? `${label} — ${description}` : label, "aria-pressed": value === name, onClick: () => {
|
|
644
639
|
onChange(name);
|
|
645
640
|
setOpen(false);
|
|
646
|
-
}, sx: {
|
|
647
|
-
display: 'block',
|
|
648
|
-
width: '100%',
|
|
649
|
-
p: 0,
|
|
650
|
-
overflow: 'hidden',
|
|
651
|
-
appearance: 'none',
|
|
652
|
-
color: 'fg.default',
|
|
653
|
-
cursor: 'pointer',
|
|
654
|
-
border: '1px solid',
|
|
655
|
-
borderRadius: 2,
|
|
656
|
-
borderColor: value === name ? 'accent.emphasis' : 'border.default',
|
|
657
|
-
bg: value === name ? 'accent.subtle' : 'canvas.default',
|
|
658
|
-
':hover': { borderColor: 'accent.emphasis' },
|
|
659
|
-
}, children: [_jsx(Box, { sx: {
|
|
660
|
-
height: 72,
|
|
661
|
-
display: 'flex',
|
|
662
|
-
alignItems: 'center',
|
|
663
|
-
justifyContent: 'center',
|
|
664
|
-
}, children: _jsx(Icon, { size: 52, themed: true, colormode: true }) }), _jsx(Text, { sx: {
|
|
641
|
+
}, display: "block", width: "100%", p: 0, overflow: "hidden", appearance: "none", color: "fg.default", cursor: "pointer", border: "1px solid", borderRadius: 2, borderColor: value === name ? 'accent.emphasis' : 'border.default', bg: value === name ? 'accent.subtle' : 'canvas.default', hover: { borderColor: 'accent.emphasis' }, children: [_jsx(Box, { height: 72, display: "flex", alignItems: "center", justifyContent: "center", children: _jsx(Icon, { size: 52, themed: true, colormode: true }) }), _jsx(Text, { sx: {
|
|
665
642
|
display: 'block',
|
|
666
643
|
px: 2,
|
|
667
644
|
py: 1,
|
|
@@ -679,7 +656,7 @@ export function PrincipalBannerPicker({ value, onChange, disabled = false, showP
|
|
|
679
656
|
const [selectedName, setSelectedName] = useState(value);
|
|
680
657
|
useEffect(() => setSelectedName(value), [value]);
|
|
681
658
|
const selected = PRINCIPAL_BANNERS.find(option => option.name === selectedName);
|
|
682
|
-
return (_jsxs(_Fragment, { children: [showPreview && selected ? (_jsx(Box, {
|
|
659
|
+
return (_jsxs(_Fragment, { children: [showPreview && selected ? (_jsx(Box, { mb: 2, children: _jsx(PrincipalBannerImage, { banner: selected.name, height: 120 }) })) : null, _jsx(Button, { type: "button", disabled: disabled, onClick: () => setOpen(true), children: selected ? `Change Banner (${selected.label})` : 'Choose Banner' }), open ? (_jsx(Dialog, { title: "Choose a Banner", onClose: () => setOpen(false), width: "xlarge",
|
|
683
660
|
// Under `&&` for the reason given on the avatar picker: a plain
|
|
684
661
|
// `sx` ties with the named width and may lose to it.
|
|
685
662
|
sx: {
|
|
@@ -687,38 +664,17 @@ export function PrincipalBannerPicker({ value, onChange, disabled = false, showP
|
|
|
687
664
|
width: 'min(960px, calc(100vw - 32px))',
|
|
688
665
|
maxWidth: 'none',
|
|
689
666
|
},
|
|
690
|
-
}, children: _jsx(Box, {
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
695
|
-
gridTemplateColumns: ['1fr', 'repeat(4, minmax(0, 1fr))'],
|
|
696
|
-
gap: 3,
|
|
697
|
-
}, children: PRINCIPAL_BANNERS.map(({ name, label, Component }) => (_jsxs(Box, { as: "button", type: "button", "aria-label": label, "aria-pressed": selectedName === name, onClick: () => {
|
|
667
|
+
}, children: _jsx(Box, { display: "grid",
|
|
668
|
+
// Four to a row, so a banner is seen against its neighbours
|
|
669
|
+
// rather than one at a time; one column on a narrow overlay,
|
|
670
|
+
// where four would be four slivers.
|
|
671
|
+
gridTemplateColumns: ['1fr', 'repeat(4, minmax(0, 1fr))'], gap: 3, children: PRINCIPAL_BANNERS.map(({ name, label, Component }) => (_jsxs(Box, { as: "button", type: "button", "aria-label": label, "aria-pressed": selectedName === name, onClick: () => {
|
|
698
672
|
setSelectedName(name);
|
|
699
673
|
onChange(name);
|
|
700
674
|
setOpen(false);
|
|
701
|
-
}, sx: {
|
|
702
|
-
display: 'block',
|
|
703
|
-
width: '100%',
|
|
704
|
-
p: 0,
|
|
705
|
-
overflow: 'hidden',
|
|
706
|
-
appearance: 'none',
|
|
707
|
-
color: 'fg.default',
|
|
708
|
-
cursor: 'pointer',
|
|
709
|
-
border: '1px solid',
|
|
710
|
-
borderRadius: 2,
|
|
711
|
-
borderColor: selectedName === name
|
|
712
|
-
? 'accent.emphasis'
|
|
713
|
-
: 'border.default',
|
|
714
|
-
bg: selectedName === name ? 'accent.subtle' : 'canvas.default',
|
|
715
|
-
textAlign: 'left',
|
|
716
|
-
':hover': { borderColor: 'accent.emphasis' },
|
|
717
|
-
}, children: [_jsx(Box, { sx: {
|
|
675
|
+
}, display: "block", width: "100%", p: 0, overflow: "hidden", appearance: "none", color: "fg.default", cursor: "pointer", border: "1px solid", borderRadius: 2, borderColor: selectedName === name ? 'accent.emphasis' : 'border.default', bg: selectedName === name ? 'accent.subtle' : 'canvas.default', textAlign: "left", hover: { borderColor: 'accent.emphasis' }, children: [_jsx(Box, { aspectRatio: "3 / 1", overflow: "hidden", sx: {
|
|
718
676
|
position: 'relative',
|
|
719
677
|
width: '100%',
|
|
720
|
-
aspectRatio: '3 / 1',
|
|
721
|
-
overflow: 'hidden',
|
|
722
678
|
'& > svg': {
|
|
723
679
|
position: 'absolute',
|
|
724
680
|
inset: 0,
|
|
@@ -28,34 +28,14 @@ export function PrincipalAvatar({ kind, avatarUrl, avatarIcon, avatarEmoji, alt,
|
|
|
28
28
|
return (_jsx(UserAvatar, { avatarUrl: avatarUrl, avatarIcon: avatarIcon, avatarEmoji: avatarEmoji, size: size, square: square, iconSize: getFallbackIconSize(size), ring: ring, className: className }));
|
|
29
29
|
}
|
|
30
30
|
if (SelectedIcon) {
|
|
31
|
-
return (_jsx(Box, { className: className,
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
alignItems: 'center',
|
|
36
|
-
justifyContent: 'center',
|
|
37
|
-
overflow: 'hidden',
|
|
38
|
-
borderRadius: square ? 2 : '50%',
|
|
39
|
-
// The disc of `UserAvatar`, for the same reason: the shape is what
|
|
40
|
-
// says "avatar", and an icon drawn on nothing shows none of it.
|
|
41
|
-
bg: 'accent.subtle',
|
|
42
|
-
...ringSx,
|
|
43
|
-
}, "aria-label": alt || `${kind} avatar`, children: _jsx(SelectedIcon, { size: getFallbackIconSize(size), themed: true, colormode: true }) }));
|
|
31
|
+
return (_jsx(Box, { className: className, width: size, height: size, display: "inline-flex", alignItems: "center", justifyContent: "center", overflow: "hidden", borderRadius: square ? 2 : '50%',
|
|
32
|
+
// The disc of `UserAvatar`, for the same reason: the shape is what
|
|
33
|
+
// says "avatar", and an icon drawn on nothing shows none of it.
|
|
34
|
+
bg: "accent.subtle", sx: ringSx, "aria-label": alt || `${kind} avatar`, children: _jsx(SelectedIcon, { size: getFallbackIconSize(size), themed: true, colormode: true }) }));
|
|
44
35
|
}
|
|
45
36
|
const iconSize = getFallbackIconSize(size);
|
|
46
37
|
const borderRadius = square ? 2 : '50%';
|
|
47
38
|
const Icon = kind === 'team' ? PeopleIcon : OrganizationIcon;
|
|
48
|
-
return (_jsx(Box, { className: className, sx: {
|
|
49
|
-
width: size,
|
|
50
|
-
height: size,
|
|
51
|
-
display: 'inline-flex',
|
|
52
|
-
alignItems: 'center',
|
|
53
|
-
justifyContent: 'center',
|
|
54
|
-
bg: 'canvas.subtle',
|
|
55
|
-
borderRadius,
|
|
56
|
-
border: '1px solid',
|
|
57
|
-
borderColor: 'border.default',
|
|
58
|
-
...ringSx,
|
|
59
|
-
}, "aria-label": alt || (kind === 'team' ? 'Team' : 'Organization'), children: _jsx(Icon, { size: iconSize }) }));
|
|
39
|
+
return (_jsx(Box, { className: className, width: size, height: size, display: "inline-flex", alignItems: "center", justifyContent: "center", bg: "canvas.subtle", borderRadius: borderRadius, border: "1px solid", borderColor: "border.default", sx: ringSx, "aria-label": alt || (kind === 'team' ? 'Team' : 'Organization'), children: _jsx(Icon, { size: iconSize }) }));
|
|
60
40
|
}
|
|
61
41
|
export default PrincipalAvatar;
|
|
@@ -4,7 +4,8 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
|
4
4
|
* Distributed under the terms of the Modified BSD License.
|
|
5
5
|
*/
|
|
6
6
|
import { useMemo } from 'react';
|
|
7
|
-
import { Box
|
|
7
|
+
import { Box } from '@datalayer/primer-addons';
|
|
8
|
+
import { Label, Text } from '@primer/react';
|
|
8
9
|
import { useCache } from '../../hooks/index.js';
|
|
9
10
|
import { useIAMStore } from '../../state/substates/index.js';
|
|
10
11
|
import { useSelectedPrincipal } from '../../hooks/useSelectedPrincipal.js';
|
|
@@ -220,17 +221,6 @@ export const PrincipalBadge = ({ principal: providedPrincipal, showPrincipalLabe
|
|
|
220
221
|
resolvedOrganization?.avatarIcon,
|
|
221
222
|
resolvedUser?.origin,
|
|
222
223
|
]);
|
|
223
|
-
return (_jsxs(Box, { sx: {
|
|
224
|
-
display: 'inline-flex',
|
|
225
|
-
alignItems: 'center',
|
|
226
|
-
gap: 2,
|
|
227
|
-
px: 2,
|
|
228
|
-
py: 1,
|
|
229
|
-
border: '1px solid',
|
|
230
|
-
borderColor: 'border.default',
|
|
231
|
-
borderRadius: 2,
|
|
232
|
-
bg: 'canvas.subtle',
|
|
233
|
-
...sx,
|
|
234
|
-
}, children: [showPrincipalLabel && (_jsx(Label, { size: "small", variant: "accent", children: principalLabel })), showApplyingToText && (_jsx(Text, { sx: { fontSize: 1, color: 'fg.muted' }, children: "Applying to" })), _jsx(Principal, { principal: principal, isAdmin: isAdmin }), showOriginLabel && principal.origin && (_jsx(Label, { size: "small", variant: "secondary", children: principal.origin }))] }));
|
|
224
|
+
return (_jsxs(Box, { display: "inline-flex", alignItems: "center", gap: 2, px: 2, py: 1, border: "1px solid", borderColor: "border.default", borderRadius: 2, bg: "canvas.subtle", sx: sx, children: [showPrincipalLabel && (_jsx(Label, { size: "small", variant: "accent", children: principalLabel })), showApplyingToText && (_jsx(Text, { sx: { fontSize: 1, color: 'fg.muted' }, children: "Applying to" })), _jsx(Principal, { principal: principal, isAdmin: isAdmin }), showOriginLabel && principal.origin && (_jsx(Label, { size: "small", variant: "secondary", children: principal.origin }))] }));
|
|
235
225
|
};
|
|
236
226
|
export default PrincipalBadge;
|
|
@@ -8,7 +8,8 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
|
8
8
|
* (user, organization, or team) with a colored visual so a user
|
|
9
9
|
* can immediately see which principal a settings page applies to.
|
|
10
10
|
*/
|
|
11
|
-
import { Box
|
|
11
|
+
import { Box } from '@datalayer/primer-addons';
|
|
12
|
+
import { Label, Text } from '@primer/react';
|
|
12
13
|
import { OrganizationIcon, PeopleIcon, PersonIcon, } from '@primer/octicons-react';
|
|
13
14
|
import { useSelectedPrincipal } from '../../hooks/useSelectedPrincipal.js';
|
|
14
15
|
import { useIAMStore } from '../../state/substates/index.js';
|
|
@@ -39,33 +40,7 @@ export const PrincipalBanner = ({ caption, rightContent, }) => {
|
|
|
39
40
|
? 'attention.muted'
|
|
40
41
|
: 'accent.muted';
|
|
41
42
|
const fg = isOrganization ? 'done.fg' : isTeam ? 'attention.fg' : 'accent.fg';
|
|
42
|
-
return (_jsxs(Box, { sx: {
|
|
43
|
-
display: 'flex',
|
|
44
|
-
alignItems: 'center',
|
|
45
|
-
gap: 3,
|
|
46
|
-
p: 3,
|
|
47
|
-
border: '1px solid',
|
|
48
|
-
borderColor,
|
|
49
|
-
borderRadius: 2,
|
|
50
|
-
bg,
|
|
51
|
-
}, children: [_jsx(Box, { sx: {
|
|
52
|
-
width: 40,
|
|
53
|
-
height: 40,
|
|
54
|
-
display: 'flex',
|
|
55
|
-
alignItems: 'center',
|
|
56
|
-
justifyContent: 'center',
|
|
57
|
-
borderRadius: '50%',
|
|
58
|
-
bg: 'canvas.default',
|
|
59
|
-
border: '1px solid',
|
|
60
|
-
borderColor,
|
|
61
|
-
color: fg,
|
|
62
|
-
flex: '0 0 auto',
|
|
63
|
-
}, children: _jsx(Icon, { size: 20 }) }), _jsxs(Box, { sx: { minWidth: 0, flex: 1 }, children: [_jsxs(Box, { sx: {
|
|
64
|
-
display: 'flex',
|
|
65
|
-
alignItems: 'center',
|
|
66
|
-
gap: 2,
|
|
67
|
-
flexWrap: 'wrap',
|
|
68
|
-
}, children: [_jsx(Text, { sx: {
|
|
43
|
+
return (_jsxs(Box, { display: "flex", alignItems: "center", gap: 3, p: 3, border: "1px solid", borderColor: borderColor, borderRadius: 2, bg: bg, children: [_jsx(Box, { width: 40, height: 40, display: "flex", alignItems: "center", justifyContent: "center", borderRadius: "50%", bg: "canvas.default", border: "1px solid", borderColor: borderColor, color: fg, flex: "0 0 auto", children: _jsx(Icon, { size: 20 }) }), _jsxs(Box, { minWidth: 0, flex: 1, children: [_jsxs(Box, { display: "flex", alignItems: "center", gap: 2, flexWrap: "wrap", children: [_jsx(Text, { sx: {
|
|
69
44
|
color: 'fg.muted',
|
|
70
45
|
fontSize: 0,
|
|
71
46
|
textTransform: 'uppercase',
|
|
@@ -76,9 +51,6 @@ export const PrincipalBanner = ({ caption, rightContent, }) => {
|
|
|
76
51
|
? 'Organization'
|
|
77
52
|
: isTeam
|
|
78
53
|
? 'Team'
|
|
79
|
-
: 'User' }), caption && (_jsx(Text, { as: "p", sx: { m: 0, mt: 1, color: 'fg.muted', fontSize: 1 }, children: caption }))] }), rightContent ? (_jsx(Box, {
|
|
80
|
-
flex: ['1 1 100%', '0 0 auto'],
|
|
81
|
-
width: ['100%', 'min(640px, 58%)'],
|
|
82
|
-
}, children: rightContent })) : null] }));
|
|
54
|
+
: 'User' }), caption && (_jsx(Text, { as: "p", sx: { m: 0, mt: 1, color: 'fg.muted', fontSize: 1 }, children: caption }))] }), rightContent ? (_jsx(Box, { flex: ['1 1 100%', '0 0 auto'], width: ['100%', 'min(640px, 58%)'], children: rightContent })) : null] }));
|
|
83
55
|
};
|
|
84
56
|
export default PrincipalBanner;
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
-
import {
|
|
2
|
+
import { Box } from '@datalayer/primer-addons';
|
|
3
|
+
import { ActionMenu, Button, Label, Text, ThemeProvider } from '@primer/react';
|
|
3
4
|
import { useNavigate } from '../../hooks/index.js';
|
|
4
5
|
import { PrincipalAvatar } from './PrincipalAvatar.js';
|
|
5
6
|
import { displayHandleText } from '../display/DisplayHandle.js';
|
|
@@ -139,18 +140,13 @@ export function PrincipalDetailsCard({ kind, uid, displayName, name, description
|
|
|
139
140
|
const organizationPath = teamOrganizationHandle
|
|
140
141
|
? `/${teamOrganizationHandle.replace(/^@+/, '')}`
|
|
141
142
|
: '';
|
|
142
|
-
return (_jsxs(Box, {
|
|
143
|
+
return (_jsxs(Box, { display: "grid", gap: 3, p: 4, minWidth: 420, children: [_jsxs(Box, { display: "flex", alignItems: "center", gap: 2, children: [_jsx(PrincipalAvatar, { kind: kind, avatarUrl: avatarUrl, avatarIcon: avatarIcon, avatarEmoji: avatarEmoji, alt: normalizedDisplayName, size: 40,
|
|
143
144
|
// The card sets the avatar on its own ground, the same colour
|
|
144
145
|
// the avatar itself is on: without an edge of its own it has
|
|
145
146
|
// no visible shape at all. Round, and ringed.
|
|
146
|
-
square: false, ring: true }), _jsxs(Box, {
|
|
147
|
+
square: false, ring: true }), _jsxs(Box, { display: "grid", gap: 0.5, children: [_jsx(Text, { sx: { fontWeight: 'semibold' }, children: normalizedDisplayName }), kind === 'team' ? (teamHandleOnly ? (_jsxs(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: [displayHandleText(teamHandleOnly), teamOrganizationHandle
|
|
147
148
|
? ` · @${teamOrganizationHandle.replace(/^@+/, '')}`
|
|
148
|
-
: ''] })) : null) : resolvedHandle ? (_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: displayHandleText(resolvedHandle) })) : null] })] }), _jsxs(Box, { sx: {
|
|
149
|
-
display: 'grid',
|
|
150
|
-
gridTemplateColumns: '110px 1fr',
|
|
151
|
-
gap: 1,
|
|
152
|
-
alignItems: 'baseline',
|
|
153
|
-
}, children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Kind" }), _jsx(Text, { sx: { fontSize: 1 }, children: kind }), resolvedHandle && kind !== 'team' ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Handle" }), _jsx(Text, { sx: { fontSize: 1 }, children: displayHandleText(resolvedHandle) })] })) : null, normalizedUid ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "UID" }), _jsx(Text, { sx: { fontSize: 1 }, children: normalizedUid })] })) : null, kind === 'personal' ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "First name" }), _jsx(Text, { sx: { fontSize: 1 }, children: firstName || 'N/A' }), _jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Last name" }), _jsx(Text, { sx: { fontSize: 1 }, children: lastName || 'N/A' }), email ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Email" }), _jsx(Text, { sx: { fontSize: 1 }, children: email })] })) : null, _jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Origin" }), _jsx(Label, { size: "small", variant: "secondary", title: normalizedOrigin, sx: {
|
|
149
|
+
: ''] })) : null) : resolvedHandle ? (_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: displayHandleText(resolvedHandle) })) : null] })] }), _jsxs(Box, { display: "grid", gridTemplateColumns: "110px 1fr", gap: 1, alignItems: "baseline", children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Kind" }), _jsx(Text, { sx: { fontSize: 1 }, children: kind }), resolvedHandle && kind !== 'team' ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Handle" }), _jsx(Text, { sx: { fontSize: 1 }, children: displayHandleText(resolvedHandle) })] })) : null, normalizedUid ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "UID" }), _jsx(Text, { sx: { fontSize: 1 }, children: normalizedUid })] })) : null, kind === 'personal' ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "First name" }), _jsx(Text, { sx: { fontSize: 1 }, children: firstName || 'N/A' }), _jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Last name" }), _jsx(Text, { sx: { fontSize: 1 }, children: lastName || 'N/A' }), email ? (_jsxs(_Fragment, { children: [_jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Email" }), _jsx(Text, { sx: { fontSize: 1 }, children: email })] })) : null, _jsx(Text, { sx: { fontSize: 0, color: 'fg.muted' }, children: "Origin" }), _jsx(Label, { size: "small", variant: "secondary", title: normalizedOrigin, sx: {
|
|
154
150
|
justifySelf: 'start',
|
|
155
151
|
width: 'fit-content',
|
|
156
152
|
maxWidth: '100%',
|
|
@@ -166,7 +162,7 @@ export function PrincipalDetailsCard({ kind, uid, displayName, name, description
|
|
|
166
162
|
overflow: 'hidden',
|
|
167
163
|
textOverflow: 'ellipsis',
|
|
168
164
|
whiteSpace: 'nowrap',
|
|
169
|
-
}, children: normalizedOrigin })] }))] }), _jsxs(Box, {
|
|
165
|
+
}, children: normalizedOrigin })] }))] }), _jsxs(Box, { display: "flex", justifyContent: "flex-end", gap: 2, children: [kind === 'team' && organizationPath ? (_jsx(Button, { size: "small", variant: "invisible", onClick: () => go(organizationPath), children: "View Organization" })) : null, _jsx(Button, { size: "small", onClick: () => go(targetPath), disabled: !targetPath, children: "View Profile" })] })] }));
|
|
170
166
|
}
|
|
171
167
|
/**
|
|
172
168
|
* A principal's details, shown from a click on their name.
|
|
@@ -179,18 +175,6 @@ export function PrincipalDetailsOverlay(props) {
|
|
|
179
175
|
normalize(props.handle) ||
|
|
180
176
|
normalize(props.uid) ||
|
|
181
177
|
'Principal';
|
|
182
|
-
return (_jsx(ThemeProvider, { children: _jsxs(ActionMenu, { children: [_jsx(ActionMenu.Anchor, { children: _jsx(Box, { as: "button", type: "button",
|
|
183
|
-
fontWeight: 'semibold',
|
|
184
|
-
color: 'accent.fg',
|
|
185
|
-
textDecoration: 'underline',
|
|
186
|
-
background: 'transparent',
|
|
187
|
-
border: 0,
|
|
188
|
-
padding: 0,
|
|
189
|
-
margin: 0,
|
|
190
|
-
cursor: 'pointer',
|
|
191
|
-
':hover': {
|
|
192
|
-
textDecoration: 'underline',
|
|
193
|
-
},
|
|
194
|
-
}, children: normalizedDisplayName }) }), _jsx(ActionMenu.Overlay, { width: "large", children: _jsx(PrincipalDetailsCard, { ...props }) })] }) }));
|
|
178
|
+
return (_jsx(ThemeProvider, { children: _jsxs(ActionMenu, { children: [_jsx(ActionMenu.Anchor, { children: _jsx(Box, { as: "button", type: "button", fontWeight: "semibold", color: "accent.fg", textDecoration: "underline", background: "transparent", border: 0, padding: 0, margin: 0, cursor: "pointer", hover: { textDecoration: 'underline' }, children: normalizedDisplayName }) }), _jsx(ActionMenu.Overlay, { width: "large", children: _jsx(PrincipalDetailsCard, { ...props }) })] }) }));
|
|
195
179
|
}
|
|
196
180
|
export default PrincipalDetailsOverlay;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { useCallback, useEffect, useRef, useState } from 'react';
|
|
3
|
-
import {
|
|
3
|
+
import { Box } from '@datalayer/primer-addons';
|
|
4
|
+
import { AnchoredOverlay, ThemeProvider } from '@primer/react';
|
|
4
5
|
import { PrincipalDetailsCard, } from './PrincipalDetailsOverlay.js';
|
|
5
6
|
/** How long the card lingers after the pointer leaves, to let it be entered. */
|
|
6
7
|
const HIDE_DELAY_MS = 200;
|
|
@@ -30,23 +31,19 @@ export function PrincipalHoverCard({ children, className, ...principal }) {
|
|
|
30
31
|
onMouseEnter: show,
|
|
31
32
|
onMouseLeave: hide,
|
|
32
33
|
preventFocusOnOpen: true,
|
|
33
|
-
}, renderAnchor: anchorProps => (_jsx(Box
|
|
34
|
+
}, renderAnchor: anchorProps => (_jsx(Box
|
|
35
|
+
// Primer's anchor props, as the record of props Box takes.
|
|
36
|
+
, { ...anchorProps, className: [className, anchorProps.className]
|
|
34
37
|
.filter(Boolean)
|
|
35
|
-
.join(' '), onMouseEnter: show, onMouseLeave: hide, onFocus: show, onBlur: hide,
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
* square one clipped a round avatar into a square. It takes the
|
|
46
|
-
* shape of what it wraps.
|
|
47
|
-
*/
|
|
48
|
-
borderRadius: '50%',
|
|
49
|
-
overflow: 'hidden',
|
|
50
|
-
}, children: children })), children: _jsx(ThemeProvider, { children: _jsx(PrincipalDetailsCard, { ...principal }) }) }));
|
|
38
|
+
.join(' '), onMouseEnter: show, onMouseLeave: hide, onFocus: show, onBlur: hide, display: "flex", alignItems: "center", justifyContent: "center", cursor: "pointer",
|
|
39
|
+
/*
|
|
40
|
+
* Round, like the face it holds.
|
|
41
|
+
*
|
|
42
|
+
* This box stands between the stack and the avatar — it is the
|
|
43
|
+
* element `AvatarStack` sizes and clips as one of its items — so a
|
|
44
|
+
* square one clipped a round avatar into a square. It takes the
|
|
45
|
+
* shape of what it wraps.
|
|
46
|
+
*/
|
|
47
|
+
borderRadius: "50%", overflow: "hidden", children: children })), children: _jsx(ThemeProvider, { children: _jsx(PrincipalDetailsCard, { ...principal }) }) }));
|
|
51
48
|
}
|
|
52
49
|
export default PrincipalHoverCard;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { useEffect, useMemo, useState } from 'react';
|
|
3
|
-
import {
|
|
3
|
+
import { Box } from '@datalayer/primer-addons';
|
|
4
|
+
import { ActionList, ActionMenu, Button, Text, ThemeProvider, } from '@primer/react';
|
|
4
5
|
import { OrganizationIcon, PeopleIcon, PersonIcon, TriangleDownIcon, } from '@primer/octicons-react';
|
|
5
6
|
import { useCache, useAuthorization } from '../../hooks/index.js';
|
|
6
7
|
import { useCoreStore } from '../../state/index.js';
|
|
@@ -198,38 +199,12 @@ export function PrincipalSwitcherMenu({ maxLabelChars = 48, fullWidth = true, sh
|
|
|
198
199
|
color: 'accent.fg',
|
|
199
200
|
fontWeight: 'semibold',
|
|
200
201
|
};
|
|
201
|
-
return (_jsx(ThemeProvider, { children: _jsxs(ActionMenu, { children: [_jsx(ActionMenu.Anchor, { children: showClosedBorder ? (_jsxs(Box, { as: "button", type: "button", "aria-label": "Switch principal",
|
|
202
|
-
width: fullWidth ? '100%' : 'auto',
|
|
203
|
-
boxSizing: 'border-box',
|
|
204
|
-
px: 2,
|
|
205
|
-
py: 2,
|
|
206
|
-
fontSize: 0,
|
|
207
|
-
display: 'flex',
|
|
208
|
-
alignItems: 'center',
|
|
209
|
-
justifyContent: 'space-between',
|
|
210
|
-
gap: 2,
|
|
202
|
+
return (_jsx(ThemeProvider, { children: _jsxs(ActionMenu, { children: [_jsx(ActionMenu.Anchor, { children: showClosedBorder ? (_jsxs(Box, { as: "button", type: "button", "aria-label": "Switch principal", width: fullWidth ? '100%' : 'auto', boxSizing: "border-box", px: 2, py: 2, fontSize: 0, display: "flex", alignItems: "center", justifyContent: "space-between", gap: 2, bg: "canvas.subtle", border: "1px solid", borderColor: "border.default", borderRadius: 2, cursor: "pointer", textAlign: "left", transition: "background-color 120ms ease", hover: { bg: 'canvas.subtle' }, focusVisible: {
|
|
211
203
|
bg: 'canvas.subtle',
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
textAlign: 'left',
|
|
217
|
-
transition: 'background-color 120ms ease',
|
|
218
|
-
':hover': {
|
|
219
|
-
bg: 'canvas.subtle',
|
|
220
|
-
},
|
|
221
|
-
':focus-visible': {
|
|
222
|
-
bg: 'canvas.subtle',
|
|
223
|
-
outline: '2px solid',
|
|
224
|
-
outlineColor: 'accent.emphasis',
|
|
225
|
-
outlineOffset: '2px',
|
|
226
|
-
},
|
|
227
|
-
}, children: [_jsx(Box, { sx: {
|
|
228
|
-
display: 'inline-flex',
|
|
229
|
-
alignItems: 'center',
|
|
230
|
-
color: 'fg.muted',
|
|
231
|
-
flexShrink: 0,
|
|
232
|
-
}, children: selectedPrincipalKind === 'organization' ? (_jsx(PeopleIcon, { size: 16 })) : selectedPrincipalKind === 'team' ? (_jsx(OrganizationIcon, { size: 16 })) : (_jsx(PersonIcon, { size: 16 })) }), _jsx(Box, { sx: { minWidth: 0, flex: 1 }, children: _jsx(Text, { sx: {
|
|
204
|
+
outline: '2px solid',
|
|
205
|
+
outlineColor: 'accent.emphasis',
|
|
206
|
+
outlineOffset: '2px',
|
|
207
|
+
}, children: [_jsx(Box, { display: "inline-flex", alignItems: "center", color: "fg.muted", flexShrink: 0, children: selectedPrincipalKind === 'organization' ? (_jsx(PeopleIcon, { size: 16 })) : selectedPrincipalKind === 'team' ? (_jsx(OrganizationIcon, { size: 16 })) : (_jsx(PersonIcon, { size: 16 })) }), _jsx(Box, { minWidth: 0, flex: 1, children: _jsx(Text, { sx: {
|
|
233
208
|
display: 'block',
|
|
234
209
|
color: 'accent.fg',
|
|
235
210
|
fontWeight: 'semibold',
|
|
@@ -238,35 +213,10 @@ export function PrincipalSwitcherMenu({ maxLabelChars = 48, fullWidth = true, sh
|
|
|
238
213
|
overflow: 'hidden',
|
|
239
214
|
textOverflow: 'ellipsis',
|
|
240
215
|
maxWidth: '100%',
|
|
241
|
-
}, children: selectedPrincipalLabelClosed }) }), isPlatformAdmin && isCurrentUserPrincipal ? (_jsx(Box, { sx: {
|
|
242
|
-
flexShrink: 0,
|
|
243
|
-
display: 'inline-flex',
|
|
244
|
-
alignItems: 'center',
|
|
245
|
-
}, children: _jsx(AdminLabel, {}) })) : null, _jsx(Box, { sx: {
|
|
246
|
-
display: 'inline-flex',
|
|
247
|
-
alignItems: 'center',
|
|
248
|
-
color: 'fg.muted',
|
|
249
|
-
flexShrink: 0,
|
|
250
|
-
ml: isPlatformAdmin && isCurrentUserPrincipal ? 1 : 0,
|
|
251
|
-
}, children: _jsx(TriangleDownIcon, { size: 12 }) })] })) : (_jsx(Button, { variant: "invisible", size: "small", "aria-label": "Switch principal", trailingVisual: TriangleDownIcon, sx: {
|
|
216
|
+
}, children: selectedPrincipalLabelClosed }) }), isPlatformAdmin && isCurrentUserPrincipal ? (_jsx(Box, { flexShrink: 0, display: "inline-flex", alignItems: "center", children: _jsx(AdminLabel, {}) })) : null, _jsx(Box, { display: "inline-flex", alignItems: "center", color: "fg.muted", flexShrink: 0, ml: isPlatformAdmin && isCurrentUserPrincipal ? 1 : 0, children: _jsx(TriangleDownIcon, { size: 12 }) })] })) : (_jsx(Button, { variant: "invisible", size: "small", "aria-label": "Switch principal", trailingVisual: TriangleDownIcon, sx: {
|
|
252
217
|
maxWidth: fullWidth ? '100%' : ['200px', '260px', '360px'],
|
|
253
218
|
width: fullWidth ? '100%' : 'auto',
|
|
254
|
-
}, children: _jsxs(Box, { sx: {
|
|
255
|
-
display: 'inline-flex',
|
|
256
|
-
alignItems: 'center',
|
|
257
|
-
gap: 1,
|
|
258
|
-
minWidth: 0,
|
|
259
|
-
}, children: [_jsx(Box, { sx: {
|
|
260
|
-
display: 'inline-flex',
|
|
261
|
-
alignItems: 'center',
|
|
262
|
-
color: 'fg.muted',
|
|
263
|
-
flexShrink: 0,
|
|
264
|
-
}, children: selectedPrincipalKind === 'organization' ? (_jsx(PeopleIcon, { size: 16 })) : selectedPrincipalKind === 'team' ? (_jsx(OrganizationIcon, { size: 16 })) : (_jsx(PersonIcon, { size: 16 })) }), _jsx(Box, { sx: {
|
|
265
|
-
minWidth: 0,
|
|
266
|
-
overflow: 'hidden',
|
|
267
|
-
textOverflow: 'ellipsis',
|
|
268
|
-
whiteSpace: 'nowrap',
|
|
269
|
-
}, children: _jsx(Text, { sx: {
|
|
219
|
+
}, children: _jsxs(Box, { display: "inline-flex", alignItems: "center", gap: 1, minWidth: 0, children: [_jsx(Box, { display: "inline-flex", alignItems: "center", color: "fg.muted", flexShrink: 0, children: selectedPrincipalKind === 'organization' ? (_jsx(PeopleIcon, { size: 16 })) : selectedPrincipalKind === 'team' ? (_jsx(OrganizationIcon, { size: 16 })) : (_jsx(PersonIcon, { size: 16 })) }), _jsx(Box, { minWidth: 0, overflow: "hidden", textOverflow: "ellipsis", whiteSpace: "nowrap", children: _jsx(Text, { sx: {
|
|
270
220
|
color: 'accent.fg',
|
|
271
221
|
fontWeight: 'semibold',
|
|
272
222
|
}, children: selectedPrincipalLabelClosed }) }), isPlatformAdmin && isCurrentUserPrincipal ? (_jsx(AdminLabel, {})) : null] }) })) }), _jsx(ActionMenu.Overlay, { width: "large", children: _jsxs(ActionList, { selectionVariant: "single", children: [_jsxs(ActionList.Group, { children: [_jsx(ActionList.GroupHeading, { children: "Personal" }), _jsxs(ActionList.Item, { disabled: isCurrentUserPrincipal, selected: isCurrentUserPrincipal, sx: isCurrentUserPrincipal ? selectedItemSx : undefined, onSelect: () => {
|
|
@@ -276,16 +226,10 @@ export function PrincipalSwitcherMenu({ maxLabelChars = 48, fullWidth = true, sh
|
|
|
276
226
|
if (personalUid && personalHandle) {
|
|
277
227
|
selectUser(personalUid, personalHandle);
|
|
278
228
|
}
|
|
279
|
-
}, children: [_jsx(ActionList.LeadingVisual, { children: _jsx(UserAvatar, { avatarUrl: user?.avatarUrl, avatarIcon: user?.avatarIcon, size: 16, square: false, ring: true }) }), _jsxs(Box, { as: "span",
|
|
280
|
-
display: 'block',
|
|
281
|
-
minWidth: 0,
|
|
282
|
-
overflow: 'hidden',
|
|
283
|
-
textOverflow: 'ellipsis',
|
|
284
|
-
whiteSpace: 'nowrap',
|
|
285
|
-
}, children: [String(user?.friendlyName ||
|
|
229
|
+
}, children: [_jsx(ActionList.LeadingVisual, { children: _jsx(UserAvatar, { avatarUrl: user?.avatarUrl, avatarIcon: user?.avatarIcon, size: 16, square: false, ring: true }) }), _jsxs(Box, { as: "span", display: "block", minWidth: 0, overflow: "hidden", textOverflow: "ellipsis", whiteSpace: "nowrap", children: [String(user?.friendlyName ||
|
|
286
230
|
user?.displayName ||
|
|
287
231
|
personalHandle ||
|
|
288
|
-
'Me').trim(), _jsxs(Box, { as: "span",
|
|
232
|
+
'Me').trim(), _jsxs(Box, { as: "span", color: "fg.muted", children: [' ', "\u00B7 ", _jsx(DisplayHandle, { handle: personalHandle || 'me' })] })] }), isPlatformAdmin ? (_jsx(ActionList.TrailingVisual, { children: _jsx(AdminLabel, {}) })) : null] })] }), _jsxs(ActionList.Group, { children: [_jsx(ActionList.GroupHeading, { children: "Organizations" }), organizations.length === 0 ? (_jsx(ActionList.Item, { disabled: true, children: "No organizations" })) : (organizations.map((organization) => {
|
|
289
233
|
const organizationUid = getOrganizationUid(organization);
|
|
290
234
|
const isCurrentOrganizationPrincipal = selectedPrincipalKind === 'organization' &&
|
|
291
235
|
selectedPrincipalUid === organizationUid;
|
|
@@ -298,17 +242,11 @@ export function PrincipalSwitcherMenu({ maxLabelChars = 48, fullWidth = true, sh
|
|
|
298
242
|
if (organizationUid && organization.handle) {
|
|
299
243
|
selectOrganization(organizationUid, organization.handle);
|
|
300
244
|
}
|
|
301
|
-
}, children: [_jsx(ActionList.LeadingVisual, { children: _jsx(PeopleIcon, {}) }), _jsxs(Box, { as: "span", title: displayHandleText(organization.handle),
|
|
302
|
-
display: 'block',
|
|
303
|
-
minWidth: 0,
|
|
304
|
-
overflow: 'hidden',
|
|
305
|
-
textOverflow: 'ellipsis',
|
|
306
|
-
whiteSpace: 'nowrap',
|
|
307
|
-
}, children: [String(organization?.display_name ||
|
|
245
|
+
}, children: [_jsx(ActionList.LeadingVisual, { children: _jsx(PeopleIcon, {}) }), _jsxs(Box, { as: "span", title: displayHandleText(organization.handle), display: "block", minWidth: 0, overflow: "hidden", textOverflow: "ellipsis", whiteSpace: "nowrap", children: [String(organization?.display_name ||
|
|
308
246
|
organization?.displayName ||
|
|
309
247
|
organization?.name ||
|
|
310
248
|
organization?.handle ||
|
|
311
|
-
'Organization').trim(), _jsxs(Box, { as: "span",
|
|
249
|
+
'Organization').trim(), _jsxs(Box, { as: "span", color: "fg.muted", children: [' ', "\u00B7 ", _jsx(DisplayHandle, { handle: organization.handle })] })] })] }, organizationUid));
|
|
312
250
|
}))] }), _jsxs(ActionList.Group, { children: [_jsx(ActionList.GroupHeading, { children: "Teams" }), teams.length === 0 ? (_jsx(ActionList.Item, { disabled: true, children: "No teams" })) : (teams.map(team => {
|
|
313
251
|
const isCurrentTeamPrincipal = selectedPrincipalKind === 'team' &&
|
|
314
252
|
selectedPrincipalUid === team.uid;
|
|
@@ -320,16 +258,10 @@ export function PrincipalSwitcherMenu({ maxLabelChars = 48, fullWidth = true, sh
|
|
|
320
258
|
return;
|
|
321
259
|
}
|
|
322
260
|
selectTeam(team, orgHandle);
|
|
323
|
-
}, children: [_jsx(ActionList.LeadingVisual, { children: _jsx(OrganizationIcon, {}) }), _jsxs(Box, { as: "span", title: `${displayHandleText(orgHandle)}/${displayHandleText(team.handle, { withAt: false })}`,
|
|
324
|
-
display: 'block',
|
|
325
|
-
minWidth: 0,
|
|
326
|
-
overflow: 'hidden',
|
|
327
|
-
textOverflow: 'ellipsis',
|
|
328
|
-
whiteSpace: 'nowrap',
|
|
329
|
-
}, children: [String(team.displayName ||
|
|
261
|
+
}, children: [_jsx(ActionList.LeadingVisual, { children: _jsx(OrganizationIcon, {}) }), _jsxs(Box, { as: "span", title: `${displayHandleText(orgHandle)}/${displayHandleText(team.handle, { withAt: false })}`, display: "block", minWidth: 0, overflow: "hidden", textOverflow: "ellipsis", whiteSpace: "nowrap", children: [String(team.displayName ||
|
|
330
262
|
team.name ||
|
|
331
263
|
team.handle ||
|
|
332
|
-
'Team').trim(), _jsxs(Box, { as: "span",
|
|
264
|
+
'Team').trim(), _jsxs(Box, { as: "span", color: "fg.muted", children: [' ', "\u00B7 ", _jsx(DisplayHandle, { handle: orgHandle }), "/", _jsx(DisplayHandle, { handle: team.handle, withAt: false })] })] })] }, team.uid));
|
|
333
265
|
}))] })] }) })] }) }));
|
|
334
266
|
}
|
|
335
267
|
export default PrincipalSwitcherMenu;
|