2个不稳定版本
0.2.0 | 2022年12月1日 |
---|---|
0.1.0 | 2020年10月27日 |
#239 in 调试
每月2,141次下载
57KB
849 代码行
rusteval
此crate提供了一些特性和宏,使您的应用程序的struct和函数可交互。
使用 #[derive(Interactive)]
注释一个struct,使用 #[Methods]
注释一个struct的方法,以及使用 #[Function]
注释一个自由函数,将实现一组特性和宏,使您可以像Rust有REPL一样访问它们。
将此crate用作“打印调试”或作为人性化的测试API的替代品。
此crate与 no_std
兼容,因此您可以使用它与嵌入式设备交互,并通过USB或UART连接闪烁LED。
使用方法
- 使用
Interactive
、Methods
和Function
注释您想访问的一切 - 定义一个新struct,它拥有或持有您想访问的对象的引用
- 为它推导
InteractiveRoot
- 使用特性的方法评估一个字符串(最简单的一个是
eval_to_string
但其他还允许更定制的行为) - 访问字段将给出它的调试表示形式
- 调用函数或方法将解析其参数并给出其返回值的调试表示形式
由于这个crate大量使用了Debug
特质,因此提供了一个辅助宏PartialDebug
。它为struct实现了Debug
,用占位符替换了所有未实现Debug
的字段。
CLI使用方法
提供了如get_all_field_names
之类的函数。这使得实现自动完成等功能成为可能。
请参考使用rustyline crate实现的自动完成示例。
示例
use rusteval::{Interactive, Methods, InteractiveRoot, Function, PartialDebug};
#[derive(Default)]
struct NoDebug;
#[derive(Interactive, PartialDebug, Default)]
struct ChildStruct {
last_sum: f32,
no_debug: NoDebug,
}
#[Methods]
impl ChildStruct {
fn add(&mut self, a: f32, b: f32) -> f32 {
self.last_sum = a + b;
self.last_sum
}
}
#[derive(Interactive, Debug, Default)]
struct ParentStruct {
child: ChildStruct,
}
#[derive(InteractiveRoot, Debug, Default)]
struct Root {
parent: ParentStruct,
}
#[Function]
fn split_str_at(s: &str, mid: usize) -> (&str, &str) {
s.split_at(mid)
}
let mut root = Root::default();
assert_eq!(root.eval_to_string("parent.child.add(4.2, 6.9)"), "11.1");
assert_eq!(root.eval_to_string("parent.child"), "ChildStruct { last_sum: 11.1, no_debug: Unknown }");
// split_str_at("foobar", 3) => ("foo", "bar")
assert_eq!(root.eval_to_string("split_str_at(\"foobar\", 3)"), "(\"foo\", \"bar\")");
工作原理
该crate使用了不稳定的功能specialization
,因此仅在nightly版本中可用。
在所有类型上实现了如try_as_interactive
之类的函数。通常情况下,该方法返回一个错误,但在特殊情况下,会返回一个特质对象(在本例中为&dyn Interactive
)。
然后,宏实现了一些类似这样的getter
fn get_field<'a>(&'a self, field_name: &'a str) -> Result<'_, &dyn Interactive> {
match field_name {
"field1" => self.field1.try_as_interactive(),
"field2" => self.field2.try_as_interactive(),
_ => Err(InteractiveError::FieldNotFound {
type_name: "Struct",
field_name,
}),
}
}
请参阅宏的文档以获取更多详细信息。
当前限制
- 只有当其参数类型受支持时,才能将方法和函数设置为交互式
- 枚举不受支持
许可证
根据您的选择,许可协议为Apache License, Version 2.0或MIT许可证。除非您明确表示,否则根据Apache-2.0许可证定义的任何有意提交以包含在此crate中的贡献,都将如上所述双重许可,而不附加任何其他条款或条件。
依赖关系
~310–770KB
~18K SLoC