当前位置: 首页 > news >正文

Rust eyre 错误处理实战教程

在《Rust 错误处理库: thiserror 和 anyhow》中我们介绍了Rust简化处理错误策略,本文解释eyre错误处理库,并通过多个实际示例进行说明,最后于anyhow库进行对比,让你更好理解其应用场景。

eyre是一个用于 Rust 的错误处理库,它提供了方便、灵活且具有良好错误信息显示的功能。其主要目标是简化在 Rust 程序中处理错误的过程,尤其是在处理复杂的错误场景和嵌套的ResultOption类型时。与 Rust 标准库的错误处理相比,eyre提供了更丰富的上下文信息。例如,当发生错误时,它可以包含更多关于错误发生位置(如文件名、行号等)的详细信息,并且在报告错误时可以提供更友好的用户界面,使得开发者更容易理解和定位错误。
在这里插入图片描述

读取文件示例

use std::fs::File;
use eyre::Result;
fn read_file() -> Result<String> {let mut file = File::open("example.txt")?;let mut contents = String::new();file.read_to_string(&mut contents)?;Ok(contents)
}
fn main() {match read_file() {Ok(contents) => println!("File contents: {}", contents),Err(e) => eprintln!("Error: {}", e),}
}

read_file函数中,首先尝试打开一个名为example.txt的文件。File::open函数返回一个Result类型,?操作符在这里用于传播错误。如果文件打开失败,?会立即返回错误,并且eyre会自动捕获一些关于这个错误的上下文信息,如函数调用位置等。接着,读取文件内容到一个String变量中,同样使用?操作符来处理read_to_string函数可能产生的错误。

main函数中,通过match语句来处理read_file函数返回的Result类型。如果成功,打印文件内容;如果失败,使用eprintln!打印错误信息,eyre提供的错误信息会包含详细的错误原因和位置相关内容。

自定义错误类型

use eyre::{Context, Result};
use std::num::ParseIntError;
#[derive(Debug)]
struct MyError {inner: ParseIntError,context: String,
}
impl std::fmt::Display for MyError {fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {write!(f, "Error in context '{}': {}", self.context, self.inner)}
}
impl std::error::Error for MyError {fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {Some(&self.inner)}
}
fn parse_number(s: &str) -> Result<i32> {let number = s.parse::<i32>().map_err(|e| MyError {inner: e,context: "Parsing number".to_string(),})?;Ok(number)
}
fn main() {match parse_number("not a number") {Ok(n) => println!("Parsed number: {}", n),Err(e) => eprintln!("Error: {}", e),}
}

首先定义了一个自定义的错误类型MyError,它包含了一个内部错误(这里是ParseIntError类型,用于表示数字解析错误)和一个错误上下文信息(context字段)。实现了DisplayError trait,用于格式化错误信息和提供错误源信息。

parse_number函数中,尝试将一个字符串解析为i32类型的数字。如果解析失败,会使用map_err函数将ParseIntError转换为自定义的MyError类型,并添加错误上下文信息。同样,?操作符用于传播错误。

main函数中,通过match语句处理parse_number函数返回的Result类型,打印解析后的数字或者错误信息。eyre会根据自定义的错误类型和相关实现来提供详细的错误显示,包括自定义的上下文信息和内部错误的详细内容。

异步函数错误处理

在 Rust 的异步编程中,经常会使用async函数,这些函数返回Result类型来表示成功或失败的结果。eyre包可以很好地与这种异步函数结合使用,帮助我们处理错误。

use std::fs::File;
use tokio::io::AsyncReadExt;
use eyre::Result;
use tokio::task;
async fn read_file_async() -> Result<String> {let mut file = File::open("example.txt").await?;let mut contents = String::new();file.read_to_string(&mut contents).await?;Ok(contents)
}
#[tokio::main]
async fn main() {match read_file_async().await {Ok(contents) => println!("File contents: {}", contents),Err(e) => eprintln!("Error: {}", e),}
}

