Skip to content

Commit

Permalink
Merge pull request prometheus#15096 from prometheus/notification-styl…
Browse files Browse the repository at this point in the history
…e-cleanups

Style cleanups, mostly for web notifications and startup alert
  • Loading branch information
juliusv authored Oct 4, 2024
2 parents 4fc7b88 + 3d2194f commit a1c2f59
Show file tree
Hide file tree
Showing 4 changed files with 121 additions and 63 deletions.
136 changes: 90 additions & 46 deletions web/ui/mantine-ui/src/components/NotificationsIcon.tsx
Original file line number Diff line number Diff line change
@@ -1,61 +1,105 @@
import { ActionIcon, Indicator, Popover, Card, Text, Stack, ScrollArea, Group } from "@mantine/core";
import { IconBell, IconAlertTriangle, IconNetworkOff } from "@tabler/icons-react";
import { useNotifications } from '../state/useNotifications';
import {
ActionIcon,
Indicator,
Popover,
Card,
Text,
Stack,
ScrollArea,
Group,
rem,
} from "@mantine/core";
import {
IconAlertTriangle,
IconNetworkOff,
IconMessageExclamation,
} from "@tabler/icons-react";
import { useNotifications } from "../state/useNotifications";
import { actionIconStyle } from "../styles";
import { useSettings } from '../state/settingsSlice';
import { useSettings } from "../state/settingsSlice";
import { formatTimestamp } from "../lib/formatTime";

