Rust 获取系统内存 CPU 信息并实现图片采集设置壁纸
介绍使用 Rust 编程语言获取系统内存、CPU、磁盘及网络信息的方法。通过 sysinfo 库实现系统监控程序,解决版本 API 变更问题。此外,结合 reqwest 和 wallpaper 库,实现了自动下载必应每日壁纸并设置为系统桌面的功能,展示了 Rust 在系统级操作中的应用。

介绍使用 Rust 编程语言获取系统内存、CPU、磁盘及网络信息的方法。通过 sysinfo 库实现系统监控程序,解决版本 API 变更问题。此外,结合 reqwest 和 wallpaper 库,实现了自动下载必应每日壁纸并设置为系统桌面的功能,展示了 Rust 在系统级操作中的应用。


微信公众号「极客日志」,在微信中扫描左侧二维码关注。展示文案:极客日志 zeeklog
将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online
将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online
将 Markdown(GFM)转为 HTML 片段,浏览器内 marked 解析;与 HTML 转 Markdown 互为补充。 在线工具,Markdown 转 HTML在线工具,online
将 HTML 片段转为 GitHub Flavored Markdown,支持标题、列表、链接、代码块与表格等;浏览器内处理,可链接预填。 在线工具,HTML 转 Markdown在线工具,online
通过删除不必要的空白来缩小和压缩JSON。 在线工具,JSON 压缩在线工具,online
将JSON字符串修饰为友好的可读格式。 在线工具,JSON美化和格式化在线工具,online
本文介绍使用 Rust 编程语言获取系统基本信息的功能,直接通过代码体验。
首先在 Cargo.toml 中添加依赖:
[dependencies]
sysinfo = "0.29"
运行 cargo run。
在新版本中,global_cpu_usage() 方法已被移除。需要使用 ProcessExt trait 来使用 memory() 方法。
完成报错代码修改后,下面是完整可运行的代码。
完成代码如下:
use sysinfo::{System, SystemExt, CpuExt, DiskExt, NetworkExt, ProcessExt};
fn main() {
let mut sys = System::new_all();
// 刷新所有信息
sys.refresh_all();
// 内存信息
println!("=== 内存信息 ===");
println!("总内存:{} MB", sys.total_memory() / 1024 / 1024);
println!("已用内存:{} MB", sys.used_memory() / 1024 / 1024);
println!("可用内存:{} MB", sys.available_memory() / 1024 / 1024);
println!("总交换空间:{} MB", sys.total_swap() / 1024 / 1024);
println!("已用交换空间:{} MB", sys.used_swap() / 1024 / 1024);
// CPU 信息
println!("\n=== CPU 信息 ===");
println!("CPU 数量:{}", sys.cpus().len());
// 计算全局 CPU 使用率的方法
let global_cpu_usage = if !sys.cpus().is_empty() {
sys.cpus()
.iter()
.map(|cpu| cpu.cpu_usage())
.sum::<f32>()
/ sys.cpus().len() as f32
} else {
0.0
};
println!("全局 CPU 使用率:{:.1}%", global_cpu_usage);
// 显示每个 CPU 核心的使用率
for (i, cpu) in sys.cpus().iter().enumerate() {
println!("CPU {}: {:.1}%", i, cpu.cpu_usage());
}
// 系统信息
println!("\n=== 系统信息 ===");
println!("系统名称:{:?}", sys.name());
println!("内核版本:{:?}", sys.kernel_version());
println!("OS 版本:{:?}", sys.os_version());
println!("主机名:{:?}", sys.host_name());
// 磁盘信息
println!("\n=== 磁盘信息 ===");
for disk in sys.disks() {
println!(
"磁盘:{:?} 总大小:{} GB 可用:{} GB",
disk.name(),
disk.total_space() / 1024 / 1024 / 1024,
disk.available_space() / 1024 / 1024 / 1024
);
}
// 网络信息
println!("\n=== 网络信息 ===");
for (interface_name, data) in sys.networks() {
println!(
"{}: 接收 {} MB, 发送 {} MB",
interface_name,
data.received() / 1024 / 1024,
data.transmitted() / 1024 / 1024
);
}
// 进程信息 - 修正部分
println!("\n=== 进程信息 ===");
println!("进程数量:{}", sys.processes().len());
// 显示前 5 个内存使用最多的进程
let mut processes: Vec<_> = sys.processes().values().collect();
processes.sort_by(|a, b| b.memory().cmp(&a.memory()));
for process in processes.iter().take(5) {
println!(
"PID: {} 名称:{:?} 内存:{} MB",
process.pid(),
process.name(),
process.memory() / 1024 / 1024
);
}
}


