Skip to content

Commit

Permalink
feat: new metric widgets
Browse files Browse the repository at this point in the history
Signed-off-by: 35C4n0r <[email protected]>
  • Loading branch information
35C4n0r committed Oct 21, 2024
1 parent 4765d2e commit ad669ae
Show file tree
Hide file tree
Showing 8 changed files with 683 additions and 219 deletions.
66 changes: 46 additions & 20 deletions keep-ui/app/dashboard/GridItem.tsx
Original file line number Diff line number Diff line change
@@ -1,40 +1,66 @@
import React from "react";
import { Card } from "@tremor/react";
import {AreaChart, Card} from "@tremor/react";
import MenuButton from "./MenuButton";
import { WidgetData } from "./types";
import {WidgetData, WidgetType} from "./types";

interface GridItemProps {
item: WidgetData;
onEdit: (id: string) => void;
onDelete: (id: string) => void;
}

const GridItem: React.FC<GridItemProps> = ({ item, onEdit, onDelete }) => {
const GridItem: React.FC<GridItemProps> = ({item, onEdit, onDelete}) => {

const getColor = () => {
let color = '#000000';
for (let i = item.thresholds.length - 1; i >= 0; i--) {
if (item.preset.alerts_count >= item.thresholds[i].value) {
color = item.thresholds[i].color;
break;
if (item.widgetType === WidgetType.PRESET && item.thresholds && item.preset) {
let color = '#000000';
for (let i = item.thresholds.length - 1; i >= 0; i--) {
if (item.preset.alerts_count >= item.thresholds[i].value) {
color = item.thresholds[i].color;
break;
}
}
return color;
}
return color;
};


return (
<Card className="relative w-full h-full p-4">
<div className="flex flex-col h-full">
<div className="flex-none h-1/5 p-2 flex items-center justify-between">
<span className="text-lg font-semibold truncate">{item.name}</span>
<MenuButton onEdit={() => onEdit(item.i)} onDelete={() => onDelete(item.i)} />
</div>
<div className="flex-1 h-4/5 flex items-center justify-center grid-item__widget">
<div className="text-4xl font-bold" style={{ color: getColor() }}>
{item.preset.alerts_count}
<Card className="relative w-full h-full p-4">
<div className="flex flex-col h-full">
<div className="flex-none h-1/5 p-2 flex items-center justify-between">
<span className="text-lg font-semibold truncate">{item.name}</span>
<MenuButton onEdit={() => onEdit(item.i)} onDelete={() => onDelete(item.i)}/>
</div>
<div className={(item.widgetType === WidgetType.METRIC ? 'h-56 w-full ' : 'h-4/5 ') + "flex-1 flex items-center justify-center grid-item__widget"}>
{item.widgetType === WidgetType.PRESET && item.preset ?
<div className="text-4xl font-bold" style={{color: getColor()}}>
{item.preset.alerts_count}
</div> : item.metric ?
<div className={"w-[80%]"}>
<AreaChart
className="h-56"
data={item.metric?.data}
index="hour"
categories={[item.metric?.id === "mttr" ? "mttr" : "number"]}
valueFormatter={(number: number) =>
`${Intl.NumberFormat().format(number).toString()}`
}
yAxisWidth={40}
startEndOnly
connectNulls
showLegend={false}
showTooltip={true}
xAxisLabel="24H Activity Data"
/>
</div> :
<div>
Something Went Wrong!
</div>
}
</div>
</div>
</div>
</Card>
</Card>
);
};

Expand Down
77 changes: 44 additions & 33 deletions keep-ui/app/dashboard/GridLayout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import GridItemContainer from "./GridItemContainer";
import { LayoutItem, WidgetData } from "./types";
import "react-grid-layout/css/styles.css";
import { Preset } from "app/alerts/models";
import {MetricsWidget} from "@/utils/hooks/useDashboardMetricWidgets";

const ResponsiveGridLayout = WidthProvider(Responsive);

Expand All @@ -14,43 +15,53 @@ interface GridLayoutProps {
onEdit: (id: string) => void;
onDelete: (id: string) => void;
presets: Preset[];
metrics: MetricsWidget[];
}

const GridLayout: React.FC<GridLayoutProps> = ({ layout, onLayoutChange, data, onEdit, onDelete, presets }) => {
const layouts = { lg: layout };
const GridLayout: React.FC<GridLayoutProps> = ({layout, onLayoutChange, data, onEdit, onDelete, presets, metrics}) => {
const layouts = {lg: layout};

return (
<ResponsiveGridLayout
className="layout"
layouts={layouts}
onLayoutChange={(currentLayout: Layout[]) => {
const updatedLayout = currentLayout.map(item => ({
...item,
static: item.static ?? false // Ensure static is a boolean
}));
onLayoutChange(updatedLayout as LayoutItem[]);
}}
breakpoints={{ lg: 1200, md: 996, sm: 768, xs: 480, xxs: 0 }}
cols={{ lg: 12, md: 10, sm: 6, xs: 4, xxs: 2 }}
rowHeight={30}
containerPadding={[0, 0]}
margin={[10, 10]}
useCSSTransforms={true}
isDraggable={true}
isResizable={true}
compactType={null}
draggableHandle=".grid-item__widget"
>
{data.map((item) => {
//Fixing the static hardcode db value.
const preset = presets?.find(p => p?.id === item?.preset?.id);
item.preset = { ...item.preset,alerts_count: preset?.alerts_count ?? 0};
return (
<div key={item.i} data-grid={item}>
<GridItemContainer item={item} onEdit={onEdit} onDelete={onDelete} />
</div>
)})}
</ResponsiveGridLayout>
<ResponsiveGridLayout
className="layout"
layouts={layouts}
onLayoutChange={(currentLayout: Layout[]) => {
const updatedLayout = currentLayout.map(item => ({
...item,
static: item.static ?? false // Ensure static is a boolean
}));
onLayoutChange(updatedLayout as LayoutItem[]);
}}
breakpoints={{lg: 1200, md: 996, sm: 768, xs: 480, xxs: 0}}
cols={{lg: 12, md: 10, sm: 6, xs: 4, xxs: 2}}
rowHeight={30}
containerPadding={[0, 0]}
margin={[10, 10]}
useCSSTransforms={true}
isDraggable={true}
isResizable={true}
compactType={null}
draggableHandle=".grid-item__widget"
>
{data.map((item) => {
//Fixing the static hardcode db value.
if (item.preset) {
const preset = presets?.find(p => p?.id === item?.preset?.id);
item.preset = {...item.preset, alerts_count: preset?.alerts_count ?? 0};
} else if (item.metric) {
const metric = metrics?.find(m => m?.id === item?.metric?.id);
if (metric) {
item.metric = {...metric}
}
}
return (
<div key={item.i} data-grid={item}>
<GridItemContainer item={item} onEdit={onEdit} onDelete={onDelete}/>
</div>
)
}
)}
</ResponsiveGridLayout>
);
};

Expand Down
Loading

0 comments on commit ad669ae

Please sign in to comment.