fix: error after changed table mode in overview (#30)
Co-authored-by: yaojiping <yaojiping@infini.ltd>
This commit is contained in:
parent
cfdc1870a9
commit
a08e33a570
|
@ -301,6 +301,7 @@ export default forwardRef((props: IProps, ref: any) => {
|
||||||
setSelectedItem(item);
|
setSelectedItem(item);
|
||||||
drawRef.current?.open();
|
drawRef.current?.open();
|
||||||
}}
|
}}
|
||||||
|
parentLoading={loading}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -1,303 +1,233 @@
|
||||||
import React, { useState, useEffect, useMemo } from "react";
|
import React, { useState, useEffect, useMemo } from "react";
|
||||||
import { Table, Tooltip, Progress } from "antd";
|
import { Table, Tooltip, Progress } from "antd";
|
||||||
import { formatter } from "@/utils/format";
|
import { formatter } from "@/utils/format";
|
||||||
import { formatUtcTimeToLocal } from "@/utils/utils";
|
|
||||||
import { formatMessage } from "umi/locale";
|
import { formatMessage } from "umi/locale";
|
||||||
import { SearchEngineIcon } from "@/lib/search_engines";
|
import { SearchEngineIcon } from "@/lib/search_engines";
|
||||||
import { HealthStatusView } from "@/components/infini/health_status_view";
|
import { HealthStatusView } from "@/components/infini/health_status_view";
|
||||||
import { StatusBlockGroup } from "@/components/infini/status_block";
|
import { StatusBlockGroup } from "@/components/infini/status_block";
|
||||||
import { Providers, ProviderIcon } from "@/lib/providers";
|
import { Providers, ProviderIcon } from "@/lib/providers";
|
||||||
import request from "@/utils/request";
|
import CommonTable from "../../components/CommonTable";
|
||||||
import styles from "./index.less"
|
|
||||||
|
|
||||||
export default (props) => {
|
export default (props) => {
|
||||||
const {
|
|
||||||
dataSource,
|
|
||||||
total,
|
|
||||||
from,
|
|
||||||
pageSize,
|
|
||||||
loading,
|
|
||||||
onPageChange,
|
|
||||||
onPageSizeChange,
|
|
||||||
onRowClick,
|
|
||||||
infoAction
|
|
||||||
} = props;
|
|
||||||
|
|
||||||
const [infos, setInfos] = useState({});
|
|
||||||
|
|
||||||
const fetchListInfo = async (data) => {
|
|
||||||
const res = await Promise.all(data?.map((item) => request(infoAction, {
|
|
||||||
method: "POST",
|
|
||||||
body: [item.id],
|
|
||||||
}, false, false)));
|
|
||||||
if (res) {
|
|
||||||
let newInfos = {}
|
|
||||||
res.forEach((item) => {
|
|
||||||
if (item && !item.error) {
|
|
||||||
newInfos = {
|
|
||||||
...newInfos,
|
|
||||||
...item
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
setInfos(newInfos);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
fetchListInfo(dataSource);
|
|
||||||
}, [JSON.stringify(dataSource)])
|
|
||||||
|
|
||||||
const [tableData] = useMemo(() => {
|
|
||||||
let tableData = dataSource?.map((item) => {
|
|
||||||
const id = item?._id;
|
|
||||||
const metadata = item._source || {};
|
|
||||||
const info = id && infos[id] ? infos[id] : {};
|
|
||||||
const summary = info.summary || {};
|
|
||||||
const metrics = info.metrics || {};
|
|
||||||
const fs_total_in_bytes = summary?.fs?.total_in_bytes || 0;
|
|
||||||
const fs_available_in_bytes = summary?.fs?.available_in_bytes || 0;
|
|
||||||
const fs_used_in_bytes = fs_total_in_bytes - fs_available_in_bytes;
|
|
||||||
const jvm_mem_total_in_bytes = summary?.jvm?.heap_max_in_bytes || 0;
|
|
||||||
const jvm_mem_used_in_bytes = summary?.jvm?.heap_used_in_bytes || 0;
|
|
||||||
|
|
||||||
const disk_percent =
|
|
||||||
fs_total_in_bytes > 0
|
|
||||||
? Math.round((fs_used_in_bytes / fs_total_in_bytes) * 100)
|
|
||||||
: 0;
|
|
||||||
const jvm_mem_percent =
|
|
||||||
jvm_mem_total_in_bytes > 0
|
|
||||||
? Math.round((jvm_mem_used_in_bytes / jvm_mem_total_in_bytes) * 100)
|
|
||||||
: 0;
|
|
||||||
|
|
||||||
const metrics_status = metrics?.status || {};
|
|
||||||
|
|
||||||
return {
|
|
||||||
id,
|
|
||||||
metadata,
|
|
||||||
summary,
|
|
||||||
metrics_status,
|
|
||||||
fs_total_in_bytes,
|
|
||||||
fs_available_in_bytes,
|
|
||||||
fs_used_in_bytes,
|
|
||||||
jvm_mem_total_in_bytes,
|
|
||||||
jvm_mem_used_in_bytes,
|
|
||||||
disk_percent,
|
|
||||||
jvm_mem_percent,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
return [tableData];
|
|
||||||
}, [JSON.stringify(dataSource), JSON.stringify(infos)]);
|
|
||||||
|
|
||||||
const [columns] = useMemo(() => {
|
|
||||||
let columns = [
|
|
||||||
{
|
|
||||||
title: "Name",
|
|
||||||
dataIndex: "name",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
placement="topLeft"
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Host: {record.metadata?.host}
|
|
||||||
<br />
|
|
||||||
Provider:{" "}
|
|
||||||
{formatMessage({
|
|
||||||
id: `cluster.providers.${record.metadata?.location
|
|
||||||
?.provider ?? Providers.OnPremises}`,
|
|
||||||
})}
|
|
||||||
<br />
|
|
||||||
Region: {record.metadata?.location?.region ?? ""}
|
|
||||||
<br />
|
|
||||||
Version: {record.metadata?.version ?? ""}
|
|
||||||
<br />
|
|
||||||
Tags:{" "}
|
|
||||||
{record.metadata?.tags ? record.metadata.tags.toString() : ""}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<div style={{ display: "flex", alignContent: "center", gap: 5 }}>
|
|
||||||
<SearchEngineIcon
|
|
||||||
distribution={record.metadata?.distribution}
|
|
||||||
width="20px"
|
|
||||||
height="20px"
|
|
||||||
/>
|
|
||||||
<span>{record.metadata?.name}</span>
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Version",
|
|
||||||
dataIndex: "version",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.metadata?.version ?? "";
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Health",
|
|
||||||
dataIndex: "health_status",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span
|
|
||||||
style={{
|
|
||||||
display: "flex",
|
|
||||||
flexDirection: "column",
|
|
||||||
gap: 5,
|
|
||||||
padding: 5,
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<StatusBlockGroup data={record.metrics_status?.data} />
|
|
||||||
<span>
|
|
||||||
{record.metrics_status?.metric?.label +
|
|
||||||
"(" +
|
|
||||||
(record.metrics_status?.data?.length || 14) +
|
|
||||||
" " +
|
|
||||||
record.metrics_status?.metric?.units +
|
|
||||||
")"}
|
|
||||||
</span>
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<div>
|
|
||||||
<HealthStatusView
|
|
||||||
status={record.metadata?.labels?.health_status}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Nodes",
|
|
||||||
dataIndex: "nodes",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.summary?.number_of_nodes || 0;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Indices",
|
|
||||||
dataIndex: "Indices",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.summary?.number_of_indices || 0;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Shards",
|
|
||||||
dataIndex: "Shards",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.summary?.number_of_shards || 0;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Docs",
|
|
||||||
dataIndex: "Docs",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={`Docs:${formatter.number(
|
|
||||||
record.summary?.number_of_documents
|
|
||||||
)}`}
|
|
||||||
>
|
|
||||||
{formatter.numberToHuman(record.summary?.number_of_documents)}
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Disk Usage",
|
|
||||||
dataIndex: "DiskUsage",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Total:{formatter.bytes(record.fs_total_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Used:{formatter.bytes(record.fs_used_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Free:{formatter.bytes(record.fs_available_in_bytes)}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Progress
|
|
||||||
strokeLinecap="square"
|
|
||||||
strokeColor="#558EF0"
|
|
||||||
strokeWidth={12}
|
|
||||||
percent={record.disk_percent}
|
|
||||||
format={(percent) => `${percent}%`}
|
|
||||||
/>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "JVM Heap",
|
|
||||||
dataIndex: "JVMHeap",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Total:{formatter.bytes(record.jvm_mem_total_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Used:{formatter.bytes(record.jvm_mem_used_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Free:
|
|
||||||
{formatter.bytes(
|
|
||||||
record.jvm_mem_total_in_bytes - record.jvm_mem_used_in_bytes
|
|
||||||
)}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Progress
|
|
||||||
strokeLinecap="square"
|
|
||||||
strokeColor="#00BFB3"
|
|
||||||
strokeWidth={12}
|
|
||||||
percent={record.jvm_mem_percent}
|
|
||||||
format={(percent) => `${percent}%`}
|
|
||||||
/>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
];
|
|
||||||
return [columns];
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="table-wrap">
|
<CommonTable
|
||||||
<Table
|
{...props}
|
||||||
size={"small"}
|
columns={[
|
||||||
loading={loading}
|
{
|
||||||
columns={columns}
|
title: "Name",
|
||||||
dataSource={tableData}
|
dataIndex: "name",
|
||||||
rowKey={"id"}
|
render: (text, record) => {
|
||||||
pagination={{
|
return (
|
||||||
size: "small",
|
<Tooltip
|
||||||
total,
|
placement="topLeft"
|
||||||
pageSize,
|
title={
|
||||||
onChange: onPageChange,
|
<span>
|
||||||
showSizeChanger: true,
|
Host: {record.metadata?.host}
|
||||||
onShowSizeChange: (_, size) => {
|
<br />
|
||||||
onPageSizeChange(size);
|
Provider:{" "}
|
||||||
|
{formatMessage({
|
||||||
|
id: `cluster.providers.${record.metadata?.location
|
||||||
|
?.provider ?? Providers.OnPremises}`,
|
||||||
|
})}
|
||||||
|
<br />
|
||||||
|
Region: {record.metadata?.location?.region ?? ""}
|
||||||
|
<br />
|
||||||
|
Version: {record.metadata?.version ?? ""}
|
||||||
|
<br />
|
||||||
|
Tags:{" "}
|
||||||
|
{record.metadata?.tags ? record.metadata.tags.toString() : ""}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<div style={{ display: "flex", alignContent: "center", gap: 5 }}>
|
||||||
|
<SearchEngineIcon
|
||||||
|
distribution={record.metadata?.distribution}
|
||||||
|
width="20px"
|
||||||
|
height="20px"
|
||||||
|
/>
|
||||||
|
<span>{record.metadata?.name}</span>
|
||||||
|
</div>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
showTotal: (total, range) =>
|
},
|
||||||
`${range[0]}-${range[1]} of ${total} items`,
|
{
|
||||||
}}
|
title: "Version",
|
||||||
onRow={(record, i) => {
|
dataIndex: "version",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.metadata?.version ?? "";
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Health",
|
||||||
|
dataIndex: "health_status",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span
|
||||||
|
style={{
|
||||||
|
display: "flex",
|
||||||
|
flexDirection: "column",
|
||||||
|
gap: 5,
|
||||||
|
padding: 5,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<StatusBlockGroup data={record.metrics_status?.data} />
|
||||||
|
<span>
|
||||||
|
{record.metrics_status?.metric?.label +
|
||||||
|
"(" +
|
||||||
|
(record.metrics_status?.data?.length || 14) +
|
||||||
|
" " +
|
||||||
|
record.metrics_status?.metric?.units +
|
||||||
|
")"}
|
||||||
|
</span>
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<div>
|
||||||
|
<HealthStatusView
|
||||||
|
status={record.metadata?.labels?.health_status}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Nodes",
|
||||||
|
dataIndex: "nodes",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.summary?.number_of_nodes || 0;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Indices",
|
||||||
|
dataIndex: "Indices",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.summary?.number_of_indices || 0;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Shards",
|
||||||
|
dataIndex: "Shards",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.summary?.number_of_shards || 0;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Docs",
|
||||||
|
dataIndex: "Docs",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={`Docs:${formatter.number(
|
||||||
|
record.summary?.number_of_documents
|
||||||
|
)}`}
|
||||||
|
>
|
||||||
|
{formatter.numberToHuman(record.summary?.number_of_documents)}
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Disk Usage",
|
||||||
|
dataIndex: "DiskUsage",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span>
|
||||||
|
Total:{formatter.bytes(record.fs_total_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Used:{formatter.bytes(record.fs_used_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Free:{formatter.bytes(record.fs_available_in_bytes)}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Progress
|
||||||
|
strokeLinecap="square"
|
||||||
|
strokeColor="#558EF0"
|
||||||
|
strokeWidth={12}
|
||||||
|
percent={record.disk_percent}
|
||||||
|
format={(percent) => `${percent}%`}
|
||||||
|
/>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "JVM Heap",
|
||||||
|
dataIndex: "JVMHeap",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span>
|
||||||
|
Total:{formatter.bytes(record.jvm_mem_total_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Used:{formatter.bytes(record.jvm_mem_used_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Free:
|
||||||
|
{formatter.bytes(
|
||||||
|
record.jvm_mem_total_in_bytes - record.jvm_mem_used_in_bytes
|
||||||
|
)}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Progress
|
||||||
|
strokeLinecap="square"
|
||||||
|
strokeColor="#00BFB3"
|
||||||
|
strokeWidth={12}
|
||||||
|
percent={record.jvm_mem_percent}
|
||||||
|
format={(percent) => `${percent}%`}
|
||||||
|
/>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
formatData={(dataSource, infos) => {
|
||||||
|
const newData = dataSource?.map((item) => {
|
||||||
|
const id = item?._id;
|
||||||
|
const metadata = item._source || {};
|
||||||
|
const info = id && infos[id] ? infos[id] : {};
|
||||||
|
const summary = info.summary || {};
|
||||||
|
const metrics = info.metrics || {};
|
||||||
|
const fs_total_in_bytes = summary?.fs?.total_in_bytes || 0;
|
||||||
|
const fs_available_in_bytes = summary?.fs?.available_in_bytes || 0;
|
||||||
|
const fs_used_in_bytes = fs_total_in_bytes - fs_available_in_bytes;
|
||||||
|
const jvm_mem_total_in_bytes = summary?.jvm?.heap_max_in_bytes || 0;
|
||||||
|
const jvm_mem_used_in_bytes = summary?.jvm?.heap_used_in_bytes || 0;
|
||||||
|
|
||||||
|
const disk_percent =
|
||||||
|
fs_total_in_bytes > 0
|
||||||
|
? Math.round((fs_used_in_bytes / fs_total_in_bytes) * 100)
|
||||||
|
: 0;
|
||||||
|
const jvm_mem_percent =
|
||||||
|
jvm_mem_total_in_bytes > 0
|
||||||
|
? Math.round((jvm_mem_used_in_bytes / jvm_mem_total_in_bytes) * 100)
|
||||||
|
: 0;
|
||||||
|
|
||||||
|
const metrics_status = metrics?.status || {};
|
||||||
|
|
||||||
return {
|
return {
|
||||||
onClick: (event) => {
|
id,
|
||||||
onRowClick(dataSource[i]);
|
metadata,
|
||||||
},
|
summary,
|
||||||
|
metrics_status,
|
||||||
|
fs_total_in_bytes,
|
||||||
|
fs_available_in_bytes,
|
||||||
|
fs_used_in_bytes,
|
||||||
|
jvm_mem_total_in_bytes,
|
||||||
|
jvm_mem_used_in_bytes,
|
||||||
|
disk_percent,
|
||||||
|
jvm_mem_percent,
|
||||||
};
|
};
|
||||||
}}
|
});
|
||||||
rowClassName={() => styles.rowPointer}
|
return newData
|
||||||
/>
|
}}
|
||||||
</div>
|
/>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,208 +1,167 @@
|
||||||
import React, { useState, useEffect, useMemo } from "react";
|
import React, { useState, useEffect, useMemo } from "react";
|
||||||
import { Table, Tooltip, Progress, Icon } from "antd";
|
import { Tooltip, Progress, Icon } from "antd";
|
||||||
import { formatter } from "@/utils/format";
|
import { formatter } from "@/utils/format";
|
||||||
import { formatUtcTimeToLocal } from "@/utils/utils";
|
import { formatUtcTimeToLocal } from "@/utils/utils";
|
||||||
import { formatMessage } from "umi/locale";
|
import { formatMessage } from "umi/locale";
|
||||||
import { SearchEngineIcon } from "@/lib/search_engines";
|
|
||||||
import { HealthStatusView } from "@/components/infini/health_status_view";
|
import { HealthStatusView } from "@/components/infini/health_status_view";
|
||||||
import { StatusBlockGroup } from "@/components/infini/status_block";
|
import { StatusBlockGroup } from "@/components/infini/status_block";
|
||||||
|
import CommonTable from "../../components/CommonTable";
|
||||||
|
|
||||||
export default (props) => {
|
export default (props) => {
|
||||||
const {
|
|
||||||
infos,
|
|
||||||
dataSource,
|
|
||||||
total,
|
|
||||||
from,
|
|
||||||
pageSize,
|
|
||||||
loading,
|
|
||||||
onPageChange,
|
|
||||||
onPageSizeChange,
|
|
||||||
onRowClick,
|
|
||||||
} = props;
|
|
||||||
|
|
||||||
const [tableData] = useMemo(() => {
|
|
||||||
let tableData = dataSource?.map((item) => {
|
|
||||||
const id = item?._source?.metadata?.index_id;
|
|
||||||
const metadata = item?._source?.metadata || {};
|
|
||||||
const info = id && infos[id] ? infos[id] : {};
|
|
||||||
const summary = info.summary || {};
|
|
||||||
const metrics = info.metrics || {};
|
|
||||||
|
|
||||||
const timestamp = item?._source?.timestamp
|
|
||||||
? formatUtcTimeToLocal(item?._source?.timestamp)
|
|
||||||
: "N/A";
|
|
||||||
const metrics_status = metrics?.status || {};
|
|
||||||
|
|
||||||
return {
|
|
||||||
id,
|
|
||||||
metadata,
|
|
||||||
summary,
|
|
||||||
metrics_status,
|
|
||||||
timestamp,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
return [tableData];
|
|
||||||
}, [JSON.stringify(dataSource), JSON.stringify(infos)]);
|
|
||||||
|
|
||||||
const [columns] = useMemo(() => {
|
|
||||||
let columns = [
|
|
||||||
{
|
|
||||||
title: "Name",
|
|
||||||
dataIndex: "name",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
placement="topLeft"
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Cluster: {record.metadata?.cluster_name}
|
|
||||||
<br />
|
|
||||||
Aliases: {record.metadata?.aliases?.join(",")}
|
|
||||||
<br />
|
|
||||||
Timestamp: {record.timestamp}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<div style={{ display: "flex", alignContent: "center", gap: 5 }}>
|
|
||||||
<span>
|
|
||||||
<Icon type="table" />
|
|
||||||
</span>
|
|
||||||
<span>{record.metadata?.index_name}</span>
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Health",
|
|
||||||
dataIndex: "health_status",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span
|
|
||||||
style={{
|
|
||||||
display: "flex",
|
|
||||||
flexDirection: "column",
|
|
||||||
gap: 5,
|
|
||||||
padding: 5,
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<StatusBlockGroup data={record.metrics_status?.data} />
|
|
||||||
<span>
|
|
||||||
{record.metrics_status?.metric?.label +
|
|
||||||
"(" +
|
|
||||||
(record.metrics_status?.data?.length || 14) +
|
|
||||||
" " +
|
|
||||||
record.metrics_status?.metric?.units +
|
|
||||||
")"}
|
|
||||||
</span>
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<div>
|
|
||||||
<HealthStatusView
|
|
||||||
status={record.metadata?.labels?.health_status}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Status",
|
|
||||||
dataIndex: "index_status",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.metadata?.labels?.state ?? "N/A";
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Store Size",
|
|
||||||
dataIndex: "store_size",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.summary?.index_info?.store_size?.toUpperCase() || "N/A";
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Shards",
|
|
||||||
dataIndex: "Shards",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Unassigned Shards:
|
|
||||||
{record.summary?.unassigned_shards || 0}
|
|
||||||
<br />
|
|
||||||
Shards:
|
|
||||||
{record.summary?.index_info?.shards || 0}
|
|
||||||
<br />
|
|
||||||
Replicas:
|
|
||||||
{record.summary?.index_info?.replicas || 0}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
{record.summary?.unassigned_shards || 0} /{" "}
|
|
||||||
{record.summary?.index_info?.shards ||
|
|
||||||
0 + (record.summary?.index_info?.replicas || 0)}
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Docs",
|
|
||||||
dataIndex: "Docs",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Deleted:
|
|
||||||
{formatter.number(record.summary?.docs?.deleted || 0)}
|
|
||||||
<br />
|
|
||||||
Total:
|
|
||||||
{formatter.number(record.summary?.docs?.count || 0)}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
{formatter.numberToHuman(record.summary?.docs?.deleted)} /{" "}
|
|
||||||
{formatter.numberToHuman(record.summary?.docs?.count)}
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
];
|
|
||||||
return [columns];
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="table-wrap">
|
<CommonTable
|
||||||
<Table
|
{...props}
|
||||||
size={"small"}
|
columns={[
|
||||||
loading={loading}
|
{
|
||||||
columns={columns}
|
title: "Name",
|
||||||
dataSource={tableData}
|
dataIndex: "name",
|
||||||
rowKey={"id"}
|
render: (text, record) => {
|
||||||
pagination={{
|
return (
|
||||||
size: "small",
|
<Tooltip
|
||||||
total,
|
placement="topLeft"
|
||||||
pageSize,
|
title={
|
||||||
onChange: onPageChange,
|
<span>
|
||||||
showSizeChanger: true,
|
Cluster: {record.metadata?.cluster_name}
|
||||||
onShowSizeChange: (_, size) => {
|
<br />
|
||||||
onPageSizeChange(size);
|
Aliases: {record.metadata?.aliases?.join(",")}
|
||||||
|
<br />
|
||||||
|
Timestamp: {record.timestamp}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<div style={{ display: "flex", alignContent: "center", gap: 5 }}>
|
||||||
|
<span>
|
||||||
|
<Icon type="table" />
|
||||||
|
</span>
|
||||||
|
<span>{record.metadata?.index_name}</span>
|
||||||
|
</div>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
showTotal: (total, range) =>
|
},
|
||||||
`${range[0]}-${range[1]} of ${total} items`,
|
{
|
||||||
}}
|
title: "Health",
|
||||||
onRow={(record, i) => {
|
dataIndex: "health_status",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span
|
||||||
|
style={{
|
||||||
|
display: "flex",
|
||||||
|
flexDirection: "column",
|
||||||
|
gap: 5,
|
||||||
|
padding: 5,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<StatusBlockGroup data={record.metrics_status?.data} />
|
||||||
|
<span>
|
||||||
|
{record.metrics_status?.metric?.label +
|
||||||
|
"(" +
|
||||||
|
(record.metrics_status?.data?.length || 14) +
|
||||||
|
" " +
|
||||||
|
record.metrics_status?.metric?.units +
|
||||||
|
")"}
|
||||||
|
</span>
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<div>
|
||||||
|
<HealthStatusView
|
||||||
|
status={record.metadata?.labels?.health_status}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Status",
|
||||||
|
dataIndex: "index_status",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.metadata?.labels?.state ?? "N/A";
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Store Size",
|
||||||
|
dataIndex: "store_size",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.summary?.index_info?.store_size?.toUpperCase() || "N/A";
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Shards",
|
||||||
|
dataIndex: "Shards",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span>
|
||||||
|
Unassigned Shards:
|
||||||
|
{record.summary?.unassigned_shards || 0}
|
||||||
|
<br />
|
||||||
|
Shards:
|
||||||
|
{record.summary?.index_info?.shards || 0}
|
||||||
|
<br />
|
||||||
|
Replicas:
|
||||||
|
{record.summary?.index_info?.replicas || 0}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
{record.summary?.unassigned_shards || 0} /{" "}
|
||||||
|
{record.summary?.index_info?.shards ||
|
||||||
|
0 + (record.summary?.index_info?.replicas || 0)}
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Docs",
|
||||||
|
dataIndex: "Docs",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span>
|
||||||
|
Deleted:
|
||||||
|
{formatter.number(record.summary?.docs?.deleted || 0)}
|
||||||
|
<br />
|
||||||
|
Total:
|
||||||
|
{formatter.number(record.summary?.docs?.count || 0)}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
{formatter.numberToHuman(record.summary?.docs?.deleted)} /{" "}
|
||||||
|
{formatter.numberToHuman(record.summary?.docs?.count)}
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
formatData={(dataSource, infos) => {
|
||||||
|
const newData = dataSource?.map((item) => {
|
||||||
|
const id = item?._source?.metadata?.index_id;
|
||||||
|
const metadata = item?._source?.metadata || {};
|
||||||
|
const info = id && infos[id] ? infos[id] : {};
|
||||||
|
const summary = info.summary || {};
|
||||||
|
const metrics = info.metrics || {};
|
||||||
|
|
||||||
|
const timestamp = item?._source?.timestamp
|
||||||
|
? formatUtcTimeToLocal(item?._source?.timestamp)
|
||||||
|
: "N/A";
|
||||||
|
const metrics_status = metrics?.status || {};
|
||||||
|
|
||||||
return {
|
return {
|
||||||
onClick: (event) => {
|
id,
|
||||||
onRowClick(dataSource[i]);
|
metadata,
|
||||||
},
|
summary,
|
||||||
|
metrics_status,
|
||||||
|
timestamp,
|
||||||
};
|
};
|
||||||
}}
|
});
|
||||||
/>
|
return newData
|
||||||
</div>
|
}}
|
||||||
|
/>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,257 +1,213 @@
|
||||||
import React, { useState, useEffect, useMemo } from "react";
|
import React, { useState, useEffect, useMemo } from "react";
|
||||||
import { Table, Tooltip, Progress, Icon } from "antd";
|
import { Tooltip, Progress, Icon } from "antd";
|
||||||
import { formatter } from "@/utils/format";
|
import { formatter } from "@/utils/format";
|
||||||
import { formatUtcTimeToLocal } from "@/utils/utils";
|
|
||||||
import { formatMessage } from "umi/locale";
|
|
||||||
import { SearchEngineIcon } from "@/lib/search_engines";
|
|
||||||
import { HealthStatusView } from "@/components/infini/health_status_view";
|
import { HealthStatusView } from "@/components/infini/health_status_view";
|
||||||
import { StatusBlockGroup } from "@/components/infini/status_block";
|
import { StatusBlockGroup } from "@/components/infini/status_block";
|
||||||
|
import CommonTable from "../../components/CommonTable";
|
||||||
|
|
||||||
export default (props) => {
|
export default (props) => {
|
||||||
const {
|
|
||||||
infos,
|
|
||||||
dataSource,
|
|
||||||
total,
|
|
||||||
from,
|
|
||||||
pageSize,
|
|
||||||
loading,
|
|
||||||
onPageChange,
|
|
||||||
onPageSizeChange,
|
|
||||||
onRowClick,
|
|
||||||
} = props;
|
|
||||||
|
|
||||||
const [tableData] = useMemo(() => {
|
|
||||||
let tableData = dataSource?.map((item) => {
|
|
||||||
const id = item?._source?.metadata?.node_id;
|
|
||||||
const metadata = item._source?.metadata || {};
|
|
||||||
const info = id && infos[id] ? infos[id] : {};
|
|
||||||
const summary = info.summary || {};
|
|
||||||
const metrics = info.metrics || {};
|
|
||||||
const fs_total_in_bytes = summary?.fs?.total?.total_in_bytes || 0;
|
|
||||||
const fs_available_in_bytes = summary?.fs?.total?.available_in_bytes || 0;
|
|
||||||
const fs_used_in_bytes = fs_total_in_bytes - fs_available_in_bytes;
|
|
||||||
const jvm_mem_total_in_bytes = summary?.jvm?.mem?.heap_max_in_bytes || 0;
|
|
||||||
const jvm_mem_used_in_bytes = summary?.jvm?.mem?.heap_used_in_bytes || 0;
|
|
||||||
|
|
||||||
const disk_percent =
|
|
||||||
fs_total_in_bytes > 0
|
|
||||||
? Math.round((fs_used_in_bytes / fs_total_in_bytes) * 100)
|
|
||||||
: 0;
|
|
||||||
const jvm_mem_percent =
|
|
||||||
jvm_mem_total_in_bytes > 0
|
|
||||||
? Math.round((jvm_mem_used_in_bytes / jvm_mem_total_in_bytes) * 100)
|
|
||||||
: 0;
|
|
||||||
|
|
||||||
const metrics_status = metrics?.status || {};
|
|
||||||
|
|
||||||
return {
|
|
||||||
id,
|
|
||||||
metadata,
|
|
||||||
summary,
|
|
||||||
metrics_status,
|
|
||||||
fs_total_in_bytes,
|
|
||||||
fs_available_in_bytes,
|
|
||||||
fs_used_in_bytes,
|
|
||||||
jvm_mem_total_in_bytes,
|
|
||||||
jvm_mem_used_in_bytes,
|
|
||||||
disk_percent,
|
|
||||||
jvm_mem_percent,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
return [tableData];
|
|
||||||
}, [JSON.stringify(dataSource), JSON.stringify(infos)]);
|
|
||||||
|
|
||||||
const [columns] = useMemo(() => {
|
|
||||||
let columns = [
|
|
||||||
{
|
|
||||||
title: "Name",
|
|
||||||
dataIndex: "name",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
placement="topLeft"
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Transport Address:{" "}
|
|
||||||
{record.metadata?.labels?.transport_address}
|
|
||||||
<br />
|
|
||||||
Cluster: {record.metadata?.cluster_name ?? ""}
|
|
||||||
<br />
|
|
||||||
Version: {record.metadata?.labels?.version ?? ""}
|
|
||||||
<br />
|
|
||||||
Roles:{" "}
|
|
||||||
{record.metadata?.labels?.roles
|
|
||||||
? record.metadata?.labels?.roles?.toString()
|
|
||||||
: ""}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<div style={{ display: "flex", alignContent: "center", gap: 5 }}>
|
|
||||||
<span>
|
|
||||||
{record.summary?.is_master_node ? (
|
|
||||||
<Icon type="star" theme="filled" />
|
|
||||||
) : (
|
|
||||||
<Icon type="database" />
|
|
||||||
)}
|
|
||||||
</span>
|
|
||||||
<span>{record.metadata?.node_name}</span>
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Status",
|
|
||||||
dataIndex: "status",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span
|
|
||||||
style={{
|
|
||||||
display: "flex",
|
|
||||||
flexDirection: "column",
|
|
||||||
gap: 5,
|
|
||||||
padding: 5,
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<StatusBlockGroup data={record.metrics_status?.data} />
|
|
||||||
<span>
|
|
||||||
{record.metrics_status?.metric?.label +
|
|
||||||
"(" +
|
|
||||||
(record.metrics_status?.data?.length || 14) +
|
|
||||||
" " +
|
|
||||||
record.metrics_status?.metric?.units +
|
|
||||||
")"}
|
|
||||||
</span>
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<div>
|
|
||||||
<HealthStatusView status={record.metadata?.labels?.status} />
|
|
||||||
</div>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Indices",
|
|
||||||
dataIndex: "Indices",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.summary?.shard_info?.indices_count || 0;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Shards",
|
|
||||||
dataIndex: "Shards",
|
|
||||||
render: (text, record) => {
|
|
||||||
return record.summary?.shard_info?.shard_count || 0;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Docs",
|
|
||||||
dataIndex: "Docs",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={`Docs:${formatter.number(
|
|
||||||
record.summary?.indices?.docs?.count
|
|
||||||
)}`}
|
|
||||||
>
|
|
||||||
{formatter.numberToHuman(record.summary?.indices?.docs?.count)}
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "Disk Usage",
|
|
||||||
dataIndex: "DiskUsage",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Total:{formatter.bytes(record.fs_total_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Used:{formatter.bytes(record.fs_used_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Free:{formatter.bytes(record.fs_available_in_bytes)}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Progress
|
|
||||||
strokeLinecap="square"
|
|
||||||
strokeColor="#558EF0"
|
|
||||||
strokeWidth={12}
|
|
||||||
percent={record.disk_percent}
|
|
||||||
format={(percent) => `${percent}%`}
|
|
||||||
/>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
title: "JVM Heap",
|
|
||||||
dataIndex: "JVMHeap",
|
|
||||||
render: (text, record) => {
|
|
||||||
return (
|
|
||||||
<Tooltip
|
|
||||||
title={
|
|
||||||
<span>
|
|
||||||
Total:{formatter.bytes(record.jvm_mem_total_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Used:{formatter.bytes(record.jvm_mem_used_in_bytes)}
|
|
||||||
<br />
|
|
||||||
Free:
|
|
||||||
{formatter.bytes(
|
|
||||||
record.jvm_mem_total_in_bytes - record.jvm_mem_used_in_bytes
|
|
||||||
)}
|
|
||||||
</span>
|
|
||||||
}
|
|
||||||
>
|
|
||||||
<Progress
|
|
||||||
strokeLinecap="square"
|
|
||||||
strokeColor="#00BFB3"
|
|
||||||
strokeWidth={12}
|
|
||||||
percent={record.jvm_mem_percent}
|
|
||||||
format={(percent) => `${percent}%`}
|
|
||||||
/>
|
|
||||||
</Tooltip>
|
|
||||||
);
|
|
||||||
},
|
|
||||||
},
|
|
||||||
];
|
|
||||||
return [columns];
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="table-wrap">
|
<CommonTable
|
||||||
<Table
|
{...props}
|
||||||
size={"small"}
|
columns={[
|
||||||
loading={loading}
|
{
|
||||||
columns={columns}
|
title: "Name",
|
||||||
dataSource={tableData}
|
dataIndex: "name",
|
||||||
rowKey={"id"}
|
render: (text, record) => {
|
||||||
pagination={{
|
return (
|
||||||
size: "small",
|
<Tooltip
|
||||||
total,
|
placement="topLeft"
|
||||||
pageSize,
|
title={
|
||||||
onChange: onPageChange,
|
<span>
|
||||||
showSizeChanger: true,
|
Transport Address:{" "}
|
||||||
onShowSizeChange: (_, size) => {
|
{record.metadata?.labels?.transport_address}
|
||||||
onPageSizeChange(size);
|
<br />
|
||||||
|
Cluster: {record.metadata?.cluster_name ?? ""}
|
||||||
|
<br />
|
||||||
|
Version: {record.metadata?.labels?.version ?? ""}
|
||||||
|
<br />
|
||||||
|
Roles:{" "}
|
||||||
|
{record.metadata?.labels?.roles
|
||||||
|
? record.metadata?.labels?.roles?.toString()
|
||||||
|
: ""}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<div style={{ display: "flex", alignContent: "center", gap: 5 }}>
|
||||||
|
<span>
|
||||||
|
{record.summary?.is_master_node ? (
|
||||||
|
<Icon type="star" theme="filled" />
|
||||||
|
) : (
|
||||||
|
<Icon type="database" />
|
||||||
|
)}
|
||||||
|
</span>
|
||||||
|
<span>{record.metadata?.node_name}</span>
|
||||||
|
</div>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
showTotal: (total, range) =>
|
},
|
||||||
`${range[0]}-${range[1]} of ${total} items`,
|
{
|
||||||
}}
|
title: "Status",
|
||||||
onRow={(record, i) => {
|
dataIndex: "status",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span
|
||||||
|
style={{
|
||||||
|
display: "flex",
|
||||||
|
flexDirection: "column",
|
||||||
|
gap: 5,
|
||||||
|
padding: 5,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<StatusBlockGroup data={record.metrics_status?.data} />
|
||||||
|
<span>
|
||||||
|
{record.metrics_status?.metric?.label +
|
||||||
|
"(" +
|
||||||
|
(record.metrics_status?.data?.length || 14) +
|
||||||
|
" " +
|
||||||
|
record.metrics_status?.metric?.units +
|
||||||
|
")"}
|
||||||
|
</span>
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<div>
|
||||||
|
<HealthStatusView status={record.metadata?.labels?.status} />
|
||||||
|
</div>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Indices",
|
||||||
|
dataIndex: "Indices",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.summary?.shard_info?.indices_count || 0;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Shards",
|
||||||
|
dataIndex: "Shards",
|
||||||
|
render: (text, record) => {
|
||||||
|
return record.summary?.shard_info?.shard_count || 0;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Docs",
|
||||||
|
dataIndex: "Docs",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={`Docs:${formatter.number(
|
||||||
|
record.summary?.indices?.docs?.count
|
||||||
|
)}`}
|
||||||
|
>
|
||||||
|
{formatter.numberToHuman(record.summary?.indices?.docs?.count)}
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Disk Usage",
|
||||||
|
dataIndex: "DiskUsage",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span>
|
||||||
|
Total:{formatter.bytes(record.fs_total_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Used:{formatter.bytes(record.fs_used_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Free:{formatter.bytes(record.fs_available_in_bytes)}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Progress
|
||||||
|
strokeLinecap="square"
|
||||||
|
strokeColor="#558EF0"
|
||||||
|
strokeWidth={12}
|
||||||
|
percent={record.disk_percent}
|
||||||
|
format={(percent) => `${percent}%`}
|
||||||
|
/>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "JVM Heap",
|
||||||
|
dataIndex: "JVMHeap",
|
||||||
|
render: (text, record) => {
|
||||||
|
return (
|
||||||
|
<Tooltip
|
||||||
|
title={
|
||||||
|
<span>
|
||||||
|
Total:{formatter.bytes(record.jvm_mem_total_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Used:{formatter.bytes(record.jvm_mem_used_in_bytes)}
|
||||||
|
<br />
|
||||||
|
Free:
|
||||||
|
{formatter.bytes(
|
||||||
|
record.jvm_mem_total_in_bytes - record.jvm_mem_used_in_bytes
|
||||||
|
)}
|
||||||
|
</span>
|
||||||
|
}
|
||||||
|
>
|
||||||
|
<Progress
|
||||||
|
strokeLinecap="square"
|
||||||
|
strokeColor="#00BFB3"
|
||||||
|
strokeWidth={12}
|
||||||
|
percent={record.jvm_mem_percent}
|
||||||
|
format={(percent) => `${percent}%`}
|
||||||
|
/>
|
||||||
|
</Tooltip>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]}
|
||||||
|
formatData={(dataSource, infos) => {
|
||||||
|
const newData = dataSource?.map((item) => {
|
||||||
|
const id = item?._source?.metadata?.node_id;
|
||||||
|
const metadata = item._source?.metadata || {};
|
||||||
|
const info = id && infos[id] ? infos[id] : {};
|
||||||
|
const summary = info.summary || {};
|
||||||
|
const metrics = info.metrics || {};
|
||||||
|
const fs_total_in_bytes = summary?.fs?.total?.total_in_bytes || 0;
|
||||||
|
const fs_available_in_bytes = summary?.fs?.total?.available_in_bytes || 0;
|
||||||
|
const fs_used_in_bytes = fs_total_in_bytes - fs_available_in_bytes;
|
||||||
|
const jvm_mem_total_in_bytes = summary?.jvm?.mem?.heap_max_in_bytes || 0;
|
||||||
|
const jvm_mem_used_in_bytes = summary?.jvm?.mem?.heap_used_in_bytes || 0;
|
||||||
|
|
||||||
|
const disk_percent =
|
||||||
|
fs_total_in_bytes > 0
|
||||||
|
? Math.round((fs_used_in_bytes / fs_total_in_bytes) * 100)
|
||||||
|
: 0;
|
||||||
|
const jvm_mem_percent =
|
||||||
|
jvm_mem_total_in_bytes > 0
|
||||||
|
? Math.round((jvm_mem_used_in_bytes / jvm_mem_total_in_bytes) * 100)
|
||||||
|
: 0;
|
||||||
|
|
||||||
|
const metrics_status = metrics?.status || {};
|
||||||
|
|
||||||
return {
|
return {
|
||||||
onClick: (event) => {
|
id,
|
||||||
onRowClick(dataSource[i]);
|
metadata,
|
||||||
},
|
summary,
|
||||||
|
metrics_status,
|
||||||
|
fs_total_in_bytes,
|
||||||
|
fs_available_in_bytes,
|
||||||
|
fs_used_in_bytes,
|
||||||
|
jvm_mem_total_in_bytes,
|
||||||
|
jvm_mem_used_in_bytes,
|
||||||
|
disk_percent,
|
||||||
|
jvm_mem_percent,
|
||||||
};
|
};
|
||||||
}}
|
});
|
||||||
/>
|
return newData
|
||||||
</div>
|
}}
|
||||||
|
/>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
|
@ -0,0 +1,91 @@
|
||||||
|
import React, { useState, useEffect, useMemo } from "react";
|
||||||
|
import { Table, Tooltip, Progress } from "antd";
|
||||||
|
import { formatter } from "@/utils/format";
|
||||||
|
import { formatUtcTimeToLocal } from "@/utils/utils";
|
||||||
|
import { formatMessage } from "umi/locale";
|
||||||
|
import { SearchEngineIcon } from "@/lib/search_engines";
|
||||||
|
import { HealthStatusView } from "@/components/infini/health_status_view";
|
||||||
|
import { StatusBlockGroup } from "@/components/infini/status_block";
|
||||||
|
import { Providers, ProviderIcon } from "@/lib/providers";
|
||||||
|
import request from "@/utils/request";
|
||||||
|
import styles from "./index.less"
|
||||||
|
|
||||||
|
export default (props) => {
|
||||||
|
const {
|
||||||
|
dataSource,
|
||||||
|
total,
|
||||||
|
from,
|
||||||
|
pageSize,
|
||||||
|
loading,
|
||||||
|
onPageChange,
|
||||||
|
onPageSizeChange,
|
||||||
|
onRowClick,
|
||||||
|
infoAction,
|
||||||
|
formatData,
|
||||||
|
columns = [],
|
||||||
|
parentLoading
|
||||||
|
} = props;
|
||||||
|
|
||||||
|
const [infos, setInfos] = useState({});
|
||||||
|
|
||||||
|
const fetchListInfo = async (data) => {
|
||||||
|
const res = await Promise.all(data?.map((item) => request(infoAction, {
|
||||||
|
method: "POST",
|
||||||
|
body: [item.id],
|
||||||
|
}, false, false)));
|
||||||
|
if (res) {
|
||||||
|
let newInfos = {}
|
||||||
|
res.forEach((item) => {
|
||||||
|
if (item && !item.error) {
|
||||||
|
newInfos = {
|
||||||
|
...newInfos,
|
||||||
|
...item
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
setInfos(newInfos);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (!parentLoading) {
|
||||||
|
fetchListInfo(dataSource);
|
||||||
|
}
|
||||||
|
}, [JSON.stringify(dataSource), parentLoading])
|
||||||
|
|
||||||
|
const tableData = useMemo(() => {
|
||||||
|
return formatData(dataSource, infos);
|
||||||
|
}, [JSON.stringify(dataSource), JSON.stringify(infos)]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="table-wrap">
|
||||||
|
<Table
|
||||||
|
size={"small"}
|
||||||
|
loading={loading}
|
||||||
|
columns={columns}
|
||||||
|
dataSource={tableData}
|
||||||
|
rowKey={"id"}
|
||||||
|
pagination={{
|
||||||
|
size: "small",
|
||||||
|
total,
|
||||||
|
pageSize,
|
||||||
|
onChange: onPageChange,
|
||||||
|
showSizeChanger: true,
|
||||||
|
onShowSizeChange: (_, size) => {
|
||||||
|
onPageSizeChange(size);
|
||||||
|
},
|
||||||
|
showTotal: (total, range) =>
|
||||||
|
`${range[0]}-${range[1]} of ${total} items`,
|
||||||
|
}}
|
||||||
|
onRow={(record, i) => {
|
||||||
|
return {
|
||||||
|
onClick: (event) => {
|
||||||
|
onRowClick(dataSource[i]);
|
||||||
|
},
|
||||||
|
};
|
||||||
|
}}
|
||||||
|
rowClassName={() => styles.rowPointer}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
Loading…
Reference in New Issue