mirror of
https://git.mirrors.martin98.com/https://github.com/SigNoz/signoz
synced 2025-08-14 01:15:52 +08:00
feat: Added Resizable Wrapper for Ant Design Table (#2014)
* feat: Added Resizable Wrapper for AntD Table * chore: Merging upstream develop into fork * chore: updated lock file * fix: Lint issues resolved * fix: Lint issues resolved * fix: Types issues * fix: linting issues * fix: Types issues * fix: POC of new resize lib * fix: linting issues * chore: resize is updated * fix: added old lib logic * fix: removed console.log * chore: types are updated * chore: removed un used style --------- Co-authored-by: Palash Gupta <palashgdev@gmail.com>
This commit is contained in:
parent
846da08cbd
commit
152846f554
@ -138,6 +138,7 @@
|
|||||||
"@types/react-dom": "18.0.10",
|
"@types/react-dom": "18.0.10",
|
||||||
"@types/react-grid-layout": "^1.1.2",
|
"@types/react-grid-layout": "^1.1.2",
|
||||||
"@types/react-redux": "^7.1.11",
|
"@types/react-redux": "^7.1.11",
|
||||||
|
"@types/react-resizable": "3.0.3",
|
||||||
"@types/react-router-dom": "^5.1.6",
|
"@types/react-router-dom": "^5.1.6",
|
||||||
"@types/redux": "^3.6.0",
|
"@types/redux": "^3.6.0",
|
||||||
"@types/styled-components": "^5.1.4",
|
"@types/styled-components": "^5.1.4",
|
||||||
@ -176,6 +177,7 @@
|
|||||||
"portfinder-sync": "^0.0.2",
|
"portfinder-sync": "^0.0.2",
|
||||||
"prettier": "2.2.1",
|
"prettier": "2.2.1",
|
||||||
"react-hot-loader": "^4.13.0",
|
"react-hot-loader": "^4.13.0",
|
||||||
|
"react-resizable": "3.0.4",
|
||||||
"ts-jest": "^27.1.4",
|
"ts-jest": "^27.1.4",
|
||||||
"ts-node": "^10.2.1",
|
"ts-node": "^10.2.1",
|
||||||
"typescript-plugin-css-modules": "^3.4.0",
|
"typescript-plugin-css-modules": "^3.4.0",
|
||||||
|
@ -0,0 +1,51 @@
|
|||||||
|
import React, { useMemo } from 'react';
|
||||||
|
import { Resizable, ResizeCallbackData } from 'react-resizable';
|
||||||
|
|
||||||
|
import { enableUserSelectHack } from './config';
|
||||||
|
import { SpanStyle } from './styles';
|
||||||
|
|
||||||
|
function ResizableHeader(props: ResizableHeaderProps): JSX.Element {
|
||||||
|
const { onResize, width, ...restProps } = props;
|
||||||
|
|
||||||
|
const handle = useMemo(
|
||||||
|
() => (
|
||||||
|
<SpanStyle
|
||||||
|
className="react-resizable-handle"
|
||||||
|
onClick={(e): void => e.stopPropagation()}
|
||||||
|
/>
|
||||||
|
),
|
||||||
|
[],
|
||||||
|
);
|
||||||
|
|
||||||
|
const draggableOpts = useMemo(
|
||||||
|
() => ({
|
||||||
|
enableUserSelectHack,
|
||||||
|
}),
|
||||||
|
[],
|
||||||
|
);
|
||||||
|
|
||||||
|
if (!width) {
|
||||||
|
// eslint-disable-next-line react/jsx-props-no-spreading
|
||||||
|
return <th {...restProps} />;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<Resizable
|
||||||
|
width={width}
|
||||||
|
height={0}
|
||||||
|
handle={handle}
|
||||||
|
onResize={onResize}
|
||||||
|
draggableOpts={draggableOpts}
|
||||||
|
>
|
||||||
|
{/* eslint-disable-next-line react/jsx-props-no-spreading */}
|
||||||
|
<th {...restProps} />
|
||||||
|
</Resizable>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
interface ResizableHeaderProps {
|
||||||
|
onResize: (e: React.SyntheticEvent<Element>, data: ResizeCallbackData) => void;
|
||||||
|
width: number;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default ResizableHeader;
|
@ -0,0 +1,47 @@
|
|||||||
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import React, { useCallback, useMemo, useState } from 'react';
|
||||||
|
import { ResizeCallbackData } from 'react-resizable';
|
||||||
|
|
||||||
|
function ResizeTableWrapper({
|
||||||
|
children,
|
||||||
|
columns,
|
||||||
|
}: ResizeTableWrapperProps): JSX.Element {
|
||||||
|
const [columnsData, setColumns] = useState<ColumnsType>(columns);
|
||||||
|
|
||||||
|
const handleResize = useCallback(
|
||||||
|
(index: number) => (
|
||||||
|
_e: React.SyntheticEvent<Element>,
|
||||||
|
{ size }: ResizeCallbackData,
|
||||||
|
): void => {
|
||||||
|
const newColumns = [...columnsData];
|
||||||
|
newColumns[index] = {
|
||||||
|
...newColumns[index],
|
||||||
|
width: size.width,
|
||||||
|
};
|
||||||
|
setColumns(newColumns);
|
||||||
|
},
|
||||||
|
[columnsData],
|
||||||
|
);
|
||||||
|
|
||||||
|
const mergeColumns = useMemo(
|
||||||
|
() =>
|
||||||
|
columnsData.map((col, index) => ({
|
||||||
|
...col,
|
||||||
|
onHeaderCell: (column: ColumnsType<unknown>[number]): unknown => ({
|
||||||
|
width: column.width,
|
||||||
|
onResize: handleResize(index),
|
||||||
|
}),
|
||||||
|
})),
|
||||||
|
[columnsData, handleResize],
|
||||||
|
);
|
||||||
|
|
||||||
|
return <> {React.cloneElement(children, { columns: mergeColumns })}</>;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface ResizeTableWrapperProps {
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||||
|
columns: ColumnsType<any>;
|
||||||
|
children: JSX.Element;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default ResizeTableWrapper;
|
1
frontend/src/components/ResizeTableWrapper/config.ts
Normal file
1
frontend/src/components/ResizeTableWrapper/config.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export const enableUserSelectHack = { enableUserSelectHack: false };
|
4
frontend/src/components/ResizeTableWrapper/index.ts
Normal file
4
frontend/src/components/ResizeTableWrapper/index.ts
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
import ResizableHeader from './ResizableHeader';
|
||||||
|
import ResizeTableWrapper from './ResizeTableWrapper';
|
||||||
|
|
||||||
|
export { ResizableHeader, ResizeTableWrapper };
|
11
frontend/src/components/ResizeTableWrapper/styles.ts
Normal file
11
frontend/src/components/ResizeTableWrapper/styles.ts
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
import styled from 'styled-components';
|
||||||
|
|
||||||
|
export const SpanStyle = styled.span`
|
||||||
|
position: absolute;
|
||||||
|
right: -5px;
|
||||||
|
bottom: 0;
|
||||||
|
z-index: 1;
|
||||||
|
width: 10px;
|
||||||
|
height: 100%;
|
||||||
|
cursor: col-resize;
|
||||||
|
`;
|
@ -1,6 +1,10 @@
|
|||||||
/* eslint-disable react/display-name */
|
/* eslint-disable react/display-name */
|
||||||
import { Button, notification, Table } from 'antd';
|
import { Button, notification, Table } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import useComponentPermission from 'hooks/useComponentPermission';
|
import useComponentPermission from 'hooks/useComponentPermission';
|
||||||
import history from 'lib/history';
|
import history from 'lib/history';
|
||||||
@ -34,11 +38,13 @@ function AlertChannels({ allChannels }: AlertChannelsProps): JSX.Element {
|
|||||||
title: t('column_channel_name'),
|
title: t('column_channel_name'),
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
key: 'name',
|
key: 'name',
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('column_channel_type'),
|
title: t('column_channel_type'),
|
||||||
dataIndex: 'type',
|
dataIndex: 'type',
|
||||||
key: 'type',
|
key: 'type',
|
||||||
|
width: 80,
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
@ -48,6 +54,7 @@ function AlertChannels({ allChannels }: AlertChannelsProps): JSX.Element {
|
|||||||
dataIndex: 'id',
|
dataIndex: 'id',
|
||||||
key: 'action',
|
key: 'action',
|
||||||
align: 'center',
|
align: 'center',
|
||||||
|
width: 80,
|
||||||
render: (id: string): JSX.Element => (
|
render: (id: string): JSX.Element => (
|
||||||
<>
|
<>
|
||||||
<Button onClick={(): void => onClickEditHandler(id)} type="link">
|
<Button onClick={(): void => onClickEditHandler(id)} type="link">
|
||||||
@ -62,8 +69,13 @@ function AlertChannels({ allChannels }: AlertChannelsProps): JSX.Element {
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{Element}
|
{Element}
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table rowKey="id" dataSource={channels} columns={columns} />
|
<Table
|
||||||
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
|
dataSource={channels}
|
||||||
|
rowKey="id"
|
||||||
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -16,6 +16,10 @@ import { ColumnsType } from 'antd/lib/table';
|
|||||||
import { FilterConfirmProps } from 'antd/lib/table/interface';
|
import { FilterConfirmProps } from 'antd/lib/table/interface';
|
||||||
import getAll from 'api/errors/getAll';
|
import getAll from 'api/errors/getAll';
|
||||||
import getErrorCounts from 'api/errors/getErrorCounts';
|
import getErrorCounts from 'api/errors/getErrorCounts';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import dayjs from 'dayjs';
|
import dayjs from 'dayjs';
|
||||||
import useUrlQuery from 'hooks/useUrlQuery';
|
import useUrlQuery from 'hooks/useUrlQuery';
|
||||||
@ -259,6 +263,7 @@ function AllErrors(): JSX.Element {
|
|||||||
const columns: ColumnsType<Exception> = [
|
const columns: ColumnsType<Exception> = [
|
||||||
{
|
{
|
||||||
title: 'Exception Type',
|
title: 'Exception Type',
|
||||||
|
width: 100,
|
||||||
dataIndex: 'exceptionType',
|
dataIndex: 'exceptionType',
|
||||||
key: 'exceptionType',
|
key: 'exceptionType',
|
||||||
...getFilter(onExceptionTypeFilter, 'Search By Exception', 'exceptionType'),
|
...getFilter(onExceptionTypeFilter, 'Search By Exception', 'exceptionType'),
|
||||||
@ -284,6 +289,7 @@ function AllErrors(): JSX.Element {
|
|||||||
title: 'Error Message',
|
title: 'Error Message',
|
||||||
dataIndex: 'exceptionMessage',
|
dataIndex: 'exceptionMessage',
|
||||||
key: 'exceptionMessage',
|
key: 'exceptionMessage',
|
||||||
|
width: 100,
|
||||||
render: (value): JSX.Element => (
|
render: (value): JSX.Element => (
|
||||||
<Tooltip overlay={(): JSX.Element => value}>
|
<Tooltip overlay={(): JSX.Element => value}>
|
||||||
<Typography.Paragraph
|
<Typography.Paragraph
|
||||||
@ -298,6 +304,7 @@ function AllErrors(): JSX.Element {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Count',
|
title: 'Count',
|
||||||
|
width: 50,
|
||||||
dataIndex: 'exceptionCount',
|
dataIndex: 'exceptionCount',
|
||||||
key: 'exceptionCount',
|
key: 'exceptionCount',
|
||||||
sorter: true,
|
sorter: true,
|
||||||
@ -310,6 +317,7 @@ function AllErrors(): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Last Seen',
|
title: 'Last Seen',
|
||||||
dataIndex: 'lastSeen',
|
dataIndex: 'lastSeen',
|
||||||
|
width: 80,
|
||||||
key: 'lastSeen',
|
key: 'lastSeen',
|
||||||
render: getDateValue,
|
render: getDateValue,
|
||||||
sorter: true,
|
sorter: true,
|
||||||
@ -322,6 +330,7 @@ function AllErrors(): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'First Seen',
|
title: 'First Seen',
|
||||||
dataIndex: 'firstSeen',
|
dataIndex: 'firstSeen',
|
||||||
|
width: 80,
|
||||||
key: 'firstSeen',
|
key: 'firstSeen',
|
||||||
render: getDateValue,
|
render: getDateValue,
|
||||||
sorter: true,
|
sorter: true,
|
||||||
@ -334,6 +343,7 @@ function AllErrors(): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Application',
|
title: 'Application',
|
||||||
dataIndex: 'serviceName',
|
dataIndex: 'serviceName',
|
||||||
|
width: 100,
|
||||||
key: 'serviceName',
|
key: 'serviceName',
|
||||||
sorter: true,
|
sorter: true,
|
||||||
defaultSortOrder: getDefaultOrder(
|
defaultSortOrder: getDefaultOrder(
|
||||||
@ -382,10 +392,11 @@ function AllErrors(): JSX.Element {
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{NotificationElement}
|
{NotificationElement}
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
dataSource={data?.payload as Exception[]}
|
dataSource={data?.payload as Exception[]}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
rowKey="firstSeen"
|
rowKey="firstSeen"
|
||||||
loading={isLoading || false || errorCountResponse.status === 'loading'}
|
loading={isLoading || false || errorCountResponse.status === 'loading'}
|
||||||
pagination={{
|
pagination={{
|
||||||
@ -397,6 +408,7 @@ function AllErrors(): JSX.Element {
|
|||||||
}}
|
}}
|
||||||
onChange={onChangeHandler}
|
onChange={onChangeHandler}
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,10 @@
|
|||||||
import { Button, Divider, notification, Space, Table, Typography } from 'antd';
|
import { Button, Divider, notification, Space, Table, Typography } from 'antd';
|
||||||
import getNextPrevId from 'api/errors/getNextPrevId';
|
import getNextPrevId from 'api/errors/getNextPrevId';
|
||||||
import Editor from 'components/Editor';
|
import Editor from 'components/Editor';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import { getNanoSeconds } from 'container/AllError/utils';
|
import { getNanoSeconds } from 'container/AllError/utils';
|
||||||
import dayjs from 'dayjs';
|
import dayjs from 'dayjs';
|
||||||
import history from 'lib/history';
|
import history from 'lib/history';
|
||||||
@ -53,12 +57,14 @@ function ErrorDetails(props: ErrorDetailsProps): JSX.Element {
|
|||||||
() => [
|
() => [
|
||||||
{
|
{
|
||||||
title: 'Key',
|
title: 'Key',
|
||||||
|
width: 100,
|
||||||
dataIndex: 'key',
|
dataIndex: 'key',
|
||||||
key: 'key',
|
key: 'key',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Value',
|
title: 'Value',
|
||||||
dataIndex: 'value',
|
dataIndex: 'value',
|
||||||
|
width: 100,
|
||||||
key: 'value',
|
key: 'value',
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
@ -170,7 +176,13 @@ function ErrorDetails(props: ErrorDetailsProps): JSX.Element {
|
|||||||
|
|
||||||
<EditorContainer>
|
<EditorContainer>
|
||||||
<Space direction="vertical">
|
<Space direction="vertical">
|
||||||
<Table tableLayout="fixed" columns={columns} dataSource={data} />
|
<ResizeTableWrapper columns={columns}>
|
||||||
|
<Table
|
||||||
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
|
tableLayout="fixed"
|
||||||
|
dataSource={data}
|
||||||
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</Space>
|
</Space>
|
||||||
</EditorContainer>
|
</EditorContainer>
|
||||||
</>
|
</>
|
||||||
|
@ -1,5 +1,9 @@
|
|||||||
import { Table } from 'antd';
|
import { Table } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { useTranslation } from 'react-i18next';
|
import { useTranslation } from 'react-i18next';
|
||||||
import { License } from 'types/api/licenses/def';
|
import { License } from 'types/api/licenses/def';
|
||||||
@ -13,25 +17,37 @@ function ListLicenses({ licenses }: ListLicensesProps): JSX.Element {
|
|||||||
title: t('column_license_status'),
|
title: t('column_license_status'),
|
||||||
dataIndex: 'status',
|
dataIndex: 'status',
|
||||||
key: 'status',
|
key: 'status',
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('column_license_key'),
|
title: t('column_license_key'),
|
||||||
dataIndex: 'key',
|
dataIndex: 'key',
|
||||||
key: 'key',
|
key: 'key',
|
||||||
|
width: 80,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('column_valid_from'),
|
title: t('column_valid_from'),
|
||||||
dataIndex: 'ValidFrom',
|
dataIndex: 'ValidFrom',
|
||||||
key: 'valid from',
|
key: 'valid from',
|
||||||
|
width: 80,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('column_valid_until'),
|
title: t('column_valid_until'),
|
||||||
dataIndex: 'ValidUntil',
|
dataIndex: 'ValidUntil',
|
||||||
key: 'valid until',
|
key: 'valid until',
|
||||||
|
width: 80,
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
return <Table rowKey="id" dataSource={licenses} columns={columns} />;
|
return (
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
|
<Table
|
||||||
|
rowKey="id"
|
||||||
|
dataSource={licenses}
|
||||||
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
interface ListLicensesProps {
|
interface ListLicensesProps {
|
||||||
|
@ -2,6 +2,10 @@
|
|||||||
import { PlusOutlined } from '@ant-design/icons';
|
import { PlusOutlined } from '@ant-design/icons';
|
||||||
import { notification, Table, Typography } from 'antd';
|
import { notification, Table, Typography } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import TextToolTip from 'components/TextToolTip';
|
import TextToolTip from 'components/TextToolTip';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import useComponentPermission from 'hooks/useComponentPermission';
|
import useComponentPermission from 'hooks/useComponentPermission';
|
||||||
@ -60,6 +64,7 @@ function ListAlert({ allAlertRules, refetch }: ListAlertProps): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Status',
|
title: 'Status',
|
||||||
dataIndex: 'state',
|
dataIndex: 'state',
|
||||||
|
width: 80,
|
||||||
key: 'state',
|
key: 'state',
|
||||||
sorter: (a, b): number =>
|
sorter: (a, b): number =>
|
||||||
(b.state ? b.state.charCodeAt(0) : 1000) -
|
(b.state ? b.state.charCodeAt(0) : 1000) -
|
||||||
@ -69,6 +74,7 @@ function ListAlert({ allAlertRules, refetch }: ListAlertProps): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Alert Name',
|
title: 'Alert Name',
|
||||||
dataIndex: 'alert',
|
dataIndex: 'alert',
|
||||||
|
width: 100,
|
||||||
key: 'name',
|
key: 'name',
|
||||||
sorter: (a, b): number =>
|
sorter: (a, b): number =>
|
||||||
(a.alert ? a.alert.charCodeAt(0) : 1000) -
|
(a.alert ? a.alert.charCodeAt(0) : 1000) -
|
||||||
@ -84,6 +90,7 @@ function ListAlert({ allAlertRules, refetch }: ListAlertProps): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Severity',
|
title: 'Severity',
|
||||||
dataIndex: 'labels',
|
dataIndex: 'labels',
|
||||||
|
width: 80,
|
||||||
key: 'severity',
|
key: 'severity',
|
||||||
sorter: (a, b): number =>
|
sorter: (a, b): number =>
|
||||||
(a.labels ? a.labels.severity.length : 0) -
|
(a.labels ? a.labels.severity.length : 0) -
|
||||||
@ -101,7 +108,7 @@ function ListAlert({ allAlertRules, refetch }: ListAlertProps): JSX.Element {
|
|||||||
dataIndex: 'labels',
|
dataIndex: 'labels',
|
||||||
key: 'tags',
|
key: 'tags',
|
||||||
align: 'center',
|
align: 'center',
|
||||||
width: 350,
|
width: 100,
|
||||||
render: (value): JSX.Element => {
|
render: (value): JSX.Element => {
|
||||||
const objectKeys = Object.keys(value);
|
const objectKeys = Object.keys(value);
|
||||||
const withOutSeverityKeys = objectKeys.filter((e) => e !== 'severity');
|
const withOutSeverityKeys = objectKeys.filter((e) => e !== 'severity');
|
||||||
@ -128,6 +135,7 @@ function ListAlert({ allAlertRules, refetch }: ListAlertProps): JSX.Element {
|
|||||||
title: 'Action',
|
title: 'Action',
|
||||||
dataIndex: 'id',
|
dataIndex: 'id',
|
||||||
key: 'action',
|
key: 'action',
|
||||||
|
width: 120,
|
||||||
render: (id: GettableAlert['id'], record): JSX.Element => (
|
render: (id: GettableAlert['id'], record): JSX.Element => (
|
||||||
<>
|
<>
|
||||||
<ToggleAlertState disabled={record.disabled} setData={setData} id={id} />
|
<ToggleAlertState disabled={record.disabled} setData={setData} id={id} />
|
||||||
@ -164,8 +172,13 @@ function ListAlert({ allAlertRules, refetch }: ListAlertProps): JSX.Element {
|
|||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
</ButtonContainer>
|
</ButtonContainer>
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table rowKey="id" columns={columns} dataSource={data} />
|
<Table
|
||||||
|
rowKey="id"
|
||||||
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
|
dataSource={data}
|
||||||
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -10,6 +10,10 @@ import {
|
|||||||
} from 'antd';
|
} from 'antd';
|
||||||
import createDashboard from 'api/dashboard/create';
|
import createDashboard from 'api/dashboard/create';
|
||||||
import { AxiosError } from 'axios';
|
import { AxiosError } from 'axios';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import TextToolTip from 'components/TextToolTip';
|
import TextToolTip from 'components/TextToolTip';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import SearchFilter from 'container/ListOfDashboard/SearchFilter';
|
import SearchFilter from 'container/ListOfDashboard/SearchFilter';
|
||||||
@ -74,20 +78,24 @@ function ListOfAllDashboard(): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Name',
|
title: 'Name',
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
|
width: 100,
|
||||||
render: Name,
|
render: Name,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Description',
|
title: 'Description',
|
||||||
|
width: 100,
|
||||||
dataIndex: 'description',
|
dataIndex: 'description',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Tags (can be multiple)',
|
title: 'Tags (can be multiple)',
|
||||||
dataIndex: 'tags',
|
dataIndex: 'tags',
|
||||||
|
width: 80,
|
||||||
render: Tags,
|
render: Tags,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Created At',
|
title: 'Created At',
|
||||||
dataIndex: 'createdBy',
|
dataIndex: 'createdBy',
|
||||||
|
width: 80,
|
||||||
sorter: (a: Data, b: Data): number => {
|
sorter: (a: Data, b: Data): number => {
|
||||||
const prev = new Date(a.createdBy).getTime();
|
const prev = new Date(a.createdBy).getTime();
|
||||||
const next = new Date(b.createdBy).getTime();
|
const next = new Date(b.createdBy).getTime();
|
||||||
@ -98,6 +106,7 @@ function ListOfAllDashboard(): JSX.Element {
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Last Updated Time',
|
title: 'Last Updated Time',
|
||||||
|
width: 90,
|
||||||
dataIndex: 'lastUpdatedTime',
|
dataIndex: 'lastUpdatedTime',
|
||||||
sorter: (a: Data, b: Data): number => {
|
sorter: (a: Data, b: Data): number => {
|
||||||
const prev = new Date(a.lastUpdatedTime).getTime();
|
const prev = new Date(a.lastUpdatedTime).getTime();
|
||||||
@ -114,6 +123,7 @@ function ListOfAllDashboard(): JSX.Element {
|
|||||||
title: 'Action',
|
title: 'Action',
|
||||||
dataIndex: '',
|
dataIndex: '',
|
||||||
key: 'x',
|
key: 'x',
|
||||||
|
width: 40,
|
||||||
render: DeleteButton,
|
render: DeleteButton,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -271,6 +281,7 @@ function ListOfAllDashboard(): JSX.Element {
|
|||||||
uploadedGrafana={uploadedGrafana}
|
uploadedGrafana={uploadedGrafana}
|
||||||
onModalHandler={(): void => onModalHandler(false)}
|
onModalHandler={(): void => onModalHandler(false)}
|
||||||
/>
|
/>
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
pagination={{
|
pagination={{
|
||||||
pageSize: 9,
|
pageSize: 9,
|
||||||
@ -280,10 +291,11 @@ function ListOfAllDashboard(): JSX.Element {
|
|||||||
bordered
|
bordered
|
||||||
sticky
|
sticky
|
||||||
loading={loading}
|
loading={loading}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
dataSource={data}
|
dataSource={data}
|
||||||
showSorterTooltip
|
showSorterTooltip
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</TableContainer>
|
</TableContainer>
|
||||||
</Card>
|
</Card>
|
||||||
);
|
);
|
||||||
|
@ -2,6 +2,10 @@ import { blue, orange } from '@ant-design/colors';
|
|||||||
import { Input, Table } from 'antd';
|
import { Input, Table } from 'antd';
|
||||||
import AddToQueryHOC from 'components/Logs/AddToQueryHOC';
|
import AddToQueryHOC from 'components/Logs/AddToQueryHOC';
|
||||||
import CopyClipboardHOC from 'components/Logs/CopyClipboardHOC';
|
import CopyClipboardHOC from 'components/Logs/CopyClipboardHOC';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import flatten from 'flat';
|
import flatten from 'flat';
|
||||||
import { fieldSearchFilter } from 'lib/logs/fieldSearch';
|
import { fieldSearchFilter } from 'lib/logs/fieldSearch';
|
||||||
import React, { useMemo, useState } from 'react';
|
import React, { useMemo, useState } from 'react';
|
||||||
@ -56,7 +60,7 @@ function TableView({ logData }: TableViewProps): JSX.Element | null {
|
|||||||
title: 'Field',
|
title: 'Field',
|
||||||
dataIndex: 'field',
|
dataIndex: 'field',
|
||||||
key: 'field',
|
key: 'field',
|
||||||
width: '35%',
|
width: 100,
|
||||||
render: (field: string): JSX.Element => {
|
render: (field: string): JSX.Element => {
|
||||||
const fieldKey = field.split('.').slice(-1);
|
const fieldKey = field.split('.').slice(-1);
|
||||||
const renderedField = <span style={{ color: blue[4] }}>{field}</span>;
|
const renderedField = <span style={{ color: blue[4] }}>{field}</span>;
|
||||||
@ -75,15 +79,16 @@ function TableView({ logData }: TableViewProps): JSX.Element | null {
|
|||||||
title: 'Value',
|
title: 'Value',
|
||||||
dataIndex: 'value',
|
dataIndex: 'value',
|
||||||
key: 'value',
|
key: 'value',
|
||||||
|
width: 80,
|
||||||
ellipsis: false,
|
ellipsis: false,
|
||||||
render: (field: never): JSX.Element => (
|
render: (field: never): JSX.Element => (
|
||||||
<CopyClipboardHOC textToCopy={field}>
|
<CopyClipboardHOC textToCopy={field}>
|
||||||
<span style={{ color: orange[6] }}>{field}</span>
|
<span style={{ color: orange[6] }}>{field}</span>
|
||||||
</CopyClipboardHOC>
|
</CopyClipboardHOC>
|
||||||
),
|
),
|
||||||
width: '60%',
|
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div style={{ position: 'relative' }}>
|
<div style={{ position: 'relative' }}>
|
||||||
<Input
|
<Input
|
||||||
@ -92,13 +97,15 @@ function TableView({ logData }: TableViewProps): JSX.Element | null {
|
|||||||
value={fieldSearchInput}
|
value={fieldSearchInput}
|
||||||
onChange={(e): void => setFieldSearchInput(e.target.value)}
|
onChange={(e): void => setFieldSearchInput(e.target.value)}
|
||||||
/>
|
/>
|
||||||
|
<ResizeTableWrapper columns={columns as never}>
|
||||||
<Table
|
<Table
|
||||||
// scroll={{ x: true }}
|
// scroll={{ x: true }}
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
dataSource={dataSource}
|
dataSource={dataSource}
|
||||||
columns={columns as never}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
pagination={false}
|
pagination={false}
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,9 @@
|
|||||||
import { Table, Tooltip, Typography } from 'antd';
|
import { Table, Tooltip, Typography } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import { METRICS_PAGE_QUERY_PARAM } from 'constants/query';
|
import { METRICS_PAGE_QUERY_PARAM } from 'constants/query';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import history from 'lib/history';
|
import history from 'lib/history';
|
||||||
@ -51,7 +55,7 @@ function TopOperationsTable(props: TopOperationsTableProps): JSX.Element {
|
|||||||
title: 'Name',
|
title: 'Name',
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
key: 'name',
|
key: 'name',
|
||||||
ellipsis: true,
|
width: 100,
|
||||||
render: (text: string): JSX.Element => (
|
render: (text: string): JSX.Element => (
|
||||||
<Tooltip placement="topLeft" title={text}>
|
<Tooltip placement="topLeft" title={text}>
|
||||||
<Typography.Link onClick={(): void => handleOnClick(text)}>
|
<Typography.Link onClick={(): void => handleOnClick(text)}>
|
||||||
@ -64,6 +68,7 @@ function TopOperationsTable(props: TopOperationsTableProps): JSX.Element {
|
|||||||
title: 'P50 (in ms)',
|
title: 'P50 (in ms)',
|
||||||
dataIndex: 'p50',
|
dataIndex: 'p50',
|
||||||
key: 'p50',
|
key: 'p50',
|
||||||
|
width: 50,
|
||||||
sorter: (a: DataProps, b: DataProps): number => a.p50 - b.p50,
|
sorter: (a: DataProps, b: DataProps): number => a.p50 - b.p50,
|
||||||
render: (value: number): string => (value / 1000000).toFixed(2),
|
render: (value: number): string => (value / 1000000).toFixed(2),
|
||||||
},
|
},
|
||||||
@ -71,6 +76,7 @@ function TopOperationsTable(props: TopOperationsTableProps): JSX.Element {
|
|||||||
title: 'P95 (in ms)',
|
title: 'P95 (in ms)',
|
||||||
dataIndex: 'p95',
|
dataIndex: 'p95',
|
||||||
key: 'p95',
|
key: 'p95',
|
||||||
|
width: 50,
|
||||||
sorter: (a: DataProps, b: DataProps): number => a.p95 - b.p95,
|
sorter: (a: DataProps, b: DataProps): number => a.p95 - b.p95,
|
||||||
render: (value: number): string => (value / 1000000).toFixed(2),
|
render: (value: number): string => (value / 1000000).toFixed(2),
|
||||||
},
|
},
|
||||||
@ -78,6 +84,7 @@ function TopOperationsTable(props: TopOperationsTableProps): JSX.Element {
|
|||||||
title: 'P99 (in ms)',
|
title: 'P99 (in ms)',
|
||||||
dataIndex: 'p99',
|
dataIndex: 'p99',
|
||||||
key: 'p99',
|
key: 'p99',
|
||||||
|
width: 50,
|
||||||
sorter: (a: DataProps, b: DataProps): number => a.p99 - b.p99,
|
sorter: (a: DataProps, b: DataProps): number => a.p99 - b.p99,
|
||||||
render: (value: number): string => (value / 1000000).toFixed(2),
|
render: (value: number): string => (value / 1000000).toFixed(2),
|
||||||
},
|
},
|
||||||
@ -85,20 +92,23 @@ function TopOperationsTable(props: TopOperationsTableProps): JSX.Element {
|
|||||||
title: 'Number of Calls',
|
title: 'Number of Calls',
|
||||||
dataIndex: 'numCalls',
|
dataIndex: 'numCalls',
|
||||||
key: 'numCalls',
|
key: 'numCalls',
|
||||||
|
width: 50,
|
||||||
sorter: (a: TopOperationListItem, b: TopOperationListItem): number =>
|
sorter: (a: TopOperationListItem, b: TopOperationListItem): number =>
|
||||||
a.numCalls - b.numCalls,
|
a.numCalls - b.numCalls,
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
showHeader
|
showHeader
|
||||||
title={(): string => 'Key Operations'}
|
title={(): string => 'Key Operations'}
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
dataSource={data}
|
dataSource={data}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
rowKey="name"
|
rowKey="name"
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,6 +8,10 @@ import type {
|
|||||||
} from 'antd/es/table/interface';
|
} from 'antd/es/table/interface';
|
||||||
import localStorageGet from 'api/browser/localstorage/get';
|
import localStorageGet from 'api/browser/localstorage/get';
|
||||||
import localStorageSet from 'api/browser/localstorage/set';
|
import localStorageSet from 'api/browser/localstorage/set';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import { SKIP_ONBOARDING } from 'constants/onboarding';
|
import { SKIP_ONBOARDING } from 'constants/onboarding';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import React, { useCallback, useMemo, useState } from 'react';
|
import React, { useCallback, useMemo, useState } from 'react';
|
||||||
@ -101,6 +105,7 @@ function Metrics(): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Application',
|
title: 'Application',
|
||||||
dataIndex: 'serviceName',
|
dataIndex: 'serviceName',
|
||||||
|
width: 200,
|
||||||
key: 'serviceName',
|
key: 'serviceName',
|
||||||
...getColumnSearchProps('serviceName'),
|
...getColumnSearchProps('serviceName'),
|
||||||
},
|
},
|
||||||
@ -108,6 +113,7 @@ function Metrics(): JSX.Element {
|
|||||||
title: 'P99 latency (in ms)',
|
title: 'P99 latency (in ms)',
|
||||||
dataIndex: 'p99',
|
dataIndex: 'p99',
|
||||||
key: 'p99',
|
key: 'p99',
|
||||||
|
width: 150,
|
||||||
defaultSortOrder: 'descend',
|
defaultSortOrder: 'descend',
|
||||||
sorter: (a: DataProps, b: DataProps): number => a.p99 - b.p99,
|
sorter: (a: DataProps, b: DataProps): number => a.p99 - b.p99,
|
||||||
render: (value: number): string => (value / 1000000).toFixed(2),
|
render: (value: number): string => (value / 1000000).toFixed(2),
|
||||||
@ -116,6 +122,7 @@ function Metrics(): JSX.Element {
|
|||||||
title: 'Error Rate (% of total)',
|
title: 'Error Rate (% of total)',
|
||||||
dataIndex: 'errorRate',
|
dataIndex: 'errorRate',
|
||||||
key: 'errorRate',
|
key: 'errorRate',
|
||||||
|
width: 150,
|
||||||
sorter: (a: DataProps, b: DataProps): number => a.errorRate - b.errorRate,
|
sorter: (a: DataProps, b: DataProps): number => a.errorRate - b.errorRate,
|
||||||
render: (value: number): string => value.toFixed(2),
|
render: (value: number): string => value.toFixed(2),
|
||||||
},
|
},
|
||||||
@ -123,6 +130,7 @@ function Metrics(): JSX.Element {
|
|||||||
title: 'Operations Per Second',
|
title: 'Operations Per Second',
|
||||||
dataIndex: 'callRate',
|
dataIndex: 'callRate',
|
||||||
key: 'callRate',
|
key: 'callRate',
|
||||||
|
width: 150,
|
||||||
sorter: (a: DataProps, b: DataProps): number => a.callRate - b.callRate,
|
sorter: (a: DataProps, b: DataProps): number => a.callRate - b.callRate,
|
||||||
render: (value: number): string => value.toFixed(2),
|
render: (value: number): string => value.toFixed(2),
|
||||||
},
|
},
|
||||||
@ -141,12 +149,14 @@ function Metrics(): JSX.Element {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Container>
|
<Container>
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
loading={loading}
|
loading={loading}
|
||||||
dataSource={services}
|
dataSource={services}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
rowKey="serviceName"
|
rowKey="serviceName"
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</Container>
|
</Container>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -2,6 +2,10 @@ import { blue, red } from '@ant-design/colors';
|
|||||||
import { PlusOutlined } from '@ant-design/icons';
|
import { PlusOutlined } from '@ant-design/icons';
|
||||||
import { Button, Modal, notification, Row, Space, Table, Tag } from 'antd';
|
import { Button, Modal, notification, Row, Space, Table, Tag } from 'antd';
|
||||||
import { NotificationInstance } from 'antd/es/notification/interface';
|
import { NotificationInstance } from 'antd/es/notification/interface';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import React, { useRef, useState } from 'react';
|
import React, { useRef, useState } from 'react';
|
||||||
import { connect, useSelector } from 'react-redux';
|
import { connect, useSelector } from 'react-redux';
|
||||||
import { bindActionCreators, Dispatch } from 'redux';
|
import { bindActionCreators, Dispatch } from 'redux';
|
||||||
@ -104,15 +108,18 @@ function VariablesSetting({
|
|||||||
{
|
{
|
||||||
title: 'Variable',
|
title: 'Variable',
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
|
width: 100,
|
||||||
key: 'name',
|
key: 'name',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Definition',
|
title: 'Definition',
|
||||||
dataIndex: 'description',
|
dataIndex: 'description',
|
||||||
|
width: 100,
|
||||||
key: 'description',
|
key: 'description',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Actions',
|
title: 'Actions',
|
||||||
|
width: 50,
|
||||||
key: 'action',
|
key: 'action',
|
||||||
render: (_: IDashboardVariable): JSX.Element => (
|
render: (_: IDashboardVariable): JSX.Element => (
|
||||||
<Space>
|
<Space>
|
||||||
@ -161,7 +168,12 @@ function VariablesSetting({
|
|||||||
<PlusOutlined /> New Variables
|
<PlusOutlined /> New Variables
|
||||||
</Button>
|
</Button>
|
||||||
</Row>
|
</Row>
|
||||||
<Table columns={columns} dataSource={variablesTableData} />
|
<ResizeTableWrapper columns={columns}>
|
||||||
|
<Table
|
||||||
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
|
dataSource={variablesTableData}
|
||||||
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
<Modal
|
<Modal
|
||||||
|
@ -4,6 +4,10 @@ import { ColumnsType } from 'antd/lib/table';
|
|||||||
import deleteDomain from 'api/SAML/deleteDomain';
|
import deleteDomain from 'api/SAML/deleteDomain';
|
||||||
import listAllDomain from 'api/SAML/listAllDomain';
|
import listAllDomain from 'api/SAML/listAllDomain';
|
||||||
import updateDomain from 'api/SAML/updateDomain';
|
import updateDomain from 'api/SAML/updateDomain';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import TextToolTip from 'components/TextToolTip';
|
import TextToolTip from 'components/TextToolTip';
|
||||||
import { SIGNOZ_UPGRADE_PLAN_URL } from 'constants/app';
|
import { SIGNOZ_UPGRADE_PLAN_URL } from 'constants/app';
|
||||||
import { FeatureKeys } from 'constants/featureKeys';
|
import { FeatureKeys } from 'constants/featureKeys';
|
||||||
@ -168,6 +172,7 @@ function AuthDomains(): JSX.Element {
|
|||||||
title: 'Domain',
|
title: 'Domain',
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
key: 'name',
|
key: 'name',
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: (
|
title: (
|
||||||
@ -183,6 +188,7 @@ function AuthDomains(): JSX.Element {
|
|||||||
),
|
),
|
||||||
dataIndex: 'ssoEnabled',
|
dataIndex: 'ssoEnabled',
|
||||||
key: 'ssoEnabled',
|
key: 'ssoEnabled',
|
||||||
|
width: 80,
|
||||||
render: (value: boolean, record: AuthDomain): JSX.Element => {
|
render: (value: boolean, record: AuthDomain): JSX.Element => {
|
||||||
if (!SSOFlag) {
|
if (!SSOFlag) {
|
||||||
return (
|
return (
|
||||||
@ -209,6 +215,7 @@ function AuthDomains(): JSX.Element {
|
|||||||
title: '',
|
title: '',
|
||||||
dataIndex: 'description',
|
dataIndex: 'description',
|
||||||
key: 'description',
|
key: 'description',
|
||||||
|
width: 100,
|
||||||
render: (_, record: AuthDomain): JSX.Element => {
|
render: (_, record: AuthDomain): JSX.Element => {
|
||||||
if (!SSOFlag) {
|
if (!SSOFlag) {
|
||||||
return (
|
return (
|
||||||
@ -233,6 +240,7 @@ function AuthDomains(): JSX.Element {
|
|||||||
title: 'Action',
|
title: 'Action',
|
||||||
dataIndex: 'action',
|
dataIndex: 'action',
|
||||||
key: 'action',
|
key: 'action',
|
||||||
|
width: 50,
|
||||||
render: (_, record): JSX.Element => (
|
render: (_, record): JSX.Element => (
|
||||||
<Button
|
<Button
|
||||||
disabled={!SSOFlag}
|
disabled={!SSOFlag}
|
||||||
@ -267,12 +275,14 @@ function AuthDomains(): JSX.Element {
|
|||||||
setIsSettingsOpen={setIsSettingsOpen}
|
setIsSettingsOpen={setIsSettingsOpen}
|
||||||
/>
|
/>
|
||||||
</Modal>
|
</Modal>
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
rowKey={(record: AuthDomain): string => record.name + v4()}
|
rowKey={(record: AuthDomain): string => record.name + v4()}
|
||||||
dataSource={!SSOFlag ? notEntripriseData : []}
|
dataSource={!SSOFlag ? notEntripriseData : []}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</Space>
|
</Space>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -317,13 +327,15 @@ function AuthDomains(): JSX.Element {
|
|||||||
<Space direction="vertical" size="middle">
|
<Space direction="vertical" size="middle">
|
||||||
<AddDomain refetch={refetch} />
|
<AddDomain refetch={refetch} />
|
||||||
|
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
dataSource={tableData}
|
dataSource={tableData}
|
||||||
loading={isLoading}
|
loading={isLoading}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
rowKey={(record: AuthDomain): string => record.name + v4()}
|
rowKey={(record: AuthDomain): string => record.name + v4()}
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</Space>
|
</Space>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
@ -4,6 +4,10 @@ import deleteUser from 'api/user/deleteUser';
|
|||||||
import editUserApi from 'api/user/editUser';
|
import editUserApi from 'api/user/editUser';
|
||||||
import getOrgUser from 'api/user/getOrgUser';
|
import getOrgUser from 'api/user/getOrgUser';
|
||||||
import updateRole from 'api/user/updateRole';
|
import updateRole from 'api/user/updateRole';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import dayjs from 'dayjs';
|
import dayjs from 'dayjs';
|
||||||
import React, { useEffect, useState } from 'react';
|
import React, { useEffect, useState } from 'react';
|
||||||
import { useTranslation } from 'react-i18next';
|
import { useTranslation } from 'react-i18next';
|
||||||
@ -258,21 +262,25 @@ function Members(): JSX.Element {
|
|||||||
title: 'Name',
|
title: 'Name',
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
key: 'name',
|
key: 'name',
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Emails',
|
title: 'Emails',
|
||||||
dataIndex: 'email',
|
dataIndex: 'email',
|
||||||
key: 'email',
|
key: 'email',
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Access Level',
|
title: 'Access Level',
|
||||||
dataIndex: 'accessLevel',
|
dataIndex: 'accessLevel',
|
||||||
key: 'accessLevel',
|
key: 'accessLevel',
|
||||||
|
width: 50,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Joined On',
|
title: 'Joined On',
|
||||||
dataIndex: 'joinedOn',
|
dataIndex: 'joinedOn',
|
||||||
key: 'joinedOn',
|
key: 'joinedOn',
|
||||||
|
width: 60,
|
||||||
render: (_, record): JSX.Element => {
|
render: (_, record): JSX.Element => {
|
||||||
const { joinedOn } = record;
|
const { joinedOn } = record;
|
||||||
return (
|
return (
|
||||||
@ -285,6 +293,7 @@ function Members(): JSX.Element {
|
|||||||
{
|
{
|
||||||
title: 'Action',
|
title: 'Action',
|
||||||
dataIndex: 'action',
|
dataIndex: 'action',
|
||||||
|
width: 80,
|
||||||
render: (_, record): JSX.Element => (
|
render: (_, record): JSX.Element => (
|
||||||
<UserFunction
|
<UserFunction
|
||||||
{...{
|
{...{
|
||||||
@ -303,13 +312,15 @@ function Members(): JSX.Element {
|
|||||||
return (
|
return (
|
||||||
<Space direction="vertical" size="middle">
|
<Space direction="vertical" size="middle">
|
||||||
<Typography.Title level={3}>Members</Typography.Title>
|
<Typography.Title level={3}>Members</Typography.Title>
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
dataSource={dataSource}
|
dataSource={dataSource}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
pagination={false}
|
pagination={false}
|
||||||
loading={status === 'loading'}
|
loading={status === 'loading'}
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</Space>
|
</Space>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -4,6 +4,10 @@ import { ColumnsType } from 'antd/lib/table';
|
|||||||
import deleteInvite from 'api/user/deleteInvite';
|
import deleteInvite from 'api/user/deleteInvite';
|
||||||
import getPendingInvites from 'api/user/getPendingInvites';
|
import getPendingInvites from 'api/user/getPendingInvites';
|
||||||
import sendInvite from 'api/user/sendInvite';
|
import sendInvite from 'api/user/sendInvite';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import { INVITE_MEMBERS_HASH } from 'constants/app';
|
import { INVITE_MEMBERS_HASH } from 'constants/app';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import React, { useCallback, useEffect, useState } from 'react';
|
import React, { useCallback, useEffect, useState } from 'react';
|
||||||
@ -141,26 +145,31 @@ function PendingInvitesContainer(): JSX.Element {
|
|||||||
title: 'Name',
|
title: 'Name',
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
key: 'name',
|
key: 'name',
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Emails',
|
title: 'Emails',
|
||||||
dataIndex: 'email',
|
dataIndex: 'email',
|
||||||
key: 'email',
|
key: 'email',
|
||||||
|
width: 80,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Access Level',
|
title: 'Access Level',
|
||||||
dataIndex: 'accessLevel',
|
dataIndex: 'accessLevel',
|
||||||
key: 'accessLevel',
|
key: 'accessLevel',
|
||||||
|
width: 50,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Invite Link',
|
title: 'Invite Link',
|
||||||
dataIndex: 'inviteLink',
|
dataIndex: 'inviteLink',
|
||||||
key: 'Invite Link',
|
key: 'Invite Link',
|
||||||
ellipsis: true,
|
ellipsis: true,
|
||||||
|
width: 100,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Action',
|
title: 'Action',
|
||||||
dataIndex: 'action',
|
dataIndex: 'action',
|
||||||
|
width: 80,
|
||||||
key: 'Action',
|
key: 'Action',
|
||||||
render: (_, record): JSX.Element => (
|
render: (_, record): JSX.Element => (
|
||||||
<Space direction="horizontal">
|
<Space direction="horizontal">
|
||||||
@ -263,13 +272,15 @@ function PendingInvitesContainer(): JSX.Element {
|
|||||||
{t('invite_members')}
|
{t('invite_members')}
|
||||||
</Button>
|
</Button>
|
||||||
</TitleWrapper>
|
</TitleWrapper>
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
tableLayout="fixed"
|
tableLayout="fixed"
|
||||||
dataSource={dataSource}
|
dataSource={dataSource}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
pagination={false}
|
pagination={false}
|
||||||
loading={getPendingInvitesResponse.status === 'loading'}
|
loading={getPendingInvitesResponse.status === 'loading'}
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
</Space>
|
</Space>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
@ -1,5 +1,9 @@
|
|||||||
import { Table, TableProps, Tag, Typography } from 'antd';
|
import { Table, TableProps, Tag, Typography } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import ROUTES from 'constants/routes';
|
import ROUTES from 'constants/routes';
|
||||||
import {
|
import {
|
||||||
getSpanOrder,
|
getSpanOrder,
|
||||||
@ -73,6 +77,7 @@ function TraceTable(): JSX.Element {
|
|||||||
title: 'Date',
|
title: 'Date',
|
||||||
dataIndex: 'timestamp',
|
dataIndex: 'timestamp',
|
||||||
key: 'timestamp',
|
key: 'timestamp',
|
||||||
|
width: 120,
|
||||||
sorter: true,
|
sorter: true,
|
||||||
render: (value: TableType['timestamp']): JSX.Element => {
|
render: (value: TableType['timestamp']): JSX.Element => {
|
||||||
const day = dayjs(value);
|
const day = dayjs(value);
|
||||||
@ -83,18 +88,21 @@ function TraceTable(): JSX.Element {
|
|||||||
title: 'Service',
|
title: 'Service',
|
||||||
dataIndex: 'serviceName',
|
dataIndex: 'serviceName',
|
||||||
key: 'serviceName',
|
key: 'serviceName',
|
||||||
|
width: 50,
|
||||||
render: getValue,
|
render: getValue,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Operation',
|
title: 'Operation',
|
||||||
dataIndex: 'operation',
|
dataIndex: 'operation',
|
||||||
key: 'operation',
|
key: 'operation',
|
||||||
|
width: 110,
|
||||||
render: getValue,
|
render: getValue,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Duration',
|
title: 'Duration',
|
||||||
dataIndex: 'durationNano',
|
dataIndex: 'durationNano',
|
||||||
key: 'durationNano',
|
key: 'durationNano',
|
||||||
|
width: 50,
|
||||||
sorter: true,
|
sorter: true,
|
||||||
render: (value: TableType['durationNano']): JSX.Element => (
|
render: (value: TableType['durationNano']): JSX.Element => (
|
||||||
<Typography>
|
<Typography>
|
||||||
@ -109,12 +117,14 @@ function TraceTable(): JSX.Element {
|
|||||||
title: 'Method',
|
title: 'Method',
|
||||||
dataIndex: 'method',
|
dataIndex: 'method',
|
||||||
key: 'method',
|
key: 'method',
|
||||||
|
width: 50,
|
||||||
render: getHttpMethodOrStatus,
|
render: getHttpMethodOrStatus,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: 'Status Code',
|
title: 'Status Code',
|
||||||
dataIndex: 'statusCode',
|
dataIndex: 'statusCode',
|
||||||
key: 'statusCode',
|
key: 'statusCode',
|
||||||
|
width: 50,
|
||||||
render: getHttpMethodOrStatus,
|
render: getHttpMethodOrStatus,
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
@ -180,11 +190,12 @@ function TraceTable(): JSX.Element {
|
|||||||
) as number;
|
) as number;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
<ResizeTableWrapper columns={columns}>
|
||||||
<Table
|
<Table
|
||||||
onChange={onChangeHandler}
|
onChange={onChangeHandler}
|
||||||
dataSource={spansAggregate.data}
|
dataSource={spansAggregate.data}
|
||||||
loading={loading || filterLoading}
|
loading={loading || filterLoading}
|
||||||
columns={columns}
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
rowKey={(record): string => `${record.traceID}-${record.spanID}-${v4()}`}
|
rowKey={(record): string => `${record.traceID}-${record.spanID}-${v4()}`}
|
||||||
style={{
|
style={{
|
||||||
cursor: 'pointer',
|
cursor: 'pointer',
|
||||||
@ -208,6 +219,7 @@ function TraceTable(): JSX.Element {
|
|||||||
total: totalCount,
|
total: totalCount,
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,10 @@
|
|||||||
/* eslint-disable react/display-name */
|
/* eslint-disable react/display-name */
|
||||||
import { Table, Tag, Typography } from 'antd';
|
import { Table, Tag, Typography } from 'antd';
|
||||||
import { ColumnsType } from 'antd/lib/table';
|
import { ColumnsType } from 'antd/lib/table';
|
||||||
|
import {
|
||||||
|
ResizableHeader,
|
||||||
|
ResizeTableWrapper,
|
||||||
|
} from 'components/ResizeTableWrapper';
|
||||||
import AlertStatus from 'container/TriggeredAlerts/TableComponents/AlertStatus';
|
import AlertStatus from 'container/TriggeredAlerts/TableComponents/AlertStatus';
|
||||||
import convertDateToAmAndPm from 'lib/convertDateToAmAndPm';
|
import convertDateToAmAndPm from 'lib/convertDateToAmAndPm';
|
||||||
import getFormattedDate from 'lib/getFormatedDate';
|
import getFormattedDate from 'lib/getFormatedDate';
|
||||||
@ -21,6 +25,7 @@ function NoFilterTable({
|
|||||||
{
|
{
|
||||||
title: 'Status',
|
title: 'Status',
|
||||||
dataIndex: 'status',
|
dataIndex: 'status',
|
||||||
|
width: 80,
|
||||||
key: 'status',
|
key: 'status',
|
||||||
sorter: (a, b): number =>
|
sorter: (a, b): number =>
|
||||||
b.labels.severity.length - a.labels.severity.length,
|
b.labels.severity.length - a.labels.severity.length,
|
||||||
@ -30,6 +35,7 @@ function NoFilterTable({
|
|||||||
title: 'Alert Name',
|
title: 'Alert Name',
|
||||||
dataIndex: 'labels',
|
dataIndex: 'labels',
|
||||||
key: 'alertName',
|
key: 'alertName',
|
||||||
|
width: 100,
|
||||||
sorter: (a, b): number =>
|
sorter: (a, b): number =>
|
||||||
(a.labels?.alertname?.charCodeAt(0) || 0) -
|
(a.labels?.alertname?.charCodeAt(0) || 0) -
|
||||||
(b.labels?.alertname?.charCodeAt(0) || 0),
|
(b.labels?.alertname?.charCodeAt(0) || 0),
|
||||||
@ -42,6 +48,7 @@ function NoFilterTable({
|
|||||||
title: 'Tags',
|
title: 'Tags',
|
||||||
dataIndex: 'labels',
|
dataIndex: 'labels',
|
||||||
key: 'tags',
|
key: 'tags',
|
||||||
|
width: 100,
|
||||||
render: (labels): JSX.Element => {
|
render: (labels): JSX.Element => {
|
||||||
const objectKeys = Object.keys(labels);
|
const objectKeys = Object.keys(labels);
|
||||||
const withOutSeverityKeys = objectKeys.filter((e) => e !== 'severity');
|
const withOutSeverityKeys = objectKeys.filter((e) => e !== 'severity');
|
||||||
@ -63,6 +70,7 @@ function NoFilterTable({
|
|||||||
title: 'Severity',
|
title: 'Severity',
|
||||||
dataIndex: 'labels',
|
dataIndex: 'labels',
|
||||||
key: 'severity',
|
key: 'severity',
|
||||||
|
width: 100,
|
||||||
sorter: (a, b): number => {
|
sorter: (a, b): number => {
|
||||||
const severityValueA = a.labels.severity;
|
const severityValueA = a.labels.severity;
|
||||||
const severityValueB = b.labels.severity;
|
const severityValueB = b.labels.severity;
|
||||||
@ -79,6 +87,7 @@ function NoFilterTable({
|
|||||||
{
|
{
|
||||||
title: 'Firing Since',
|
title: 'Firing Since',
|
||||||
dataIndex: 'startsAt',
|
dataIndex: 'startsAt',
|
||||||
|
width: 100,
|
||||||
sorter: (a, b): number =>
|
sorter: (a, b): number =>
|
||||||
new Date(a.startsAt).getTime() - new Date(b.startsAt).getTime(),
|
new Date(a.startsAt).getTime() - new Date(b.startsAt).getTime(),
|
||||||
render: (date): JSX.Element => {
|
render: (date): JSX.Element => {
|
||||||
@ -94,7 +103,13 @@ function NoFilterTable({
|
|||||||
];
|
];
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Table rowKey="startsAt" dataSource={filteredAlerts} columns={columns} />
|
<ResizeTableWrapper columns={columns}>
|
||||||
|
<Table
|
||||||
|
rowKey="startsAt"
|
||||||
|
dataSource={filteredAlerts}
|
||||||
|
components={{ header: { cell: ResizableHeader } }}
|
||||||
|
/>
|
||||||
|
</ResizeTableWrapper>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
File diff suppressed because it is too large
Load Diff
Loading…
x
Reference in New Issue
Block a user