const NotificationsIcon = () => {
const { notifications, isConnectionError } = useNotifications();
const { useLocalTime } = useSettings();

return (
(notifications.length === 0 && !isConnectionError) ? null : (
<Indicator
color={"red"}
size={16}
label={isConnectionError ? "!" : notifications.length}
>
<Popover position="bottom-end" shadow="md" withArrow>
<Popover.Target>
<ActionIcon color="gray" title="Notifications" aria-label="Notifications" size={32}>
<IconBell style={actionIconStyle}/>
</ActionIcon>
</Popover.Target>
return notifications.length === 0 && !isConnectionError ? null : (
<Indicator
color={"red"}
size={16}
label={isConnectionError ? "!" : notifications.length}
>
<Popover position="bottom-end" shadow="md" withArrow>
<Popover.Target>
<ActionIcon
color="gray"
title="Notifications"
aria-label="Notifications"
size={32}
>
<IconMessageExclamation style={actionIconStyle} />
</ActionIcon>
</Popover.Target>

<Popover.Dropdown>
<Stack gap="xs">
<Text fw={700} size="xs" color="dimmed" ta="center">Notifications</Text>
<ScrollArea.Autosize mah={200}>
{ isConnectionError ? (
<Card p="xs" color="red">
<Group wrap="nowrap">
<IconNetworkOff color="red" size={20} />
<Stack gap="0">
<Text size="sm" fw={500}>Real-time notifications interrupted.</Text>
<Text size="xs" color="dimmed">Please refresh the page or check your connection.</Text>
</Stack>
</Group>
</Card>
) : notifications.length === 0 ? (
<Text ta="center" color="dimmed">No notifications</Text>
) : (notifications.map((notification, index) => (
<Popover.Dropdown>
<Stack gap="xs">
<Text fw={700} size="xs" c="dimmed" ta="center">
Notifications
</Text>
<ScrollArea.Autosize mah={200}>
{isConnectionError ? (
<Card p="xs" color="red">
<Group wrap="nowrap">
<IconNetworkOff
color="red"
style={{ width: rem(20), height: rem(20) }}
/>
<Stack gap="0">
<Text size="sm" fw={500}>
Real-time notifications interrupted.
</Text>
<Text size="xs" c="dimmed">
Please refresh the page or check your connection.
</Text>
</Stack>
</Group>
</Card>
) : notifications.length === 0 ? (
<Text ta="center" c="dimmed">
No notifications
</Text>
) : (
notifications.map((notification, index) => (
<Card key={index} p="xs">
<Group wrap="nowrap">
<IconAlertTriangle color="red" size={20} />
<Stack style={{ maxWidth: 250 }} gap={0}>
<Text size="sm" fw={500}>{notification.text}</Text>
<Text size="xs" color="dimmed">{formatTimestamp(new Date(notification.date).valueOf() / 1000, useLocalTime)}</Text>
<Group wrap="nowrap" align="flex-start">
<IconAlertTriangle
color="red"
style={{
width: rem(20),
height: rem(20),
marginTop: rem(3),
}}
/>
<Stack maw={250} gap={5}>
<Text size="sm" fw={500}>
{notification.text}
</Text>
<Text size="xs" c="dimmed">
{formatTimestamp(
new Date(notification.date).valueOf() / 1000,
useLocalTime
)}
</Text>
</Stack>
</Group>
</Card>
)))}
</ScrollArea.Autosize>
</Stack>
</Popover.Dropdown>
</Popover>
</Indicator>
)
))
)}
</ScrollArea.Autosize>
</Stack>
</Popover.Dropdown>
</Popover>
</Indicator>
);
};

Expand Down
34 changes: 20 additions & 14 deletions web/ui/mantine-ui/src/components/ReadinessWrapper.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { useAppDispatch } from "../state/hooks";
import { updateSettings, useSettings } from "../state/settingsSlice";
import { useSuspenseAPIQuery } from "../api/api";
import { WALReplayStatus } from "../api/responseTypes/walreplay";
import { Progress, Alert } from "@mantine/core";
import { Progress, Alert, Stack } from "@mantine/core";
import { useSuspenseQuery } from "@tanstack/react-query";

const STATUS_STARTING = "is starting up...";
Expand Down Expand Up @@ -57,14 +57,12 @@ const ReadinessLoader: FC = () => {
// Only call WAL replay status API if the service is starting up.
const shouldQueryWALReplay = statusMessage === STATUS_STARTING;

const {
data: walData,
isSuccess: walSuccess,
} = useSuspenseAPIQuery<WALReplayStatus>({
path: "/status/walreplay",
key: ["walreplay", queryKey],
enabled: shouldQueryWALReplay, // Only enabled when service is starting up.
});
const { data: walData, isSuccess: walSuccess } =
useSuspenseAPIQuery<WALReplayStatus>({
path: "/status/walreplay",
key: ["walreplay", queryKey],
enabled: shouldQueryWALReplay, // Only enabled when service is starting up.
});

useEffect(() => {
if (ready) {
Expand All @@ -80,24 +78,32 @@ const ReadinessLoader: FC = () => {
return (
<Alert
color="yellow"
title={"Prometheus " + (agentMode && "Agent "||"") + (statusMessage || STATUS_LOADING)}
icon={<IconAlertTriangle/>}
title={
"Prometheus " +
((agentMode && "Agent ") || "") +
(statusMessage || STATUS_LOADING)
}
icon={<IconAlertTriangle />}
maw={500}
mx="auto"
mt="lg"
>
{shouldQueryWALReplay && walSuccess && walData && (
<>
<Stack>
<strong>
Replaying WAL ({walData.data.current}/{walData.data.max})
</strong>
<Progress
size="xl"
animated
color="yellow"
value={((walData.data.current - walData.data.min + 1) / (walData.data.max - walData.data.min + 1)) * 100}
value={
((walData.data.current - walData.data.min + 1) /
(walData.data.max - walData.data.min + 1)) *
100
}
/>
</>
</Stack>
)}
</Alert>
);
Expand Down
9 changes: 7 additions & 2 deletions web/ui/mantine-ui/src/pages/RulesPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import {
Badge,
Card,
Group,
rem,
Stack,
Text,
Tooltip,
Expand Down Expand Up @@ -135,11 +136,15 @@ export default function RulesPage() {
<Group gap="xs" wrap="nowrap">
{r.type === "alerting" ? (
<Tooltip label="Alerting rule" withArrow>
<IconBell size={15} />
<IconBell
style={{ width: rem(15), height: rem(15) }}
/>
</Tooltip>
) : (
<Tooltip label="Recording rule" withArrow>
<IconTimeline size={15} />
<IconTimeline
style={{ width: rem(15), height: rem(15) }}
/>
</Tooltip>
)}
<Text>{r.name}</Text>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import {
Skeleton,
Stack,
Table,
rem,
} from "@mantine/core";
import { escapeString } from "../../../lib/escapeString";
import serializeNode from "../../../promql/serialize";
Expand Down Expand Up @@ -326,7 +327,9 @@ const LabelsExplorer: FC<LabelsExplorerProps> = ({
title="Cancel"
style={{ flexShrink: 0 }}
>
<IconX size={18} />
<IconX
style={{ width: rem(18), height: rem(18) }}
/>
</Button>
</Group>
) : (
Expand Down

0 comments on commit a1c2f59

Please sign in to comment.