read_file_async异步函数中,首先尝试异步打开一个名为example.txt的文件。注意这里使用了await关键字来等待文件打开操作完成,并且?操作符用于处理File::open返回的Result类型中的错误。如果文件打开失败,?会立即返回错误,eyre会捕获相关的错误上下文信息。接着,异步读取文件内容到一个String变量中,同样使用await?操作符来处理read_to_string操作可能产生的错误。

main函数中,通过match语句来处理read_file_async函数返回的Result类型。由于read_file_async是异步函数,所以需要使用await来等待它完成。如果成功,打印文件内容;如果失败,使用eprintln!打印错误信息,eyre提供的错误信息会包含详细的错误原因和位置相关内容。

多个异步函数错误处理

在异步编程中,经常需要同时执行多个异步任务,Tokio提供了join!try_join!宏来处理这种情况。join!会等待所有任务完成,而try_join!会在其中一个任务出现错误时立即返回错误。

use tokio::task;
use eyre::Result;
async fn task1() -> Result<i32> {Ok(1)
}
async fn task2() -> Result<i32> {Err(eyre::eyre!("Task 2 error"))
}
#[tokio::main]
async fn main() {let result = task::try_join!(task1(), task2()).map_err(|e| {eprintln!("Error in tasks: {}", e);e});match result {Ok((res1, res2)) => println!("Results: {}, {}", res1, res2),Err(e) => {}}
}

定义了两个异步任务task1task2,其中task1返回成功的结果,task2返回一个错误。

main函数中,使用try_join!宏来同时执行这两个任务。如果task2出现错误,try_join!会立即返回错误,并且map_err函数用于处理这个错误,在这里打印错误信息。通过match语句来处理try_join!的结果。如果成功,打印两个任务的结果;如果失败,因为已经在map_err中处理了错误信息,所以这里的Err分支可以为空。eyre帮助我们在处理多个异步任务的错误时,提供清晰的错误信息和方便的错误处理机制。

eyre与anyhow的区别

eyreanyhow都是 Rust 语言中用于简化错误处理的库。它们的主要目标是提供一种更方便的方式来处理错误,尤其是在处理复杂的ResultOption类型时,减少样板代码,并且能够提供比较友好的错误信息。

在许多常见的 Rust 应用场景中,如文件读取、网络请求、数据库操作等,当需要处理可能出现错误的操作时,这两个库都可以发挥作用。例如,在处理文件读取可能出现的IoError,或者网络请求返回的错误码时,它们都可以帮助开发者更高效地处理这些错误情况。

eyre 特点

eyre提供了更丰富的错误上下文信息。它可以包含诸如发生错误的文件名、行号等详细信息。当一个错误在复杂的函数调用栈中传播时,eyre能够很好地追踪这些信息,并且在报告错误时提供完整的上下文。例如,在一个多层嵌套的函数调用中,eyre可以精确地指出错误是在哪个文件的哪一行的哪个函数调用中产生的。

eyre在与其他库集成时,可能需要更多的适配工作,尤其是当涉及到与其他具有复杂错误处理机制的库一起使用时。因为eyre本身的错误类型和处理方式比较丰富,所以在集成过程中可能需要编写一些转换代码来确保不同库之间的错误能够顺利地传递和处理。

anyhow特点

anyhow相对来说更侧重于简单地将错误信息进行包装和传播。它的错误信息主要是基于开发者提供的错误描述或者从底层错误类型转换而来的简单文本信息。虽然它也能够有效地传播错误,但在提供详细的错误发生位置等上下文信息方面不如eyre

anyhow由于其简单的错误包装方式,在与其他库集成时通常更加方便。它可以很容易地将其他库产生的错误转换为anyhow::Error类型,并且在整个应用程序的不同层次之间传递这些错误,而不需要过多复杂的适配代码。例如,在一个使用多个第三方库的项目中,anyhow可以快速地将这些库产生的各种错误统一起来进行处理。

相关文章:

Rust eyre 错误处理实战教程

在《Rust 错误处理库: thiserror 和 anyhow》中我们介绍了Rust简化处理错误策略&#xff0c;本文解释eyre错误处理库&#xff0c;并通过多个实际示例进行说明&#xff0c;最后于anyhow库进行对比&#xff0c;让你更好理解其应用场景。 eyre是一个用于 Rust 的错误处理库&#x…...

