diff --git a/app/vmui/packages/vmui/src/components/Main/Icons/index.tsx b/app/vmui/packages/vmui/src/components/Main/Icons/index.tsx index 6e96b3cee..4831ba7ec 100644 --- a/app/vmui/packages/vmui/src/components/Main/Icons/index.tsx +++ b/app/vmui/packages/vmui/src/components/Main/Icons/index.tsx @@ -430,3 +430,23 @@ export const ListIcon = () => ( ); + +export const StarBorderIcon = () => ( + + + +); + +export const StarIcon = () => ( + + + +); diff --git a/app/vmui/packages/vmui/src/constants/graph.ts b/app/vmui/packages/vmui/src/constants/graph.ts index 48147c639..97d0fcd27 100644 --- a/app/vmui/packages/vmui/src/constants/graph.ts +++ b/app/vmui/packages/vmui/src/constants/graph.ts @@ -1,6 +1,7 @@ import { GraphSize, SeriesItemStats } from "../types"; export const MAX_QUERY_FIELDS = 4; +export const MAX_QUERIES_HISTORY = 25; export const DEFAULT_MAX_SERIES = { table: 100, chart: 20, diff --git a/app/vmui/packages/vmui/src/hooks/useFetchQuery.ts b/app/vmui/packages/vmui/src/hooks/useFetchQuery.ts index 4ab13b24d..a4c39f56c 100644 --- a/app/vmui/packages/vmui/src/hooks/useFetchQuery.ts +++ b/app/vmui/packages/vmui/src/hooks/useFetchQuery.ts @@ -125,7 +125,7 @@ export const useFetchQuery = ({ } isHistogramResult = isDisplayChart && isHistogramData(resp.data.result); - seriesLimit = isHistogramResult ? Infinity : Math.max(totalLength, defaultLimit); + seriesLimit = isHistogramResult ? Infinity : defaultLimit; const freeTempSize = seriesLimit - tempData.length; resp.data.result.slice(0, freeTempSize).forEach((d: MetricBase) => { d.group = counter; @@ -140,7 +140,7 @@ export const useFetchQuery = ({ counter++; } - const limitText = `Showing ${seriesLimit} series out of ${totalLength} series due to performance reasons. Please narrow down the query, so it returns less series`; + const limitText = `Showing ${tempData.length} series out of ${totalLength} series due to performance reasons. Please narrow down the query, so it returns less series`; setWarning(totalLength > seriesLimit ? limitText : ""); isDisplayChart ? setGraphData(tempData as MetricResult[]) : setLiveData(tempData as InstantMetricResult[]); setTraces(tempTraces); diff --git a/app/vmui/packages/vmui/src/pages/CustomPanel/QueryConfigurator/QueryConfigurator.tsx b/app/vmui/packages/vmui/src/pages/CustomPanel/QueryConfigurator/QueryConfigurator.tsx index badf930ee..7648ffc0b 100644 --- a/app/vmui/packages/vmui/src/pages/CustomPanel/QueryConfigurator/QueryConfigurator.tsx +++ b/app/vmui/packages/vmui/src/pages/CustomPanel/QueryConfigurator/QueryConfigurator.tsx @@ -2,7 +2,7 @@ import React, { FC, StateUpdater, useEffect, useState } from "preact/compat"; import QueryEditor from "../../../components/Configurators/QueryEditor/QueryEditor"; import AdditionalSettings from "../../../components/Configurators/AdditionalSettings/AdditionalSettings"; import usePrevious from "../../../hooks/usePrevious"; -import { MAX_QUERY_FIELDS } from "../../../constants/graph"; +import { MAX_QUERIES_HISTORY, MAX_QUERY_FIELDS } from "../../../constants/graph"; import { useQueryDispatch, useQueryState } from "../../../state/query/QueryStateContext"; import { useTimeDispatch } from "../../../state/time/TimeStateContext"; import { @@ -22,7 +22,7 @@ import { arrayEquals } from "../../../utils/array"; import useDeviceDetect from "../../../hooks/useDeviceDetect"; import { QueryStats } from "../../../api/types"; import { usePrettifyQuery } from "./hooks/usePrettifyQuery"; -import QueryHistoryList from "../QueryHistory/QueryHistoryList"; +import QueryHistory from "../QueryHistory/QueryHistory"; export interface QueryConfiguratorProps { queryErrors: string[]; @@ -66,7 +66,7 @@ const QueryConfigurator: FC = ({ const newValues = !queryEqual && q ? [...h.values, q] : h.values; // limit the history - if (newValues.length > 25) newValues.shift(); + if (newValues.length > MAX_QUERIES_HISTORY) newValues.shift(); return { index: h.values.length - Number(queryEqual), @@ -243,10 +243,7 @@ const QueryConfigurator: FC = ({
- + {stateQuery.length < MAX_QUERY_FIELDS && ( +
+ )} +
+ + + )} + + ); +}; + +export default QueryHistory; diff --git a/app/vmui/packages/vmui/src/pages/CustomPanel/QueryHistory/QueryHistoryItem.tsx b/app/vmui/packages/vmui/src/pages/CustomPanel/QueryHistory/QueryHistoryItem.tsx new file mode 100644 index 000000000..23e54efc1 --- /dev/null +++ b/app/vmui/packages/vmui/src/pages/CustomPanel/QueryHistory/QueryHistoryItem.tsx @@ -0,0 +1,65 @@ +import React, { FC, useMemo } from "preact/compat"; +import Button from "../../../components/Main/Button/Button"; +import { CopyIcon, PlayCircleOutlineIcon, StarBorderIcon, StarIcon } from "../../../components/Main/Icons"; +import Tooltip from "../../../components/Main/Tooltip/Tooltip"; +import useCopyToClipboard from "../../../hooks/useCopyToClipboard"; +import "./style.scss"; + +interface Props { + query: string; + favorites: string[]; + onRun: (query: string) => void; + onToggleFavorite: (query: string, isFavorite: boolean) => void; +} + +const QueryHistoryItem: FC = ({ query, favorites, onRun, onToggleFavorite }) => { + const copyToClipboard = useCopyToClipboard(); + const isFavorite = useMemo(() => favorites.includes(query), [query, favorites]); + + const handleCopyQuery = async () => { + await copyToClipboard(query, "Query has been copied"); + }; + + const handleRunQuery = () => { + onRun(query); + }; + + const handleToggleFavorite = () => { + onToggleFavorite(query, isFavorite); + }; + + return ( +
+ {query} +
+ +
+
+ ); +}; + +export default QueryHistoryItem; diff --git a/app/vmui/packages/vmui/src/pages/CustomPanel/QueryHistory/QueryHistoryList.tsx b/app/vmui/packages/vmui/src/pages/CustomPanel/QueryHistory/QueryHistoryList.tsx deleted file mode 100644 index 0ce8ddf35..000000000 --- a/app/vmui/packages/vmui/src/pages/CustomPanel/QueryHistory/QueryHistoryList.tsx +++ /dev/null @@ -1,114 +0,0 @@ -import React, { FC, useMemo } from "preact/compat"; -import Button from "../../../components/Main/Button/Button"; -import { ClockIcon, CopyIcon, PlayCircleOutlineIcon } from "../../../components/Main/Icons"; -import Tooltip from "../../../components/Main/Tooltip/Tooltip"; -import { QueryHistory } from "../../../state/query/reducer"; -import useBoolean from "../../../hooks/useBoolean"; -import Modal from "../../../components/Main/Modal/Modal"; -import "./style.scss"; -import Tabs from "../../../components/Main/Tabs/Tabs"; -import { useState } from "react"; -import useCopyToClipboard from "../../../hooks/useCopyToClipboard"; -import useDeviceDetect from "../../../hooks/useDeviceDetect"; -import classNames from "classnames"; - -interface QueryHistoryProps { - history: QueryHistory[]; - handleSelectQuery: (query: string, index: number) => void -} - -const QueryHistoryList: FC = ({ history, handleSelectQuery }) => { - const { isMobile } = useDeviceDetect(); - const copyToClipboard = useCopyToClipboard(); - const { - value: openModal, - setTrue: handleOpenModal, - setFalse: handleCloseModal, - } = useBoolean(false); - - const [activeTab, setActiveTab] = useState("0"); - const tabs = useMemo(() => history.map((item, i) => ({ - value: `${i}`, - label: `Query ${i+1}`, - })), [history]); - - const queries = useMemo(() => { - const historyItem = history[+activeTab]; - return historyItem ? historyItem.values.filter(q => q).reverse() : []; - }, [activeTab, history]); - - const handleCopyQuery = (value: string) => async () => { - await copyToClipboard(value, "Query has been copied"); - }; - - const handleRunQuery = (value: string, index: number) => () => { - handleSelectQuery(value, index); - handleCloseModal(); - }; - - return ( - <> - -