项目基于oshi库快速搭建一个cpu监控面板

在这里插入图片描述

后端:

      <dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><dependency><groupId>com.github.oshi</groupId><artifactId>oshi-core</artifactId><version>5.8.5</version></dependency>
package org.example.cputest;import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import oshi.SystemInfo;
import oshi.hardware.CentralProcessor;
import oshi.hardware.HardwareAbstractionLayer;import java.util.Comparator;
import java.util.Map;
import java.util.TreeMap;@CrossOrigin("*")
@RestController
@RequestMapping("/api/cpu")
public class CpuUsageController {private final SystemInfo systemInfo = new SystemInfo();private final HardwareAbstractionLayer hardware = systemInfo.getHardware();private final CentralProcessor processor = hardware.getProcessor();private long[][] prevTicks = processor.getProcessorCpuLoadTicks();@GetMapping("/usage")public String getCpuUsage() throws JsonProcessingException {// 获取当前的 tick 数long[][] ticks = processor.getProcessorCpuLoadTicks();// 获取 CPU 核心数int logicalProcessorCount = processor.getLogicalProcessorCount();// 计算每个核心的 CPU 使用率Map<String, Double> cpuUsages = new TreeMap<>(new Comparator<String>() {@Overridepublic int compare(String core1, String core2) {int num1 = Integer.parseInt(core1.replace("Core ", ""));int num2 = Integer.parseInt(core2.replace("Core ", ""));return Integer.compare(num1, num2);}});for (int i = 0; i < logicalProcessorCount; i++) {long user = ticks[i][CentralProcessor.TickType.USER.getIndex()] - prevTicks[i][CentralProcessor.TickType.USER.getIndex()];long nice = ticks[i][CentralProcessor.TickType.NICE.getIndex()] - prevTicks[i][CentralProcessor.TickType.NICE.getIndex()];long sys = ticks[i][CentralProcessor.TickType.SYSTEM.getIndex()] - prevTicks[i][CentralProcessor.TickType.SYSTEM.getIndex()];long idle = ticks[i][CentralProcessor.TickType.IDLE.getIndex()] - prevTicks[i][CentralProcessor.TickType.IDLE.getIndex()];long iowait = ticks[i][CentralProcessor.TickType.IOWAIT.getIndex()] - prevTicks[i][CentralProcessor.TickType.IOWAIT.getIndex()];long irq = ticks[i][CentralProcessor.TickType.IRQ.getIndex()] - prevTicks[i][CentralProcessor.TickType.IRQ.getIndex()];long softirq = ticks[i][CentralProcessor.TickType.SOFTIRQ.getIndex()] - prevTicks[i][CentralProcessor.TickType.SOFTIRQ.getIndex()];long steal = ticks[i][CentralProcessor.TickType.STEAL.getIndex()] - prevTicks[i][CentralProcessor.TickType.STEAL.getIndex()];long totalCpu = user + nice + sys + idle + iowait + irq + softirq + steal;// 检查 totalCpu 是否为零if (totalCpu == 0) {cpuUsages.put("Core " + i, 0.0);} else {double cpuUsage = (totalCpu - idle) * 100.0 / totalCpu;cpuUsages.put("Core " + i, cpuUsage);}}// 更新 prevTicksSystem.arraycopy(ticks, 0, prevTicks, 0, ticks.length);// 将结果转换为 JSON 字符串ObjectMapper objectMapper = new ObjectMapper();return objectMapper.writeValueAsString(cpuUsages);}
}

前端

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Dynamic CPU Performance Monitor 🖥️</title><!-- Vue and ECharts CDN --><script src="https://cdn.jsdelivr.net/npm/vue@2"></script><script src="https://cdn.jsdelivr.net/npm/echarts@5.3.2/dist/echarts.min.js"></script><style>body {font-family: Arial, sans-serif;background-color: #f0f0f0;text-align: center;}#app {display: flex;flex-wrap: wrap;justify-content: space-around;max-width: 1200px;margin: 0 auto;padding: 20px;}.chart-container {width: 300px;height: 350px;margin: 10px;background-color: white;border-radius: 10px;box-shadow: 0 4px 6px rgba(0,0,0,0.1);padding: 10px;position: relative;}.core-status {position: absolute;top: 10px;right: 10px;font-size: 24px;}h1 {color: #333;display: flex;align-items: center;justify-content: center;}h1 span {margin: 0 10px;}</style>
</head>
<body>
<h1><span>🖥️</span>CPU Performance Monitoring Dashboard<span>📊</span>
</h1>
<div id="app"><div v-for="(usage, core) in cpuUsageData" :key="core" class="chart-container"><div class="core-status"><span v-if="usage < 30">😎</span><span v-else-if="usage < 60">😓</span><span v-else-if="usage < 80">🥵</span><span v-else>🔥</span></div><div :ref="`chart-${core}`" style="width: 100%; height: 280px;"></div></div>
</div><script>// Create Vue instancenew Vue({el: '#app',data: {cpuUsageData: {},timeStamps: Array.from({length: 7}, () => 0)},mounted() {// Start timer to update data every secondthis.updateChart();},methods: {async updateChart() {try {// Fetch CPU usage dataconst response = await fetch('http://localhost:8080/api/cpu/usage');const data = await response.json();// Update CPU usage datathis.cpuUsageData = data;// Update timestampsthis.timeStamps.shift();this.timeStamps.push(new Date().toLocaleTimeString());// Iterate through each core, initialize or update EChartsObject.keys(this.cpuUsageData).forEach(core => {const usage = this.cpuUsageData[core];const chartContainer = this.$refs[`chart-${core}`][0];// Initialize chart if not existsif (!chartContainer.__chart) {chartContainer.__chart = echarts.init(chartContainer);chartContainer.__chart.setOption({title: {text: `Core ${core}`,left: 'center'},tooltip: {trigger: 'axis'},xAxis: {type: 'category',data: this.timeStamps},yAxis: {type: 'value',axisLabel: {formatter: '{value} %'},min: 0,max: 100},series: [{name: 'CPU Usage',type: 'line',smooth: true,  // 使线条平滑areaStyle: {color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [{offset: 0, color: 'rgba(58,77,233,0.8)'},{offset: 1, color: 'rgba(58,77,233,0.3)'}])},data: Array.from({length: 7}, () => 0)}]});}// Update chart dataconst seriesData = chartContainer.__chart.getOption().series[0].data;seriesData.shift();seriesData.push(usage);chartContainer.__chart.setOption({xAxis: {data: this.timeStamps},series: [{data: seriesData}]});});} catch (error) {console.error('Error fetching CPU usage data:', error);}// Update every secondsetTimeout(this.updateChart, 1000);}}});
</script>
</body>
</html>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/484959.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【LLMs】用LM Studio本地部署离线大语言模型

文章目录 一、下载LM Studio二、下载大语言模型1. 查看模型介绍2. 点击模型文件进行下载2.1 完整下载2.2 部分下载 三、加载模型1. 打开LM Studio图形化界面&#xff0c;点击**My Models**2. 然后&#xff0c;点击“...”&#xff0c;选择“change”&#xff0c;选择刚下载好的…

Redis——主从复制原理

Redis的主从复制原理是其高可用性和分布式读取能力的重要基础。以下是Redis主从复制原理的详细解释&#xff1a; 一、主从复制的基本概念 Redis的主从复制是一种数据复制和备份的方式&#xff0c;它允许一个主节点&#xff08;Master&#xff09;将其所有的数据同步到一个或多…

单链表---合并两个链表

将两个升序链表合并为一个新的升序链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。 struct ListNode {int val;struct ListNode* next; }; w 方法一---不使用哨兵位 我们创建一个新链表用于合并两个升序链表&#xff0c; 将两个链表中最小的结点依次尾插到…

【AI系统】MobileNet 系列

MobileNet 系列 在本文会介绍 MobileNet 系列&#xff0c;重点在于其模型结构的轻量化设计&#xff0c;主要介绍详细的轻量化设计原则&#xff0c;基于这原则&#xff0c;MobileNetV1 是如何设计成一个小型&#xff0c;低延迟&#xff0c;低功耗的参数化模型&#xff0c;可以满…

25.k个一组翻转链表 python

k个一组翻转链表 题目题目描述示例 1&#xff1a;示例 2&#xff1a;提示&#xff1a;题目链接 题解解题思路python实现代码分析提交结果 题目 题目描述 给你链表的头节点 head &#xff0c;每 k 个节点一组进行翻转&#xff0c;请你返回修改后的链表。 k 是一个正整数&…

开源即时通讯与闭源即时通讯该怎么选择,其优势是什么?

在选择即时通讯软件时&#xff0c;应根据企业的经营领域来选择适合自身需求的开源或闭源方案。不同领域对开源和闭源即时通讯的理念存在差异&#xff0c;因此总结两个点简要分析这两种选择&#xff0c;有助于做出更明智的决策。 一、开源与闭源的根本区别在于软件的源代码是否…

etcd分布式存储系统快速入门指南

在分布式系统的复杂世界中&#xff0c;确保有效的数据管理至关重要。分布式可靠的键值存储在维护跨分布式环境的数据一致性和可伸缩性方面起着关键作用。 在这个全面的教程中&#xff0c;我们将深入研究etcd&#xff0c;这是一个开源的分布式键值存储。我们将探索其基本概念、特…

大语言模型微调与 XTuner 微调实战

1 大语言模型微调 1.1 什么是微调 大语言模型微调&#xff08;Fine-tuning of Large Language Models&#xff09;是指在预训练的大型语言模型基础上&#xff0c;使用特定任务的数据进一步训练模型&#xff0c;以使其更好地适应和执行特定任务的过程&#xff0c;用于使LLM&am…

计算机网络复习5——运输层

运输层解决的是进程之间的逻辑通信问题 两个主机进行通信归根结底是两个主机中的应用程序互相通信&#xff0c;又称为“端到端的通信” 端口 运行在计算机中的进程是用进程标识符来标志的。但不同的操作系统标识进程的方法不统一&#xff0c;因特网重新以统一的方法对TCP/IP…

秒懂:使用js验证hash, content hash , chunk hash的区别

一、使用js验证hash, content hash , chunk hash的区别 1、计算一般的 Hash&#xff08;以简单字符串为例&#xff09; 使用crypto-js库来进行哈希计算&#xff0c;需提前引入npm install crypto-js库。 crypto-js&#xff1a; 是一个JavaScript加密算法库&#xff0c;用于实…

从零开始配置 Docker 网络:快速掌握各类型网络的设置与使用场景

文章目录 📖 介绍 📖🏡 演示环境 🏡📒 文章内容 📒📝 Docker 网络类型概述🎯 Bridge 驱动🎯 Host 驱动🎯 None 驱动🎯 Overlay 驱动🎯 Macvlan 驱动🔖 获取网络接口📝 总结:选择合适的网络类型⚓️ 相关链接 ⚓️📖 介绍 📖 如果你曾经在搭建…

PHP语法学习(第六天)

&#x1f4a1;依照惯例&#xff0c;回顾一下昨天讲的内容 PHP语法学习(第五天)主要讲了PHP中的常量和运算符的运用。 &#x1f525; 想要学习更多PHP语法相关内容点击“PHP专栏” 今天给大家讲课的角色是&#x1f34d;菠萝吹雪&#xff0c;“我菠萝吹雪吹的不是雪&#xff0c;而…

一键部署 Poste.io 邮件/邮局/完整教程

在使用 Nginx 或宝塔面板的基础上部署 Poste.io 时&#xff0c;经常会遇到证书申请失败或无法访问等问题。本教程将为您提供一个完整的解决方案。 特别说明&#xff1a;如果您的服务器 IP 已被 Outlook 列入黑名单&#xff0c;发送到 Outlook 邮箱的邮件将会失败。其他邮箱服务…

如何搭建Python的本地Pypi源

前言 在实际生产环境中工作中&#xff0c;为了安全&#xff0c;内网主机是无法连接外网的&#xff0c;开发同事在写Python相关程序时&#xff0c;需要安装大量开发所需的模块&#xff0c;如果单独安装模块的话&#xff0c;有可能会存在大量的依赖&#xff0c;需要一个一个查找…

iOS与Windows间传文件

想用数据线从 windows 手提电脑传文件入 iPhone&#xff0c;有点迂回。 参考 [1]&#xff0c;要在 windows 装 Apple Devices。装完、打开、插线之后会检测到手机&#xff0c;界面&#xff1a; 点左侧栏「文件」&#xff0c;不是就直接可以传&#xff0c;而是要通过某个应用传…

如何高效地架构一个Java项目

引言 Java是企业级应用开发的主流语言之一&#xff0c;而我们作为使用Java语言的程序员&#xff0c;职称有初级、中级、高级、资深、经理、架构&#xff0c;但我们往往只是慢慢通过经验的积累迭代了自己的等级&#xff0c;如果没有保持学习的习惯&#xff0c;大多数程序员会停留…

pytest(一)csv数据驱动

一、csv数据驱动 csv文件内容 1,1,2 3,6,9 100,200,3000csv数据驱动使用方法 import csv import pytestdef get_csv():with open("data.csv") as file:raw csv.reader(file)data []for line in raw:data.append(line)# print(data) #[[1, 1, 2], [3, 6, 9],…

Linux C/C++编程之静态库

【图书推荐】《Linux C与C一线开发实践&#xff08;第2版&#xff09;》_linux c与c一线开发实践pdf-CSDN博客《Linux C与C一线开发实践&#xff08;第2版&#xff09;&#xff08;Linux技术丛书&#xff09;》(朱文伟&#xff0c;李建英)【摘要 书评 试读】- 京东图书 (jd.com…

001集—— 创建一个WPF项目 ——WPF应用程序入门 C#

本例为一个WPF应用&#xff08;.NET FrameWork&#xff09;。 首先创建一个项目 双击xaml文件 双击xaml文件进入如下界面&#xff0c;开始编写代码。 效果如下&#xff1a; 付代码&#xff1a; <Window x:Class"WpfDemoFW.MainWindow"xmlns"http://schema…

优傲协作机器人 Remote TCP Toolpath URCap(操作记录)

目录 一、新机设置项 1、设置管理员密码 2、设置安全密码 3、设置负载 二、激活 Remote TCP & Toolpath URCap 1、插入U盘 2、打开激活面板 3、导入许可证 4、查看是否激活成功 5、启用功能 三、使用流程&#xff08;官方&#xff09; 步骤一 步骤二 步骤三 …