面试小札:JVM虚拟机

1. 定义与基本概念 - JVM&#xff08;Java Virtual Machine&#xff09;即Java虚拟机&#xff0c;是Java程序的运行核心。它是一个虚构出来的计算机&#xff0c;通过在实际的计算机上仿真模拟各种计算机功能来运行Java字节码。字节码是一种中间格式&#xff0c;它使得Java程序能…...

Docker扩容操作(docker总是空间不足)

Docker扩容操作(docker总是空间不足) 1、df二连&#xff0c;一共也就70g&#xff0c;总是占满93%以上。所以需要移动到其他目录上 查看docker镜像和容器存储目录的空间大小 du -sh /var/lib/docker/2、停止docker服务 systemctl stop docker3、首先创建目录并迁移 # 首先创…...

数字图像处理(4):FPGA中的定点数、浮点数

&#xff08;1&#xff09;定点数&#xff1a;小数点固定在数据的某一位置的数&#xff0c;可以分为定点整数和定点小数和普通定点数。定点数广泛应用于数字图像处理&#xff08;图像滤波、图像缩放&#xff09;和数字信号处理&#xff08;如FFT、定点卷积&#xff09;中。 定…...

毕昇入门学习

schemas.py 概述 这段代码主要定义了一系列基于 Pydantic 的数据模型&#xff08;BaseModel&#xff09;&#xff0c;用于数据验证和序列化&#xff0c;通常用于构建 API&#xff08;如使用 FastAPI&#xff09;。这些模型涵盖了用户认证、聊天消息、知识库管理、模型配置等多…...

2411C++,学习C++提示4