推荐使用 sysinfo 库,因为它功能全面、文档完善,并且在所有主要平台上都能良好工作。
通过上面可以获取到系统基本信息后,那么就可以做一个简单的实时监控,查看系统整体运行情况的程序,类似一个任务管理器一样。
这个错误是因为 refresh_cpu_usage() 方法在新版本中已被移除。正确的做法是使用 refresh_cpu()。
这个错误是因为 uptime() 是实例方法,不是静态方法。需要从系统实例调用。
完成代码如下:
use std::{thread, time::Duration};
use sysinfo::{System, SystemExt, CpuExt, ProcessExt};
fn monitor_system() {
let mut sys = System::new_all();
loop {
// 刷新系统信息
sys.refresh_cpu();
thread::sleep(Duration::from_secs(1));
sys.refresh_memory();
sys.refresh_processes();
// 清屏并显示信息
println!("\x1B[2J\x1B[1;1H");
println!("=== 系统实时监控 ===");
println!("更新时间:{:?}", sys.uptime());
// 内存信息
println!("\n=== 内存信息 ===");
println!("总内存:{:>6} MB", sys.total_memory() / 1024 / 1024);
println!("已用内存:{:>6} MB", sys.used_memory() / 1024 / 1024);
println!("可用内存:{:>6} MB", sys.available_memory() / 1024 / 1024);
println!(
"使用率:{:>6.1}%",
(sys.used_memory() as f64 / sys.total_memory() as f64) *
);
();
= !sys.().() {
sys.()
.()
.(|cpu| cpu.())
.sum::<>()
/ sys.().()
} {
};
(, sys.().());
(, global_cpu_usage);
(i, cpu) sys.().().() {
= cpu.();
= (usage / ) ;
= .(bars.());
= .( - bars.());
(
,
i, bar, spaces, usage
);
}
();
: <_> = sys.().().();
processes.(|a, b| b.().(&a.()));
(, , , );
(, .());
processes.().() {
(
,
process.(),
process.(),
process.() / /
);
}
();
(, sys.());
(, sys.().());
();
thread::(Duration::());
}
}
() {
();
();
thread::(Duration::());
();
}

actix-web = "4.4"
reqwest = { version = "0.11", features = ["blocking", "json"] }
serde = { version = "1.0", features = ["derive"] }
serde_json = "1.0"
chrono = { version = "0.4", features = ["serde"] }
image = "0.24"
wallpaper = "3"
dirs = "4.0"
下面的错误表示 wallpaper 当前的版本不存在,并且还给出了建议。
设置好正确的版本后,保存,然后 cargo run 运行后会自动下载依赖。
use std::fs::File;
use std::io::copy;
use std::path::PathBuf;
use dirs::picture_dir;
fn main() -> Result<(), Box<dyn std::error::Error>> {
println!("开始获取必应每日壁纸...");
// 1. 获取必应图片 URL
let image_url = get_bing_image_url()?;
println!("获取到图片 URL: {}", image_url);
// 2. 下载图片
let image_path = download_image(&image_url)?;
println!("图片已下载到:{:?}", image_path);
// 3. 设置为壁纸
set_wallpaper(&image_path)?;
println!("壁纸设置成功!");
Ok(())
}
fn get_bing_image_url() -> Result<String, Box<dyn std::error::Error>> {
// 必应每日图片 API
let api_url = "https://cn.bing.com/HPImageArchive.aspx?format=js&idx=0&n=1&mkt=zh-CN";
let response = reqwest::blocking::get(api_url)?;
let json: serde_json::Value = response.json()?;
// 解析 JSON 获取图片 URL
if let Some(images) = json[].() {
(first_image) = images.() {
(url) = first_image[].() {
= (, url);
(full_url);
}
}
}
(.())
}
(url: &) <PathBuf, < std::error::Error>> {
= reqwest::blocking::(url)?;
= url.() || url.() {
} url.() {
} {
};
= (
,
chrono::Local::().format(),
extension
);
= ().()?;
picture_dir.();
std::fs::(&picture_dir)?;
= picture_dir.(file_name);
= File::(&file_path)?;
= std::io::Cursor::(response.()?);
(& content, & dest)?;
(file_path)
}
(image_path: &PathBuf) <(), < std::error::Error>> {
wallpaper::(image_path.().()?)?;
wallpaper::(wallpaper::Mode::Crop)?;
(())
}

上图已经提示已经下载到本地,并且设置好了壁纸,到对应文件夹目录即可看到下载好的壁纸图片。


在使用过程中,发现有些版本和当前使用的方法不一致,这点在使用时需要注意。整体来说,想要的方法和解决方案都能快速找到,只要养成了解的编程习惯和思维,很多开发语言都是相通的,上手会相对快一些。