chore: Add CPU core count to CPUMetrics

This commit adds the `cores` field to the `CPUMetrics` struct in order to include the number of CPU cores in the collected metrics. This information is useful for understanding the processing power of the server.
This commit is contained in:
Simon Larsen
2024-07-02 13:54:04 +01:00
parent 0df7209723
commit 9791aa1259
7 changed files with 162 additions and 8 deletions

View File

@@ -8,6 +8,7 @@ export interface MemoryMetrics {
export interface CPUMetrics {
percentUsed: number;
cores: number;
}
export interface BasicDiskMetrics {

9
Common/Utils/Memory.ts Normal file
View File

@@ -0,0 +1,9 @@
import NumberUtil from "./Number";
export default class MemoryUtil {
public static convertToGb(memoryInBytes: number): number {
const gb: number = memoryInBytes / 1024 / 1024 / 1024;
//return two decimal places
return NumberUtil.convertToTwoDecimalPlaces(gb);
}
}

5
Common/Utils/Number.ts Normal file
View File

@@ -0,0 +1,5 @@
export default class NumberUtil {
public static convertToTwoDecimalPlaces(value: number): number {
return Math.round(value * 100) / 100;
}
}

View File

@@ -1,11 +1,15 @@
import OneUptimeDate from "Common/Types/Date";
import { BasicDiskMetrics } from "Common/Types/Infrastructure/BasicMetrics";
import ServerMonitorResponse from "Common/Types/Monitor/ServerMonitor/ServerMonitorResponse";
import Button, { ButtonStyleType } from "CommonUI/src/Components/Button/Button";
import Detail from "CommonUI/src/Components/Detail/Detail";
import Field from "CommonUI/src/Components/Detail/Field";
import InfoCard from "CommonUI/src/Components/InfoCard/InfoCard";
import FieldType from "CommonUI/src/Components/Types/FieldType";
import { GetReactElementFunction } from "CommonUI/src/Types/FunctionTypes";
import React, { FunctionComponent, ReactElement } from "react";
import MemoryUtil from "Common/Utils/Memory";
import NumberUtil from "Common/Utils/Number";
export interface ComponentProps {
serverMonitorResponse: ServerMonitorResponse;
@@ -27,14 +31,130 @@ const ServerMonitorSummaryView: FunctionComponent<ComponentProps> = (
});
}
if(props.serverMonitorResponse.basicInfrastructureMetrics){
fields.push({
key: "basicInfrastructureMetrics",
title: "Basic Infrastructure Metrics",
description: "CPU, Memory, Disk and Network usage.",
fieldType: FieldType.JSON,
});
}
const getCpuMetrics: GetReactElementFunction = (): ReactElement => {
return (
<div className="flex space-x-3">
<InfoCard
className="w-1/2 shadow-none border-2 border-gray-100 "
title="CPU % Used"
value={
props.serverMonitorResponse?.basicInfrastructureMetrics?.cpuMetrics?.percentUsed?.toString()
? NumberUtil.convertToTwoDecimalPlaces(
props.serverMonitorResponse.basicInfrastructureMetrics
.cpuMetrics.percentUsed,
).toString()
: "-"
}
/>
<InfoCard
className="w-1/2 shadow-none border-2 border-gray-100 "
title="CPU Cores"
value={
props.serverMonitorResponse?.basicInfrastructureMetrics?.cpuMetrics?.cores?.toString() ||
"-" ||
"-"
}
/>
</div>
);
};
const getMemoryMetrics: GetReactElementFunction = (): ReactElement => {
return (
<div className="flex space-x-3 mt-3">
<InfoCard
className="w-1/3 shadow-none border-2 border-gray-100 "
title="Total Memory (GB)"
value={
props.serverMonitorResponse?.basicInfrastructureMetrics?.memoryMetrics?.total?.toString()
? MemoryUtil.convertToGb(
props.serverMonitorResponse.basicInfrastructureMetrics
.memoryMetrics.total,
).toString()
: "-"
}
/>
<InfoCard
className="w-1/3 shadow-none border-2 border-gray-100 "
title="Memory % Used"
value={
props.serverMonitorResponse?.basicInfrastructureMetrics?.memoryMetrics?.percentUsed?.toString()
? NumberUtil.convertToTwoDecimalPlaces(
props.serverMonitorResponse.basicInfrastructureMetrics
.memoryMetrics.percentUsed,
).toString()
: "-"
}
/>
<InfoCard
className="w-1/3 shadow-none border-2 border-gray-100 "
title="Memory % Free"
value={
props.serverMonitorResponse?.basicInfrastructureMetrics?.memoryMetrics?.percentFree?.toString()
? NumberUtil.convertToTwoDecimalPlaces(
props.serverMonitorResponse.basicInfrastructureMetrics
.memoryMetrics.percentFree,
).toString()
: "-"
}
/>
</div>
);
};
const getDiskMetrics: GetReactElementFunction = (): ReactElement => {
const diskMetrics: Array<BasicDiskMetrics> | undefined =
props.serverMonitorResponse?.basicInfrastructureMetrics?.diskMetrics;
if (!diskMetrics) {
return <div></div>;
}
const diskMetricsElements: Array<ReactElement> = diskMetrics.map(
(diskMetric: BasicDiskMetrics, index: number) => {
return (
<div className="mt-3">
<div className="mb-1">Disk {diskMetric.diskPath}</div>
<div key={index} className="flex space-x-3">
<InfoCard
className="w-1/3 shadow-none border-2 border-gray-100 "
title={`Total Size (GB)`}
value={
diskMetric.total.toString()
? MemoryUtil.convertToGb(diskMetric.total).toString()
: "-"
}
/>
<InfoCard
className="w-1/3 shadow-none border-2 border-gray-100 "
title={`% Used`}
value={
diskMetric.percentUsed.toString()
? NumberUtil.convertToTwoDecimalPlaces(
diskMetric.percentUsed,
).toString()
: "-"
}
/>
<InfoCard
className="w-1/3 shadow-none border-2 border-gray-100 "
title={`% Free`}
value={
diskMetric.percentFree.toString()
? NumberUtil.convertToTwoDecimalPlaces(
diskMetric.percentFree,
).toString()
: "-"
}
/>
</div>
</div>
);
},
);
return <div className="mb-3">{diskMetricsElements}</div>;
};
return (
<div className="space-y-5">
@@ -69,6 +189,15 @@ const ServerMonitorSummaryView: FunctionComponent<ComponentProps> = (
{showMoreDetails && fields.length > 0 && (
<div>
{props.serverMonitorResponse?.basicInfrastructureMetrics
?.cpuMetrics && getCpuMetrics()}
{props.serverMonitorResponse?.basicInfrastructureMetrics
?.memoryMetrics && getMemoryMetrics()}
{props.serverMonitorResponse?.basicInfrastructureMetrics
?.diskMetrics && getDiskMetrics()}
<Detail<ServerMonitorResponse>
id={"website-monitor-summary-detail"}
item={props.serverMonitorResponse}

View File

@@ -70,4 +70,10 @@ sudo ./oneuptime-infrastructure-agent configure --secret-key=YOUR_SECRET_KEY --o
```bash
sudo ./oneuptime-infrastructure-agent start
```
### Stopping the agent
```bash
sudo ./oneuptime-infrastructure-agent stop
```

View File

@@ -2,4 +2,5 @@ package model
type CPUMetrics struct {
PercentUsed float64 `json:"percentUsed"`
Cores int `json:"cores"`
}

View File

@@ -54,8 +54,11 @@ func GetCpuMetrics() *model.CPUMetrics {
}
cpuUsagePercent := (1 - idleDelta/totalDelta) * 100
numberOfCpuCores, err := cpu.Counts(true)
return &model.CPUMetrics{
PercentUsed: cpuUsagePercent,
Cores: numberOfCpuCores,
}
}