结构绑定 auto [first, ...ts] std::tuple{1, 2 ,3};assert(1 first);浮点作为非类型模板参数 template<double Value> constexpr auto value Value;int main() {std::cout << value<4.2>; // prints 4.2 }template<double... Vl1s, double... Vl2s&g…...

STM32-- 看门狗--介绍、使用场景、失效场景

STM32 中的看门狗&#xff08;Watchdog Timer&#xff0c;简称 WDG&#xff09;有两种主要类型&#xff1a;独立看门狗&#xff08;IWDG&#xff09; 和 窗口看门狗&#xff08;WWDG&#xff09;。它们的喂狗机制各有特点&#xff0c;主要区别如下&#xff1a; 1. 独立看门狗&a…...

【赵渝强老师】PostgreSQL的数据库

PostgreSQL的逻辑存储结构主要是指数据库中的各种数据库对象&#xff0c;包括&#xff1a;数据库集群、数据库、表、索引、视图等等。所有数据库对象都有各自的对象标识符oid&#xff08;object identifiers&#xff09;,它是一个无符号的四字节整数&#xff0c;相关对象的oid都…...

linux安全管理-会话安全

文章目录 1 设置命令行界面超时退出2 配置终端登录失败策略3 配置 SSH 登录失败策略 1 设置命令行界面超时退出 1、检查内容 检查操作系统是否设置命令行界面超时退出。 2、配置要求 操作系统设置命令行界面超时退出。 3、配置方法 配置命令行界面超时时间&#xff0c;编辑/et…...

Ubuntu监视显卡占用情况

在终端中运行 watch -n 0.5 nvidia-smi【以下内容由大模型生成】 watch -n 0.5 nvidia-smi 是一个组合命令&#xff0c;用于在 Linux 终端中定期执行 nvidia-smi 命令并显示其输出。让我们分解一下这个命令的各个部分&#xff1a; watch: watch 是一个用于定期执行其他命令并显…...

学成在线day06

上传视屏 断点续传 通常视频文件都比较大&#xff0c;所以对于媒资系统上传文件的需求要满足大文件的上传要求。http协议本身对上传文件大小没有限制&#xff0c;但是客户的网络环境质量、电脑硬件环境等参差不齐&#xff0c;如果一个大文件快上传完了网断了没有上传完成&…...

Mac安装及合规无限使用Beyond Compare

文章目录 Beyond CompareBeyond Compare简介Beyond Compare安装Beyond Compare到期后继续免费使用 Beyond Compare Beyond Compare简介 Beyond Compare 是一款由 Scooter Software 开发的文件和文件夹比较工具。它主要用于对比两个文件或文件夹之间的差异&#xff0c;并支持文…...

【青牛科技】2K02 电动工具专用调速电路芯片描述

概述&#xff1a; 2K02 是电动工具专用调速电路。内置稳压电路&#xff0c;温度系数好&#xff0c;可以调节输出频率以及占空比的振荡输出&#xff0c;广泛的应用于小型电钻&#xff0c;割草机等工具。 主要特点&#xff1a; ● 电源电压范围宽 ● 占空比可调 ● 温度系数好 …...

基于SpringBoot实现的民宿管理系统(代码+论文)

&#x1f389;博主介绍&#xff1a;Java领域优质创作者&#xff0c;阿里云博客专家&#xff0c;计算机毕设实战导师。专注Java项目实战、毕设定制/协助 &#x1f4e2;主要服务内容&#xff1a;选题定题、开题报告、任务书、程序开发、项目定制、论文辅导 &#x1f496;精彩专栏…...

安装QT6.8(MSVC MinGW)+QT webengine+QT5.15.2

本篇主要针对只使用过QT5的qmake&#xff0c;没有用过MSVC&#xff0c;VS的老同学。 建议一部分一部分安装&#xff0c;全部勾选安装遇到问题会中断&#xff0c;前功尽弃。 我自己需要的是QT5&#xff0c;编出的软件用在公司设备上。 QT6&#xff1a;建议也安装学习&#xf…...

MinIO常见操作及Python实现对象的增删改查

MinIO常见操作 MinIO是一个高性能的开源对象存储服务&#xff0c;它兼容Amazon S3云存储服务API。在MinIO中&#xff0c;常见的操作包括&#xff1a; 存储桶操作&#xff1a; 创建、列出、获取信息、删除存储桶。 对象操作&#xff1a; 上传、下载、列出、删除对象。 权限管理&…...

网络编程中的字节序函数htonl()、htons()、ntohl()和ntohs()

目录 1&#xff0c;网络字节序和主机字节序 2. 函数的具体作用 2.1,htonl&#xff08;Host to Network Long&#xff09; 2.2,htons&#xff08;Host to Network Short) 2.3,ntohl&#xff08;Network to Host Long&#xff09; 2.4,ntohs&#xff08;Network to Host Sho…...

【dvwa靶场:File Upload系列】File Upload低-中-高级别,通关啦

目录 一、low级别,直接上传木马文件 1.1、准备一个木马文件 1.2、直接上传木马文件 1.3、访问木马链接 1.4、连接蚁剑 二、medium级别&#xff1a;抓包文件缀名 2.1、准备一个木马文件&#xff0c;修改后缀名为图片的后缀名 2.2、上传文件&#xff0c;打开burpSuite&…...

RHCE NFS

RHCE NFS 1.11. 2 NFS 主机名格式1.3 NFS 服务器配置1.3.1 /etc/exports 配置文件1.3.1.1 导出条目1.3.1.2 默认选项1.3.1.3 默认和覆盖选项 1.4 启动 NFS 服务器1.5 练习1.5.1 配置 NFS 服务器和客户端挂载1.5.2 配置autofs自动挂载&#xff08;需要时才挂载&#xff09; 1.6 …...

【数据结构】ArrayList与顺序表

ArrayList与顺序表 1.线性表2.顺序表2.1 接口的实现 3. ArrayList简介4. ArrayList使用4.2 ArrayList常见操作4.3 ArrayList的遍历4.4 ArrayList的扩容机制 5. ArrayList的具体使用5.1 杨辉三角5.2 简单的洗牌算法 6. ArrayList的问题及思考 【本节目标】 线性表顺序表ArrayLis…...

selenium学习实战【Python爬虫】

selenium学习实战【Python爬虫】 文章目录 selenium学习实战【Python爬虫】一、声明二、学习目标三、安装依赖3.1 安装selenium库3.2 安装浏览器驱动3.2.1 查看Edge版本3.2.2 驱动安装 四、代码讲解4.1 配置浏览器4.2 加载更多4.3 寻找内容4.4 完整代码 五、报告文件爬取5.1 提…...

VM虚拟机网络配置(ubuntu24桥接模式):配置静态IP

编辑-虚拟网络编辑器-更改设置 选择桥接模式&#xff0c;然后找到相应的网卡&#xff08;可以查看自己本机的网络连接&#xff09; windows连接的网络点击查看属性 编辑虚拟机设置更改网络配置&#xff0c;选择刚才配置的桥接模式 静态ip设置&#xff1a; 我用的ubuntu24桌…...

【JVM面试篇】高频八股汇总——类加载和类加载器

目录 1. 讲一下类加载过程&#xff1f; 2. Java创建对象的过程&#xff1f; 3. 对象的生命周期&#xff1f; 4. 类加载器有哪些&#xff1f; 5. 双亲委派模型的作用&#xff08;好处&#xff09;&#xff1f; 6. 讲一下类的加载和双亲委派原则&#xff1f; 7. 双亲委派模…...

[ACTF2020 新生赛]Include 1(php://filter伪协议)

题目 做法 启动靶机&#xff0c;点进去 点进去 查看URL&#xff0c;有 ?fileflag.php说明存在文件包含&#xff0c;原理是php://filter 协议 当它与包含函数结合时&#xff0c;php://filter流会被当作php文件执行。 用php://filter加编码&#xff0c;能让PHP把文件内容…...

Qemu arm操作系统开发环境

使用qemu虚拟arm硬件比较合适。 步骤如下&#xff1a; 安装qemu apt install qemu-system安装aarch64-none-elf-gcc 需要手动下载&#xff0c;下载地址&#xff1a;https://developer.arm.com/-/media/Files/downloads/gnu/13.2.rel1/binrel/arm-gnu-toolchain-13.2.rel1-x…...

链式法则中 复合函数的推导路径 多变量“信息传递路径”

非常好&#xff0c;我们将之前关于偏导数链式法则中不能“约掉”偏导符号的问题&#xff0c;统一使用 二重复合函数&#xff1a; z f ( u ( x , y ) , v ( x , y ) ) \boxed{z f(u(x,y),\ v(x,y))} zf(u(x,y), v(x,y))​ 来全面说明。我们会展示其全微分形式&#xff08;偏导…...

2.2.2 ASPICE的需求分析

ASPICE的需求分析是汽车软件开发过程中至关重要的一环&#xff0c;它涉及到对需求进行详细分析、验证和确认&#xff0c;以确保软件产品能够满足客户和用户的需求。在ASPICE中&#xff0c;需求分析的关键步骤包括&#xff1a; 需求细化&#xff1a;将从需求收集阶段获得的高层需…...

Tauri2学习笔记

教程地址&#xff1a;https://www.bilibili.com/video/BV1Ca411N7mF?spm_id_from333.788.player.switch&vd_source707ec8983cc32e6e065d5496a7f79ee6 官方指引&#xff1a;https://tauri.app/zh-cn/start/ 目前Tauri2的教程视频不多&#xff0c;我按照Tauri1的教程来学习&…...

MeshGPT 笔记

[2311.15475] MeshGPT: Generating Triangle Meshes with Decoder-Only Transformers https://library.scholarcy.com/try 真正意义上的AI生成三维模型MESHGPT来袭&#xff01;_哔哩哔哩_bilibili GitHub - lucidrains/meshgpt-pytorch: Implementation of MeshGPT, SOTA Me…...

JavaScript 标签加载

目录 JavaScript 标签加载script 标签的 async 和 defer 属性&#xff0c;分别代表什么&#xff0c;有什么区别1. 普通 script 标签2. async 属性3. defer 属性4. type"module"5. 各种加载方式的对比6. 使用建议 JavaScript 标签加载 script 标签的 async 和 defer …...