@jsenv/os-metrics 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +131 -0
- package/package.json +23 -0
- package/src/available_cpu.js +9 -0
- package/src/available_memory.js +3 -0
- package/src/cpu_monitoring.js +17 -0
- package/src/cpu_usage.js +219 -0
- package/src/cpu_usage.test_manual.js +17 -0
- package/src/main.js +12 -0
- package/src/memory_monitoring.js +21 -0
- package/src/metric_monitoring.js +44 -0
- package/src/os_version.js +3 -0
- package/src/process_memory_monitoring.js +9 -0
package/README.md
ADDED
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
# @jsenv/os-metrics
|
|
2
|
+
|
|
3
|
+
[](https://www.npmjs.com/package/@jsenv/os-metrics)
|
|
4
|
+
|
|
5
|
+
A lightweight library for monitoring CPU and memory usage of both your Node.js process and the operating system.
|
|
6
|
+
|
|
7
|
+
## Features
|
|
8
|
+
|
|
9
|
+
- Simple API for monitoring system resources
|
|
10
|
+
- Process-specific and OS-wide metrics
|
|
11
|
+
- Statistical analysis (min, max, median) for measurement periods
|
|
12
|
+
- Zero dependencies
|
|
13
|
+
|
|
14
|
+
## Installation
|
|
15
|
+
|
|
16
|
+
```console
|
|
17
|
+
npm install @jsenv/os-metrics
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## CPU Usage Monitoring
|
|
21
|
+
|
|
22
|
+
Monitor CPU usage for both the current process and the entire operating system:
|
|
23
|
+
|
|
24
|
+
```js
|
|
25
|
+
// Start monitoring
|
|
26
|
+
const [processCpuMonitoring, osCpuMonitoring] = startMonitoringCpuUsage();
|
|
27
|
+
|
|
28
|
+
// Take measurements at regular intervals
|
|
29
|
+
const interval = setInterval(() => {
|
|
30
|
+
const processCpuUsage = processCpuMonitoring.measure(); // Returns value between 0-1
|
|
31
|
+
const osCpuUsage = osCpuMonitoring.measure(); // Returns value between 0-1
|
|
32
|
+
|
|
33
|
+
console.log(`Process CPU: ${(processCpuUsage * 100).toFixed(2)}%`);
|
|
34
|
+
console.log(`System CPU: ${(osCpuUsage * 100).toFixed(2)}%`);
|
|
35
|
+
}, 500);
|
|
36
|
+
|
|
37
|
+
// When finished monitoring
|
|
38
|
+
clearInterval(interval);
|
|
39
|
+
processCpuMonitoring.end();
|
|
40
|
+
osCpuMonitoring.end();
|
|
41
|
+
|
|
42
|
+
// Access statistical information
|
|
43
|
+
const { info: processInfo } = processCpuMonitoring;
|
|
44
|
+
console.log({
|
|
45
|
+
minCpuUsage: processInfo.min,
|
|
46
|
+
maxCpuUsage: processInfo.max,
|
|
47
|
+
medianCpuUsage: processInfo.median,
|
|
48
|
+
});
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
## Measuring Usage Monitoring
|
|
52
|
+
|
|
53
|
+
Track memory consumption for both the current process and the system:
|
|
54
|
+
|
|
55
|
+
```js
|
|
56
|
+
import { startMonitoringMemoryUsage } from "@jsenv/os-metrics";
|
|
57
|
+
|
|
58
|
+
// Start monitoring
|
|
59
|
+
const [processMemoryMonitoring, osMemoryMonitoring] =
|
|
60
|
+
startMonitoringMemoryUsage();
|
|
61
|
+
|
|
62
|
+
// Take measurements at regular intervals
|
|
63
|
+
const interval = setInterval(() => {
|
|
64
|
+
const processMemoryBytes = processMemoryMonitoring.measure(); // Returns bytes used
|
|
65
|
+
const osMemoryBytes = osMemoryMonitoring.measure(); // Returns bytes used
|
|
66
|
+
|
|
67
|
+
console.log(
|
|
68
|
+
`Process memory: ${(processMemoryBytes / 1024 / 1024).toFixed(2)} MB`,
|
|
69
|
+
);
|
|
70
|
+
console.log(`System memory: ${(osMemoryBytes / 1024 / 1024).toFixed(2)} MB`);
|
|
71
|
+
}, 500);
|
|
72
|
+
|
|
73
|
+
// When finished monitoring
|
|
74
|
+
clearInterval(interval);
|
|
75
|
+
processMemoryMonitoring.end();
|
|
76
|
+
osMemoryMonitoring.end();
|
|
77
|
+
|
|
78
|
+
// Access statistical information
|
|
79
|
+
const { info: memoryInfo } = processMemoryMonitoring;
|
|
80
|
+
console.log({
|
|
81
|
+
minMemoryUsage: `${(memoryInfo.min / 1024 / 1024).toFixed(2)} MB`,
|
|
82
|
+
maxMemoryUsage: `${(memoryInfo.max / 1024 / 1024).toFixed(2)} MB`,
|
|
83
|
+
medianMemoryUsage: `${(memoryInfo.median / 1024 / 1024).toFixed(2)} MB`,
|
|
84
|
+
});
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
Each call to `measure()` returns memory usage (a number representing the number of bytes being used).
|
|
88
|
+
`end()` stops the monitoring and fill `.info` of the memory metric.
|
|
89
|
+
|
|
90
|
+
```js
|
|
91
|
+
const { info } = processMemoryMonitoring;
|
|
92
|
+
|
|
93
|
+
info.min; // the min cpu usage between startMonitoringCpuUsage() and end()
|
|
94
|
+
info.max; // the max cpu usage between startMonitoringCpuUsage() and end()
|
|
95
|
+
info.median; // the median usage between startMonitoringCpuUsage() and end()
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
## API Reference
|
|
99
|
+
|
|
100
|
+
### `startMonitoringCpuUsage()`
|
|
101
|
+
|
|
102
|
+
Starts monitoring CPU usage and returns two monitoring objects:
|
|
103
|
+
|
|
104
|
+
- First: Process CPU monitoring
|
|
105
|
+
- Second: OS-wide CPU monitoring
|
|
106
|
+
|
|
107
|
+
### `startMonitoringMemoryUsage()`
|
|
108
|
+
|
|
109
|
+
Starts monitoring memory usage and returns two monitoring objects:
|
|
110
|
+
|
|
111
|
+
- First: Process memory monitoring
|
|
112
|
+
- Second: OS-wide memory monitoring
|
|
113
|
+
|
|
114
|
+
### Monitoring Object Methods
|
|
115
|
+
|
|
116
|
+
Each monitoring object provides:
|
|
117
|
+
|
|
118
|
+
- `measure()`: Take a measurement and return the current value
|
|
119
|
+
- `end()`: Stop monitoring and calculate statistical information
|
|
120
|
+
- `info`: Object containing min, max, and median values (available after calling end())
|
|
121
|
+
|
|
122
|
+
## Use Cases
|
|
123
|
+
|
|
124
|
+
- Performance testing and benchmarking
|
|
125
|
+
- Resource usage optimization
|
|
126
|
+
- System monitoring in Node.js applications
|
|
127
|
+
- Detecting memory leaks and CPU spikes
|
|
128
|
+
|
|
129
|
+
## Platform Support
|
|
130
|
+
|
|
131
|
+
Works on all major operating systems supported by Node.js (Windows, macOS, Linux).
|
package/package.json
ADDED
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@jsenv/os-metrics",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"license": "MIT",
|
|
5
|
+
"repository": {
|
|
6
|
+
"type": "git",
|
|
7
|
+
"url": "https://github.com/jsenv/core",
|
|
8
|
+
"directory": "packages/independent/tooling/os-metrics"
|
|
9
|
+
},
|
|
10
|
+
"author": {
|
|
11
|
+
"name": "dmail",
|
|
12
|
+
"email": "dmaillard06@gmail.com"
|
|
13
|
+
},
|
|
14
|
+
"publishConfig": {
|
|
15
|
+
"access": "public"
|
|
16
|
+
},
|
|
17
|
+
"type": "module",
|
|
18
|
+
"main": "./src/main.js",
|
|
19
|
+
"files": [
|
|
20
|
+
"/src/"
|
|
21
|
+
],
|
|
22
|
+
"sideEffects": false
|
|
23
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
// https://gist.github.com/GaetanoPiazzolla/c40e1ebb9f709d091208e89baf9f4e00
|
|
2
|
+
|
|
3
|
+
import { startMeasuringTotalCpuUsage } from "./cpu_usage.js";
|
|
4
|
+
import { startMonitoringMetric } from "./metric_monitoring.js";
|
|
5
|
+
|
|
6
|
+
export const startMonitoringCpuUsage = () => {
|
|
7
|
+
const cpuUsage = startMeasuringTotalCpuUsage();
|
|
8
|
+
const processCpuUsageMonitoring = startMonitoringMetric(() => {
|
|
9
|
+
return cpuUsage.thisProcess.active;
|
|
10
|
+
});
|
|
11
|
+
const osCpuUsageMonitoring = startMonitoringMetric(() => {
|
|
12
|
+
return cpuUsage.overall.active;
|
|
13
|
+
});
|
|
14
|
+
const result = [processCpuUsageMonitoring, osCpuUsageMonitoring];
|
|
15
|
+
result.stop = cpuUsage.stop;
|
|
16
|
+
return result;
|
|
17
|
+
};
|
package/src/cpu_usage.js
ADDED
|
@@ -0,0 +1,219 @@
|
|
|
1
|
+
import { cpus } from "node:os";
|
|
2
|
+
import { cpuUsage } from "node:process";
|
|
3
|
+
|
|
4
|
+
export const startMeasuringTotalCpuUsage = () => {
|
|
5
|
+
let previousCpuArray = cpus();
|
|
6
|
+
let previousMs = Date.now();
|
|
7
|
+
let previousCpuUsage = cpuUsage();
|
|
8
|
+
|
|
9
|
+
const overall = {
|
|
10
|
+
inactive: 100,
|
|
11
|
+
active: 0,
|
|
12
|
+
system: 0,
|
|
13
|
+
user: 0,
|
|
14
|
+
};
|
|
15
|
+
const thisProcess = {
|
|
16
|
+
active: 0,
|
|
17
|
+
system: 0,
|
|
18
|
+
user: 0,
|
|
19
|
+
};
|
|
20
|
+
const details = previousCpuArray.map(() => {
|
|
21
|
+
return {
|
|
22
|
+
inactive: 100,
|
|
23
|
+
active: 0,
|
|
24
|
+
system: 0,
|
|
25
|
+
user: 0,
|
|
26
|
+
};
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
const samples = [];
|
|
30
|
+
const interval = setInterval(() => {
|
|
31
|
+
let cpuArray = cpus();
|
|
32
|
+
const ms = Date.now();
|
|
33
|
+
const ellapsedMs = ms - previousMs;
|
|
34
|
+
const cpuUsageSampleArray = [];
|
|
35
|
+
let overallSystemMs = 0;
|
|
36
|
+
let overallUserMs = 0;
|
|
37
|
+
let overallInactiveMs = 0;
|
|
38
|
+
let overallActiveMs = 0;
|
|
39
|
+
let overallMsEllapsed = 0;
|
|
40
|
+
let index = 0;
|
|
41
|
+
for (const cpu of cpuArray) {
|
|
42
|
+
const previousCpuTimes = previousCpuArray[index].times;
|
|
43
|
+
const cpuTimes = cpu.times;
|
|
44
|
+
const systemMs = cpuTimes.sys - previousCpuTimes.sys;
|
|
45
|
+
const userMs = cpuTimes.user - previousCpuTimes.user;
|
|
46
|
+
const activeMs = systemMs + userMs;
|
|
47
|
+
const inactiveMs = ellapsedMs - activeMs;
|
|
48
|
+
const cpuUsageSample = {
|
|
49
|
+
inactive: inactiveMs / ellapsedMs,
|
|
50
|
+
active: activeMs / ellapsedMs,
|
|
51
|
+
system: systemMs / ellapsedMs,
|
|
52
|
+
user: userMs / ellapsedMs,
|
|
53
|
+
};
|
|
54
|
+
cpuUsageSampleArray.push(cpuUsageSample);
|
|
55
|
+
|
|
56
|
+
overallSystemMs += systemMs;
|
|
57
|
+
overallUserMs += userMs;
|
|
58
|
+
overallInactiveMs += inactiveMs;
|
|
59
|
+
overallActiveMs += activeMs;
|
|
60
|
+
overallMsEllapsed += ellapsedMs;
|
|
61
|
+
index++;
|
|
62
|
+
}
|
|
63
|
+
const overallUsageSample = {
|
|
64
|
+
inactive: overallInactiveMs / overallMsEllapsed,
|
|
65
|
+
active: overallActiveMs / overallMsEllapsed,
|
|
66
|
+
system: overallSystemMs / overallMsEllapsed,
|
|
67
|
+
user: overallUserMs / overallMsEllapsed,
|
|
68
|
+
};
|
|
69
|
+
previousCpuArray = cpuArray;
|
|
70
|
+
previousMs = ms;
|
|
71
|
+
|
|
72
|
+
const processCpuUsage = cpuUsage();
|
|
73
|
+
const thisProcessSystemMs = Math.round(
|
|
74
|
+
(processCpuUsage.system - previousCpuUsage.system) / 1000,
|
|
75
|
+
);
|
|
76
|
+
const thisProcessUserMs = Math.round(
|
|
77
|
+
(processCpuUsage.user - previousCpuUsage.user) / 1000,
|
|
78
|
+
);
|
|
79
|
+
previousCpuUsage = processCpuUsage;
|
|
80
|
+
|
|
81
|
+
const thisProcessActiveMs = thisProcessSystemMs + thisProcessUserMs;
|
|
82
|
+
const thisProcessInactiveMs = overallMsEllapsed - thisProcessActiveMs;
|
|
83
|
+
const thisProcessSample = {
|
|
84
|
+
inactive: thisProcessInactiveMs / overallMsEllapsed,
|
|
85
|
+
active: thisProcessActiveMs / overallMsEllapsed,
|
|
86
|
+
system: thisProcessSystemMs / overallMsEllapsed,
|
|
87
|
+
user: thisProcessUserMs / overallMsEllapsed,
|
|
88
|
+
};
|
|
89
|
+
samples.push({
|
|
90
|
+
cpuUsageSampleArray,
|
|
91
|
+
overallUsageSample,
|
|
92
|
+
thisProcessSample,
|
|
93
|
+
});
|
|
94
|
+
if (samples.length === 10) {
|
|
95
|
+
per_cpu: {
|
|
96
|
+
let index = 0;
|
|
97
|
+
for (const detail of details) {
|
|
98
|
+
let systemSum = 0;
|
|
99
|
+
let userSum = 0;
|
|
100
|
+
let inactiveSum = 0;
|
|
101
|
+
let activeSum = 0;
|
|
102
|
+
for (const sample of samples) {
|
|
103
|
+
const { cpuUsageSampleArray } = sample;
|
|
104
|
+
const cpuUsageSample = cpuUsageSampleArray[index];
|
|
105
|
+
inactiveSum += cpuUsageSample.inactive;
|
|
106
|
+
activeSum += cpuUsageSample.active;
|
|
107
|
+
systemSum += cpuUsageSample.system;
|
|
108
|
+
userSum += cpuUsageSample.user;
|
|
109
|
+
}
|
|
110
|
+
Object.assign(detail, {
|
|
111
|
+
inactive: inactiveSum / samples.length,
|
|
112
|
+
active: activeSum / samples.length,
|
|
113
|
+
system: systemSum / samples.length,
|
|
114
|
+
user: userSum / samples.length,
|
|
115
|
+
});
|
|
116
|
+
index++;
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
all: {
|
|
120
|
+
let overallSystemSum = 0;
|
|
121
|
+
let overallUserSum = 0;
|
|
122
|
+
let overallInactiveSum = 0;
|
|
123
|
+
let overallActiveSum = 0;
|
|
124
|
+
for (const sample of samples) {
|
|
125
|
+
const { overallUsageSample } = sample;
|
|
126
|
+
overallSystemSum += overallUsageSample.system;
|
|
127
|
+
overallUserSum += overallUsageSample.user;
|
|
128
|
+
overallInactiveSum += overallUsageSample.inactive;
|
|
129
|
+
overallActiveSum += overallUsageSample.active;
|
|
130
|
+
}
|
|
131
|
+
Object.assign(overall, {
|
|
132
|
+
inactive: overallInactiveSum / samples.length,
|
|
133
|
+
active: overallActiveSum / samples.length,
|
|
134
|
+
system: overallSystemSum / samples.length,
|
|
135
|
+
user: overallUserSum / samples.length,
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
this_process: {
|
|
139
|
+
let thisProcessSystemSum = 0;
|
|
140
|
+
let thisProcessUserSum = 0;
|
|
141
|
+
let thisProcessInactiveSum = 0;
|
|
142
|
+
let thisProcessActiveSum = 0;
|
|
143
|
+
for (const sample of samples) {
|
|
144
|
+
const { thisProcessSample } = sample;
|
|
145
|
+
thisProcessSystemSum += thisProcessSample.system;
|
|
146
|
+
thisProcessUserSum += thisProcessSample.user;
|
|
147
|
+
thisProcessInactiveSum += thisProcessSample.inactive;
|
|
148
|
+
thisProcessActiveSum += thisProcessSample.active;
|
|
149
|
+
}
|
|
150
|
+
Object.assign(thisProcess, {
|
|
151
|
+
inactive: thisProcessInactiveSum / samples.length,
|
|
152
|
+
active: thisProcessActiveSum / samples.length,
|
|
153
|
+
system: thisProcessSystemSum / samples.length,
|
|
154
|
+
user: thisProcessUserSum / samples.length,
|
|
155
|
+
});
|
|
156
|
+
}
|
|
157
|
+
samples.length = 0;
|
|
158
|
+
}
|
|
159
|
+
}, 15);
|
|
160
|
+
interval.unref();
|
|
161
|
+
|
|
162
|
+
return {
|
|
163
|
+
overall,
|
|
164
|
+
thisProcess,
|
|
165
|
+
details,
|
|
166
|
+
stop: () => {
|
|
167
|
+
clearInterval(interval);
|
|
168
|
+
},
|
|
169
|
+
};
|
|
170
|
+
};
|
|
171
|
+
|
|
172
|
+
export const startMeasuringCpuUsage = () => {
|
|
173
|
+
let previousHrtime = process.hrtime();
|
|
174
|
+
let previousCpuUsage = process.cpuUsage();
|
|
175
|
+
|
|
176
|
+
const info = {
|
|
177
|
+
used: 0,
|
|
178
|
+
};
|
|
179
|
+
|
|
180
|
+
const interval = setInterval(() => {
|
|
181
|
+
const hrtime = process.hrtime(previousHrtime);
|
|
182
|
+
previousHrtime = hrtime;
|
|
183
|
+
const cpuUsage = process.cpuUsage(previousCpuUsage);
|
|
184
|
+
previousCpuUsage = cpuUsage;
|
|
185
|
+
|
|
186
|
+
const ellapsedMs = hrtime[0] * 1000 + hrtime[1] / 1000000;
|
|
187
|
+
const userMs = Math.round(cpuUsage.user / 1000);
|
|
188
|
+
const systemMs = Math.round(cpuUsage.system / 1000);
|
|
189
|
+
const activeMs = userMs + systemMs;
|
|
190
|
+
const usedRatio = activeMs / ellapsedMs;
|
|
191
|
+
const used = Math.round(usedRatio * 100) / 100;
|
|
192
|
+
info.used = used;
|
|
193
|
+
}, 15);
|
|
194
|
+
interval.unref();
|
|
195
|
+
|
|
196
|
+
return {
|
|
197
|
+
info,
|
|
198
|
+
stop: () => {
|
|
199
|
+
clearInterval(interval);
|
|
200
|
+
},
|
|
201
|
+
};
|
|
202
|
+
};
|
|
203
|
+
|
|
204
|
+
export const formatUsage = (usageInfo) => {
|
|
205
|
+
const { active, inactive, system, user } = usageInfo;
|
|
206
|
+
|
|
207
|
+
return `${ratioAsPercentage(active)} (system: ${ratioAsPercentage(
|
|
208
|
+
system,
|
|
209
|
+
)}, user: ${ratioAsPercentage(user)}), inactive: ${ratioAsPercentage(
|
|
210
|
+
inactive,
|
|
211
|
+
)}`;
|
|
212
|
+
};
|
|
213
|
+
|
|
214
|
+
export const ratioAsPercentage = (ratio) => {
|
|
215
|
+
const percentageAsNumber = ratio * 100;
|
|
216
|
+
const percentageAsNumberRounded = Math.round(percentageAsNumber);
|
|
217
|
+
const percentage = `${percentageAsNumberRounded}%`;
|
|
218
|
+
return percentage;
|
|
219
|
+
};
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import {
|
|
2
|
+
formatUsage,
|
|
3
|
+
startMeasuringCpuUsage,
|
|
4
|
+
startMeasuringTotalCpuUsage,
|
|
5
|
+
} from "./cpu_usage.js";
|
|
6
|
+
|
|
7
|
+
const cpuUsage = startMeasuringCpuUsage();
|
|
8
|
+
setInterval(() => {
|
|
9
|
+
console.log(cpuUsage.info.used);
|
|
10
|
+
}, 400);
|
|
11
|
+
|
|
12
|
+
const totalCpuUsage = startMeasuringTotalCpuUsage();
|
|
13
|
+
setInterval(() => {
|
|
14
|
+
console.log(`overall: ${formatUsage(totalCpuUsage.overall)}
|
|
15
|
+
this process: ${formatUsage(totalCpuUsage.thisProcess)}
|
|
16
|
+
`);
|
|
17
|
+
}, 400);
|
package/src/main.js
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export { countAvailableCpus } from "./available_cpu.js";
|
|
2
|
+
export { getAvailableMemory } from "./available_memory.js";
|
|
3
|
+
export { getOsVersion } from "./os_version.js";
|
|
4
|
+
|
|
5
|
+
export { startMonitoringCpuUsage } from "./cpu_monitoring.js";
|
|
6
|
+
export { startMonitoringMemoryUsage } from "./memory_monitoring.js";
|
|
7
|
+
|
|
8
|
+
export {
|
|
9
|
+
startMeasuringCpuUsage,
|
|
10
|
+
startMeasuringTotalCpuUsage,
|
|
11
|
+
} from "./cpu_usage.js";
|
|
12
|
+
export { startMonitoringMetric } from "./metric_monitoring.js";
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { freemem, totalmem } from "node:os";
|
|
2
|
+
import { memoryUsage } from "node:process";
|
|
3
|
+
import { startMonitoringMetric } from "./metric_monitoring.js";
|
|
4
|
+
|
|
5
|
+
export const startMonitoringMemoryUsage = () => {
|
|
6
|
+
const processMemoryUsageMonitoring = startMonitoringMetric(() => {
|
|
7
|
+
return memoryUsage().rss;
|
|
8
|
+
});
|
|
9
|
+
const osMemoryUsageMonitoring = startMonitoringMetric(() => {
|
|
10
|
+
const total = totalmem();
|
|
11
|
+
const free = freemem();
|
|
12
|
+
return total - free;
|
|
13
|
+
});
|
|
14
|
+
const stop = () => {
|
|
15
|
+
processMemoryUsageMonitoring.stop();
|
|
16
|
+
osMemoryUsageMonitoring.stop();
|
|
17
|
+
};
|
|
18
|
+
const result = [processMemoryUsageMonitoring, osMemoryUsageMonitoring];
|
|
19
|
+
result.stop = stop;
|
|
20
|
+
return result;
|
|
21
|
+
};
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
export const startMonitoringMetric = (measure) => {
|
|
2
|
+
const metrics = [];
|
|
3
|
+
const takeMeasure = () => {
|
|
4
|
+
const value = measure();
|
|
5
|
+
metrics.push(value);
|
|
6
|
+
return value;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
const info = {
|
|
10
|
+
start: takeMeasure(),
|
|
11
|
+
min: null,
|
|
12
|
+
max: null,
|
|
13
|
+
median: null,
|
|
14
|
+
end: null,
|
|
15
|
+
};
|
|
16
|
+
return {
|
|
17
|
+
info,
|
|
18
|
+
measure: takeMeasure,
|
|
19
|
+
end: () => {
|
|
20
|
+
info.end = takeMeasure();
|
|
21
|
+
metrics.sort((a, b) => a - b);
|
|
22
|
+
info.min = metrics[0];
|
|
23
|
+
info.max = metrics[metrics.length - 1];
|
|
24
|
+
info.median = medianFromSortedArray(metrics);
|
|
25
|
+
metrics.length = 0;
|
|
26
|
+
},
|
|
27
|
+
};
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
export const medianFromSortedArray = (array) => {
|
|
31
|
+
const length = array.length;
|
|
32
|
+
const isOdd = length % 2 === 1;
|
|
33
|
+
if (isOdd) {
|
|
34
|
+
const medianNumberIndex = (length - 1) / 2;
|
|
35
|
+
const medianNumber = array[medianNumberIndex];
|
|
36
|
+
return medianNumber;
|
|
37
|
+
}
|
|
38
|
+
const rightMiddleNumberIndex = length / 2;
|
|
39
|
+
const leftMiddleNumberIndex = rightMiddleNumberIndex - 1;
|
|
40
|
+
const leftMiddleNumber = array[leftMiddleNumberIndex];
|
|
41
|
+
const rightMiddleNumber = array[rightMiddleNumberIndex];
|
|
42
|
+
const medianNumber = (leftMiddleNumber + rightMiddleNumber) / 2;
|
|
43
|
+
return medianNumber;
|
|
44
|
+
};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { memoryUsage } from "node:process";
|
|
2
|
+
import { startMonitoringMetric } from "./metric_monitoring.js";
|
|
3
|
+
|
|
4
|
+
export const startMeasuringProcessMemoryUsage = () => {
|
|
5
|
+
const processMemoryUsageMonitoring = startMonitoringMetric(() => {
|
|
6
|
+
return memoryUsage().rss;
|
|
7
|
+
});
|
|
8
|
+
return processMemoryUsageMonitoring;
|
|
9
|
+
};
|